我有VueJS单页应用程序内的Spring Boot 应用程序,我想使vue路由器处理所有的请求,而不是这些URL以/rest/**
开头的请求。
因此我编写了正则表达式^(?!/rest/).*
来匹配所有不以/rest/
开头的内容,并尝试将请求Map为:
@Controller
public class MainController {
@RequestMapping(value = "/{path:^(?!/rest/).*}")
public String forwardRequests() {
return "forward:/";
}
}
但没用我哪里做错了
编辑
我有剩余的控制器文件:
@RestController
@RequestMapping(path = "/rest/project")
public class ProjectController {
@Autowired
private ProjectService projectService;
@GetMapping(value = "/{id}")
public Project getProjectById(@PathVariable Long id) {
return projectService.getProjectById(id);
}
}
它返回包含项目详细信息的JSON。我有一些像/login
和/projekty
这样的页面,所以我需要将它们转发到index.html
,以便处理vue的路由。我知道我可以做这样的事情:
@Controller
public class MainController {
@RequestMapping(value = {"/login", "/projekty"}, method = RequestMethod.GET)
public String forwardRequests() {
return "forward:/";
}
}
它工作的很好,但是我不想显式的指定每个url,这就是为什么我尝试使用正则表达式,我想我用错了path
变量,但是我不知道怎么用。
https://spring.io/guides/tutorials/spring-security-and-angular-js/截面Using "Natural" Routes
5条答案
按热度按时间a7qyws3x1#
正如@JDB所说,
AntPathMatcher
会比较路径并找到最佳匹配,因此您不必担心端点,因为端点已经指定了路径,就像我的/rest
API一样。您可以添加以下内容:
并且您的所有请求(例如
/login
)将被正确地转发到index.html
,在index.html
中JavaScript可以处理它。问题出在像
/project/edit/33
这样的URL上,它们与这个正则表达式不匹配,所以你会看到Whitelabel Error Page 404 Not Found
。它工作正常,但如果启用了安全性,
/ouath/token
将返回:所以你必须排除oauth网址:
而且效果很好。
如果框架提供的其他端点(如
/health
)有问题,可以将正则表达式更改为/**/{path:^(?!oauth|health).*}/{path:[^\\.]*}
它看起来很糟糕,但它很有效。我相信有人会在这里发布一个更好更干净的解决方案。
p1tboqfb2#
我并不特别了解Spring,所以我只是根据使用其他框架的经验做出最好的猜测。
首先,既然已经在路径中包含了正斜杠,那么模式是否不应该排除它呢?
如果这不起作用,那么我所能想到的就是AntPathMatcher不支持lookaheads。
这种设计的典型模式是同时实现
/rest/*
和/*
路由。在某些框架中,这仅仅是为了正确地排序它们。根据Spring MVC的文档,您可能需要尝试一些规则来使/rest/*
路由“更具体”。规则如下:
当多个模式匹配一个URL时,必须通过AntPathMatcher.getPatternComparator(字符串路径)比较它们以找到最佳匹配。
如果一个模式的URI变量和单个通配符计数较低,则该模式的特定性较低,单个通配符计数为1,双个通配符计数为2。如果得分相等,则选择较长的模式。如果得分和长度相同,则选择URI变量比通配符多的模式。
默认Map模式/不包含在评分中,始终排在最后。此外,前缀模式(如/public/)被认为不如其他没有双通配符的模式具体。
有关完整的细节,请参见AntPathMatcher中的AntPatternComparator。另外,请记住,所使用的PathMatcher实现可以自定义。
因此,根据我对这些规则和您的代码的解释,我认为沿着几种方法可以起作用:
l3zydbqr3#
可以添加缺省处理程序方法
4c8rllxm4#
再看一遍...字符串是
/{path:^(?!/rest/).*}
。存在第一个
/
,然后正则表达式也声明第一个/
。此正则表达式将匹配/rest/*
,因为它验证/(?!/rest/).*
而不是(?!/rest/).*
。旧答案错误,请参见@加多宝评论
/
字符是正则表达式中的特殊字符,需要进行转义。由于
\
在Java中也是字符串的转义字符,因此需要两个转义字符。r3i60tvu5#
对于我们想要排除的情况,尝试请求路径匹配通常是很麻烦的,我们可以使用ResourceResolver处理WebHistory重定向的特定情况。
我的案例是:
后台静态文件由SpringBoot作为
/admin
下的静态资源提供。我需要将/admin/**
资源(不是静态资源,而是webapp路由)作为index.html
提供。对于该用例,我实现了一个简单的ResourceResolver
。然后示例化处理程序,如下所示: