2016-03-02 53 views
3

我在前端使用弹簧引导和角度。有时我想直接从服务重定向。我们只使用.html,.css和脚本文件(不包括.jsp)。无法找到与弹簧启动的HTML页面

这是return "static/pages/savepassword.html";我如何试图重定向到savepassword

所以第一个问题,我怎么在这种情况下,适当地重定向?

接下来,Spring没有找到我的html文件。我有这样的结构

enter image description here

,我读了春天应该会自动查找所有静态文件中的“静”,但事实并非如此。所以,我想配置我ViewControllerRegistry和RessourceControllerRegistry

@Override 
    public void addResourceHandlers(ResourceHandlerRegistry registry) { 
     super.addResourceHandlers(registry); 
     registry.addResourceHandler("/static/**").addResourceLocations("/static/"); 
//  registry.addResourceHandler("/stylesheets/**").addResourceLocations("/stylesheets/"); 
//  registry.addResourceHandler("/scripts/**").addResourceLocations("/scripts/"); 
//  registry.addResourceHandler("/pages/**").addResourceLocations("/pages/"); 
    } 

    @Override 
    public void addViewControllers(ViewControllerRegistry registry) { 
     super.addViewControllers(registry); 
     registry.addViewController("/savePassword").setViewName("static/pages/savePassword.html"); 
     registry.addViewController("/login").setViewName("static/pages/login.html"); 
     registry.setOrder(Ordered.HIGHEST_PRECEDENCE); 
    } 

当我称之为“静态/页/ login.html的”直接,它的作品。当我想打电话“/登录”它说404. 第二个问题:我需要什么配置,什么不是?

UPDATE-1:春季安全

http 
      .authorizeRequests().antMatchers("/login", "/logout", "/user/**").permitAll() 
      .anyRequest().authenticated() 
     .and() 
      .exceptionHandling() 
      .accessDeniedHandler(new CustomAccessDeniedHandler()) 
      .authenticationEntryPoint(new CustomAuthenticationEntryPoint()) 
     .and() 
      .requiresChannel() 
      .anyRequest().requiresSecure() 
     .and() 
      .csrf() 
      .disable() 
      //.csrfTokenRepository(csrfTokenRepository()) 
      .addFilterBefore(new MDCFilter(), ExceptionTranslationFilter.class) 
      // .addFilterBefore(new CorsFilter(),// ChannelProcessingFilter.class) 
      //.addFilterAfter(new CsrfHeaderFilter(), CsrfFilter.class) 
      .formLogin() 
      .successHandler(new CustomSuccessAuthenticationHandler()) 
      .failureHandler(new CustomFailureHandler()) 
      .loginPage("/login").permitAll(); 

UPDATE-2 我更新了我的结构,但仍然有问题,与/登录重定向到自定义登录。 enter image description here

UPDATE-3 我看了一下鲍勃·希尔兹第二评论:https://spring.io/blog/2013/12/19/serving-static-web-content-with-spring-boot 我做了以下内容:

@Override 
    public void addResourceHandlers(ResourceHandlerRegistry registry) { 
     super.addResourceHandlers(registry); 
     registry.addResourceHandler("/resources/**").addResourceLocations("/resources/"); 
    } 

    @Override 
    public void addViewControllers(ViewControllerRegistry registry) { 
     super.addViewControllers(registry); 
     registry.addViewController("/savepassword").setViewName("savepassword.html"); 
     registry.addViewController("/login").setViewName("login.html"); 
     registry.setOrder(Ordered.HIGHEST_PRECEDENCE); 
    } 

我设置的.html,否则/登录会导致递归问题。使用此配置,我可以输入/ login并调用/templates/login.html(与savepassword.html相同)。

现在,我想知道如何在HTML中包括我的CSS/JS:

<link rel="stylesheet" type="text/css" href="..resources/stylesheets/bootstrap.min.css" /> 
    <script src="..resources/scripts/angular.min.js"></script> 
    <script src="..resources/scripts/login.js"></script> 

这不工作...但我卡恩直接/脚本/登录调用我的脚本.js文件。

+0

你可以尝试使用/login.html吗? –

+0

不,因为默认的Spring Security页面出现了。 Regulary,我们自定义的login.html(static/pages/login.html)应该显示出来。 我更新了我的答案,所以你可以看到弹簧安全配置。 我以为'ViewControllerRegistry'解析登录到静态/页面/登录,HTML,并将采取此登录页面 – Andy

+0

我可能需要将静态文件夹放在src/main/ressource而不是放入webapp? – Andy

回答

2

好吧,现在我完全明白了。我尝试尽可能具体。

我的最终结构

structure

1.静态Ressources

