Search code examples
vaadinvaadin-flowvaadin23

Vaadin23 route navigation with parameters


I have the following route:

@Route(value = "jobs/:jobId", layout = JobsLayout.class)
@AnonymousAllowed
public class ViewJob extends VerticalLayout implements BeforeEnterObserver, HasUrlParameter<String> {

When I access the application by the following url:

/jobs/456/test

I correctly enters ViewJob view.

Now, I'd like to programmatically move to this view from another Vaadin view. For this, I'm trying to do the following:

UI.getCurrent().navigate(ViewJob.class, "456/test");

but the application fails with the following exception:

com.vaadin.flow.router.NotFoundException: No route found for the given navigation target 'com.example.ui.views.job.view.ViewJob' and parameters '{___url_parameter=456/test}'
    at com.vaadin.flow.router.RouteConfiguration.getUrl(RouteConfiguration.java:515)
    at com.vaadin.flow.component.UI.navigate(UI.java:914)

What am I doing wrong and how to correctly navigate to the ViewJob view?

UPDATED

The goal - I'm trying to implement the logic similar to StackOverflow - when you access the question page without a slug, for example Vaadin23 route navigation with parameters you will be automatically redirected to the correct url with slug added - Vaadin23 route navigation with parameters

For that I have the following view:

@Route(value = "jobs", layout = JobsLayout.class)
@AnonymousAllowed
public class AllJobsView extends VerticalLayout implements LocaleChangeObserver, HasUrlParameter<String> {

@Override
    public void setParameter(BeforeEvent event, @OptionalParameter String parameter) {
        try {
            Long jobId = Long.parseLong(parameter);
            Vacancy vacancy = vacancyService.findById(jobId, VaadinUtils.getCurrentLocaleIso6391());

            UI.getCurrent().navigate(ViewJob.class, new RouteParameters(Map.of(ViewJob.JOB_ID_PARAMETER, parameter, HasUrlParameterFormat.PARAMETER_NAME, vacancy.getNameSlug())));
            return;
        } catch (Exception e) {
            e.printStackTrace();
        }

This is ViewJob view:

@Route(value = "jobs/:jobId", layout = JobsLayout.class)
@AnonymousAllowed
public class ViewJob extends VerticalLayout implements BeforeEnterObserver, HasUrlParameter<String> {
....
}

When I try to access /jobs - AllJobsView is correctly rendered. When I try to access /jobs/507/vacancy5 - JobView is correctly rendered

but when I try to access /jobs/507 the following redirection logic is involed from AllJobsView.setParameter method:

UI.getCurrent().navigate(ViewJob.class, new RouteParameters(Map.of(ViewJob.JOB_ID_PARAMETER, parameter, HasUrlParameterFormat.PARAMETER_NAME, vacancy.getNameSlug())));

After that the user is correctly navigated to /jobs/507/vacancy5 url but the JobView content is not rendered.. only JobsLayout part.

What am I doing wrong?


Solution

  • You have defined a route parameter in the url (:jobId). This has to match with the route parameter given to the URL:

    UI.getCurrent().navigate(ViewJob.class, new RouteParameter("jobId", "456"));