smiley

阅读: 评论:0

smiley

smiley

如题;

使用smiley-http-proxy-servlet 主要是方便在项目内部直接进行代理,省的在搞nginx;这样稳定性又会搞一些;OK,项目已经升级到springboot3了,由于springboot3使用的servlet的包名更换了,也就是jakarta开头的,之前是javax开头,因此目前代理服务不支持jakarta,需要升级才行;我到官网看了,他们还在讨论升级问题,维护中有计划升级,至于什么时候,不晓得了;我这边就看了下源码,比较简单就改了下,,直接把源码调整下即可,其实这个项目就一个文件,哈哈,比较简单,直接拷贝调整即可;

官网已经升级了哈,直接采用最新版本即可

<dependency><groupId>org.mitre.dsmiley.httpproxy</groupId><artifactId>smiley-http-proxy-servlet</artifactId><version>2.0</version>
</dependency>

代码如下,把之前的依赖,也就是

<dependency>

<groupId>org.mitre.dsmiley.httpproxy</groupId>

<artifactId>smiley-http-proxy-servlet</artifactId>

<version>1.12.1</version>

</dependency>

注释掉,然后创建ProxyServlet 这个类,把下面代码拷贝进去,调整项目类路径,采用自定义的此类即可


import jakarta.servlet.ServletException;
import jakarta.servlet.http.Cookie;
import jakarta.servlet.http.HttpServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.SneakyThrows;
import org.apache.http.*;
import org.apache.http.client.HttpClient;
import org.apache.fig.CookieSpecs;
import org.apache.fig.RequestConfig;
import org.apache.hods.AbortableHttpRequest;
import org.apache.http.client.utils.URIUtils;
import org.fig.SocketConfig;
import org.ity.InputStreamEntity;
import org.apache.http.impl.client.HttpClientBuilder;
import org.ssage.BasicHeader;
import org.ssage.BasicHttpEntityEnclosingRequest;
import org.ssage.BasicHttpRequest;
import org.ssage.HeaderGroup;
import org.apache.http.util.EntityUtils;import java.io.Closeable;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.HttpCookie;
import java.URI;
import java.util.BitSet;
import java.util.Enumeration;
import java.util.Formatter;@SuppressWarnings({"deprecation", "serial", "WeakerAccess"})
public class ProxyServlet extends HttpServlet {/* INIT PARAMETER NAME CONSTANTS *//** A boolean parameter name to enable logging of input and target URLs to the servlet log. */public static final String P_LOG = "log";/** A boolean parameter name to enable forwarding of the client IP  */public static final String P_FORWARDEDFOR = "forwardip";/** A boolean parameter name to keep HOST parameter as-is  */public static final String P_PRESERVEHOST = "preserveHost";/** A boolean parameter name to keep COOKIES as-is  */public static final String P_PRESERVECOOKIES = "preserveCookies";/** A boolean parameter name to keep COOKIE path as-is  */public static final String P_PRESERVECOOKIEPATH = "preserveCookiePath";/** A boolean parameter name to have auto-handle redirects */public static final String P_HANDLEREDIRECTS = "http.protocol.handle-redirects"; // ClientPNames.HANDLE_REDIRECTS/** An integer parameter name to set the socket connection timeout (millis) */public static final String P_CONNECTTIMEOUT = "http.socket.timeout"; // CoreConnectionPNames.SO_TIMEOUT/** An integer parameter name to set the socket read timeout (millis) */public static final String P_READTIMEOUT = &#ad.timeout";/** An integer parameter name to set the connection request timeout (millis) */public static final String P_CONNECTIONREQUESTTIMEOUT = &#tionrequest.timeout";/** An integer parameter name to set max connection number */public static final String P_MAXCONNECTIONS = "http.maxConnections";/** A boolean parameter whether to use JVM-defined system properties to configure various networking aspects. */public static final String P_USESYSTEMPROPERTIES = "useSystemProperties";/** A boolean parameter to enable handling of compression in the servlet. If it is false, compressed streams are passed through unmodified. */public static final String P_HANDLECOMPRESSION = "handleCompression";/** The parameter name for the target (destination) URI to proxy to. */public static final String P_TARGET_URI = "targetUri";protected static final String ATTR_TARGET_URI =SimpleName() + ".targetUri";protected static final String ATTR_TARGET_HOST =SimpleName() + ".targetHost";/* MISC */protected boolean doLog = false;protected boolean doForwardIP = true;/** User agents shouldn't send the url fragment but what if it does? */protected boolean doSendUrlFragment = true;protected boolean doPreserveHost = false;protected boolean doPreserveCookies = false;protected boolean doPreserveCookiePath = false;protected boolean doHandleRedirects = false;protected boolean useSystemProperties = true;protected boolean doHandleCompression = false;protected int connectTimeout = -1;protected int readTimeout = -1;protected int connectionRequestTimeout = -1;protected int maxConnections = -1;//These next 3 are cached here, and should only be referred to in initialization logic. See the// ATTR_* parameters./** From the configured parameter "targetUri". */protected String targetUri;protected URI targetUriObj;//new URI(targetUri)protected HttpHost targetHost;//actHost(targetUriObj);private HttpClient proxyClient;@Overridepublic String getServletInfo() {return "A proxy servlet by David Smiley, dsmiley@apache";}protected String getTargetUri(HttpServletRequest servletRequest) {return (String) Attribute(ATTR_TARGET_URI);}protected HttpHost getTargetHost(HttpServletRequest servletRequest) {return (HttpHost) Attribute(ATTR_TARGET_HOST);}/*** Reads a configuration parameter. By default it reads servlet init parameters but* it can be overridden.*/protected String getConfigParam(String key) {return getServletConfig().getInitParameter(key);}@SneakyThrows@Overridepublic void init() {String doLogStr = getConfigParam(P_LOG);if (doLogStr != null) {this.doLog = Boolean.parseBoolean(doLogStr);}String doForwardIPString = getConfigParam(P_FORWARDEDFOR);if (doForwardIPString != null) {this.doForwardIP = Boolean.parseBoolean(doForwardIPString);}String preserveHostString = getConfigParam(P_PRESERVEHOST);if (preserveHostString != null) {this.doPreserveHost = Boolean.parseBoolean(preserveHostString);}String preserveCookiesString = getConfigParam(P_PRESERVECOOKIES);if (preserveCookiesString != null) {this.doPreserveCookies = Boolean.parseBoolean(preserveCookiesString);}String preserveCookiePathString = getConfigParam(P_PRESERVECOOKIEPATH);if (preserveCookiePathString != null) {this.doPreserveCookiePath = Boolean.parseBoolean(preserveCookiePathString);}String handleRedirectsString = getConfigParam(P_HANDLEREDIRECTS);if (handleRedirectsString != null) {this.doHandleRedirects = Boolean.parseBoolean(handleRedirectsString);}String connectTimeoutString = getConfigParam(P_CONNECTTIMEOUT);if (connectTimeoutString != null) {tTimeout = Integer.parseInt(connectTimeoutString);}String readTimeoutString = getConfigParam(P_READTIMEOUT);if (readTimeoutString != null) {adTimeout = Integer.parseInt(readTimeoutString);}String connectionRequestTimeout = getConfigParam(P_CONNECTIONREQUESTTIMEOUT);if (connectionRequestTimeout != null) {tionRequestTimeout = Integer.parseInt(connectionRequestTimeout);}String maxConnections = getConfigParam(P_MAXCONNECTIONS);if (maxConnections != null) {this.maxConnections = Integer.parseInt(maxConnections);}String useSystemPropertiesString = getConfigParam(P_USESYSTEMPROPERTIES);if (useSystemPropertiesString != null) {this.useSystemProperties = Boolean.parseBoolean(useSystemPropertiesString);}String doHandleCompression = getConfigParam(P_HANDLECOMPRESSION);if (doHandleCompression != null) {this.doHandleCompression = Boolean.parseBoolean(doHandleCompression);}initTarget();//sets target*proxyClient = createHttpClient();}/*** Sub-classes can override specific behaviour of {@link org.apache.fig.RequestConfig}.*/protected RequestConfig buildRequestConfig() {return RequestConfig.custom().setRedirectsEnabled(doHandleRedirects).setCookieSpec(CookieSpecs.IGNORE_COOKIES) // we handle them in the servlet instead.setConnectTimeout(connectTimeout).setSocketTimeout(readTimeout).setConnectionRequestTimeout(connectionRequestTimeout).build();}/*** Sub-classes can override specific behaviour of {@link org.fig.SocketConfig}.*/protected SocketConfig buildSocketConfig() {if (readTimeout < 1) {return null;}return SocketConfig.custom().setSoTimeout(readTimeout).build();}protected void initTarget() throws ServletException {targetUri = getConfigParam(P_TARGET_URI);if (targetUri == null) {throw new ServletException(P_TARGET_URI+" is required.");}//test it's validtry {targetUriObj = new URI(targetUri);} catch (Exception e) {throw new ServletException("Trying to process targetUri init parameter: "+e,e);}targetHost = actHost(targetUriObj);}/*** Called from {@link #(javax.servlet.ServletConfig)}.* HttpClient offers many opportunities for customization.* In any case, it should be thread-safe.*/protected HttpClient createHttpClient() {HttpClientBuilder clientBuilder = getHttpClientBuilder().setDefaultRequestConfig(buildRequestConfig()).setDefaultSocketConfig(buildSocketConfig());clientBuilder.setMaxConnTotal(maxConnections);clientBuilder.setMaxConnPerRoute(maxConnections);if(! doHandleCompression) {clientBuilder.disableContentCompression();}if (useSystemProperties) {clientBuilder = clientBuilder.useSystemProperties();}return buildHttpClient(clientBuilder);}/*** Creates a HttpClient from the given builder. Meant as postprocessor* to possibly adapt the client builder prior to creating the* HttpClient.** @param clientBuilder pre-configured client builder* @return HttpClient*/protected HttpClient buildHttpClient(HttpClientBuilder clientBuilder) {return clientBuilder.build();}/*** Creates a {@code HttpClientBuilder}. Meant as preprocessor to possibly* adapt the client builder prior to any configuration got applied.** @return HttpClient builder*/protected HttpClientBuilder getHttpClientBuilder() {ate();}/*** The http client used.* @see #createHttpClient()*/protected HttpClient getProxyClient() {return proxyClient;}@Overridepublic void destroy() {//Usually, clients implement Closeable:if (proxyClient instanceof Closeable) {try {((Closeable) proxyClient).close();} catch (IOException e) {log("While destroying servlet, shutting down HttpClient: "+e, e);}} else {//Older releases require we do this:if (proxyClient != null) {ConnectionManager().shutdown();}}super.destroy();}@SneakyThrows@Overrideprotected void service(HttpServletRequest servletRequest, HttpServletResponse servletResponse)throws IOException {//initialize request attributes from caches if unset by a subclass by this pointif (Attribute(ATTR_TARGET_URI) == null) {servletRequest.setAttribute(ATTR_TARGET_URI, targetUri);}if (Attribute(ATTR_TARGET_HOST) == null) {servletRequest.setAttribute(ATTR_TARGET_HOST, targetHost);}// Make the Request//note: we won't transfer the protocol version because I'm not sure it would truly be compatibleString method = Method();String proxyRequestUri = rewriteUrlFromRequest(servletRequest);HttpRequest proxyRequest;//spec: RFC 2616, sec 4.3: either of these two headers signal that there is a message body.if (Header(HttpHeaders.CONTENT_LENGTH) != null ||Header(HttpHeaders.TRANSFER_ENCODING) != null) {proxyRequest = newProxyRequestWithEntity(method, proxyRequestUri, servletRequest);} else {proxyRequest = new BasicHttpRequest(method, proxyRequestUri);}copyRequestHeaders(servletRequest, proxyRequest);setXForwardedForHeader(servletRequest, proxyRequest);HttpResponse proxyResponse = null;try {// Execute the requestproxyResponse = doExecute(servletRequest, servletResponse, proxyRequest);// Process the response:// Pass the response code. This method with the "reason phrase" is deprecated but it's the//   only way to pass the reason along too.int statusCode = StatusLine().getStatusCode();//noinspection deprecationservletResponse.setStatus(statusCode);// Copying response headers to make sure SESSIONID or other Cookie which comes from the remote// server will be saved in client when the proxied url was redirected to another one.// See issue [#51]()copyResponseHeaders(proxyResponse, servletRequest, servletResponse);if (statusCode == HttpServletResponse.SC_NOT_MODIFIED) {// 304 needs special handling.  See:// .html#Code304// Don't send body entity/content!servletResponse.setIntHeader(HttpHeaders.CONTENT_LENGTH, 0);} else {// Send the content to the clientcopyResponseEntity(proxyResponse, servletResponse, proxyRequest, servletRequest);}} catch (Exception e) {handleRequestException(proxyRequest, proxyResponse, e);} finally {// make sure the entire entity was consumed, so the connection is releasedif (proxyResponse != null) {Entity());}//Note: Don't need to close servlet outputStream:// }}protected void handleRequestException(HttpRequest proxyRequest, HttpResponse proxyResonse, Exception e) throws ServletException, IOException {//abort request, according to best practice with HttpClientif (proxyRequest instanceof AbortableHttpRequest) {AbortableHttpRequest abortableHttpRequest = (AbortableHttpRequest) proxyRequest;abortableHttpRequest.abort();}// If the response is a chunked response, it is read to completion when// #close is called. If the sending site does not timeout or keeps sending,// the connection will be kept open indefinitely. Closing the respone// object terminates the stream.if (proxyResonse instanceof Closeable) {((Closeable) proxyResonse).close();}if (e instanceof RuntimeException) {throw (RuntimeException)e;}if (e instanceof ServletException) {throw (ServletException)e;}//noinspection ConstantConditionsif (e instanceof IOException) {throw (IOException) e;}throw new RuntimeException(e);}protected HttpResponse doExecute(HttpServletRequest servletRequest, HttpServletResponse servletResponse,HttpRequest proxyRequest) throws IOException {if (doLog) {log("proxy " + Method() + " uri: " + RequestURI() + " -- " &#RequestLine().getUri());}ute(getTargetHost(servletRequest), proxyRequest);}protected HttpRequest newProxyRequestWithEntity(String method, String proxyRequestUri,HttpServletRequest servletRequest)throws IOException {HttpEntityEnclosingRequest eProxyRequest =new BasicHttpEntityEnclosingRequest(method, proxyRequestUri);// Add the input entity (streamed)//  note: we don't bother ensuring we close the servletInputStream since the container handles iteProxyRequest.setEntity(new InputStream(), getContentLength(servletRequest)));return eProxyRequest;}// Get the header value as a long in order to more correctly proxy very large requestsprivate long getContentLength(HttpServletRequest request) {String contentLengthHeader = Header("Content-Length");if (contentLengthHeader != null) {return Long.parseLong(contentLengthHeader);}return -1L;}protected void closeQuietly(Closeable closeable) {try {closeable.close();} catch (IOException e) {Message(), e);}}/** These are the "hop-by-hop" headers that should not be copied.* .html* I use an HttpClient HeaderGroup class instead of Set&lt;String&gt; because this* approach does case insensitive lookup faster.*/protected static final HeaderGroup hopByHopHeaders;static {hopByHopHeaders = new HeaderGroup();String[] headers = new String[] {"Connection", "Keep-Alive", "Proxy-Authenticate", "Proxy-Authorization","TE", "Trailers", "Transfer-Encoding", "Upgrade" };for (String header : headers) {hopByHopHeaders.addHeader(new BasicHeader(header, null));}}/*** Copy request headers from the servlet client to the proxy request.* This is easily overridden to add your own.*/protected void copyRequestHeaders(HttpServletRequest servletRequest, HttpRequest proxyRequest) {// Get an Enumeration of all of the header names sent by the client@SuppressWarnings("unchecked")Enumeration<String> enumerationOfHeaderNames = HeaderNames();while (enumerationOfHeaderNames.hasMoreElements()) {String headerName = Element();copyRequestHeader(servletRequest, proxyRequest, headerName);}}/*** Copy a request header from the servlet client to the proxy request.* This is easily overridden to filter out certain headers if desired.*/protected void copyRequestHeader(HttpServletRequest servletRequest, HttpRequest proxyRequest,String headerName) {//Instead the content-length is effectively set via InputStreamEntityif (headerName.equalsIgnoreCase(HttpHeaders.CONTENT_LENGTH)) {return;}if (ainsHeader(headerName)) {return;}// If compression is handled in the servlet, apache http client needs to// control the Accept-Encoding header, not the clientif (doHandleCompression && headerName.equalsIgnoreCase(HttpHeaders.ACCEPT_ENCODING)) {return;}@SuppressWarnings("unchecked")Enumeration<String> headers = Headers(headerName);while (headers.hasMoreElements()) {//sometimes more than one valueString headerValue = Element();// In case the proxy host is running multiple virtual servers,// rewrite the Host header to ensure that we get content from// the correct virtual serverif (!doPreserveHost && headerName.equalsIgnoreCase(HttpHeaders.HOST)) {HttpHost host = getTargetHost(servletRequest);headerValue = HostName();if (Port() != -1) {headerValue += ":"&#Port();}} else if (!doPreserveCookies && headerName.equalsIgnoreCase(org.kie.SM.COOKIE)) {headerValue = getRealCookie(headerValue);}proxyRequest.addHeader(headerName, headerValue);}}private void setXForwardedForHeader(HttpServletRequest servletRequest,HttpRequest proxyRequest) {if (doForwardIP) {String forHeaderName = "X-Forwarded-For";String forHeader = RemoteAddr();String existingForHeader = Header(forHeaderName);if (existingForHeader != null) {forHeader = existingForHeader + ", " + forHeader;}proxyRequest.setHeader(forHeaderName, forHeader);String protoHeaderName = "X-Forwarded-Proto";String protoHeader = Scheme();proxyRequest.setHeader(protoHeaderName, protoHeader);}}/** Copy proxied response headers back to the servlet client. */protected void copyResponseHeaders(HttpResponse proxyResponse, HttpServletRequest servletRequest,HttpServletResponse servletResponse) {for (Header header : AllHeaders()) {copyResponseHeader(servletRequest, servletResponse, header);}}/** Copy a proxied response header back to the servlet client.* This is easily overwritten to filter out certain headers if desired.*/protected void copyResponseHeader(HttpServletRequest servletRequest,HttpServletResponse servletResponse, Header header) {String headerName = Name();if (ainsHeader(headerName)) {return;}String headerValue = Value();if (headerName.equalsIgnoreCase(org.kie.SM.SET_COOKIE) ||headerName.equalsIgnoreCase(org.kie.SM.SET_COOKIE2)) {copyProxyCookie(servletRequest, servletResponse, headerValue);} else if (headerName.equalsIgnoreCase(HttpHeaders.LOCATION)) {// LOCATION Header may have to be rewritten.servletResponse.addHeader(headerName, rewriteUrlFromResponse(servletRequest, headerValue));} else {servletResponse.addHeader(headerName, headerValue);}}/*** Copy cookie from the proxy to the servlet client.* Replaces cookie path to local path and renames cookie to avoid collisions.*/protected void copyProxyCookie(HttpServletRequest servletRequest,HttpServletResponse servletResponse, String headerValue) {for (HttpCookie cookie : HttpCookie.parse(headerValue)) {Cookie servletCookie = createProxyCookie(servletRequest, cookie);servletResponse.addCookie(servletCookie);}}/*** Creates a proxy cookie from the original cookie.** @param servletRequest original request* @param cookie original cookie* @return proxy cookie*/protected Cookie createProxyCookie(HttpServletRequest servletRequest, HttpCookie cookie) {String proxyCookieName = getProxyCookieName(cookie);Cookie servletCookie = new Cookie(proxyCookieName, Value());servletCookie.setPath(this.doPreserveCookiePath ?Path() : // preserve original cookie pathbuildProxyCookiePath(servletRequest) //set to the path of the proxy servlet);// servletCookie.Comment());servletCookie.setMaxAge((int) MaxAge());// don't set cookie domainservletCookie.setSecure(servletRequest.isSecure() && Secure());// servletCookie.Version());servletCookie.setHttpOnly(cookie.isHttpOnly());return servletCookie;}/*** Set cookie name prefixed with a proxy value so it won't collide with other cookies.** @param cookie cookie to get proxy cookie name for* @return non-conflicting proxy cookie name*/protected String getProxyCookieName(HttpCookie cookie) {//return doPreserveCookies ? Name() : Name()) + Name();}/*** Create path for proxy cookie.** @param servletRequest original request* @return proxy cookie path*/protected String buildProxyCookiePath(HttpServletRequest servletRequest) {String path = ContextPath(); // path starts with / or is empty stringpath += ServletPath(); // servlet path starts with / or is empty stringif (path.isEmpty()) {path = "/";}return path;}/*** Take any client cookies that were originally from the proxy and prepare them to send to the* proxy.  This relies on cookie headers being set correctly according to RFC 6265 Sec 5.4.* This also blocks any local cookies from being sent to the proxy.*/protected String getRealCookie(String cookieValue) {StringBuilder escapedCookie = new StringBuilder();String cookies[] = cookieValue.split("[;,]");for (String cookie : cookies) {String cookieSplit[] = cookie.split("=");if (cookieSplit.length == 2) {String cookieName = cookieSplit[0].trim();if (cookieName.startsWith(getCookieNamePrefix(cookieName))) {cookieName = cookieName.substring(getCookieNamePrefix(cookieName).length());if (escapedCookie.length() > 0) {escapedCookie.append("; ");}escapedCookie.append(cookieName).append("=").append(cookieSplit[1].trim());}}}String();}/** The string prefixing rewritten cookies. */protected String getCookieNamePrefix(String name) {return "!Proxy!" + getServletConfig().getServletName();}/** Copy response body data (the entity) from the proxy to the servlet client. */protected void copyResponseEntity(HttpResponse proxyResponse, HttpServletResponse servletResponse,HttpRequest proxyRequest, HttpServletRequest servletRequest)throws IOException {HttpEntity entity = Entity();if (entity != null) {if (entity.isChunked()) {// Flush intermediate results before blocking on input -- needed for SSEInputStream is = Content();OutputStream os = OutputStream();byte[] buffer = new byte[10 * 1024];int read;while ((read = is.read(buffer)) != -1) {os.write(buffer, 0, read);/*-* Issue in Apache http client/JDK: if the stream from client is* compressed, apache http client will delegate to GzipInputStream.* The #available implementation of InflaterInputStream (parent of* GzipInputStream) return 1 until EOF is reached. This is not* consistent with InputStream#available, which defines:**   A single read or skip of this many bytes will not block,*   but may read or skip fewer bytes.**  To work around this, a flush is issued always if compression*  is handled by apache http client*/if (doHandleCompression || is.available() == 0 /* ad will block */) {os.flush();}}// Entity closing/cleanup is done in the caller (#service)} else {OutputStream servletOutputStream = OutputStream();entity.writeTo(servletOutputStream);}}}/*** Reads the request URI from {@code servletRequest} and rewrites it, considering targetUri.* It's used to make the new request.*/protected String rewriteUrlFromRequest(HttpServletRequest servletRequest) {StringBuilder uri = new StringBuilder(500);uri.append(getTargetUri(servletRequest));// Handle the path given to the servletString pathInfo = rewritePathInfoFromRequest(servletRequest);if (pathInfo != null) {//ex: /my/path.html// getPathInfo() returns decoded string, so we need encodeUriQuery to encode "%" charactersuri.append(encodeUriQuery(pathInfo, true));}// Handle the query string & fragmentString queryString = QueryString();//ex:(following '?'): name=value&foo=bar#fragmentString fragment = null;//split off fragment from queryString, updating queryString if foundif (queryString != null) {int fragIdx = queryString.indexOf('#');if (fragIdx >= 0) {fragment = queryString.substring(fragIdx + 1);queryString = queryString.substring(0,fragIdx);}}queryString = rewriteQueryStringFromRequest(servletRequest, queryString);if (queryString != null && queryString.length() > 0) {uri.append('?');// queryString is not decoded, so we need encodeUriQuery not to encode "%" characters, to avoid double-encodinguri.append(encodeUriQuery(queryString, false));}if (doSendUrlFragment && fragment != null) {uri.append('#');// fragment is not decoded, so we need encodeUriQuery not to encode "%" characters, to avoid double-encodinguri.append(encodeUriQuery(fragment, false));}String();}protected String rewriteQueryStringFromRequest(HttpServletRequest servletRequest, String queryString) {return queryString;}/*** Allow overrides of {@link javax.servlet.http.HttpServletRequest#getPathInfo()}.* Useful when url-pattern of servlet-mapping (l) requires manipulation.*/protected String rewritePathInfoFromRequest(HttpServletRequest servletRequest) {PathInfo();}/*** For a redirect response from the target server, this translates {@code theUrl} to redirect to* and translates it to one the original client can use.*/protected String rewriteUrlFromResponse(HttpServletRequest servletRequest, String theUrl) {//TODO document example pathsfinal String targetUri = getTargetUri(servletRequest);if (theUrl.startsWith(targetUri)) {/*-* The URL points back to the back-end server.* Instead of returning it verbatim we replace the target path with our* source path in a way that should instruct the original client to* request the URL pointed through this Proxy.* We do this by taking the current request and rewriting the path part* using this servlet's absolute path and the path from the returned URL* after the base target URL.*/StringBuffer curUrl = RequestURL();//no queryint pos;// Skip the protocol partif ((pos = curUrl.indexOf("://"))>=0) {// Skip the authority part// + 3 to skip the separator between protocol and authorityif ((pos = curUrl.indexOf("/", pos + 3)) >=0) {// Trim everything after the authority part.curUrl.setLength(pos);}}// Context path starts with a / if it is not blankcurUrl.ContextPath());// Servlet path starts with a / if it is not blankcurUrl.ServletPath());curUrl.append(theUrl, targetUri.length(), theUrl.length());String();}return theUrl;}/** The target URI as configured. Not null. */public String getTargetUri() { return targetUri; }/*** Encodes characters in the query or fragment part of the URI.** <p>Unfortunately, an incoming URI sometimes has characters disallowed by the spec.  HttpClient* insists that the outgoing proxied request has a valid URI because it uses Java's {@link URI}.* To be more forgiving, we must escape the problematic characters.  See the URI class for the* spec.** @param in example: name=value&amp;foo=bar#fragment* @param encodePercent determine whether percent characters need to be encoded*/protected CharSequence encodeUriQuery(CharSequence in, boolean encodePercent) {//Note that I can't simply use URI.java to encode because it will escape pre-existing escaped things.StringBuilder outBuf = null;Formatter formatter = null;for(int i = 0; i < in.length(); i++) {char c = in.charAt(i);boolean escape = true;if (c < 128) {if ((c) && !(encodePercent && c == '%')) {escape = false;}} else if (!Character.isISOControl(c) && !Character.isSpaceChar(c)) {//not-asciiescape = false;}if (!escape) {if (outBuf != null) {outBuf.append(c);}} else {//escapeif (outBuf == null) {outBuf = new StringBuilder(in.length() + 5*3);outBuf.append(in,0,i);formatter = new Formatter(outBuf);}//leading %, 0 padded, width 2, capital hexformatter.format("%%%02X",(int)c);//TODO}}return outBuf != null ? outBuf : in;}protected static final BitSet asciiQueryChars;static {char[] c_unreserved = "_-!.~'()*".toCharArray();//plus alphanumchar[] c_punct = ",;:$&+=".toCharArray();char[] c_reserved = "/@".toCharArray();//plus punct.  Exclude '?'; RFC-2616 3.2.2. Exclude '[', ']'; .txt, unsafe charactersasciiQueryChars = new BitSet(128);for(char c = 'a'; c <= 'z'; c++) {asciiQueryChars.set(c);}for(char c = 'A'; c <= 'Z'; c++) {asciiQueryChars.set(c);}for(char c = '0'; c <= '9'; c++) {asciiQueryChars.set(c);}for(char c : c_unreserved) {asciiQueryChars.set(c);}for(char c : c_punct) {asciiQueryChars.set(c);}for(char c : c_reserved) {asciiQueryChars.set(c);}asciiQueryChars.set('%');//leave existing percent escapes in place}}

本文发布于:2024-02-01 09:31:07,感谢您对本站的认可!

本文链接:https://www.4u4v.net/it/170675106935684.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

下一篇:EBU6304
标签:smiley
留言与评论(共有 0 条评论)
   
验证码:

Copyright ©2019-2022 Comsenz Inc.Powered by ©

网站地图1 网站地图2 网站地图3 网站地图4 网站地图5 网站地图6 网站地图7 网站地图8 网站地图9 网站地图10 网站地图11 网站地图12 网站地图13 网站地图14 网站地图15 网站地图16 网站地图17 网站地图18 网站地图19 网站地图20 网站地图21 网站地图22/a> 网站地图23