Mercurial > repos > rliterman > csp2
comparison CSP2/CSP2_env/env-d9b9114564458d9d-741b3de822f2aaca6c6caa4325c4afce/opt/bbmap-39.01-1/current/server/ServerTools.java @ 68:5028fdace37b
planemo upload commit 2e9511a184a1ca667c7be0c6321a36dc4e3d116d
author | jpayne |
---|---|
date | Tue, 18 Mar 2025 16:23:26 -0400 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
67:0e9998148a16 | 68:5028fdace37b |
---|---|
1 package server; | |
2 | |
3 import java.io.BufferedReader; | |
4 import java.io.IOException; | |
5 import java.io.InputStream; | |
6 import java.io.InputStreamReader; | |
7 import java.io.OutputStream; | |
8 import java.net.HttpURLConnection; | |
9 import java.net.InetSocketAddress; | |
10 import java.net.MalformedURLException; | |
11 import java.net.URL; | |
12 import java.net.URLConnection; | |
13 import java.util.ArrayList; | |
14 import java.util.Arrays; | |
15 import java.util.List; | |
16 import java.util.Map.Entry; | |
17 | |
18 import com.sun.net.httpserver.Headers; | |
19 import com.sun.net.httpserver.HttpExchange; | |
20 | |
21 import fileIO.ReadWrite; | |
22 import shared.Tools; | |
23 import structures.ByteBuilder; | |
24 import structures.StringNum; | |
25 | |
26 public class ServerTools { | |
27 | |
28 public static void main(String[] args){ | |
29 String address=args[0]; | |
30 int rounds=1; | |
31 String message=""; | |
32 if(args.length>1){rounds=Integer.parseInt(args[1]);} | |
33 if(args.length>2){message=args[2];} | |
34 byte[] messageBytes=message.getBytes(); | |
35 | |
36 long[] times=new long[rounds]; | |
37 StringNum response=null; | |
38 long prevTime=System.nanoTime(); | |
39 for(int i=0; i<rounds; i++){ | |
40 response=sendAndReceive(messageBytes, address); | |
41 long currentTime=System.nanoTime(); | |
42 times[i]=currentTime-prevTime; | |
43 prevTime=currentTime; | |
44 System.out.println(times[i]); | |
45 } | |
46 | |
47 System.out.println(response.s); | |
48 | |
49 Arrays.sort(times); | |
50 long sum=Tools.sum(times); | |
51 System.out.println("Avg: \t"+sum/1000000.0+" ms"); | |
52 System.out.println("QPS: \t"+(rounds*1000000000/sum)+" ms"); | |
53 System.out.println("Median: \t"+(times[rounds/2]/1000000.0)+" ms"); | |
54 | |
55 } | |
56 | |
57 public static ByteBuilder readPage(String address, boolean convert){ | |
58 if(convert){address=PercentEncoding.commonSymbolToCode(address);} | |
59 // assert(false) : address; | |
60 ByteBuilder bb=new ByteBuilder(256); | |
61 boolean success=false; | |
62 for(int i=0; i<10 && !success; i++){ | |
63 try { | |
64 URL url=new URL(address); | |
65 InputStream is=url.openStream(); | |
66 | |
67 byte[] buffer=new byte[4096]; | |
68 for(int len=is.read(buffer); len>0; len=is.read(buffer)){ | |
69 bb.append(buffer, 0, len); | |
70 } | |
71 is.close(); | |
72 success=true; | |
73 } catch (MalformedURLException e) { | |
74 e.printStackTrace(); | |
75 bb.clear(); | |
76 Tools.pause(1000); | |
77 System.err.println("Retrying; attempt "+(i+1)+", URL "+address); | |
78 } catch (IOException e) { | |
79 e.printStackTrace(); | |
80 bb.clear(); | |
81 Tools.pause(1000); | |
82 System.err.println("Retrying; attempt "+(i+1)+", URL "+address); | |
83 } | |
84 } | |
85 return bb; | |
86 } | |
87 | |
88 | |
89 /** Send a message to a remote URL, and return the response. | |
90 * Set message to null if there is no message. */ | |
91 public static StringNum sendAndReceive(byte[] message, String address){ | |
92 address=PercentEncoding.commonSymbolToCode(address); | |
93 URL url=null; | |
94 InputStream is=null; | |
95 HttpURLConnection connection=null; | |
96 OutputStream os=null; | |
97 try { | |
98 url=new URL(address); | |
99 connection=(HttpURLConnection) url.openConnection(); | |
100 connection.setDoOutput(true); | |
101 connection.setConnectTimeout(40000); //For testing | |
102 os=connection.getOutputStream(); | |
103 } catch (IOException e1) { | |
104 // System.err.println("A:\t"+address+" -> "+url+" -> "+connection+" -> "+os); | |
105 // TODO Auto-generated catch block | |
106 if(!suppressErrors){e1.printStackTrace();} | |
107 } | |
108 | |
109 if(os!=null){ | |
110 try { | |
111 //TODO: It may be useful to set a timeout here. | |
112 if(message!=null){os.write(message);} | |
113 } catch (IOException e) { | |
114 // System.err.println("B:\t"+connection+" -> "+os); | |
115 // TODO Auto-generated catch block | |
116 if(!suppressErrors){e.printStackTrace();} | |
117 } | |
118 try { | |
119 os.close(); | |
120 } catch (IOException e) { | |
121 // TODO Auto-generated catch block | |
122 e.printStackTrace(); | |
123 } | |
124 } | |
125 | |
126 String result=null; | |
127 int responseCode=1; | |
128 if(connection!=null){ | |
129 IOException noInputStream=null; | |
130 try { | |
131 is=connection.getInputStream(); | |
132 } catch (IOException e) { | |
133 noInputStream=e; | |
134 } | |
135 if(is==null){is=connection.getErrorStream();} | |
136 | |
137 try { | |
138 responseCode=connection.getResponseCode(); | |
139 if(!suppressErrors && (responseCode<200 || responseCode>299)){ | |
140 System.err.println("Error: Server returned response code "+responseCode); | |
141 } | |
142 } catch (IOException e) { | |
143 if(!suppressErrors) { | |
144 e.printStackTrace(); | |
145 } | |
146 } | |
147 | |
148 if(is!=null){ | |
149 result=readStream(is); | |
150 try { | |
151 // System.err.println("C:\t"+connection+" -> "+os+" -> "+is+" -> "+(result!=null)); | |
152 is.close(); | |
153 } catch (IOException e) { | |
154 e.printStackTrace(); | |
155 } | |
156 }else if(noInputStream!=null && !suppressErrors){ | |
157 noInputStream.printStackTrace(); | |
158 } | |
159 } | |
160 | |
161 return new StringNum(result, responseCode); | |
162 } | |
163 | |
164 | |
165 /** Send a message to a remote URL, and return the response. | |
166 * Set message to null if there is no message. */ | |
167 public static StringNum sendAndReceiveFTP(byte[] message, String address){ | |
168 address=PercentEncoding.commonSymbolToCode(address); | |
169 URL url=null; | |
170 InputStream is=null; | |
171 URLConnection connection=null; | |
172 OutputStream os=null; | |
173 try { | |
174 url=new URL(address); | |
175 connection=url.openConnection(); | |
176 connection.setDoOutput(true); | |
177 connection.setConnectTimeout(40000); //For testing | |
178 os=connection.getOutputStream(); | |
179 } catch (IOException e1) { | |
180 // System.err.println("A:\t"+address+" -> "+url+" -> "+connection+" -> "+os); | |
181 // TODO Auto-generated catch block | |
182 if(!suppressErrors){e1.printStackTrace();} | |
183 } | |
184 | |
185 if(os!=null){ | |
186 try { | |
187 //TODO: It may be useful to set a timeout here. | |
188 if(message!=null){os.write(message);} | |
189 } catch (IOException e) { | |
190 // System.err.println("B:\t"+connection+" -> "+os); | |
191 // TODO Auto-generated catch block | |
192 if(!suppressErrors){e.printStackTrace();} | |
193 } | |
194 try { | |
195 os.close(); | |
196 } catch (IOException e) { | |
197 // TODO Auto-generated catch block | |
198 e.printStackTrace(); | |
199 } | |
200 } | |
201 | |
202 String result=null; | |
203 // int responseCode=1; | |
204 if(connection!=null){ | |
205 IOException noInputStream=null; | |
206 try { | |
207 is=connection.getInputStream(); | |
208 } catch (IOException e) { | |
209 noInputStream=e; | |
210 } | |
211 | |
212 // try { | |
213 //responseCode=connection.getResponseCode(); | |
214 // if(!suppressErrors && (responseCode<200 || responseCode>299)){ | |
215 // System.err.println("Error: Server returned response code "+responseCode); | |
216 // } | |
217 // } | |
218 // catch (IOException e) { | |
219 // if(!suppressErrors) { | |
220 // e.printStackTrace(); | |
221 // } | |
222 // } | |
223 | |
224 if(is!=null){ | |
225 result=readStream(is); | |
226 try { | |
227 // System.err.println("C:\t"+connection+" -> "+os+" -> "+is+" -> "+(result!=null)); | |
228 is.close(); | |
229 } catch (IOException e) { | |
230 e.printStackTrace(); | |
231 } | |
232 }else if(noInputStream!=null && !suppressErrors){ | |
233 noInputStream.printStackTrace(); | |
234 } | |
235 } | |
236 | |
237 return new StringNum(result, 400); | |
238 } | |
239 | |
240 /** Read the body of an incoming HTTP session */ | |
241 public static String receive(HttpExchange t){ | |
242 InputStream is=t.getRequestBody(); | |
243 String s=readStream(is); | |
244 return s; | |
245 } | |
246 | |
247 /** Completely read an InputStream into a String */ | |
248 public static String readStream(InputStream is){ | |
249 if(is==null){return null;} | |
250 try { | |
251 byte[] buffer=new byte[256]; | |
252 int count=is.read(buffer); | |
253 int next=0; | |
254 while(count>-1){ | |
255 next+=count; | |
256 if(next>=buffer.length){ | |
257 buffer=Arrays.copyOf(buffer, buffer.length*2); | |
258 } | |
259 count=is.read(buffer, next, buffer.length-next); | |
260 } | |
261 is.close(); | |
262 return new String(buffer, 0, next); | |
263 } catch (IOException e) { | |
264 // TODO Auto-generated catch block | |
265 e.printStackTrace(); | |
266 } | |
267 return null; | |
268 } | |
269 | |
270 /** Write to the body of an incoming HTTP session */ | |
271 public static boolean reply(String response, String type, HttpExchange t, boolean verbose, int code, boolean close){ | |
272 if(verbose){System.err.println("Sending: "+response);} | |
273 | |
274 return reply(response.getBytes(), type, t, false, code, close); | |
275 } | |
276 | |
277 /** Write to the body of an incoming HTTP session */ | |
278 public static boolean replyWithFile(String path, String type, HttpExchange t, boolean verbose, int code, boolean close){ | |
279 if(verbose){System.err.println("Sending: "+path);} | |
280 | |
281 byte[] response=null; | |
282 try { | |
283 response=ReadWrite.readRaw(path); | |
284 } catch (IOException e1) { | |
285 // TODO Auto-generated catch block | |
286 e1.printStackTrace(); | |
287 response=new byte[0]; | |
288 code=400; //Node sure about this | |
289 } | |
290 | |
291 return reply(response, type, t, false, code, close); | |
292 } | |
293 | |
294 /** Write to the body of an incoming HTTP session */ | |
295 public static boolean reply(byte[] response, String type, HttpExchange t, boolean verbose, int code, boolean close){ | |
296 if(verbose){System.err.println("Sending: "+response);} | |
297 | |
298 { | |
299 Headers h = t.getResponseHeaders(); | |
300 // String type="text/plain"; | |
301 h.add("Content-Type", type); | |
302 } | |
303 try { | |
304 t.sendResponseHeaders(code, response.length); | |
305 OutputStream os = t.getResponseBody(); | |
306 os.write(response); | |
307 os.close(); | |
308 } catch (IOException e) { | |
309 // TODO Auto-generated catch block | |
310 e.printStackTrace(); | |
311 if(close){t.close();} | |
312 return false; | |
313 } | |
314 if(close){t.close();} | |
315 return true; | |
316 } | |
317 | |
318 | |
319 /** | |
320 * Wait for a set amount of time | |
321 * @param millis Time to wait | |
322 */ | |
323 public static void pause(long millis){ | |
324 String lock=new String("1"); | |
325 synchronized(lock){ | |
326 final long time=System.currentTimeMillis()+millis; | |
327 while(System.currentTimeMillis()<time){ | |
328 try { | |
329 lock.wait(Tools.max(100, time-System.currentTimeMillis())); | |
330 } catch (InterruptedException e) { | |
331 // TODO Auto-generated catch block | |
332 e.printStackTrace(); | |
333 } | |
334 } | |
335 } | |
336 } | |
337 | |
338 public static String getClientAddress(HttpExchange t) { | |
339 | |
340 InetSocketAddress client=t.getRemoteAddress(); | |
341 // InetSocketAddress server=t.getLocalAddress(); | |
342 | |
343 //This is for IPv4, class A. Probably extends outside of Berkeley. | |
344 String clientAddress=client.toString(); | |
345 // String ls=server.toString(); | |
346 | |
347 if(clientAddress.contains("127.0.0.1")){ | |
348 Headers clientRequestHeaders=t.getRequestHeaders(); | |
349 // Headers resh=t.getResponseHeaders(); | |
350 | |
351 String xff=clientRequestHeaders.getFirst("X-forwarded-for"); | |
352 if(xff!=null){clientAddress=xff;} | |
353 | |
354 // System.err.println("\nRequest: "); | |
355 // for(Entry<String, List<String>> entry : reqh.entrySet()){ | |
356 // System.err.println(entry.getKey()+" -> "+entry.getValue()); | |
357 // } | |
358 } | |
359 return clientAddress; | |
360 } | |
361 | |
362 public static boolean isInternalQuery(HttpExchange t, String prefix, boolean allowLocalHost, boolean printIP, boolean printHeaders){ | |
363 | |
364 InetSocketAddress client=t.getRemoteAddress(); | |
365 InetSocketAddress server=t.getLocalAddress(); | |
366 | |
367 if(printIP){System.err.println(client+"\t"+server);} | |
368 | |
369 //This is for IPv4, class A. Probably extends outside of Berkeley. | |
370 String clientAddress=client.toString(); | |
371 String serverAddress=server.toString(); | |
372 | |
373 if(clientAddress.contains("127.0.0.1")){//TODO: contains versus startsWith? | |
374 Headers requestHeaders=t.getRequestHeaders(); | |
375 | |
376 if(printHeaders){ | |
377 Headers responseHeaders=t.getResponseHeaders(); | |
378 System.err.println("\nRequest: "); | |
379 for(Entry<String, List<String>> entry : requestHeaders.entrySet()){ | |
380 System.err.println(entry.getKey()+" -> "+entry.getValue()); | |
381 } | |
382 System.err.println("\nResponse: "); | |
383 for(Entry<String, List<String>> entry : responseHeaders.entrySet()){ | |
384 System.err.println(entry.getKey()+" -> "+entry.getValue()); | |
385 } | |
386 } | |
387 | |
388 final String xff=requestHeaders.getFirst("X-forwarded-for"); | |
389 if(xff!=null){ | |
390 if(xff.startsWith(prefix)){return true;} | |
391 clientAddress=xff; | |
392 }else{ | |
393 return allowLocalHost; | |
394 } | |
395 }else{ | |
396 if(clientAddress.startsWith(prefix)){return true;} | |
397 } | |
398 | |
399 //Makes sure they match up to the first delimiter | |
400 //TODO: This needs to be reviewed | |
401 for(int i=0, max=Tools.max(clientAddress.length(), serverAddress.length()); i<max; i++){ | |
402 char cc=clientAddress.charAt(i), sc=serverAddress.charAt(i); | |
403 if(cc!=sc){break;} | |
404 if(cc=='.'){//IPv4 | |
405 return true; | |
406 }else if(cc==':'){//IPv6; probably depends on how long the mask is | |
407 return true; | |
408 } | |
409 } | |
410 | |
411 return false; | |
412 } | |
413 | |
414 public static ArrayList<String> listDirectory(String baseAddress, final int retries){ | |
415 // System.err.println("listDirectory '"+baseAddress+"'"); | |
416 while(baseAddress.endsWith("/")){baseAddress=baseAddress.substring(0, baseAddress.length()-1);} | |
417 String baseAddress2=baseAddress.substring(0, baseAddress.lastIndexOf('/')+1); | |
418 String address=baseAddress+";type=d"; | |
419 ArrayList<String> list=new ArrayList<String>(); | |
420 boolean success=false; | |
421 for(int i=Tools.min(0, retries); !success && i<=retries; i++) { | |
422 try { | |
423 // System.err.println("URL '"+address+"'"); | |
424 URL url=new URL(address); | |
425 URLConnection connection=url.openConnection(); | |
426 InputStream is=connection.getInputStream(); | |
427 BufferedReader br=new BufferedReader(new InputStreamReader(is)); | |
428 | |
429 String line=null; | |
430 while((line=br.readLine())!=null) { | |
431 list.add(baseAddress2+line); | |
432 } | |
433 | |
434 is.close(); | |
435 success=true; | |
436 } catch (IOException e) { | |
437 e.printStackTrace(); | |
438 if(i<retries){ | |
439 try { | |
440 int x=Tools.mid(30000, i*1000, 1000); | |
441 System.err.println("Sleeping for "+x+"ms..."); | |
442 Thread.sleep(x); | |
443 } catch (InterruptedException e1) { | |
444 // TODO Auto-generated catch block | |
445 e1.printStackTrace(); | |
446 } | |
447 System.err.println("** Retrying ** "+address); | |
448 list.clear(); | |
449 }else{ | |
450 System.err.println("*** Gave up ***"); | |
451 } | |
452 } | |
453 } | |
454 return list; | |
455 } | |
456 | |
457 public static ArrayList<String> readFTPFile(String address) throws Exception{ | |
458 address=PercentEncoding.commonSymbolToCode(address); | |
459 URL url = new URL(address); | |
460 URLConnection conn = url.openConnection(); | |
461 | |
462 BufferedReader reader = new BufferedReader(new InputStreamReader( | |
463 conn.getInputStream())); | |
464 ArrayList<String> list=new ArrayList<String>(); | |
465 for(String s=reader.readLine(); s!=null; s=reader.readLine()){ | |
466 list.add(s); | |
467 } | |
468 return list; | |
469 } | |
470 | |
471 /** Don't print caught exceptions */ | |
472 public static boolean suppressErrors=false; | |
473 | |
474 } |