Spring - the views context change when I use a nested mapping - java

I created my controller with spring like this:
#Controller
public class ProdutosController {
#RequestMapping("produtos/form")
public String form() {
return "produtos\\form";
}
}
Everytime that I try access it returns:
-type Status report
-message /casadocodigo/produtos/WEB-INF/views/produtos/form.jsp
-description The requested resource is not available.
It adds an "produtos/" before the WEB-INF folder, but when I change my view to:
#RequestMapping("/form")
public String form() {
return "produtos\\form";
}
It returns the correct path to my view.
Here my configuration classes:
public class ServletSpringMVC extends AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected Class<?>[] getRootConfigClasses() {
// TODO Auto-generated method stub
return null;
}
#Override
protected Class<?>[] getServletConfigClasses() {
return new Class[] {AppWebConfiguration.class};
}
#Override
protected String[] getServletMappings() {
return new String[] {"/"};
}
#EnableWebMvc
#ComponentScan(basePackageClasses={HomeController.class})
public class AppWebConfiguration {
#Bean
public InternalResourceViewResolver internalResourceViewResolver() {
InternalResourceViewResolver resolver = new InternalResourceViewResolver();
resolver.setPrefix("WEB-INF/views/");
resolver.setSuffix(".jsp");
return resolver;
}
}
I know if I create the same directory structure it will eventually work, but everytime that I map something with a nested uri I will have to create a new folder inside my webapp folder. Is there any way to solve this?
I found the problem. There was a "/" missing in the view resolver. Now the class look like this:
#Bean
public InternalResourceViewResolver internalResourceViewResolver() {
InternalResourceViewResolver resolver = new InternalResourceViewResolver();
resolver.setPrefix("/WEB-INF/views/");
resolver.setSuffix(".jsp");
return resolver;
}

Related

Spring configuration without Spring Boot

I've been trying to configure Spring without Spring Boot.
I added a Tomcat, created the MainController class, and configured the Dispatcher Servlet
but in an endpoint 'http://localhost:8080/main/hello I receive 404.
I think it is problem in the ServletDispatcherConfig.
This is my  ServletDispatcherConfig  class
#Component
public class ServletDispatcherConfig extends AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected Class<?>[] getRootConfigClasses() {
return null;
}
#Override
protected Class<?>[] getServletConfigClasses() {
return new Class[] {SpringConfig.class};
}
#Override
protected String[] getServletMappings() {
return new String[] {"/"};
}
}
and this is my SpringConfig class
#Configuration
#ComponentScan("example.test")
#EnableWebMvc
public class SpringConfig {
private final ApplicationContext applicationContext;
#Autowired
public SpringConfig(ApplicationContext applicationContext) {
this.applicationContext = applicationContext;
}
#Bean
public SpringResourceTemplateResolver templateResolver() {
var resolver = new SpringResourceTemplateResolver();
resolver.setCacheable(true);
resolver.setPrefix("/WEB-INF/templates/");
resolver.setSuffix(".html");
resolver.setApplicationContext(applicationContext);
resolver.setTemplateMode(TemplateMode.HTML);
return resolver;
}
#Bean
public SpringTemplateEngine templateEngine() {
var engine = new SpringTemplateEngine();
engine.setTemplateResolver(templateResolver());
engine.setEnableSpringELCompiler(true); // delete if any bugs will be
return engine;
}
#Bean
public ThymeleafViewResolver viewResolver() {
var templateResolver = new ThymeleafViewResolver();
templateResolver.setTemplateEngine(templateEngine());
return templateResolver;
}
}
my MainController class
#Controller
#RequestMapping("/main")
public class MainController {
#GetMapping("/first")
public String main() {
return "/main";
}
#GetMapping("/hello")
public String hello() {
return "/main";
}
}

Failed to register servlet with name 'dispatcher'.Check if there is another servlet registered under the same name.

