Merge branch 'patch/JAL-4345_pae_epas1_doubleclick' into develop
[jalview.git] / src / jalview / gui / WsParamSetManager.java
1 /*
2  * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
3  * Copyright (C) $$Year-Rel$$ The Jalview Authors
4  * 
5  * This file is part of Jalview.
6  * 
7  * Jalview is free software: you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License 
9  * as published by the Free Software Foundation, either version 3
10  * of the License, or (at your option) any later version.
11  *  
12  * Jalview is distributed in the hope that it will be useful, but 
13  * WITHOUT ANY WARRANTY; without even the implied warranty 
14  * of MERCHANTABILITY or FITNESS FOR A PARTICULAR 
15  * PURPOSE.  See the GNU General Public License for more details.
16  * 
17  * You should have received a copy of the GNU General Public License
18  * along with Jalview.  If not, see <http://www.gnu.org/licenses/>.
19  * The Jalview Authors are detailed in the 'AUTHORS' file.
20  */
21 package jalview.gui;
22
23 import jalview.bin.Cache;
24 import jalview.bin.Console;
25 import jalview.io.JalviewFileChooser;
26 import jalview.io.JalviewFileView;
27 import jalview.util.MessageManager;
28 import jalview.ws.params.ParamDatastoreI;
29 import jalview.ws.params.ParamManager;
30 import jalview.ws.params.WsParamSetI;
31 import jalview.xml.binding.jalview.ObjectFactory;
32 import jalview.xml.binding.jalview.WebServiceParameterSet;
33
34 import java.io.File;
35 import java.io.FileInputStream;
36 import java.io.FileOutputStream;
37 import java.io.IOException;
38 import java.io.InputStreamReader;
39 import java.io.OutputStreamWriter;
40 import java.io.PrintWriter;
41 import java.util.ArrayList;
42 import java.util.Hashtable;
43 import java.util.List;
44 import java.util.StringTokenizer;
45
46 import javax.xml.bind.JAXBContext;
47 import javax.xml.bind.JAXBElement;
48 import javax.xml.bind.Marshaller;
49 import javax.xml.stream.XMLInputFactory;
50 import javax.xml.stream.XMLStreamReader;
51
52 /**
53  * store and retrieve web service parameter sets.
54  * 
55  * @author JimP
56  * 
57  */
58 public class WsParamSetManager implements ParamManager
59 {
60   Hashtable<String, ParamDatastoreI> paramparsers = new Hashtable<>();
61
62   @Override
63   public WsParamSetI[] getParameterSet(String name, String serviceUrl,
64           boolean modifiable, boolean unmodifiable)
65   {
66     String files = Cache.getProperty("WS_PARAM_FILES");
67     if (files == null)
68     {
69       return null;
70     }
71     StringTokenizer st = new StringTokenizer(files, "|");
72     String pfile = null;
73     List<WsParamSetI> params = new ArrayList<>();
74     while (st.hasMoreTokens())
75     {
76       pfile = st.nextToken();
77       try
78       {
79         WsParamSetI[] pset = parseParamFile(pfile);
80         for (WsParamSetI p : pset)
81         {
82           boolean add = false;
83           if (serviceUrl != null)
84           {
85             for (String url : p.getApplicableUrls())
86             {
87               if (url.equals(serviceUrl))
88               {
89                 add = true;
90               }
91             }
92           }
93           else
94           {
95             add = true;
96           }
97           add &= (modifiable == p.isModifiable()
98                   || unmodifiable == !p.isModifiable());
99           add &= name == null || p.getName().equals(name);
100
101           if (add)
102           {
103
104             params.add(p);
105           }
106
107         }
108       } catch (IOException e)
109       {
110         Console.info("Failed to parse parameter file " + pfile
111                 + " (Check that all JALVIEW_WSPARAMFILES entries are valid!)",
112                 e);
113       }
114     }
115     return params.toArray(new WsParamSetI[0]);
116   }
117
118   private WsParamSetI[] parseParamFile(String filename) throws IOException
119   {
120     List<WsParamSetI> psets = new ArrayList<>();
121     InputStreamReader is = new InputStreamReader(
122             new FileInputStream(new File(filename)), "UTF-8");
123
124     WebServiceParameterSet wspset = null;
125     try
126     {
127       JAXBContext jc = JAXBContext
128               .newInstance("jalview.xml.binding.jalview");
129       javax.xml.bind.Unmarshaller um = jc.createUnmarshaller();
130       XMLStreamReader streamReader = XMLInputFactory.newInstance()
131               .createXMLStreamReader(is);
132       JAXBElement<WebServiceParameterSet> jbe = um.unmarshal(streamReader,
133               WebServiceParameterSet.class);
134       wspset = jbe.getValue();
135     } catch (Exception ex)
136     {
137       throw new IOException(ex);
138     }
139
140     if (wspset != null && wspset.getParameters().length() > 0)
141     {
142       List<String> urls = wspset.getServiceURL();
143       final String[] urlArray = urls.toArray(new String[urls.size()]);
144
145       for (String url : urls)
146       {
147         ParamDatastoreI parser = paramparsers.get(url);
148         if (parser != null)
149         {
150           WsParamSetI pset = parser.parseServiceParameterFile(
151                   wspset.getName(), wspset.getDescription(), urlArray,
152                   wspset.getParameters());
153           if (pset != null)
154           {
155             pset.setSourceFile(filename);
156             psets.add(pset);
157             break;
158           }
159         }
160       }
161     }
162
163     return psets.toArray(new WsParamSetI[0]);
164   }
165
166   @Override
167   public void storeParameterSet(WsParamSetI parameterSet)
168   {
169     String filename = parameterSet.getSourceFile();
170     File outfile = null;
171     try
172     {
173       if (filename != null && !((outfile = new File(filename)).canWrite()))
174       {
175         Console.warn("Can't write to " + filename
176                 + " - Prompting for new file to write to.");
177         filename = null;
178       }
179     } catch (Exception e)
180     {
181       filename = null;
182     }
183
184     ParamDatastoreI parser = null;
185     for (String urls : parameterSet.getApplicableUrls())
186     {
187       if (parser == null)
188       {
189         parser = paramparsers.get(urls);
190       }
191     }
192     if (parser == null)
193     {
194       throw new Error(MessageManager.getString(
195               "error.implementation_error_cannot_find_marshaller_for_param_set"));
196     }
197     if (filename == null)
198     {
199       // TODO: JAL-3048 webservice - not required for Jalview-JS
200
201       JalviewFileChooser chooser = new JalviewFileChooser("wsparams",
202               "Web Service Parameter File");
203       chooser.setFileView(new JalviewFileView());
204       chooser.setDialogTitle(MessageManager
205               .getString("label.choose_filename_for_param_file"));
206       chooser.setToolTipText(MessageManager.getString("action.save"));
207       int value = chooser.showSaveDialog(Desktop.instance);
208       if (value == JalviewFileChooser.APPROVE_OPTION)
209       {
210         outfile = chooser.getSelectedFile();
211         Cache.setProperty("LAST_DIRECTORY", outfile.getParent());
212         filename = outfile.getAbsolutePath();
213         if (!filename.endsWith(".wsparams"))
214         {
215           filename = filename.concat(".wsparams");
216           outfile = new File(filename);
217         }
218       }
219     }
220     if (outfile != null)
221     {
222       String paramFiles = Cache.getDefault("WS_PARAM_FILES", filename);
223       if (paramFiles.indexOf(filename) == -1)
224       {
225         if (paramFiles.length() > 0)
226         {
227           paramFiles = paramFiles.concat("|");
228         }
229         paramFiles = paramFiles.concat(filename);
230       }
231       Cache.setProperty("WS_PARAM_FILES", paramFiles);
232
233       WebServiceParameterSet paramxml = new WebServiceParameterSet();
234
235       paramxml.setName(parameterSet.getName());
236       paramxml.setDescription(parameterSet.getDescription());
237       for (String url : parameterSet.getApplicableUrls())
238       {
239         paramxml.getServiceURL().add(url);
240       }
241       paramxml.setVersion("1.0");
242       try
243       {
244         paramxml.setParameters(
245                 parser.generateServiceParameterFile(parameterSet));
246         PrintWriter out = new PrintWriter(new OutputStreamWriter(
247                 new FileOutputStream(outfile), "UTF-8"));
248         JAXBContext jaxbContext = JAXBContext
249                 .newInstance(WebServiceParameterSet.class);
250         Marshaller jaxbMarshaller = jaxbContext.createMarshaller();
251         jaxbMarshaller.marshal(
252                 new ObjectFactory().createWebServiceParameterSet(paramxml),
253                 out);
254         out.close();
255         parameterSet.setSourceFile(filename);
256       } catch (Exception e)
257       {
258         Console.error("Couldn't write parameter file to " + outfile, e);
259       }
260     }
261   }
262
263   /*
264    * 
265    * JalviewFileChooser chooser = new JalviewFileChooser(Cache
266    * .getProperty("LAST_DIRECTORY"), new String[] { "jc" }, new String[] {
267    * "Jalview User Colours" }, "Jalview User Colours"); chooser.setFileView(new
268    * jalview.io.JalviewFileView());
269    * chooser.setDialogTitle("Load colour scheme");
270    * chooser.setToolTipText("Load");
271    * 
272    * int value = chooser.showOpenDialog(this);
273    * 
274    * if (value == JalviewFileChooser.APPROVE_OPTION) { File choice =
275    * chooser.getSelectedFile(); Cache.setProperty("LAST_DIRECTORY",
276    * choice.getParent()); String defaultColours = Cache.getDefault(
277    * "USER_DEFINED_COLOURS", choice.getPath()); if
278    * (defaultColours.indexOf(choice.getPath()) == -1) { defaultColours =
279    * defaultColours.concat("|") .concat(choice.getPath()); } (non-Javadoc)
280    * 
281    * @see
282    * jalview.ws.params.ParamManager#deleteParameterSet(jalview.ws.params.WsParamSetI
283    * )
284    */
285   @Override
286   public void deleteParameterSet(WsParamSetI parameterSet)
287   {
288     String filename = parameterSet.getSourceFile();
289     if (filename == null || filename.trim().length() < 1)
290     {
291       return;
292     }
293     String paramFiles = Cache.getDefault("WS_PARAM_FILES", "");
294     if (paramFiles.indexOf(filename) > -1)
295     {
296       String nparamFiles = new String();
297       StringTokenizer st = new StringTokenizer(paramFiles, "|");
298       while (st.hasMoreElements())
299       {
300         String fl = st.nextToken();
301         if (!fl.equals(filename))
302         {
303           nparamFiles = nparamFiles.concat("|").concat(fl);
304         }
305       }
306       Cache.setProperty("WS_PARAM_FILES", nparamFiles);
307     }
308
309     try
310     {
311       File pfile = new File(filename);
312       if (pfile.exists() && pfile.canWrite())
313       {
314         if (JvOptionPane.showConfirmDialog(Desktop.instance,
315                 "Delete the preset's file, too ?", "Delete User Preset ?",
316                 JvOptionPane.OK_CANCEL_OPTION) == JvOptionPane.OK_OPTION)
317         {
318           pfile.delete();
319         }
320       }
321     } catch (Exception e)
322     {
323       Console.error(
324               "Exception when trying to delete webservice user preset: ",
325               e);
326     }
327   }
328
329   @Override
330   public void registerParser(String hosturl, ParamDatastoreI paramdataStore)
331   {
332     paramparsers.put(hosturl, paramdataStore);
333   }
334
335 }