Add a View
In this guide, you’ll learn how to create and name views in Hilla, assign multiple routes to a single view, and organize views into view directories. To reinforce your learning, a hands-on mini-tutorial at the end helps you apply these concepts in a real Vaadin application.
Creating Views
Hilla views are React components that are returned by the default exported function defined in a TSX file:
export default function HelloView() {
return <h1>Hello, World!</h1>;
}
The default way for creating routes for views in Hilla is based on the file system structure. The route for a view is determined based on:
-
where the respective file for a view is located, relative to the
src/main/frontend/views
directory, and -
how the respective file for a view is named.
For example, if the hello.tsx
file is located directly under src/main/frontend/views
, then the route for HelloView
component (default export from this file) is /hello
, which means the file name hello.tsx
excluding the .tsx
. If the application is running from the root context, users would be able to access this view by navigating to https://example.com/hello
. Moreover, moving this file under src/main/frontend/views/greeting
directory changes the route to /greeting/hello
, so the users can access this view by navigating to https://example.com/greeting/hello
.
Likewise, naming the view file as hello-world.tsx
or HelloWorld.tsx
results in the route /hello-world
or /HelloWorld
.
To avoid repeating the src/main/frontend/views
throughout this guide, views
is used as an alias to refer to this directory.
If a view is supposed to target the root route, the file should be named as @index.tsx
and located directly under the views
directory:
export default function HomeView() {
return <h1>Home</h1>;
}
Then, the route for the above component is /
, and if the application is running from the root context, users can access this view by navigating to https://example.com/
.
View Naming
React only recognizes an exported function as a component if the function name starts with an uppercase letter. For example, the following component is recognized as a valid React component:
export default function CustomersView() {
return <h1>Customers</h1>;
}
Defining the function name as customersView
or customerList
does not result in a compile or runtime error, but is not recognized as a React component either.
The routing uses the React component’s name for creating the default automatic title for the view. For example, the title for the CustomersView
component is Customers
, and the title for the HelloWorldView
component is Hello World
. This automatically-determined title is used when creating the navigation menu based on utilities from the routing API.
Another important convention to consider while naming the views and directories is to use the _
(underscore) character at the beginning of the file or directory name to instruct the routing system to ignore it. For example, a file named as _AddressFormComponent.tsx
is ignored when creating routes for views. This is useful for creating utility files and reusable components that are not intended to be available as navigation targets.
The details about the automatic title and the navigation menu are covered in more detail in the Navigate to a View guide.
Route Aliases
In Hilla, there is no shortcut for creating multiple routes that target the same view. However, you can create a new view file that exports a component returning the target component. You can place this alias component in any directory to create desired route alias. For example, the following view targets the root route (/
):
export default function RootView() {
return <h1>Home</h1>;
}
Now to have the same view accessible via /home
and /main
, you can create two additional view files:
export default function HomeView() {
return RootView();
}
and
export default function MainView() {
return RootView();
}
Directory Structure
As mentioned earlier, the file system structure determines the route for a view. Therefore, organizing views into directories helps maintain a clear structure for views and routes.
Simple views that consist of only one file can be placed directly under the views
directory. For example, "About", "Contact Us", and the "Home" view do not need a complex composition of components, nor should have a long route, so it is a good practice to place them directly under the views
directory:
src
└── main
└── frontend
└── views
├── @index.tsx
├── about.tsx
└── contact-us.tsx
This way, the routes for these views are /
, /about
, and /contact-us
, respectively.
However, for more complex views that consist of other components, or if they should accept route parameters, it is recommended to place all the files related to that view under a directory, named by the functionality they provide. For example, views related to customers can be grouped under a customers
directory, and views related to products under a products
directory. The following is an example of a directory structure for view files that handle the customer related functionalities:
src
└── main
└── frontend
└── views
└── customers
├── {id} (1)
│ ├── edit.tsx (2)
│ └── index.tsx (3)
├── @index.tsx (4)
└── new.tsx (5)
-
The
{id}
directory is a placeholder for the route parameter. You will learn more about route parameters in the Navigate to a View guide. -
The
edit.tsx
file is responsible for editing a specified customer details. The route for this view is/customers/:id/edit
. -
The
@index.tsx
file is responsible for displaying the details of a specified customer. The route for this view is/customers/:id
. -
The
index.tsx
file is responsible for displaying the list of customers. The route for this view is/customers
. -
The
new.tsx
file is responsible for adding a new customer. The route for this view is/customers/new
.
As this guide focuses on basics of creating views in Hilla, further details about routing conventions are covered in the Routing guide.
Defining Explicit Routes
So far, you have learned how to create views and how routes are automatically resolved based on the file system structure and file name. However, if you want to have a custom route for a view, you can export a ViewConfig
object named config
from the view file. The path specified for the route
overrides the automatically-resolved path according to the routing conventions. For example, the following view has a custom route /custom-route
:
import { ViewConfig } from "@vaadin/hilla-file-router/types.js";
export const config: ViewConfig = {
route: "/custom-route",
};
export default function HelloView() {
return <h1>Hello, World!</h1>;
}
Now, users can access this view by navigating to https://example.com/custom-route
.
Note
| Avoid using explicit routes unless absolutely necessary. The routing system is designed to automatically resolve the routes based on the file system structure and the file name, which helps to keep the routes consistent and predictable. |
Try It
In this mini-tutorial, you’ll explore automatically resolved routes. You’ll also create a new, simple view and specify multiple routes for it.
Set Up the Project
To start, generate a walking skeleton with a Hilla UI, open it in your IDE, and run it.
Create a Dashboard View
Next, you’ll create a new dashboard view. In the views
directory, create a file named dashboard.tsx
:
export default function DashboardView() {
return <h1>Dashboard</h1>;
}
The path for this view is automatically resolved to /dashboard
, so you can access it at: http://localhost:8080/dashboard
Create an Admin View
You’ll now create an admin view. Since it may grow in complexity, you’ll place it in its own directory. In the views
directory, create a new directory called admin
. Inside it, add a file named @index.tsx
:
export default function AdminView() {
return <h1>Admin</h1>
}
This view is automatically assigned the route /admin
. Open http://localhost:8080/admin to see it in action.
Add a Route Alias
Now, you’ll make the dashboard view the default landing page of the application. Open frontend/views/@index.tsx
and update it as follows:
...
export default function MainView() {
return DashboardView();
}
With this alias in place, the dashboard is now accessible via both http://localhost:8080 and http://localhost:8080/dashboard.
Final Thoughts
Now you’ve explored how to define and organize Hilla views in a Vaadin application. You’ve learned how to:
-
Use automatically resolved routes to structure your application’s navigation.
-
Define multiple routes for a single view, making navigation more flexible.
Next, refer to the Navigate to a View guide to learn how to navigate from one view to another.