In this example, we demonstrate basic routing using the community library modem. Modem's quickstart docs should be all you should need to get up to speed, so that's the best place to start.
Of course, it's not much fun routing without something to route to. This example lets users create new pages on the fly - a guest book for your next house party! Hospitality is very important, and guests will be sure to feel welcome when they see their name in the navigation with a special greeting page just for them.
Modem uses custom side effects and external Javascript to translate browser click and navigation events into update
messages for the Lustre runtime. All we need to use it is a route change handler function that we can pass to modem.init
in our app's init
function.
Note: See
modem.advanced
to configure more options.
Inside our on_route_change
function, we match URI path segment patterns to our routes:
fn on_route_change(uri: Uri) -> Msg {
case uri.path_segments(uri.path) {
["welcome", guest] -> OnRouteChange(WelcomeGuest(guest))
_ -> OnRouteChange(Home)
}
}
In our update
function, we assign the matched route to model.current_route
:
fn update(model: Model, msg: Msg) -> #(Model, Effect(Msg)) {
case msg {
OnRouteChange(route) -> #(
Model(..model, current_route: route),
effect.none(),
)
...
}
And in our view
function, we use model.current_route
to determine what to display to the user:
fn view(model: Model) -> Element(Msg) {
let page = case model.current_route {
Home -> render_home(model)
WelcomeGuest(name) -> render_welcome(model, name)
}
...
}
Lustre doesn't provide a traditional HTML or JSX-style templating engine, and this is by design.
Since the view
portion of this example is a bit more involved than our previous ones have been, it should start to give you more of a feel for how views in Lustre are just functions. The layout is a function. Each page view is a function. The nav is a function, and each individual nav item is a function too.
This means we can build up our entire UI using Gleam's functional syntax, benefiting from features like exhaustive pattern matching based on our routes.
Since our views are pure functions, we know they'll always render reliably.
If you're having trouble with Lustre or are not sure what the right way to do something is, the best place to get help is the Gleam Discord server. You could also open an issue on the Lustre GitHub repository.