Java Spring boot获取servlet上下文之外的应用程序基url
设置如下-我有一个定时任务,将发送验证电子邮件,以便用户:Java Spring boot获取servlet上下文之外的应用程序基url,java,spring,servlets,spring-boot,thymeleaf,Java,Spring,Servlets,Spring Boot,Thymeleaf,设置如下-我有一个定时任务,将发送验证电子邮件,以便用户: @Scheduled(cron = " 0 0-59/1 * * * * ") public void sendVerificationEmails() { //... } 在这些电子邮件中,我需要包含一个指向同一个webapp的链接。然而,我找不到任何关于如何在没有servlet上下文的情况下获取应用程序的基本url的参考 奖金 如果我可以在这里设置thymeleaf模板解析器来处理这些链接,这也会有所帮助,但为此我需要一个
@Scheduled(cron = " 0 0-59/1 * * * * ")
public void sendVerificationEmails() {
//...
}
在这些电子邮件中,我需要包含一个指向同一个webapp的链接。然而,我找不到任何关于如何在没有servlet上下文的情况下获取应用程序的基本url的参考
奖金
如果我可以在这里设置thymeleaf模板解析器来处理这些链接,这也会有所帮助,但为此我需要一个
WebContext
,它需要一个HttpServletRequest
的实例。在我的设置中,我有一个@Configuration类来设置上下文路径(硬编码)和@Value注入application.properties中的端口号。还可以将上下文路径提取到属性文件并以相同的方式注入,您可以使用:
@Value("${server.port}")
private String serverPort;
@Value("${server.contextPath}")
private String contextPath;
您还可以在组件中实现ServletContextAware,以便获得ServletContext的挂钩,该挂钩还将为您提供上下文路径
我猜您希望在电子邮件中提供完整的url(包括完整的服务器名称),但您不能确定电子邮件接收者是否通过主机名直接访问您的应用程序服务器,即它可能位于web服务器后面,代理等。您当然可以添加一个服务器名称,您知道该名称也可以作为属性从外部访问。假设您的应用程序使用嵌入式tomcat服务器,那么您的应用程序的url可能如下所示:
@Inject
private EmbeddedWebApplicationContext appContext;
public String getBaseUrl() throws UnknownHostException {
Connector connector = ((TomcatEmbeddedServletContainer) appContext.getEmbeddedServletContainer()).getTomcat().getConnector();
String scheme = connector.getScheme();
String ip = InetAddress.getLocalHost().getHostAddress();
int port = connector.getPort();
String contextPath = appContext.getServletContext().getContextPath();
return scheme + "://" + ip + ":" + port + contextPath;
}
以下是嵌入式jetty服务器的示例:
public String getBaseUrl() throws UnknownHostException {
ServerConnector connector = (ServerConnector) ((JettyEmbeddedServletContainer) appContext.getEmbeddedServletContainer()).getServer().getConnectors()[0];
String scheme = connector.getDefaultProtocol().toLowerCase().contains("ssl") ? "https" : "http";
String ip = InetAddress.getLocalHost().getHostAddress();
int port = connector.getLocalPort();
String contextPath = appContext.getServletContext().getContextPath();
return scheme + "://" + ip + ":" + port + contextPath;
}
属性文件呢。顺便问一下,为什么您不想使用servlet上下文?@kuhajeyan,因为它不是一个web请求,而是一个不同的范围。属性文件呢?请看我的答案。它很简洁,让你从所有的连接中解脱出来,不可移植,容易出错。我不是在问如何发送电子邮件或使用thymeleaf模板,这与问题无关。事实上,如果你仔细阅读这个问题,你会意识到我已经在使用thymeleaf模板和发送电子邮件了。真正的问题是,应用程序是否知道它的基本url,以及如何获取它——而你的解决方案是自己提供,这一点都没有帮助(从部署方面来说,这是一种粗糙的做法)。此外,如果你不使用
WebContext
让上下文HTTP感知,那么thymeleaf中的{}链接就不起作用了。你是对的,我完全误解了你的问题,也许我编辑的答案你会发现更有用。当部署到不同的web servlet容器时,这会起作用吗?我只使用tomcat和jetty进行了测试,请参阅我编辑过的答案。由于部署依赖性,它很混乱。尽管如此,我认为这是一个正确的答案。在SpringBoot的新版本中,它是@Value(${server.context path}”)
,但它是一个很好的解决方案,thx。