Spring有一些默认配置,你可以把你的静态ressources没有配置。您需要SRC创建这些文件夹/主/资源

  • /META-INF /资源/
  • 资源(是的,在SRC /主/资源
  • 静态
  • 额外的资源文件夹
  • 公共

看一看here in Spring Doku.举一个例子,检查由鲍勃·希尔兹第二评论:

创建一串“findme.txt”的文件,其中的每一个内有不同的“源相对的”路径字符串后,我发现,在以下位置可与“http://host/findme.txt”中获取有:

SRC /main/resources/public/findme.txt

src/main/resources/static/findme。TXT

的src /主/资源/资源/ findme.txt - (是的,资源^ 2!)

的src /主/资源/ findme.txt - 没有找到!

我将我的文件夹“脚本”和“样式表”放在静态文件夹中。当我想包括在HTML这些文件夹中的文件,源看起来像src="scripts/file.js"因为static的文件和文件夹被发现直接生根host/scripts/file.js

没有ResourceHandlerRegistry是必要的我!

2.视图控制器

我想我的根来的login.html /登录,savepassword.html到/ savepassword和我的index.html到/。下面是我做的:

registry.addViewController("/savepassword").setViewName("savepassword.html"); 
registry.addViewController("/login").setViewName("login.html"); 
registry.addViewController("/").setViewName("loggedin/index.html"); 

我设置*。html的,否则我有春天不知道/登录和登录档案(.html)之间不同的问题。 正如你所看到的,我将index.html放在了一个名为“loggedin”的不同文件夹中。这个文件夹是在我的公共文件夹(由Spring发现,见1)。为什么要这样做?看看3

3.春季安全

.authorizeRequests().antMatchers("/stylesheets/**", "/scripts/**","/login", "/user/**").permitAll() 
...omitted further configuration... 
.loginPage("/login").permitAll(); 

首先,我想,一个用户总是有先登录才可以访问任何其他网站。因此,登录页面的所有资源必须可用。

这段代码使样式表和脚本中的每个文件都可以访问。记住样式表和脚本 - 文件夹被置于静态。由于自定义登录页面,我必须设置“/ login”。 老实说,我认为.loginPage("/login").permitAll();将授予访问权限,但它不。没有它,Spring会尝试访问“/ login”,但不能导致没有权限,然后自动重定向到login => ERR_TOO_MANDY_REDIRECTS。 “/ user/**”仅用于我的一些服务,每个用户都可以使用。

正如你所看到的,我不给获得“的loggedIn” -folder,让每一位参观者可以在“的loggedIn”输入文件只有当他的loggedIn)

4.重定向

我只用@RequestController标记了我的整个控制器,它实现了@ResponseBody。当我返回一个像返回"redirect:/savepassword";这样的字符串时,Spring会将其设置为ResponseBody,并将其解释为String/Json(?)。

我必须将控制器标记为@Controller并将@ResponseBody设置为必须返回json或某物的每个服务。我应该重定向的服务仅用@RequestMapping和method = RequestMethod.GET标记。最后,我返回一个字符串,如return "redirect:/savepassword";这将使Spring重定向到/ savepassword,其实际位于src/main/resources/public/savepassword.html

最后,它的工作原理很难找到spring如何提供这些文件。我希望它可以帮助别人:)

3

在我看来,最好把你的* .HTML文件放在你的资源文件夹中,并使用所有的静态CSS字体等,如下图所示。在webapp中,您只能拥有一个WEB-INF文件夹。

我使用这种结构,我没有发现任何类的CSS或HTMLS的问题,我不使用扩展在Java(“静态/页/ login.html”像你的)结束。如果我想访问html,如果它在ex文件夹用户中,就像“user/someHtml”一样。

我知道这个答案不完全是你正在寻找的那个,但它可能在某种程度上帮助你。

enter image description here

编辑:现在为:

@Override 
    public void addViewControllers(ViewControllerRegistry registry) { 
     super.addViewControllers(registry); 
     registry.addViewController("/savePassword").setViewName("static/pages/savePassword.html"); 
     registry.addViewController("/login").setViewName("static/pages/login.html"); 
     registry.setOrder(Ordered.HIGHEST_PRECEDENCE); 
} 

比方说你有一个控制器:

@Controller 
@RequestMapping("/myController") 
public class MyController{ 
... 


@RequestMapping(value = "/login") 
public String login(Model model) { 
    // Your code .... 

    return "login"; //<- this is your login.html if it is directly in resource/templates folder 
} 
    @RequestMapping(value = "/savePassword") 
public String savePassword(Model model) { 
    // Your code .... 

    return "savePassword"; //<- this is your savePassword.html if it is directly in resource/templates folder 
} 
..... 
} 

现在你addViewController显示是这样的:

@Override 
     public void addViewControllers(ViewControllerRegistry registry) { 
      super.addViewControllers(registry); 
      registry.addViewController("/savePassword").setViewName("forward:/myController/savePassword"); 
     registry.addViewController("/login").setViewName("forward:/myController/login"); 
     registry.setOrder(Ordered.HIGHEST_PRECEDENCE); 
} 

你在你的addViewController看到您试图访问控制器不是HTML,你会通过你的方法addViewControllers访问控制器访问你的HTML。

UPDATE:

如果你把你的CSS到您的静态文件夹中的资源,如:

enter image description here

你可以简单地访问他们像这样:

<link rel="stylesheet" th:href="@{/css/bootstrap-datetimepicker.min.css}" /> 

希望这有助于!

+0

首先,谢谢;)是的,我改变了我的结构,现在(所以+1),但是仍然存在两个问题:如何重定向和设置ViewController。 – Andy

+0

那么我想你扩展了WebMvcConfigurerAdapter。因此,例如。这里是如何当您试图访问你的应用程序中,如HTTP浏览器://本地主机:8080 /,你将被重定向到“用户/ showSomething” @覆盖 公共无效addViewControllers(ViewControllerRegistry注册表){ 注册表。 addViewController(“/”).setViewName(“forward:/ user/showSomething”); registry.setOrder(Ordered.HIGHEST_PRECEDENCE); super.addViewControllers(registry); } PS:你可能错过了“前进”,就像我在前。希望这可以帮助。 –

+0

它只是不工作...不能访问任何html ...即使没有弹簧安全和wihtout ViewControllerRegistry/ResourceHandlerRegistry – Andy