diff --git a/spring-mvc-push/.gitignore b/spring-mvc-push/.gitignore
new file mode 100644
index 0000000000..448298d47f
--- /dev/null
+++ b/spring-mvc-push/.gitignore
@@ -0,0 +1 @@
+/.tern-project
diff --git a/spring-mvc-push/pom.xml b/spring-mvc-push/pom.xml
new file mode 100644
index 0000000000..2eb10381be
--- /dev/null
+++ b/spring-mvc-push/pom.xml
@@ -0,0 +1,91 @@
+
+ 4.0.0
+ com.baeldung
+ spring-mvc-push
+ war
+ 0.0.1-SNAPSHOT
+ spring-mvc-push
+
+ 1.8
+ 1.8
+ 2.20
+ 3.7.0
+ 3.2.0
+ UTF-8
+ 5.0.2
+ 5.0.2.RELEASE
+ 4.0.0
+ 1.2
+ 2.3.2-b02
+ 5.0.2
+ 1.0.2
+
+
+
+ org.springframework
+ spring-webmvc
+ ${spring.version}
+
+
+ javax.servlet
+ javax.servlet-api
+ ${servlet.version}
+ provided
+
+
+ javax.servlet
+ jstl
+ ${jstl.version}
+
+
+ javax.servlet.jsp
+ javax.servlet.jsp-api
+ ${jsp-api.version}
+
+
+
+ org.springframework
+ spring-test
+ ${spring.version}
+ test
+
+
+ org.junit.jupiter
+ junit-jupiter-engine
+ ${junit.jupiter.version}
+ test
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ ${maven.compiler.version}
+
+
+ org.apache.maven.plugins
+ maven-war-plugin
+ ${maven-war-plugin.version}
+
+ spring-mvc-push
+ false
+ ${deploy-path}
+
+
+
+ maven-surefire-plugin
+ ${maven-surefire-plugin.version}
+
+
+ org.junit.platform
+ junit-platform-surefire-provider
+ ${junit.platform.version}
+
+
+
+
+ spring-mvc-push
+
+
diff --git a/spring-mvc-push/src/main/java/com/baeldung/config/PushConfiguration.java b/spring-mvc-push/src/main/java/com/baeldung/config/PushConfiguration.java
new file mode 100644
index 0000000000..e6188da92d
--- /dev/null
+++ b/spring-mvc-push/src/main/java/com/baeldung/config/PushConfiguration.java
@@ -0,0 +1,48 @@
+package com.baeldung.config;
+
+import javax.servlet.ServletContext;
+import javax.servlet.ServletException;
+import javax.servlet.ServletRegistration;
+
+import org.springframework.context.annotation.Bean;
+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.DispatcherServlet;
+import org.springframework.web.servlet.config.annotation.EnableWebMvc;
+import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
+import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
+import org.springframework.web.servlet.view.InternalResourceViewResolver;
+
+@Configuration
+@EnableWebMvc
+@ComponentScan(basePackages = "com.baeldung.controller")
+public class PushConfiguration implements WebApplicationInitializer, WebMvcConfigurer {
+
+ @Override
+ public void onStartup(ServletContext container) throws ServletException {
+ AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext();
+ context.register(PushConfiguration.class);
+ container.addListener(new ContextLoaderListener(context));
+ ServletRegistration.Dynamic dispatcher = container.addServlet("DispatcherServlet", new DispatcherServlet(context));
+ dispatcher.setLoadOnStartup(1);
+ dispatcher.addMapping("/");
+ }
+
+ @Bean
+ public InternalResourceViewResolver jspViewResolver() {
+ InternalResourceViewResolver bean = new InternalResourceViewResolver();
+ bean.setPrefix("/WEB-INF/views/");
+ bean.setSuffix(".jsp");
+ return bean;
+ }
+
+ @Override
+ public void addResourceHandlers(ResourceHandlerRegistry registry) {
+ registry.addResourceHandler("/resources/**")
+ .addResourceLocations("/resources/");
+ }
+
+}
diff --git a/spring-mvc-push/src/main/java/com/baeldung/controller/PushController.java b/spring-mvc-push/src/main/java/com/baeldung/controller/PushController.java
new file mode 100644
index 0000000000..efee3a840f
--- /dev/null
+++ b/spring-mvc-push/src/main/java/com/baeldung/controller/PushController.java
@@ -0,0 +1,31 @@
+package com.baeldung.controller;
+
+import javax.servlet.http.PushBuilder;
+
+import org.springframework.stereotype.Controller;
+import org.springframework.web.bind.annotation.RequestMapping;
+
+@Controller
+public class PushController {
+
+ @RequestMapping(value = "/demoWithPush")
+ public String demoWithPush(PushBuilder pushBuilder) {
+ if (null != pushBuilder) {
+ pushBuilder.path("resources/logo.png")
+ .addHeader("Content-Type", "image/png")
+ .push();
+ pushBuilder.path("resources/script.js")
+ .addHeader("Content-Type", "text/javascript")
+ .push();
+ pushBuilder.path("resources/style.css")
+ .addHeader("Content-Type", "text/css")
+ .push();
+ }
+ return "demo";
+ }
+
+ @RequestMapping(value = "/demoWithoutPush")
+ public String demoWithoutPush() {
+ return "demo";
+ }
+}
\ No newline at end of file
diff --git a/spring-mvc-push/src/main/webapp/WEB-INF/views/demo.jsp b/spring-mvc-push/src/main/webapp/WEB-INF/views/demo.jsp
new file mode 100644
index 0000000000..d77619283a
--- /dev/null
+++ b/spring-mvc-push/src/main/webapp/WEB-INF/views/demo.jsp
@@ -0,0 +1,22 @@
+<%@ page language="java" contentType="text/html; charset=UTF-8"
+ pageEncoding="UTF-8"%>
+<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
+
+
+
+PushBuilder demo
+" rel="stylesheet" />
+
+
+
+ PushBuilder demo
+
+ " alt="Logo" height="126"
+ width="411">
+
+ ">
+
Go to
+ index
+
+
\ No newline at end of file
diff --git a/spring-mvc-push/src/main/webapp/index.jsp b/spring-mvc-push/src/main/webapp/index.jsp
new file mode 100644
index 0000000000..82ecb68003
--- /dev/null
+++ b/spring-mvc-push/src/main/webapp/index.jsp
@@ -0,0 +1,14 @@
+<%@ page language="java" contentType="text/html; charset=UTF-8"
+ pageEncoding="UTF-8"%>
+
+
+
+PushBuilder demo
+
+
+
+
+
\ No newline at end of file
diff --git a/spring-mvc-push/src/main/webapp/resources/logo.png b/spring-mvc-push/src/main/webapp/resources/logo.png
new file mode 100644
index 0000000000..edb83efbe3
Binary files /dev/null and b/spring-mvc-push/src/main/webapp/resources/logo.png differ
diff --git a/spring-mvc-push/src/main/webapp/resources/script.js b/spring-mvc-push/src/main/webapp/resources/script.js
new file mode 100644
index 0000000000..9bc97c006a
--- /dev/null
+++ b/spring-mvc-push/src/main/webapp/resources/script.js
@@ -0,0 +1 @@
+console.log('Script')
\ No newline at end of file
diff --git a/spring-mvc-push/src/main/webapp/resources/style.css b/spring-mvc-push/src/main/webapp/resources/style.css
new file mode 100644
index 0000000000..d5fc158135
--- /dev/null
+++ b/spring-mvc-push/src/main/webapp/resources/style.css
@@ -0,0 +1,9 @@
+.single-title {
+ font-size: 30px;
+ color: #535353;
+ font-weight: 200;
+ letter-spacing: -1.5px;
+ line-height: 64px;
+ max-width: 750px;
+ font-family: "Helvetica Neue", Helvetica, Arial, sans-serif
+}
\ No newline at end of file
diff --git a/spring-mvc-push/src/test/java/com/baeldung/controller/PushControllerIntegrationTest.java b/spring-mvc-push/src/test/java/com/baeldung/controller/PushControllerIntegrationTest.java
new file mode 100644
index 0000000000..570e05cad6
--- /dev/null
+++ b/spring-mvc-push/src/test/java/com/baeldung/controller/PushControllerIntegrationTest.java
@@ -0,0 +1,41 @@
+package com.baeldung.controller;
+
+import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
+import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
+
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Disabled;
+import org.junit.jupiter.api.Test;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.test.context.junit.jupiter.web.SpringJUnitWebConfig;
+import org.springframework.test.web.servlet.MockMvc;
+import org.springframework.test.web.servlet.setup.MockMvcBuilders;
+import org.springframework.web.context.WebApplicationContext;
+
+import com.baeldung.config.PushConfiguration;
+
+@Disabled
+@SpringJUnitWebConfig(PushConfiguration.class)
+public class PushControllerIntegrationTest {
+ @Autowired
+ private WebApplicationContext webAppContext;
+ private MockMvc mockMvc;
+
+ @BeforeEach
+ public void setup() {
+ mockMvc = MockMvcBuilders.webAppContextSetup(webAppContext)
+ .build();
+ }
+
+ @Test
+ public void whenDemoWithPushGETisPerformed_thenRetrievedStatusOk() throws Exception {
+ mockMvc.perform(get("/demoWithPush"))
+ .andExpect(status().isOk());
+ }
+
+ @Test
+ public void whenDemoWithoutPushGETisPerformed_thenRetrievedStatusOk() throws Exception {
+ mockMvc.perform(get("/demoWithoutPush"))
+ .andExpect(status().isOk());
+ }
+}
\ No newline at end of file