Tutorial: Build a Spring WebMVC App with Primefaces
Primefaces is a JavaServer Faces (JSF) component suite. It extends JSF’s capabilities with rich components, skinning framework, a handy theme collection, built-in Ajax, mobile support, push support, and more. A basic input textbox in the JSF tag library becomes a fully-featured textbox with theming in Primefaces.
Frontend frameworks like AngularJS provide UI components, Ajax capabilities, and HTML5 compliance much like Primefaces does. If you are looking for a lightweight application with quick turnaround time, AngularJS could be your best bet. However, when dealing with an enterprise Java architecture, it is often best to use a mature framework like Primefaces. It is stable and ever-evolving, with the help of an active developer community.
Primefaces also makes a UI developer’s life easier by providing a set of ready-to-use components which, otherwise, would take a considerable amount of time to code – e.g., the dashboard component with drag and drop widgets. Some other examples are slider, autocomplete components, tab views for pages, charts, calendars, etc.
Spring WebMVC and Primefaces
In Spring WebMVC, components are very loosely coupled. It is easy to integrate different libraries to the model layer or the view layer.
In this tutorial, I am going to walk you through using Spring WebMVC and Primefaces to create a basic customer management application with a robust frontend. All the code can be found on Github.
Create a Maven Project
Create a new Maven Project using your favorite IDE. After creating the project, you should see the pom.xml in the project folder. A minimal pom.xml should like this:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
<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 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.stormpath.blog</groupId>
<artifactId>SpringPrimefacesDemo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>war</packaging>
<name>SpringPrimefacesDemo</name>
<url>http://maven.apache.org</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
</project>
|
Add Spring Libraries
Next, add the necessary Spring libraries to the dependencies section of the pom.xml.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<jdk.version>1.7</jdk.version>
<spring.version>4.3.2.RELEASE</spring.version>
</properties>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>3.8.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
</dependencies>
|
Create Your Sample Project with Spring WebMVC
For the customer management application we are going to build, we need to create a mock customer database. It will be a POJO with three attributes. The Customer class would look like this:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
|
package com.stormpath.blog.SpringPrimefacesDemo.model;
public class Customer {
private String firstName;
private String lastName;
private Integer customerId;
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public Integer getCustomerId() {
return customerId;
}
public void setCustomerId(Integer customerId) {
this.customerId = customerId;
}
}
|
Then we need to create a bean class to manipulate the Customer class:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
|
package com.stormpath.blog.SpringPrimefacesDemo.presentation;
import java.util.ArrayList;
import java.util.List;
import javax.annotation.PostConstruct;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
import com.stormpath.blog.SpringPrimefacesDemo.model.Customer;
@ManagedBean
@ViewScoped
public class CustomerBean {
private List<Customer> customers;
public List<Customer> getCustomers() {
return customers;
}
@PostConstruct
public void setup() {
List<Customer> customers = new ArrayList<Customer>();
Customer customer1 = new Customer();
customer1.setFirstName("John");
customer1.setLastName("Doe");
customer1.setCustomerId(123456);
customers.add(customer1);
Customer customer2 = new Customer();
customer2.setFirstName("Adam");
customer2.setLastName("Scott");
customer2.setCustomerId(98765);
customers.add(customer2);
Customer customer3 = new Customer();
customer3.setFirstName("Jane");
customer3.setLastName("Doe");
customer3.setCustomerId(65432);
customers.add(customer3);
this.customers = customers;
}
}
|
Create the Frontend with Primefaces
Since we are going to add Primefaces components to our UI, we will need a UI with JSF capabilities. Add the JSF dependencies to your pom.xml:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
|
<properties>
…..
<servlet.version>3.1.0</servlet.version>
<jsf.version>2.2.8</jsf.version>
…..
</properties>
…
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>${servlet.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-api</artifactId>
<version>${jsf.version}</version>
</dependency>
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-impl</artifactId>
<version>${jsf.version}</version>
</dependency>
|
Note: If your target server is a Java EE compliant server like jBoss, the JSF libraries will be provided by the server. In that case, the Maven dependencies can conflict with the server libraries. You can add scope provided to the JSF libraries in the pom.xml to solve this.
1
2
3
4
5
6
7
8
9
10
11
12
13
|
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-api</artifactId>
<version>${jsf.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-impl</artifactId>
<version>${jsf.version}</version>
<scope>provided</scope>
</dependency>
|
Create a web deployment descriptor – web.xml. The folder structure needs to be as shown below (the other files referenced will be created below):
1
2
3
4
5
6
7
8
|
webapp/
├── META-INF
│ └── MANIFEST.MF
├── WEB-INF
│ ├── faces-config.xml
│ └── web.xml
└── index.xhtml
|
web.xml content:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
|
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
version="3.0">
<servlet>
<servlet-name>Faces Servlet</servlet-name>
<servlet-class>javax.faces.webapp.FacesServlet</servlet-class>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.xhtml</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>/faces/*</url-pattern>
</servlet-mapping>
<welcome-file-list>
<welcome-file>faces/index.xhtml</welcome-file>
</welcome-file-list>
</web-app>
|
Create faces-config.xml in the WEB-INF folder:
1
2
3
4
5
6
7
8
9
10
|
<?xml version="1.0" encoding="UTF-8"?>
<faces-config
xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-facesconfig_2_2.xsd"
version="2.2">
</faces-config>
|
Add index.xhtml to the webapp folder.
1
2
3
4
5
6
7
8
9
10
11
12
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:ui="http://java.sun.com/jsf/facelets">
<h:head></h:head>
<body>
<h1>Spring MVC Web with Primefaces</h1>
</body>
</html>
|
Note the XML namespaces for the JSF included in the xhtml. Now we can add the the proper dependencies to pom.xml.
1
2
3
4
5
6
7
8
9
10
11
12
13
|
…
<properties>
...
<primefaces.version>6.0</primefaces.version>
</properties>
...
<dependency>
<groupId>org.primefaces</groupId>
<artifactId>primefaces</artifactId>
<version>${primefaces.version}</version>
</dependency>
|
Finally, add a class implementing WebApplicationInitializer
interface. This will be a bootstrap class for Servlet 3.0+ environments, to start the servlet context programmatically, instead of (or in conjunction with) the web.xml approach.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
|
package com.stormpath.blog.SpringPrimefacesDemo;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.WebApplicationInitializer;
import org.springframework.web.context.ContextLoaderListener;
import org.springframework.web.context.support.AnnotationConfigWebApplicationContext;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
@EnableWebMvc
@Configuration
@ComponentScan
public class WebAppInitializer implements WebApplicationInitializer {
@Override
public void onStartup(ServletContext sc) throws ServletException {
AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext();
sc.addListener(new ContextLoaderListener(context));
}
}
|
Configure Primefaces
Now we will modify the index.xhtml file and create a data table to display the customer data. The xml namespace needs to be modified to add Primefaces reference.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:p="http://primefaces.org/ui">
<h:head></h:head>
<body>
<h1>Spring MVC Web with Primefaces</h1>
<p:dataTable var="customer" value="#{customerBean.customers}" widgetVar="customerTable" emptyMessage="No customers found">
<p:column headerText="Id">
<h:outputText value="#{customer.customerId}"/>
</p:column>
<p:column headerText="First Name">
<h:outputText value="#{customer.firstName}"/>
</p:column>
<p:column headerText="Last Name">
<h:outputText value="#{customer.lastName}"/>
</p:column>
</p:dataTable>
</body>
</html>
|
Deploy to Your Application Server (and Test)
Build the project, deploy the war to the application server and check.
Extended Capabilities
Modify the code as shown below to easily produce a sortable data table with filters. Add the following line to CustomerBean.java:
1
2
|
private List<Customer> filteredCustomers;
|
…and:
1
2
3
4
5
6
7
8
|
public List<Customer> getFilteredCustomers() {
return filteredCustomers;
}
public void setFilteredCustomers(List<Customer> filteredCustomers) {
this.filteredCustomers = filteredCustomers;
}
|
Modify index.xhtml to:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:p="http://primefaces.org/ui">
<h:head></h:head>
<body>
<h1>Spring MVC Web with Primefaces</h1>
<h:form>
<p:dataTable var="customer" value="#{customerBean.customers}" widgetVar="customerTable" emptyMessage="No customers found" filteredValue="#{customerBean.filteredCustomers}">
<p:column headerText="Id" sortBy="#{customer.customerId}" filterBy="#{customer.customerId}">
<h:outputText value="#{customer.customerId}"/>
</p:column>
<p:column headerText="First Name" sortBy="#{customer.firstName}" filterBy="#{customer.firstName}">
<h:outputText value="#{customer.firstName}"/>
</p:column>
<p:column headerText="Last Name" sortBy="#{customer.lastName}" filterBy="#{customer.lastName}">
<h:outputText value="#{customer.lastName}"/>
</p:column>
</p:dataTable>
</h:form>
</body>
</html>
|
More on Primefaces
All the UI components available with Primefaces have been showcased at Primefaces Showcase.
Apart from the components extended from the JSF Tag library, Primefaces has a lot of versatile components and plugins known as Primefaces extensions. They are meant to make developers’ lives easier and our web pages more beautiful.
And now, it’s time to add authentication to your Primefaces webapp! Learn more, and take Stormpath for a test drive, with these resources:
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?
2013-05-03 chsh命令用于修改你的登录shell