Web components do not appear to load correctly (Vaadin 14)

Hi,

I’m developing an web application with Spring Boot 2 / Vaadin 14 and have noticed that on restarting the application, the web
components appear to randomly not appear and the styling seems off.

This is an image of how it looks when it is working correctly.

https://vaadin.com/attachment/921257d8-5efd-460d-9b08-6f21e4dd351c/Screenshot_2019-09-04%20HeartSpark%20singles.png

After some code changes and restarting the application, the first time I load it often does this.

https://vaadin.com/attachment/fe397468-3194-4315-9eda-cc6fd55e0ee5/Screenshot_2019-09-04%20HeartSpark%20singles(1).png

Then, if I hit refresh on the browser, it would usually be OK, but more recently, it does this.

https://vaadin.com/attachment/dc9b160d-acb6-41e7-a9fa-65e5cd9431de/Screenshot_2019-09-04%20HeartSpark%20singles(2).png

The components appear in the DOM but they are not visible on the screen.

Looking at the JavaScript console for the last image above, it shows this.

https://vaadin.com/attachment/cef564d7-4e4d-499a-9635-06be4c6ed7f6/Screenshot%202019-09-04%20at%2012.06.20.png

I have tried deleting the node_modules/ dir and installing, rebuilding, clean etc to varying degrees of success, sometimes one field will show up, sometimes all of them.

I have no idea what is causing this so any help or suggestions would be really appreciated.

Thanks.

17824258.png
17824261.png
17824264.png
17824267.png

Hello.

