2 * Jalview - A Sequence Alignment Editor and Viewer (Development Version 2.4.1)
3 * Copyright (C) 2009 AM Waterhouse, J Procter, G Barton, M Clamp, S Searle
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License
7 * as published by the Free Software Foundation; either version 2
8 * of the License, or (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
23 import jalview.datamodel.*;
26 * A low level class for alignment and feature IO with alignment formatting
27 * methods used by both applet and application for generating flat alignment
28 * files. It also holds the lists of magic format names that the applet and
29 * application will allow the user to read or write files with.
34 public class AppletFormatAdapter
37 * List of valid format strings used in the isValidFormat method
39 public static final String[] READABLE_FORMATS = new String[]
40 { "BLC", "CLUSTAL", "FASTA", "MSF", "PileUp", "PIR", "PFAM", "STH",
41 "PDB", "JnetFile"}; //, "SimpleBLAST" };
44 * List of valid format strings for use by callers of the formatSequences
47 public static final String[] WRITEABLE_FORMATS = new String[]
48 { "BLC", "CLUSTAL", "FASTA", "MSF", "PileUp", "PIR", "PFAM", "AMSA" };
51 * List of extensions corresponding to file format types in WRITABLE_FNAMES
52 * that are writable by the application.
54 public static final String[] WRITABLE_EXTENSIONS = new String[]
55 { "fa, fasta, fastq", "aln", "pfam", "msf", "pir", "blc", "amsa", "jar" };
58 * List of writable formats by the application. Order must correspond with the
59 * WRITABLE_EXTENSIONS list of formats.
61 public static final String[] WRITABLE_FNAMES = new String[]
62 { "Fasta", "Clustal", "PFAM", "MSF", "PIR", "BLC", "AMSA", "Jalview" };
65 * List of readable format file extensions by application in order
66 * corresponding to READABLE_FNAMES
68 public static final String[] READABLE_EXTENSIONS = new String[]
69 { "fa, fasta, fastq", "aln", "pfam", "msf", "pir", "blc", "amsa", "jar"}; //, ".blast" };
72 * List of readable formats by application in order corresponding to
75 public static final String[] READABLE_FNAMES = new String[]
76 { "Fasta", "Clustal", "PFAM", "MSF", "PIR", "BLC", "AMSA", "Jalview"};// , "SimpleBLAST" };
78 public static String INVALID_CHARACTERS = "Contains invalid characters";
80 // TODO: make these messages dynamic
81 public static String SUPPORTED_FORMATS = "Formats currently supported are\n"
82 + prettyPrint(READABLE_FORMATS);
87 * @return grammatically correct(ish) list consisting of els elements.
89 public static String prettyPrint(String[] els)
91 StringBuffer list = new StringBuffer();
92 for (int i = 0, iSize = els.length - 1; i < iSize; i++)
97 list.append(" and " + els[els.length - 1] + ".");
98 return list.toString();
101 public static String FILE = "File";
103 public static String URL = "URL";
105 public static String PASTE = "Paste";
107 public static String CLASSLOADER = "ClassLoader";
109 AlignFile afile = null;
114 * check that this format is valid for reading
117 * a format string to be compared with READABLE_FORMATS
118 * @return true if format is readable
120 public static final boolean isValidFormat(String format)
122 return isValidFormat(format, false);
126 * validate format is valid for IO
129 * a format string to be compared with either READABLE_FORMATS
130 * or WRITEABLE_FORMATS
132 * when true, format is checked for containment in
134 * @return true if format is valid
136 public static final boolean isValidFormat(String format,
139 boolean valid = false;
140 String[] format_list = (forwriting) ? WRITEABLE_FORMATS
142 for (int i = 0; i < format_list.length; i++)
144 if (format_list[i].equalsIgnoreCase(format))
154 * Constructs the correct filetype parser for a characterised datasource
161 * File format of data provided by datasource
163 * @return DOCUMENT ME!
165 public Alignment readFile(String inFile, String type, String format)
166 throws java.io.IOException
168 // TODO: generalise mapping between format string and io. class instances
169 // using Constructor.invoke reflection
170 this.inFile = inFile;
173 if (format.equals("FASTA"))
175 afile = new FastaFile(inFile, type);
177 else if (format.equals("MSF"))
179 afile = new MSFfile(inFile, type);
181 else if (format.equals("PileUp"))
183 afile = new PileUpfile(inFile, type);
185 else if (format.equals("CLUSTAL"))
187 afile = new ClustalFile(inFile, type);
189 else if (format.equals("BLC"))
191 afile = new BLCFile(inFile, type);
193 else if (format.equals("PIR"))
195 afile = new PIRFile(inFile, type);
197 else if (format.equals("PFAM"))
199 afile = new PfamFile(inFile, type);
201 else if (format.equals("JnetFile"))
203 afile = new JPredFile(inFile, type);
204 ((JPredFile) afile).removeNonSequences();
206 else if (format.equals("PDB"))
208 afile = new MCview.PDBfile(inFile, type);
210 else if (format.equals("STH"))
212 afile = new StockholmFile(inFile, type);
214 else if (format.equals("SimpleBLAST"))
216 afile = new SimpleBlastFile(inFile,type);
219 Alignment al = new Alignment(afile.getSeqsAsArray());
221 afile.addAnnotations(al);
224 } catch (Exception e)
227 System.err.println("Failed to read alignment using the '" + format
228 + "' reader.\n" + e);
230 if (e.getMessage() != null
231 && e.getMessage().startsWith(INVALID_CHARACTERS))
233 throw new java.io.IOException(e.getMessage());
236 // Finally test if the user has pasted just the sequence, no id
237 if (type.equalsIgnoreCase("Paste"))
241 // Possible sequence is just residues with no label
242 afile = new FastaFile(">UNKNOWN\n" + inFile, "Paste");
243 Alignment al = new Alignment(afile.getSeqsAsArray());
244 afile.addAnnotations(al);
247 } catch (Exception ex)
249 if (ex.toString().startsWith(INVALID_CHARACTERS))
251 throw new java.io.IOException(e.getMessage());
254 ex.printStackTrace();
258 // If we get to this stage, the format was not supported
259 throw new java.io.IOException(SUPPORTED_FORMATS);
264 * Constructs the correct filetype parser for an already open datasource
267 * an existing datasource
269 * File format of data that will be provided by datasource
271 * @return DOCUMENT ME!
273 public Alignment readFromFile(FileParse source, String format)
274 throws java.io.IOException
276 // TODO: generalise mapping between format string and io. class instances
277 // using Constructor.invoke reflection
278 // This is exactly the same as the readFile method except we substitute
279 // 'inFile, type' with 'source'
280 this.inFile = source.getInFile();
281 String type = source.type;
284 if (format.equals("FASTA"))
286 afile = new FastaFile(source);
288 else if (format.equals("MSF"))
290 afile = new MSFfile(source);
292 else if (format.equals("PileUp"))
294 afile = new PileUpfile(source);
296 else if (format.equals("CLUSTAL"))
298 afile = new ClustalFile(source);
300 else if (format.equals("BLC"))
302 afile = new BLCFile(source);
304 else if (format.equals("PIR"))
306 afile = new PIRFile(source);
308 else if (format.equals("PFAM"))
310 afile = new PfamFile(source);
312 else if (format.equals("JnetFile"))
314 afile = new JPredFile(source);
315 ((JPredFile) afile).removeNonSequences();
317 else if (format.equals("PDB"))
319 afile = new MCview.PDBfile(source);
321 else if (format.equals("STH"))
323 afile = new StockholmFile(source);
325 else if (format.equals("SimpleBLAST"))
327 afile = new SimpleBlastFile(source);
330 Alignment al = new Alignment(afile.getSeqsAsArray());
332 afile.addAnnotations(al);
335 } catch (Exception e)
338 System.err.println("Failed to read alignment using the '" + format
339 + "' reader.\n" + e);
341 if (e.getMessage() != null
342 && e.getMessage().startsWith(INVALID_CHARACTERS))
344 throw new java.io.IOException(e.getMessage());
347 // Finally test if the user has pasted just the sequence, no id
348 if (type.equalsIgnoreCase("Paste"))
352 // Possible sequence is just residues with no label
353 afile = new FastaFile(">UNKNOWN\n" + inFile, "Paste");
354 Alignment al = new Alignment(afile.getSeqsAsArray());
355 afile.addAnnotations(al);
358 } catch (Exception ex)
360 if (ex.toString().startsWith(INVALID_CHARACTERS))
362 throw new java.io.IOException(e.getMessage());
365 ex.printStackTrace();
369 // If we get to this stage, the format was not supported
370 throw new java.io.IOException(SUPPORTED_FORMATS);
375 * Construct an output class for an alignment in a particular filetype
376 * TODO: allow caller to detect errors and warnings encountered when generating output
379 * string name of alignment format
381 * the alignment to be written out
383 * passed to AlnFile class controls whether /START-END is added
386 * @return alignment flat file contents
388 public String formatSequences(String format, AlignmentI alignment,
393 AlignFile afile = null;
395 if (format.equalsIgnoreCase("FASTA"))
397 afile = new FastaFile();
399 else if (format.equalsIgnoreCase("MSF"))
401 afile = new MSFfile();
403 else if (format.equalsIgnoreCase("PileUp"))
405 afile = new PileUpfile();
407 else if (format.equalsIgnoreCase("CLUSTAL"))
409 afile = new ClustalFile();
411 else if (format.equalsIgnoreCase("BLC"))
413 afile = new BLCFile();
415 else if (format.equalsIgnoreCase("PIR"))
417 afile = new PIRFile();
419 else if (format.equalsIgnoreCase("PFAM"))
421 afile = new PfamFile();
423 else if (format.equalsIgnoreCase("STH"))
425 afile = new StockholmFile();
427 else if (format.equalsIgnoreCase("AMSA"))
429 afile = new AMSAFile(alignment);
434 "Implementation error: Unknown file format string");
437 afile.addJVSuffix(jvsuffix);
439 afile.setSeqs(alignment.getSequencesArray());
441 String afileresp = afile.print();
442 if (afile.hasWarningMessage())
444 System.err.println("Warning raised when writing as "+format+" : "+afile.getWarningMessage());
447 } catch (Exception e)
449 System.err.println("Failed to write alignment as a '" + format
457 public static void main(String[] args)
460 while (i < args.length)
462 File f = new File(args[i]);
467 System.out.println("Reading file: " + f);
468 AppletFormatAdapter afa = new AppletFormatAdapter();
469 Runtime r = Runtime.getRuntime();
471 long memf = -r.totalMemory() + r.freeMemory();
472 long t1 = -System.currentTimeMillis();
473 Alignment al = afa.readFile(args[i], FILE, new IdentifyFile()
474 .Identify(args[i], FILE));
475 t1 += System.currentTimeMillis();
477 memf += r.totalMemory() - r.freeMemory();
480 System.out.println("Alignment contains " + al.getHeight()
481 + " sequences and " + al.getWidth() + " columns.");
483 System.out.println(new AppletFormatAdapter().formatSequences("FASTA", al, true));
484 } catch (Exception e)
486 System.err.println("Couln't format the alignment for output as a FASTA file.");
487 e.printStackTrace(System.err);
492 System.out.println("Couldn't read alignment");
494 System.out.println("Read took " + (t1 / 1000.0) + " seconds.");
496 .println("Difference between free memory now and before is "
497 + (memf / (1024.0 * 1024.0) * 1.0) + " MB");
499 } catch (Exception e)
501 System.err.println("Exception when dealing with " + i
502 + "'th argument: " + args[i] + "\n" + e);
507 System.err.println("Ignoring argument '" + args[i] + "' (" + i
508 + "'th)- not a readable file.");