1   //========================================================================
2   //Copyright 2006 Mort Bay Consulting Pty. Ltd.
3   //------------------------------------------------------------------------
4   //Licensed under the Apache License, Version 2.0 (the "License");
5   //you may not use this file except in compliance with the License.
6   //You may obtain a copy of the License at 
7   //http://www.apache.org/licenses/LICENSE-2.0
8   //Unless required by applicable law or agreed to in writing, software
9   //distributed under the License is distributed on an "AS IS" BASIS,
10  //WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11  //See the License for the specific language governing permissions and
12  //limitations under the License.
13  //========================================================================
14  
15  package org.mortbay.jetty.handler;
16  
17  import java.io.IOException;
18  
19  import javax.servlet.ServletException;
20  import javax.servlet.http.HttpServletRequest;
21  import javax.servlet.http.HttpServletResponse;
22  
23  import org.mortbay.jetty.HandlerContainer;
24  import org.mortbay.jetty.HttpConnection;
25  import org.mortbay.jetty.HttpHeaders;
26  import org.mortbay.jetty.Request;
27  import org.mortbay.util.URIUtil;
28  
29  /* ------------------------------------------------------------ */
30  /** Moved ContextHandler.
31   * This context can be used to replace a context that has changed
32   * location.  Requests are redirected (either to a fixed URL or to a
33   * new context base). 
34   */
35  public class MovedContextHandler extends ContextHandler
36  {
37      String _newContextURL;
38      boolean _discardPathInfo;
39      boolean _discardQuery;
40      boolean _permanent;
41      Redirector _redirector;
42      String _expires;
43  
44      public MovedContextHandler()
45      {
46          _redirector=new Redirector();
47          addHandler(_redirector);
48          setAllowNullPathInfo(true);
49      }
50      
51      public MovedContextHandler(HandlerContainer parent, String contextPath, String newContextURL)
52      {
53          super(parent,contextPath);
54          _newContextURL=newContextURL;
55          _redirector=new Redirector();
56          addHandler(_redirector);
57      }
58  
59      public boolean isDiscardPathInfo()
60      {
61          return _discardPathInfo;
62      }
63  
64      public void setDiscardPathInfo(boolean discardPathInfo)
65      {
66          _discardPathInfo = discardPathInfo;
67      }
68  
69      public String getNewContextURL()
70      {
71          return _newContextURL;
72      }
73  
74      public void setNewContextURL(String newContextURL)
75      {
76          _newContextURL = newContextURL;
77      }
78  
79      public boolean isPermanent()
80      {
81          return _permanent;
82      }
83  
84      public void setPermanent(boolean permanent)
85      {
86          _permanent = permanent;
87      }
88  
89      public boolean isDiscardQuery()
90      {
91          return _discardQuery;
92      }
93  
94      public void setDiscardQuery(boolean discardQuery)
95      {
96          _discardQuery = discardQuery;
97      }
98      
99      private class Redirector extends AbstractHandler
100     {
101         public void handle(String target, HttpServletRequest request, HttpServletResponse response, int dispatch) throws IOException, ServletException
102         {
103             if (_newContextURL==null)
104                 return;
105             
106             Request base_request=(request instanceof Request)?(Request)request:HttpConnection.getCurrentConnection().getRequest();
107             
108             String url = _newContextURL;
109             if (!_discardPathInfo && request.getPathInfo()!=null)
110                 url=URIUtil.addPaths(url, request.getPathInfo());
111             if (!_discardQuery && request.getQueryString()!=null)
112                 url+="?"+request.getQueryString();
113             
114             response.sendRedirect(url);
115 
116             String path=_newContextURL;
117             if (!_discardPathInfo && request.getPathInfo()!=null)
118                 path=URIUtil.addPaths(path, request.getPathInfo());
119             
120             StringBuilder location = URIUtil.hasScheme(path)?new StringBuilder():base_request.getRootURL();
121 
122             location.append(path);
123             if (!_discardQuery && request.getQueryString()!=null)
124             {
125                 location.append('?');
126                 location.append(request.getQueryString());
127             }
128             
129             response.setHeader(HttpHeaders.LOCATION,location.toString());
130 
131             if (_expires!=null)
132                 response.setHeader(HttpHeaders.EXPIRES,_expires);
133             
134             response.setStatus(_permanent?HttpServletResponse.SC_MOVED_PERMANENTLY:HttpServletResponse.SC_FOUND);
135             response.setContentLength(0);
136             base_request.setHandled(true);
137         }
138         
139     }
140 
141     /* ------------------------------------------------------------ */
142     /**
143      * @return the expires header value or null if no expires header
144      */
145     public String getExpires()
146     {
147         return _expires;
148     }
149 
150     /* ------------------------------------------------------------ */
151     /**
152      * @param expires the expires header value or null if no expires header
153      */
154     public void setExpires(String expires)
155     {
156         _expires = expires;
157     }
158 
159 }