095fd245a10fb5d0ccf4acc2b06bbcd8d00e6e93
[jalview.git] / src / jalview / rest / InputAlignmentEndpoint.java
1 package jalview.rest;
2
3 import java.io.File;
4 import java.io.IOException;
5 import java.net.MalformedURLException;
6 import java.net.URISyntaxException;
7 import java.net.URL;
8 import java.security.MessageDigest;
9 import java.security.NoSuchAlgorithmException;
10 import java.util.Map;
11
12 import javax.servlet.http.HttpServletRequest;
13 import javax.servlet.http.HttpServletResponse;
14 import javax.xml.bind.DatatypeConverter;
15
16 import jalview.bin.Console;
17 import jalview.gui.CutAndPasteTransfer;
18 import jalview.gui.Desktop;
19
20 public class InputAlignmentEndpoint extends AbstractEndpointAsync
21 {
22   public InputAlignmentEndpoint(API api)
23   {
24     super(api, path, name, parameters, description);
25   }
26
27   protected static final String path = "inputalignment";
28
29   private static final String name = "Input Alignment";
30
31   private static final String parameters = "POST <body> | GET ?[data=<data>|file=<fileURI>|url=<URL>]";
32
33   private static final String description = "Input an alignment from POST request body, GET request 'data' parameter, local file in 'file' parameter, url in 'url' parameter";
34
35   private String fileString;
36
37   private String urlString;
38
39   private String method;
40
41   private String data;
42
43   private String body;
44
45   private boolean isPost;
46
47   private boolean hasData;
48
49   private String access = null;
50
51   private String ref = null;
52
53   @Override
54   protected void initialise(HttpServletRequest request,
55           HttpServletResponse response)
56   {
57     fileString = request.getParameter("file");
58     urlString = request.getParameter("url");
59     method = request.getMethod().toLowerCase();
60     data = request.getParameter("data");
61     body = null;
62     isPost = method.equalsIgnoreCase("post");
63     hasData = data != null;
64
65     if (isPost)
66     {
67       access = "post";
68       try
69       {
70         body = getRequestBody(request);
71       } catch (IOException e)
72       {
73         returnError(request, response, "could not read POST body");
74         Console.debug("Could not read POST body", e);
75         return;
76       }
77       // for ref see md5 later
78     }
79     else if (hasData)
80     {
81       access = "data";
82       // for ref see md5 later
83     }
84     else if (fileString != null)
85     {
86       access = "file";
87       ref = fileString;
88     }
89     else if (urlString != null)
90     {
91       access = "url";
92       ref = urlString;
93     }
94
95     if (access == null)
96     {
97       returnError(request, response,
98               "requires POST body or one of parameters 'data', 'file' or 'url'");
99       return;
100     }
101
102     // final content used in Future
103     String content;
104     if (isPost || hasData)
105     {
106       content = isPost ? body : data;
107       objectsPassedToProcessAsync.put("content", content); // needed as "final
108                                                            // String" in process
109       try
110       {
111         MessageDigest md5 = MessageDigest.getInstance("MD5");
112         md5.update(content.getBytes());
113         byte[] digest = md5.digest();
114         ref = DatatypeConverter.printBase64Binary(digest).toLowerCase();
115       } catch (NoSuchAlgorithmException e)
116       {
117         Console.debug("Could not find MD5 algorithm", e);
118       }
119     }
120     else
121     {
122       content = null;
123     }
124     objectsPassedToProcessAsync.put("content", content);
125
126     setId(request, access + "::" + ref);
127   }
128
129   protected void process(HttpServletRequest request,
130           HttpServletResponse response)
131   {
132     processAsync(request, response, null);
133   }
134
135   protected void processAsync(HttpServletRequest request,
136           HttpServletResponse response, final Map<String, Object> finalMap)
137   {
138     String content = (String) finalMap.get("content");
139     if (isPost || hasData)
140     {
141       // Sequence file contents being posted
142       // use File -> Input Alignment -> from Textbox
143       CutAndPasteTransfer cap = new CutAndPasteTransfer();
144       cap.setText(content);
145       cap.ok_actionPerformed(null);
146       cap.cancel_actionPerformed(null);
147     }
148     else if (fileString != null)
149     {
150       // Sequence file on filesystem
151       // use File -> Input Alignment -> From File
152       URL url = null;
153       File file = null;
154       try
155       {
156         url = new URL(fileString);
157         file = new File(url.toURI());
158       } catch (MalformedURLException | URISyntaxException e)
159       {
160         returnError(request, response,
161                 "could not resolve file='" + fileString + "'");
162         Console.debug("Could not resolve file '" + fileString + "'", e);
163         return;
164       }
165       if (!file.exists())
166       {
167         returnError(request, response,
168                 "file='" + fileString + "' does not exist");
169         return;
170       }
171       Desktop.instance.openFile(file, null, null);
172     }
173     else if (urlString != null)
174     {
175       boolean success = Desktop.instance.loadUrl(urlString, null);
176       if (!success)
177       {
178         returnError(request, response,
179                 "url='" + urlString + "' could not be opened");
180         return;
181       }
182     }
183   }
184 }