View Javadoc

1   package org.xvsm.lookup.freepastry;
2   
3   import java.net.URI;
4   import java.util.Hashtable;
5   
6   import org.jdom.Element;
7   import org.xvsm.configuration.ConfigurationManager;
8   import org.xvsm.core.AtomicEntry;
9   import org.xvsm.core.Capi;
10  import org.xvsm.core.ContainerRef;
11  import org.xvsm.interfaces.ICapi;
12  import org.xvsm.interfaces.lookup.ILookup;
13  import org.xvsm.internal.exceptions.XCoreException;
14  import org.xvsm.lookup.LookupManager;
15  import org.xvsm.lookup.exceptions.ContainerAlreadyPublishedException;
16  import org.xvsm.lookup.exceptions.ContainerNotPublishedException;
17  import org.xvsm.lookup.exceptions.LookupException;
18  import org.xvsm.remote.TransportHandler;
19  import org.xvsm.remote.freepastry.FreePastryConnection;
20  import org.xvsm.selectors.KeySelector;
21  
22  import rice.p2p.commonapi.Id;
23  import rice.p2p.past.Past;
24  import rice.p2p.past.PastContent;
25  
26  /***
27   * the lookup implementation using the FreePastry-API
28   * 
29   * @author Hannu-Daniel Goiss
30   */
31  public class FreePastryLookup implements ILookup {
32  	private static ICapi capi;
33  	private FreePastryConnection freepastryconnection;
34  
35  	/***
36  	 * Constructor for use with environment variable
37  	 * 
38  	 * @param siteURI
39  	 * @param table
40  	 * @throws LookupException
41  	 */
42  	public FreePastryLookup(URI siteURI, Hashtable<String, String> table) throws LookupException {
43  		String temp;
44  		Hashtable<String, String> env = new Hashtable<String, String>();
45  
46  		try {
47  			capi = new Capi();
48  		}
49  		catch(XCoreException xce) {
50  			throw new LookupException(xce); 
51  		}
52  		
53  		temp = table.get("org.xvsm.lookup.freepastry.FreePastryLookup.RemoteURI");
54  		if(temp != null) {
55  			env.put("RemoteURI", temp);
56  		}
57  		else {
58  			throw new LookupException("RemoteURI has to be specified");
59  		}
60  		temp = table.get("org.xvsm.lookup.freepastry.FreePastryLookup.Port");
61  		if(temp != null) {
62  			env.put("Port", temp);
63  		}
64  		else {
65  			throw new LookupException("Port has to be specified");
66  		}
67  		
68  		freepastryconnection = FreePastryConnection.getInstance(env);
69  	}
70  	
71  	/***
72  	 * constructor for use with XML-file
73  	 * 
74  	 * @param siteURI
75  	 * @param element
76  	 * @throws LookupException
77  	 */
78  	public FreePastryLookup(URI siteURI, Element element) throws LookupException {
79  		Hashtable<String, String> env = new Hashtable<String, String>();
80  
81  		try {
82  			capi = new Capi();
83  		}
84  		catch(XCoreException xce) {
85  			throw new LookupException(xce); 
86  		}
87  		
88  		try {
89  			env.put("RemoteURI", element.getChild("RemoteURI").getTextTrim());
90  		}
91  		catch(NullPointerException npe) {
92  			throw new LookupException("RemoteURI has to be specified");
93  		}
94  		try {
95  			env.put("Port", element.getChild("Port").getTextTrim());
96  		}
97  		catch(NullPointerException npe) {
98  			throw new LookupException("Port has to be specified");
99  		}
100 
101 		freepastryconnection = FreePastryConnection.getInstance(env);
102 	}
103 
104 	/* (non-Javadoc)
105 	 * @see org.xvsm.interfaces.lookup.ILookup#lookup(java.lang.String)
106 	 */
107 	public ContainerRef[] lookup(String name)
108 			throws ContainerNotPublishedException, LookupException {
109 
110 		try {
111 			FreePastryConnection conn = FreePastryConnection.getInstance();
112 			Past past = conn.getPast();
113 			LookupContinuation continuation = new LookupContinuation();
114 			
115 			String publishedId = name;
116 			
117 			Id lookupKey = conn.getPastryIdFactory().buildId(publishedId);
118 		      
119 			past.lookup(lookupKey, continuation);
120 
121 			while(continuation.isFinished() == false) {
122 				try {
123 					Thread.sleep(20);
124 				}
125 				catch(Exception e) {
126 					
127 				}
128 			}
129 			if(continuation.getException() != null) {
130 				throw new LookupException(continuation.getException());
131 			}
132 
133 			ContainerRef[] containerArray = new ContainerRef[1];
134 			containerArray[0] = continuation.getCref();
135 			
136 			return containerArray;
137 		}
138 		catch(XCoreException xce) {
139 			throw new LookupException(xce);
140 		}
141 	}
142 
143 	/* (non-Javadoc)
144 	 * @see org.xvsm.interfaces.lookup.ILookup#lookup(java.util.Hashtable)
145 	 */
146 	public ContainerRef[] lookup(Hashtable list)
147 			throws ContainerNotPublishedException, LookupException {
148 		throw new LookupException("This feature is not available for FreePastry!");
149 	}
150 
151 	/* (non-Javadoc)
152 	 * @see org.xvsm.interfaces.lookup.ILookup#lookup(java.lang.String, java.util.Hashtable)
153 	 */
154 	public ContainerRef[] lookup(String name, Hashtable list)
155 			throws ContainerNotPublishedException, LookupException {
156 		throw new LookupException("This feature is not available for FreePastry!");
157 	}
158 
159 	/* (non-Javadoc)
160 	 * @see org.xvsm.interfaces.lookup.ILookup#publish(org.xvsm.core.ContainerRef)
161 	 */
162 	public void publish(ContainerRef pCref)
163 			throws ContainerAlreadyPublishedException, LookupException {
164 		ContainerRef cref = pCref;
165 		
166 		try {
167 //			cref.setSite(TransportManagerInstance.getInstance().getDefaultListener().getUri());
168 			cref.setSite(TransportHandler.getInstance().getListener(
169 					ConfigurationManager.getInstance().getStringSetting(
170 							"DefaultAnswerToProtocol")).getUri());
171 			
172 			FreePastryConnection conn = FreePastryConnection.getInstance();
173 			Past past = conn.getPast();
174 			PublishContinuation continuation = new PublishContinuation();
175 			
176 			String publishedId = this.getContainerName(cref);
177 			String publishedContent = cref.asURI().toString();			
178 			
179 			PastContent myContent = new FPPastContent(conn.getPastryIdFactory().buildId(publishedId), publishedContent);
180 
181 			past.insert(myContent, continuation);
182 			
183 			while(continuation.isFinished() == false) {
184 				try {
185 					Thread.sleep(100);
186 				}
187 				catch(Exception e) {
188 					
189 				}
190 			}
191 			if(continuation.getException() != null) {
192 				throw new LookupException(continuation.getException());
193 			}
194 		}
195 		catch(XCoreException xce) {
196 			throw new LookupException(xce);
197 		}
198 	}
199 
200 	/* (non-Javadoc)
201 	 * @see org.xvsm.interfaces.lookup.ILookup#publish(java.lang.String)
202 	 */
203 	public void publish(String name)
204 			throws ContainerAlreadyPublishedException, LookupException {
205 		
206 		try {
207 			FreePastryConnection conn = FreePastryConnection.getInstance();
208 			Past past = conn.getPast();
209 			PublishContinuation continuation = new PublishContinuation();
210 			
211 			String publishedId = name;
212 		//	String publishedContent = cref.toString();
213 			String publishedContent = name;			
214 			
215 			PastContent myContent = new FPPastContent(conn.getPastryIdFactory().buildId(publishedId), publishedContent);
216 		
217 			past.insert(myContent, continuation);
218 			
219 			while(continuation.isFinished() == false) {
220 				try {
221 					Thread.sleep(20);
222 				}
223 				catch(Exception e) {
224 					
225 				}
226 			}
227 			if(continuation.getException() != null) {
228 				//TODO: abfragen ob already gepublished...
229 				
230 				throw new LookupException(continuation.getException());
231 			}
232 		}
233 		catch(XCoreException xce) {
234 			throw new LookupException(xce);
235 		}
236 	}
237 	
238 	/* (non-Javadoc)
239 	 * @see org.xvsm.interfaces.lookup.ILookup#unpublish(org.xvsm.core.ContainerRef)
240 	 */
241 	public void unpublish(ContainerRef pCref)
242 			throws ContainerNotPublishedException, LookupException {
243 		ContainerRef cref = pCref;
244 		
245 		try {
246 			FreePastryConnection conn = FreePastryConnection.getInstance();
247 			Past past = conn.getPast();
248 			PublishContinuation continuation = new PublishContinuation();
249 			
250 			String publishedId = this.getContainerName(cref);
251 			String publishedContent = cref.toString();
252 			
253 			PastContent myContent = new FPPastContent(conn.getPastryIdFactory().buildId(publishedId), publishedContent);
254 
255 			past.insert(myContent, continuation);
256 			
257 			while(continuation.isFinished() == false) {
258 				try {
259 					Thread.sleep(100);
260 				}
261 				catch(Exception e) {
262 					
263 				}
264 			}
265 			if(continuation.getException() != null) {
266 				throw new LookupException(continuation.getException());
267 			}
268 		}
269 		catch(XCoreException xce) {
270 			throw new LookupException(xce);
271 		}
272 	}
273 
274 	/* (non-Javadoc)
275 	 * @see org.xvsm.interfaces.lookup.ILookup#updateDescription(org.xvsm.core.ContainerRef)
276 	 */
277 	public void updateDescription(ContainerRef cref)
278 			throws ContainerNotPublishedException, LookupException {
279 		throw new LookupException("This feature is not available for FreePastry!");
280 	}
281 	
282 	/***
283 	 * returns the container name of a container
284 	 * 
285 	 * @param cref
286 	 * @return
287 	 * @throws XCoreException
288 	 */
289 	public static String getContainerName(ContainerRef cref) throws XCoreException {
290 		ContainerRef metaCref = LookupManager.lookupMetaContainer(cref);
291 		String containerName = (String)((AtomicEntry) capi.read(metaCref, 0, null,
292 				new KeySelector<String>("system", "name"))[0]).getValue();
293 			
294 		return containerName;
295 	}
296 
297 	/* (non-Javadoc)
298 	 * @see org.xvsm.interfaces.lookup.ILookup#publishedContainers()
299 	 */
300 	public ContainerRef[] publishedContainers() throws LookupException {
301 		throw new LookupException("Feature cannot be implemented for Pastry");
302 	}
303 
304 }