001: // MirrorFrame.java
002: // $Id: MirrorFrame.java,v 1.13 2004/02/12 10:49:20 ylafon Exp $
003: // (c) COPYRIGHT MIT and INRIA, 1998
004: // Please first read the full copyright statement in file COPYRIGHT.html
005:
006: package org.w3c.jigsaw.proxy;
007:
008: import java.net.URL;
009:
010: import java.io.IOException;
011:
012: import org.w3c.www.http.HTTP;
013:
014: import org.w3c.tools.resources.Attribute;
015: import org.w3c.tools.resources.AttributeHolder;
016: import org.w3c.tools.resources.AttributeRegistry;
017: import org.w3c.tools.resources.BooleanAttribute;
018: import org.w3c.tools.resources.LookupResult;
019: import org.w3c.tools.resources.LookupState;
020: import org.w3c.tools.resources.ProtocolException;
021: import org.w3c.tools.resources.Resource;
022: import org.w3c.tools.resources.ResourceFrame;
023: import org.w3c.tools.resources.StringAttribute;
024:
025: import org.w3c.jigsaw.http.HTTPException;
026: import org.w3c.jigsaw.http.Reply;
027: import org.w3c.jigsaw.http.Request;
028:
029: import org.w3c.jigsaw.frames.HTTPFrame;
030:
031: public class MirrorFrame extends ForwardFrame {
032: /**
033: * Attribute index - The site we are mirroring.
034: */
035: protected static int ATTR_MIRRORS = -1;
036: /**
037: * Attribute index - Do we mirror from root or relative
038: */
039: protected static int ATTR_PARTIAL = -1;
040:
041: static {
042: Class c = null;
043: Attribute a = null;
044: try {
045: c = Class.forName("org.w3c.jigsaw.proxy.MirrorFrame");
046: } catch (Exception ex) {
047: ex.printStackTrace();
048: System.exit(1);
049: }
050: // Register the mirrored site attribute:
051: a = new StringAttribute("mirrors", null, Attribute.EDITABLE);
052: ATTR_MIRRORS = AttributeRegistry.registerAttribute(c, a);
053: // Do we allow sub mirroring (aka parts of the site)
054: // and not from root
055: a = new BooleanAttribute("partial", Boolean.FALSE,
056: Attribute.EDITABLE);
057: ATTR_PARTIAL = AttributeRegistry.registerAttribute(c, a);
058: }
059:
060: protected URL mirrors = null;
061: public static final String MIRROR_PATH = "MIRROR_PATH";
062:
063: /**
064: * Get the mirrors site attribute value.
065: * @return The String encoded URL of the site we are mirroring here.
066: */
067:
068: public String getMirrors() {
069: return getString(ATTR_MIRRORS, null);
070: }
071:
072: /**
073: * Get the mirrors site attribute value.
074: * @return The String encoded URL of the site we are mirroring here.
075: */
076:
077: public boolean isPartialMirroring() {
078: return getBoolean(ATTR_PARTIAL, false);
079: }
080:
081: /**
082: * Catch assignment to the mirror attribute, to update our cached URL.
083: * @param idx The slot to set.
084: * @param value It's new value.
085: */
086:
087: public void setValue(int idx, Object value) {
088: super .setValue(idx, value);
089: if (idx == ATTR_MIRRORS) {
090: try {
091: mirrors = new URL(getMirrors());
092: } catch (Exception ex) {
093: mirrors = null;
094: }
095: }
096: }
097:
098: /**
099: * @param request the incomming request
100: * @param rep the client reply
101: * @return A Reply instance
102: * @exception HTTPException if processing the request failed.
103: * @exception IOException if an IO error occurs.
104: */
105: protected Reply dupReply(Request request,
106: org.w3c.www.protocol.http.Reply rep) throws HTTPException,
107: IOException {
108: Reply reply = super .dupReply(request, rep);
109: // Tweak redirections ! Wow this is getting real nifty :-)
110: switch (reply.getStatus()) {
111: case HTTP.MOVED_PERMANENTLY:
112: case HTTP.TEMPORARY_REDIRECT:
113: case HTTP.FOUND:
114: case HTTP.SEE_OTHER:
115: // Have fun !
116: String location = rep.getLocation();
117: if ((mirrors != null) && (location != null)) {
118: try {
119: URL uloc = new URL(request.getURL(), location);
120: URL loc = getURL(request);
121: URL fake = null;
122: if (isPartialMirroring()) {
123: fake = new URL(request.getURL().getProtocol(),
124: loc.getHost(), loc.getPort(),
125: getURLPath() + uloc.getFile());
126: } else if (location.startsWith(mirrors.toString())) {
127: fake = new URL(request.getURL().getProtocol(),
128: loc.getHost(), loc.getPort(), uloc
129: .getFile());
130: } else {
131: fake = uloc;
132: }
133: if (fake != null) {
134: reply.setLocation(fake);
135: }
136: } catch (Exception ex) {
137: }
138: }
139: }
140: return reply;
141: }
142:
143: /**
144: * @param request the incomming request
145: * @return A client Request instance.
146: * @exception HTTPException if processing the request failed.
147: * @exception IOException if an IO error occurs.
148: */
149: protected org.w3c.www.protocol.http.Request dupRequest(
150: Request request) throws HTTPException, IOException {
151: org.w3c.www.protocol.http.Request req = super
152: .dupRequest(request);
153: // Tweak the URL :-)
154: if (isPartialMirroring()) {
155: String requrl = request.getURL().getFile();
156: String respath = getURLPath();
157: if (requrl.startsWith(respath)) {
158: String nurl = requrl.substring(respath.length());
159: req.setURL(new URL(mirrors, nurl));
160: } else {
161: req.setURL(new URL(mirrors, requrl));
162: }
163: } else {
164: req.setURL(new URL(mirrors, request.getURL().getFile()));
165: }
166: return req;
167: }
168:
169: /**
170: * Lookup for a mirrored resource.
171: * @param ls The current lookup state
172: * @param lr The result
173: * @return true if lookup is done.
174: * @exception org.w3c.tools.resources.ProtocolException If an error
175: * relative to the protocol occurs
176: */
177: public boolean lookupOther(LookupState ls, LookupResult lr)
178: throws org.w3c.tools.resources.ProtocolException {
179: // Get the full URL from the request:
180: Request request = (Request) ls.getRequest();
181: URL url = request.getURL();
182:
183: if (ls.isInternal())
184: return super .lookupOther(ls, lr);
185: if (mirrors != null) {
186: request.setProxy(true);
187: lr.setTarget(this .getResource().getResourceReference());
188: return true;
189: }
190: // Emit a not found:
191: Reply error = request.makeReply(HTTP.NOT_FOUND);
192: if (request.getMethod().equals("GET"))
193: error.setContent("Target resource not found.");
194: lr.setTarget(null);
195: lr.setReply(error);
196: return true;
197: }
198:
199: public void initialize(Object values[]) {
200: super .initialize(values);
201: String strmirrors = getMirrors();
202: try {
203: mirrors = new URL(strmirrors);
204: } catch (Exception ex) {
205: mirrors = null;
206: }
207: }
208: }
|