diff --git a/build-spring-framework/resources/changelog.txt b/build-spring-framework/resources/changelog.txt
index 843499f94e3..f8a95e3d040 100644
--- a/build-spring-framework/resources/changelog.txt
+++ b/build-spring-framework/resources/changelog.txt
@@ -22,6 +22,7 @@ Changes in version 3.1 RC2 (2011-11-15)
* The Form hidden tag supports "disabled" attribute
* Add ignoreDefaultModelOnRedirect attribute to
For example if the servlet is mapped by name, i.e. {@code "/main/*"}, + * then the resulting path will be {@code /appContext/main}. If the servlet + * path is not mapped by name, i.e. {@code "/"} or {@code "*.html"}, then + * the resulting path will contain the context path only. + */ + public static ServletUriComponentsBuilder fromServletMapping(HttpServletRequest request) { + ServletUriComponentsBuilder builder = fromContextPath(request); + if (StringUtils.hasText(new UrlPathHelper().getPathWithinServletMapping(request))) { + builder.path(request.getServletPath()); + } + return builder; + } + + /** + * Return a builder initialized with all available information in the given + * request including scheme, host, port, path, and query string. + */ + public static ServletUriComponentsBuilder fromRequest(HttpServletRequest request) { + String scheme = request.getScheme(); + int port = request.getServerPort(); + + ServletUriComponentsBuilder builder = new ServletUriComponentsBuilder(); + builder.scheme(scheme); + builder.host(request.getServerName()); + if ((scheme.equals("http") && port != 80) || (scheme.equals("https") && port != 443)) { + builder.port(port); + } + builder.path(new UrlPathHelper().getRequestUri(request)); + builder.query(request.getQueryString()); + return builder; + } + + /** + * Equivalent to {@link #fromContextPath(HttpServletRequest)} except the + * request is obtained via {@link RequestContextHolder}. + */ + public static ServletUriComponentsBuilder fromCurrentContextPath() { + return fromContextPath(getCurrentRequest()); + } + + /** + * Equivalent to {@link #fromServletMapping(HttpServletRequest)} except the + * request is obtained via {@link RequestContextHolder}. + */ + public static ServletUriComponentsBuilder fromCurrentServletMapping() { + return fromServletMapping(getCurrentRequest()); + } + + /** + * Equivalent to {@link #fromRequest(HttpServletRequest)} except the + * request is obtained via {@link RequestContextHolder}. + */ + public static ServletUriComponentsBuilder fromCurrentRequest() { + return fromRequest(getCurrentRequest()); + } + + private static HttpServletRequest getCurrentRequest() { + RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes(); + Assert.state(requestAttributes != null, "Could not find current request via RequestContextHolder"); + Assert.isInstanceOf(ServletRequestAttributes.class, requestAttributes); + HttpServletRequest servletRequest = ((ServletRequestAttributes) requestAttributes).getRequest(); + Assert.state(servletRequest != null, "Could not find current HttpServletRequest"); + return servletRequest; + } + +} diff --git a/org.springframework.web/src/test/java/org/springframework/web/util/ServletUriComponentsBuilderTests.java b/org.springframework.web/src/test/java/org/springframework/web/util/ServletUriComponentsBuilderTests.java new file mode 100644 index 00000000000..7f8c4004b09 --- /dev/null +++ b/org.springframework.web/src/test/java/org/springframework/web/util/ServletUriComponentsBuilderTests.java @@ -0,0 +1,117 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.springframework.web.util; + +import static org.junit.Assert.assertEquals; + +import org.junit.Before; +import org.junit.Test; +import org.springframework.mock.web.MockHttpServletRequest; +import org.springframework.web.context.request.RequestContextHolder; +import org.springframework.web.context.request.ServletRequestAttributes; + +/** + * @author Rossen Stoyanchev + */ +public class ServletUriComponentsBuilderTests { + + private MockHttpServletRequest request; + + @Before + public void setup() { + this.request = new MockHttpServletRequest(); + this.request.setScheme("http"); + this.request.setServerName("localhost"); + this.request.setServerPort(80); + this.request.setContextPath("/mvc-showcase"); + } + + @Test + public void fromRequest() { + request.setRequestURI("/mvc-showcase/data/param"); + request.setQueryString("foo=123"); + + String result = ServletUriComponentsBuilder.fromRequest(request).build().toUriString(); + + assertEquals("http://localhost/mvc-showcase/data/param?foo=123", result); + } + + @Test + public void fromRequestEncodedPath() { + request.setRequestURI("/mvc-showcase/data/foo%20bar;jsessionid=123"); + + String result = ServletUriComponentsBuilder.fromRequest(request).build().toUriString(); + + assertEquals("http://localhost/mvc-showcase/data/foo bar", result); + } + + @Test + public void fromRequestAtypicalHttpPort() { + request.setServerPort(8080); + String result = ServletUriComponentsBuilder.fromRequest(request).build().toUriString(); + + assertEquals("http://localhost:8080", result); + } + + @Test + public void fromRequestAtypicalHttpsPort() { + request.setScheme("https"); + request.setServerPort(9043); + + String result = ServletUriComponentsBuilder.fromRequest(request).build().toUriString(); + + assertEquals("https://localhost:9043", result); + } + + @Test + public void fromContextPath() { + request.setRequestURI("/mvc-showcase/data/param"); + request.setQueryString("foo=123"); + + String result = ServletUriComponentsBuilder.fromContextPath(request).build().toUriString(); + + assertEquals("http://localhost/mvc-showcase", result); + } + + @Test + public void fromServletMapping() { + request.setRequestURI("/mvc-showcase/app/simple"); + request.setServletPath("/app"); + request.setQueryString("foo=123"); + + String result = ServletUriComponentsBuilder.fromServletMapping(request).build().toUriString(); + + assertEquals("http://localhost/mvc-showcase/app", result); + } + + @Test + public void fromCurrentRequest() { + request.setRequestURI("/mvc-showcase/data/param"); + request.setQueryString("foo=123"); + RequestContextHolder.setRequestAttributes(new ServletRequestAttributes(this.request)); + + try { + String result = ServletUriComponentsBuilder.fromCurrentRequest().build().toUriString(); + + assertEquals("http://localhost/mvc-showcase/data/param?foo=123", result); + } + finally { + RequestContextHolder.resetRequestAttributes(); + } + } + +}