Spring I18N (Internationalization)
I18N is an acronym for internationalization, Spring framework uses it to make an application for the international level. It means we can create an application for multi region-specific like an application can be used in US, China, Russia, and in any other country of the world just by implementing i18N.
The Spring framework uses LocaleResolver to support the internationalization and localization as well. In this tutorial, we will learn to implement internationalization in our spring MVC application.
Let's create a maven based spring project, our project looks like the below and contains several source code files.
Project Structure
//AppConfig.java
This is a configuration file which is an alternate of the applicationContext.xml file that we created for the XML-based configuration example. The @Configuration
annotation indicates that this is not a simple class but a configuration class and the @ComponentScan
annotation is used to indicate the location of the component class in our spring project.
Here, we configured our application for i18n support. You can notice that apart from ViewResolver, we added a couple of methods to get a lang parameter.
package com.studytonight;
import java.util.Locale;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.support.ReloadableResourceBundleMessageSource;
import org.springframework.web.servlet.LocaleResolver;
import org.springframework.web.servlet.ViewResolver;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import org.springframework.web.servlet.i18n.LocaleChangeInterceptor;
import org.springframework.web.servlet.i18n.SessionLocaleResolver;
import org.springframework.web.servlet.view.InternalResourceViewResolver;
@EnableWebMvc
@Configuration
@ComponentScan("com.studytonight.controller")
public class AppConfig implements WebMvcConfigurer{
@Bean(name = "messageSource")
public ReloadableResourceBundleMessageSource reloadableResourceBundleMessageSource() {
ReloadableResourceBundleMessageSource messageSource = new ReloadableResourceBundleMessageSource();
messageSource.setBasenames("classpath:messages");
messageSource.setDefaultEncoding("UTF-8");
return messageSource;
}
@Bean
public ViewResolver viewResolver() {
InternalResourceViewResolver irvr = new InternalResourceViewResolver();
irvr.setPrefix("WEB-INF/views/");
irvr.setSuffix(".jsp");
irvr.setOrder(0);
return irvr;
}
@Bean(name="localeResolver")
public LocaleResolver localeResolver() {
SessionLocaleResolver slr = new SessionLocaleResolver();
slr.setDefaultLocale(Locale.US);
return slr;
}
@Bean
public LocaleChangeInterceptor localeChangeInterceptor() {
LocaleChangeInterceptor localeChangeInterceptor = new LocaleChangeInterceptor();
localeChangeInterceptor.setParamName("lang");
return localeChangeInterceptor;
}
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(localeChangeInterceptor());
}
}
// WebAppInitializer.java
This file contains code to create an IOC container for our application. The AnnotationConfigWebApplicationContext
class is used to create an object for application context.
package com.studytonight;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.ServletRegistration;
import org.springframework.web.WebApplicationInitializer;
import org.springframework.web.context.support.AnnotationConfigWebApplicationContext;
import org.springframework.web.servlet.DispatcherServlet;
public class WebAppInitializer implements WebApplicationInitializer {
@Override
public void onStartup(ServletContext servletContext) throws ServletException {
AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext();
context.register(AppConfig.class);
context.setServletContext(servletContext);
ServletRegistration.Dynamic servlet = servletContext.addServlet("dispatcher", new DispatcherServlet(context));
servlet.setLoadOnStartup(1);
servlet.addMapping("/");
context.close();
}
}
// HomeController.java
This is our controller class that returns an index JSP page to the browser when the application starts.
package com.studytonight.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class HomeController {
@GetMapping("/")
public String index() {
return "index";
}
}
These are our property files, the first contains values for the English language and the second contains Spanish language values.
// messages_en.properties
#labels
label.name=Name
label.email=Email
#buttons
label.register=Register Here
// messages_es.properties
#labels
label.name=nombre
label.email=correo electrónico
#buttons
label.register = Registrarse aquí
// index.jsp
This JSP file uses the <spring:message> tag to get the values from the property files and display them accordingly.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<%@ taglib prefix="spring" uri="http://www.springframework.org/tags"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>User Form</title>
</head>
<body>
<form action="register" method="post">
<spring:message code="label.name"/>
<br>
<input type="text" name="name"/>
<br>
<spring:message code="label.email"/>
<br>
<input type="email" name="email" />
<br>
<input type="submit" value="<spring:message code="label.register"/>">
</form>
</body>
</html>
// pom.xml
This file contains all the dependencies of this project such as spring jars, servlet jars, etc. Put these dependencies into your project to run the application.
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.studytonight</groupId>
<artifactId>springi18</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>war</packaging>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
<!-- https://mvnrepository.com/artifact/javax.xml.bind/jaxb-api -->
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>2.3.0</version>
</dependency>
</dependencies>
<properties>
<spring.version>5.2.8.RELEASE</spring.version>
</properties>
<build>
<plugins>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>3.2.3</version>
<configuration>
<warSourceDirectory>WebContent</warSourceDirectory>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.5.1</version>
<configuration>
<source>11</source>
<target>11</target>
</configuration>
</plugin>
</plugins>
</build>
</project>
Run the Application
After successfully completing the project and adding the dependencies run the application using the server and you will get the output as below.
The above form page is displayed in the US English language(default). But if we want to display it in any other language then we can do this just by setting a lang parameter to the URL. See the below output, where we passed lang=es to display the web page in the Spanish language.