What is wrong in below Java code and what does it mean? Can anyone please help me to solve this:
java.lang.IllegalArgumentException: Failed to register servlet with name 'dispatcher'.Check if there is another servlet registered under the same name.
AppConfig.java
#Configuration
#EnableWebMvc
#ComponentScan(basePackages = "com.kk.kk.config")
public class AppConfig {
//Define a bean for ViewResolver
#Bean
public ViewResolver viewResolver(){
InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
viewResolver.setPrefix("/WEB-INF/view/");
viewResolver.setSuffix(".jsp");
return viewResolver;
}
}
DispatcherServletInitializer.java
public class DispatcherServletInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected Class<?>[] getRootConfigClasses() {
//TODO Auto-generated method stub
return null;
}
#Override
protected Class<?>[] getServletConfigClasses(){
return new Class[] {AppConfig.class};
}
#Override
protected String[] getServletMappings(){
return new String[] {"/"};
}
}
AppController.java
#Controller
public class AppController {
#GetMapping("/")
public String showHome(){
return "home";
}
}
You can implement WebMvcConfigurer :
Try this:
#Configuration
#EnableWebMvc
public class AppConfig implements WebMvcConfigurer{
}

Running Spring web from IDE vs from jar file

I am trying to create a simple web application that will use angular in FE and Spring in BE.
Everything works if I run it from my IDE (IntelliJ IDEA 2017.2), but if I start the jar file it cant find the jsp page and shows an Whitelabel Error Page.
Its gradle build and thease are the dependencies
dependencies {
compile('org.springframework.boot:spring-boot-starter-data-rest')
compile('org.springframework.boot:spring-boot-starter-web')
testCompile('org.springframework.boot:spring-boot-starter-test')
compile 'javax.servlet:jstl:1.2'
}
ChartConfiguration.java
#Configuration
#EnableWebMvc
public class ChartConfiguration extends WebMvcConfigurerAdapter{
#Override
public void configureViewResolvers(ViewResolverRegistry registry) {
InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
viewResolver.setViewClass(JstlView.class);
viewResolver.setPrefix("/WEB-INF/views/");
viewResolver.setSuffix(".jsp");
registry.viewResolver(viewResolver);
}
#Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/static/**").addResourceLocations("/static/");
}
#Override
public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
configurer.enable();
}
}
ChartInitializer.java
import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;
import javax.servlet.Filter;
public class ChartInitializer extends
AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected Class<?>[] getRootConfigClasses() {
return new Class[] { ChartConfiguration.class };
}
#Override
protected Class<?>[] getServletConfigClasses() {
return null;
}
#Override
protected String[] getServletMappings() {
return new String[] { "/" };
}
#Override
protected Filter[] getServletFilters() {
Filter [] singleton = { new CORSFilter() };
return singleton;
}
}
IndexController.java
#Controller
#RequestMapping("/")
public class IndexController {
#RequestMapping(method = RequestMethod.GET)
public String getIndexPage() {
return "ChartManagement";
}
}
And my jsp page contains only a tag, nothing else.
What am I doing wrong, I cant figure it out?
So I made it work but with a little bit different configuration. I have removed
ChartConfiguration.java
ChartInitializer.java
Everything inside main/resources folder
And now I have created a folder in main/resources called templates, and inside it is index.html
Also I have added a new dependency
compile("org.springframework.boot:spring-boot-starter-thymeleaf")
And changed IndexController to
#Controller
#RequestMapping("/")
public class IndexController {
#RequestMapping(method = RequestMethod.GET)
public String getIndexPage() {
return "index";
}
}

Spring MVC and freemarker java annotation configuration

