【问题标题】:Thymeleaf: add parameter to current urlThymeleaf:将参数添加到当前 url
【发布时间】:2015-02-21 18:36:13
【问题描述】:

我在

http://example.com/some/page?p1=11

我想在当前 url 中添加一个参数,而不必重新定义它:

http://example.com/some/page?p1=11&p2=32

类似:

<a th:href="@{?(p2=32)}">Click here</a>

但是上面的代码返回http://example.com/some/page?&amp;p2=32(去掉p1参数)。

我如何使用 Thymeleaf 来做到这一点?

【问题讨论】:

  • 真的没有合适的方法来处理这个问题(截至 2016 年春季)?

标签: java spring-mvc spring-boot thymeleaf url-parameters


【解决方案1】:

您可以直接从 Thymeleaf 使用 URI 构建器。

<span th:with="urlBuilder=${T(org.springframework.web.servlet.support.ServletUriComponentsBuilder).fromCurrentRequest()}"
      th:text="${urlBuilder.replaceQueryParam('p2', '32').toUriString()}">
</span>

对于 URL http://example.com/some/page?p1=11 打印出来:

http://example.com/some/page?p1=11&p2=32

解释:

  • SpEL T operator 用于访问ServletUriComponentsBuilder 类型。
  • 工厂方法fromCurrentRequest创建的实例保存到urlBuilder变量中。
  • 通过replaceQueryParam方法在查询字符串中添加或替换参数,然后构建URL。

优点:

  • 安全的解决方案。
  • 如果查询字符串为空,则没有尾随 ?。
  • Spring 上下文中没有额外的 bean。

缺点:

  • 相当冗长。

!请注意,上述解决方案创建了一个构建器实例。这意味着构建器不能被重用,因为它仍然会修改原始 URL。对于页面上的多个 URL,您必须创建多个构建器,如下所示:

<span th:with="urlBuilder=${T(org.springframework.web.servlet.support.ServletUriComponentsBuilder)}">
    <span th:text="${urlBuilder.fromCurrentRequest().replaceQueryParam('p2', 'whatever').toUriString()}"></span>
    <span th:text="${urlBuilder.fromCurrentRequest().replaceQueryParam('p3', 'whatever').toUriString()}"></span>
    <span th:text="${urlBuilder.fromCurrentRequest().replaceQueryParam('p4', 'whatever').toUriString()}"></span>
</span>

对于http://example.com/some/page 打印:

http://example.com/some/page?p2=whatever 
http://example.com/some/page?p3=whatever     
http://example.com/some/page?p4=whatever

【讨论】:

  • 对于以后的任何人,你也可以用多个replaceQueryParam替换多个参数像这样${urlBuilder.replaceQueryParam('page', current).replaceQueryParam('size', page.size).toUriString()
  • 如何将 'p4' 设置为 'two,values' ?而不是 &p4=two,values 它不断创建两个参数,例如 &p4=two&p4=values
  • 想通了,我只是将它作为 {'two,values'} 这样的列表的第一个参数传递了
【解决方案2】:

最简单的解决方案是连接“requestURI”和“queryString”。 这是一个例子:

<div th:with="currentUrl=(${#httpServletRequest.requestURI + '?' + #strings.defaultString(#httpServletRequest.queryString, '')})">
   <a th:href="@{${currentUrl}(myparam=test)}">click here</a>
</div>

“http://localhost:8080/some-page?param1=1”的结果:

 http://localhost:8080/some-page?param1=1&myparam=test

“http://localhost:8080/some-page”的结果:

 http://localhost:8080/some-page?&myparam=test

缺点:
Thymeleaf 不会覆盖参数 - 只会将参数添加到 URL。因此,如果您用户再次单击该 URL,结果将是:

http://localhost:8080/some-page?param1=1&myparam=test&myparam=test

参考:
http://forum.thymeleaf.org/How-to-link-to-current-page-and-exchange-parameter-td4024870.html

编辑:

这里有一些解决方法,从 URL 中删除参数“myparam”:

<div th:with="currentUrl=(${@currentUrlWithoutParam.apply('myparam')})">
    <a th:href="@{${currentUrl}(myparam=test)}">click here</a>
</div>

Spring 配置中的下一步:

@Bean
public Function<String, String> currentUrlWithoutParam() {
    return param ->   ServletUriComponentsBuilder.fromCurrentRequest().replaceQueryParam(param).toUriString();
}

对于更多“全局”解决方案,我会尝试为属性“th:href”扩展处理器或创建我自己的属性。我不是百里香专家,只是面临类似的问题。

【讨论】:

  • 缺点的解决方法是创建没有我们要添加的参数的基本 url。
  • 在第一种情况下:请务必使用${#httpServletRequest.requestURI + '?' + #strings.defaultString(#httpServletRequest.queryString, '')},以避免将null附加到您的网址。
  • 感谢您注意到“queryString”可能为空。链接到javadoc。
【解决方案3】:
th:href="@{/your/link?parameter=__${appendParameter}__}"

【讨论】:

  • 请注意,__(双下划线)需要它才能工作,这些不会出现在结果中
【解决方案4】:

根据docs可以指定所有参数

th:href="@{http://example.com/some/page(p1=11,p2=32)}"

您可以使用表达式来获取值:

th:href="@{http://example.com/some/page(p1=11,p2=${someid})}"

【讨论】:

    【解决方案5】:

    这对你有用,即使是 Unicode:

     <ul class="pagination">
                    <li th:if="${currentPage > 1}"><a th:href="'/search?key=' + ${param.key[0]} + '&amp;page=' +   ${currentPage-1}">Previous</a></li>
    
                          <li th:each="i : ${#numbers.sequence( 1, total+1)}" th:class="${i==currentPage}?active:''">
                                <a th:href="'/search?key=' + ${param.key[0]} + '&amp;page=' +   ${i}" th:inline="text">
                                [[${i}]] <span  class="sr-only">(current)</span>
                                </a>
                          </li>
                          <li><a th:if="${total + 1 > currentPage}" th:href="'/search?key=' + ${param.key[0]} + '&amp;page=' +   ${currentPage+1}">Next</a></li>
                </ul>
    

    【讨论】:

      【解决方案6】:

      基于来自Raf 的answer,我最终得到了这个解决方案:

      @Bean
      public BiFunction<String, String, String> replaceOrAddParam() {
        return (paramName, newValue) -> ServletUriComponentsBuilder.fromCurrentRequest()
              .replaceQueryParam(paramName, newValue)
              .toUriString();
      }
      
      <a th:href="${@replaceOrAddParam.apply('myParamName', 'myNewValue')}">Text</a>
      

      【讨论】:

        猜你喜欢
        • 2012-01-23
        • 1970-01-01
        • 2015-01-27
        • 1970-01-01
        • 1970-01-01
        • 2013-04-08
        • 1970-01-01
        • 1970-01-01
        • 2014-06-15
        相关资源
        最近更新 更多