Generic Top

I just announced the new Learn Spring course, focused on the fundamentals of Spring 5 and Spring Boot 2:

>> CHECK OUT THE COURSE

1. Overview

In this tutorial, we're going to show how to access Spring MVC objects in Thymeleaf views that contain JavaScript code. We'll use Spring Boot and the Thymeleaf template engine in our examples, but the idea works for other template engines as well.

We're going to describe two cases: when JavaScript code is embedded or internal to the web page generated by the engine, and when it is external to the page – for example, in a separate JavaScript file.

2. Setup

Let's assume that we've already configured a Spring Boot web application that uses Thymeleaf template engine. Otherwise, you might find these tutorials useful to start:

Furthermore, let's suppose that our application has a controller corresponding to an endpoint /index that renders a view from a template named index.html. This template might include an embedded or an external JavaScript code, say script.js.

Our goal is to be able to access Spring MVC parameters from either embedded or external JavaScript (JS) code.

3. Access the Parameters

First of all, we need to create the model variables that we want to use from the JS code.

In Spring MVC, there are various ways of doing this. Let's use the ModelAndView approach:

@RequestMapping("/index")
public ModelAndView thymeleafView(Map<String, Object> model) {
    model.put("number", 1234);
    model.put("message", "Hello from Spring MVC");
    return new ModelAndView("thymeleaf/index");
}

We can find other possibilities in our tutorial on Model, ModelMap, and ModelView in Spring MVC.

4. Embedded JS Code

Embedded JS code is nothing but a part of the index.html file that is located inside the <script> element. We can pass Spring MVC variables there quite straightforwardly:

<script>
    var number = [[${number}]];
    var message = "[[${message}]]";
</script>

Thymeleaf template engine replaces every expression by a value that is available in the scope of the current execution. This means that the template engine transforms the code mentioned above into the following HTML code:

<script>
    var number = 1234;
    var message = "Hello from Spring MVC!";
</script>

5. External JS Code

Let's say that our external JS code is included in the index.html file using the same <script> tag, in which we specify the src attribute:

<script src="/js/script.js"></script>

Now, if we want to use the Spring MVC parameters from script.js, we should:

  1. define JS variables in embedded JS code as we did in the previous section
  2. access these variables from the script.js file

Note that the external JS code should be invoked after the initialization of the variables of the embedded JS code.

This can be achieved in two ways: by specifying the order of a JS code execution or by using an asynchronous JS code execution.

5.1. Specify the Order of Execution

We can do this by declaring the external JS code after the embedded one in index.html:

<script>
    var number = [[${number}]];
    var message = "[[${message}]]";
</script>
<script src="/js/script.js"></script>

5.2. Asynchronous Code Execution

In this case, the order in which we declare the external and embedded JS code in the index.html is of no importance, but we should place the code from script.js into a typical on-page-loaded wrapper:

window.onload = function() {
    // JS code
};

Despite the simplicity of this code, the most common practice is to use jQuery instead. We include this library as the first <script> element in the index.html file:

<!DOCTYPE html>
<html>
    <head>
        <script src="/js/jquery.js"></script>
        ...
    </head>
 ...
</html>

Now, we may place the JS code inside the following jQuery wrapper:

$(function () {
    // JS code
});

With this wrapper, we can guarantee that the JS code is executed only when the whole page content, and hence all other embedded JS code, is completely loaded.

6. A Bit of Explanation

In Spring MVC, the Thymeleaf template engine parses only the template file (index.html in our case) and converts it into an HTML file. This file, in its turn, might include references to other resources that are out of the scope of the template engine. It's the user's browser that parses those resources and renders the HTML view.

Therefore, those resources are not parsed by the template engine, and we may inject variables defined in the controller only into the embedded JS code that then becomes available for the external JS code.

7. Conclusion

In this tutorial, we've learned how to access Spring MVC parameters inside a JavaScript code.

As always, the complete code examples are in our GitHub repository.

Generic bottom

I just announced the new Learn Spring course, focused on the fundamentals of Spring 5 and Spring Boot 2:

>> CHECK OUT THE COURSE
Comments are closed on this article!