I'm trying to use freemarker as my template engine in my project, my views are .JSP files but with nothing of jsp code inside them, I can change them to .html but I also tried that and I get the same error
here is my JavaConfig class
#Configuration
#EnableWebMvc
#ComponentScan({"configuracion", "controladores", "seguridad"})
public class ConfigMVC extends WebMvcConfigurerAdapter {
#Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/resources/**").addResourceLocations("/WEB-INF/resources/");
}
#Bean
public FreeMarkerConfigurer freemarkerConfig() {
FreeMarkerConfigurer freeMarkerConfigurer = new FreeMarkerConfigurer();
freeMarkerConfigurer.setTemplateLoaderPath("/WEB-INF/views/");
freeMarkerConfigurer.setDefaultEncoding("UTF-8");
return freeMarkerConfigurer;
}
#Bean
public FreeMarkerViewResolver viewResolver() {
FreeMarkerViewResolver viewResolver = new FreeMarkerViewResolver();
viewResolver.setPrefix("/WEB-INF/views/");
viewResolver.setSuffix(".jsp");
viewResolver.setCache(false); //Set to true during production
viewResolver.setContentType("text/html;charset=UTF-8");
viewResolver.setOrder(0);
return viewResolver;
}
}
here is my Initializer class
public class WebInicializar extends AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected Class<?>[] getRootConfigClasses() {
return new Class[]{RootConfig.class};
}
#Override
protected Class<?>[] getServletConfigClasses() {
return new Class[]{ConfigMVC.class};
}
#Override
protected String[] getServletMappings() {
return new String[]{"/"};
}
#Override
protected Filter[] getServletFilters() {
Filter[] singleton = {new CORSFilter()};
return singleton;
}
#Override
protected DispatcherServlet createDispatcherServlet(WebApplicationContext servletAppContext) {
final DispatcherServlet dispatcherServlet = (DispatcherServlet) super.createDispatcherServlet(servletAppContext);
dispatcherServlet.setThrowExceptionIfNoHandlerFound(true);
return dispatcherServlet;
}
My Root Config
#Configuration
#ComponentScan(basePackages = {"controladores", "seguridad"})
#Import({ConfigMVC.class, SeguridadConfig.class})
public class RootConfig {
}
My Spring Version is 4.2.5.RELEASE and my freeMarker version is 2.3.21
This is the error when I lauch my web app
Advertencia: StandardWrapperValve[dispatcher]: Servlet.service() for
servlet dispatcher threw exception
javax.servlet.ServletException: Could not resolve view with name 'login' in servlet with name 'dispatcher'
at org.springframework.web.servlet.DispatcherServlet.render(DispatcherServlet.java:1226)
Freemarker uses prefix that set in FreemarkerConfigurer.
You need to remove setPrefix from FreeMarkerViewResolver

Use #Autowired in Spring MVC and JavaConfig

I have spring mvc project and i don't use #Autowired because my object always is null. How me load JavaConfig for using #Autowired, i do not use any *.xml file.
This is my controller with #Autowired field for service.
#Controller
public class WebController {
#Autowired
private ServiceWeb serviceWeb;
public void setServiceWeb(ServiceWeb serviceWeb) {
this.serviceWeb = serviceWeb;
}
...
}
This is my AbstractAnnotationConfigDispatcherServletInitializer
public class ServletInit extends
AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected Class<?>[] getRootConfigClasses() {
return new Class[] { SpringRootConfig.class};
}
#Override
protected Class<?>[] getServletConfigClasses() {
return new Class[] { SpringWebConfig.class};
}
#Override
protected String[] getServletMappings() {
return new String[] { "/" };
}
}
SpringRootConfig & SpringWebConfig
#Configuration
#ComponentScan({"web.controller"})
public class SpringRootConfig {
}
#EnableWebMvc
#Configuration
#ComponentScan({ "web.controller"})
#Import({SecurityConfig.class})
public class SpringWebConfig extends WebMvcConfigurerAdapter{
#Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/resources/**")
.addResourceLocations("/resources/");
}
#Bean
public InternalResourceViewResolver viewResolver() {
InternalResourceViewResolver viewResolver
= new InternalResourceViewResolver();
viewResolver.setViewClass(JstlView.class);
viewResolver.setPrefix("/WEB-INF/jsp/");
viewResolver.setSuffix(".jsp");
return viewResolver;
}
}
Class for #Autowiring
#Configuration
public class ConfigurationBean {
#Bean
public ServiceWeb serviceWeb(){
return new ServiceWebImpl();
}
}
Register context for spring, but where need write Init.class for loading this config ?
public class Init implements WebApplicationInitializer {
public void onStartup(ServletContext servletContext) throws ServletException {
AnnotationConfigWebApplicationContext ctx = new AnnotationConfigWebApplicationContext();
ctx.register(ConfigurationBean.class);
servletContext.addListener(new ContextLoaderListener(ctx));
ctx.setServletContext(servletContext);
}
}
Pls try this...
#Service
public class ServiceWebImpl implements ServiceWeb {
}
ServiceWeb bean is created inside ConfigurationBean class and its not visible at spring context level for autowiring.

Categories