Are you using Spring Security? If so, do you have a rule to allow requests to /VAADIN/** ?

Hi.

Yes, I am using Spring Security. The rules are set as follows. Do NPM modules have a specific path that needs excluding?

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // Not using Spring CSRF here to be able to use plain HTML for the login page
        http.csrf().disable() //
                // Register our CustomRequestCache that saves unauthorized access attempts, so
                // the user is redirected after login.
                .requestCache().requestCache(new CustomRequestCache()) //

                // Restrict access to our application.
                .and()
                .authorizeRequests()

                // Allow all flow internal requests.
                .requestMatchers(SecurityUtil::isFrameworkInternalRequest).permitAll()

                // Allow all requests by logged in users.
                .anyRequest().authenticated() //

                // Configure the login page.
                .and()
                .formLogin().loginPage(LOGIN_URL).permitAll()
                .loginProcessingUrl(LOGIN_PROCESSING_URL)
                .failureUrl(LOGIN_FAILURE_URL)

                // Configure logout
                .and().logout().logoutSuccessUrl(LOGOUT_SUCCESS_URL);
    }

    @Bean
    public BCryptPasswordEncoder bCryptPasswordEncoder() {
        return new BCryptPasswordEncoder();
    }

    @Bean(name = BeanIds.AUTHENTICATION_MANAGER)
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }

    @Autowired
    public void configureGlobal(final AuthenticationManagerBuilder auth,
                                final UserDetailsServiceBean userDetailsService) throws Exception {
        auth.userDetailsService(userDetailsService).passwordEncoder(bCryptPasswordEncoder());
    }

    @Override
    public void configure(WebSecurity web) throws Exception {
        web.ignoring().antMatchers(permitAll());
    }

    private String[] permitAll() {
        // Vaadin Flow static resources
        return new String[] {

                "/VAADIN/**",

                // the robots exclusion standard
                "/robots.txt",

                // web application manifest //
                "/manifest.webmanifest",
                "/sw.js",
                "/offline-page.html",

                // the standard favicon URI
                "/favicon.ico", "/favicon/**",

                // static images
                "/favicon/**",
                "/icon/**",
                "/image/**",

                // (development mode) static resources //
                "/frontend/**",

                // (production mode) static resources //
                "/frontend-es5/**", "/frontend-es6/**",

                // Other pre-auth screens
                "/reset-password/**",
                "/registration"
        };
    }

The components visibility thing doesn’t happen all the time. The most recent clean/build cycle shows this.

https://vaadin.com/attachment/8e7f1cca-a2f1-4962-9a58-e8e0dd3d195c/HeartSpark%20singles.png

Components look OK but the styling is missing (font sizes incorrect, colours are wrong, etc)

Very odd.
17824415.png

/VAADIN/** should be enough as far as I know. I asked because one common cause of the messages below is Spring Security blocking the request and redirecting it to /login.

The resource from “http://localhost:8080/login” was blocked due to MIME type (“text/html”) mismatch (X-Content-Type-Options: nosniff)
Loading failed for the <script> with source “http://localhost:8080/VAADIN/build/webcomponentsjs/webcomponents-loader.js”

Have you tried excluding ErrorMvcAutoConfiguration.class in the @SpringBootApplication annotation in your Application class? I had this issue too, and I believe that this stopped happening to me around the time I added that exclusion. Not 100% sure on this but worth a try.

@SpringBootApplication(exclude = ErrorMvcAutoConfiguration.class)
public class Application extends SpringBootServletInitializer {
	...
}

Gave this a go but didn’t appear to make a difference to it.

Current restart looks like this.
https://vaadin.com/attachment/2c067c7b-a8eb-42ba-9c9f-306107761018/Screenshot_2019-09-05%20HeartSpark%20singles.png

Looking at the inspector, none of the webcomponent body is generated. Just element, etc.

https://vaadin.com/attachment/0901ff3d-9229-46e2-ab61-ea596469ac80/Screenshot%202019-09-05%20at%2009.31.31.png
17825783.png
17825786.png

Same console error messages? Any other requests redirected or failed? Can you reproduce the issue when running in production mode?

Yes, same for production mode. Restarted 3 times and got 3 different variations of error.

It feels like some of the resources/styles are not loading. Comparing to a previous (Vaadin 13) working version, the styles for the H2 element, for example, are loaded from the Lumo theme. I can see the valo specific colours/spacing etc applied. In the new version, there are no Lumo styles at all for this element so styling defaults to the browser defaults.

Within the console, the only thing I almost consistently see that looks wrong is

NotSupportedError: Operation is not supported vaadin-text-field.js:137
    <anonymous> vaadin-text-field.js:137
    es6 vaadin-bundle-164b9568fe79d4d5450e.cache.js:1979
    __webpack_require__ vaadin-bundle-164b9568fe79d4d5450e.cache.js:20
    <anonymous> vaadin-text-field.js:3
    es6 vaadin-bundle-164b9568fe79d4d5450e.cache.js:2003
    __webpack_require__ vaadin-bundle-164b9568fe79d4d5450e.cache.js:20
    <anonymous> vaadin-combo-box-styles.js:4
    es6 vaadin-bundle-164b9568fe79d4d5450e.cache.js:1187
    __webpack_require__ vaadin-bundle-164b9568fe79d4d5450e.cache.js:20
    <anonymous> vaadin-combo-box.js:4
    es6 vaadin-bundle-164b9568fe79d4d5450e.cache.js:1199
    __webpack_require__ vaadin-bundle-164b9568fe79d4d5450e.cache.js:20
    <anonymous> generated-flow-imports.js:36
    es6 vaadin-bundle-164b9568fe79d4d5450e.cache.js:2207
    __webpack_require__ vaadin-bundle-164b9568fe79d4d5450e.cache.js:20
    <anonymous> vaadin-bundle-164b9568fe79d4d5450e.cache.js:84
    <anonymous> vaadin-bundle-164b9568fe79d4d5450e.cache.js:87
    InnerModuleEvaluation self-hosted:4147
    evaluation self-hosted:4101

Not sure whether that points to anything or is nothing to do with it. Doesn’t show up in the Vaadin 13 but who knows?

This should not happen. Even if webcomponents-loader.js is not being loaded, it should work in the latest Firefox.
This error is probably in Element.attachShadow as described at https://developer.mozilla.org/en-US/docs/Web/API/CustomElementRegistry/define

Note: You’ll often get NotSupportedErrors thrown that seem like define() is failing, but instead it is likely a problem with Element.attachShadow().

It could be something wrong with frontend dependencies or webpack. If you can share a minimal example with source code it will be easier to figure out.

Thanks for taking the time to help out, I really do appreciate it.

I’ve done some more investigations today and got it down to whenever I define certain elements within a view, even if I never call that view, the problem occurs.

The elements that I know are problematic are DatePicker and ComboBox. I don’t even need to add them to the DOM, i.e.

@SpringComponent
@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)
@Route(value = "some-page", layout = WebsiteTemplate.class)
public class MainView extends Div {

	public MainView() {
		ComboxBox c = new ComboBox();
	}

}

That is enough to cause the NotSupportedError: Operation is not supported vaadin-text-field.js:137 issue to occur in the Console output which is when everything else breaks.

I’ve tried cutting down the app, it’s here https://github.com/kents1/heartspark/tree/app-minimal (app-minimal branch). The UI stuff is under singles.heartspark.ui

Thanks for the code. I was able to reproduce de issue. It doesn’t seem to be related at all to Spring Security. I’ll try to figure out what is going on.

Removing package-lock.json along with node_modules and webpack.* seemed to fix the issue for me.

I gave this a try but it didn’t fix the issue for me. :frowning:

Did you remove both the one on the top level and the one in heartspark-core?

Sorry, I didn’t perform a mvn clean before rebuilding. On doing this it is working correctly again. Thanks for all your help looking into it.

Just so I understand the issue, changes caused an issue with the webpack / javascript dependencies which were causing the client side compilation to fail? Deleting these files caused Vaadin to re-build from fresh with all the correct requirements / dependencies?

I think this was the underlying problem: https://github.com/vaadin/vaadin-combo-box/issues/835. It has been fixed today.

The issue was causing the vaadin-text-field to be registered twice, which is not supported.

Deleting these files caused Vaadin to re-build from fresh with all the correct requirements / dependencies?

Yes