]> git.donarmstrong.com Git - mothur.git/blob - parsefastaqcommand.cpp
7f4fbbab1096101aa8f09931e4c9ac40e04052b1
[mothur.git] / parsefastaqcommand.cpp
1 /*
2  *  parsefastaqcommand.cpp
3  *  Mothur
4  *
5  *  Created by westcott on 9/30/10.
6  *  Copyright 2010 Schloss Lab. All rights reserved.
7  *
8  */
9
10 #include "parsefastaqcommand.h"
11 #include "sequence.hpp"
12
13 //**********************************************************************************************************************
14 vector<string> ParseFastaQCommand::getValidParameters(){        
15         try {
16                 string Array[] =  {"fastq", "outputdir","inputdir"};
17                 vector<string> myArray (Array, Array+(sizeof(Array)/sizeof(string)));
18                 return myArray;
19         }
20         catch(exception& e) {
21                 m->errorOut(e, "ParseFastaQCommand", "getValidParameters");
22                 exit(1);
23         }
24 }
25 //**********************************************************************************************************************
26 ParseFastaQCommand::ParseFastaQCommand(){       
27         try {
28                 abort = true; calledHelp = true; 
29                 vector<string> tempOutNames;
30                 outputTypes["fasta"] = tempOutNames;
31                 outputTypes["qual"] = tempOutNames;
32         }
33         catch(exception& e) {
34                 m->errorOut(e, "ParseFastaQCommand", "ParseFastaQCommand");
35                 exit(1);
36         }
37 }
38 //**********************************************************************************************************************
39 vector<string> ParseFastaQCommand::getRequiredParameters(){     
40         try {
41                 string Array[] =  {"fastq"};
42                 vector<string> myArray (Array, Array+(sizeof(Array)/sizeof(string)));
43                 return myArray;
44         }
45         catch(exception& e) {
46                 m->errorOut(e, "ParseFastaQCommand", "getRequiredParameters");
47                 exit(1);
48         }
49 }
50 //**********************************************************************************************************************
51 vector<string> ParseFastaQCommand::getRequiredFiles(){  
52         try {
53                 vector<string> myArray;
54                 return myArray;
55         }
56         catch(exception& e) {
57                 m->errorOut(e, "ParseFastaQCommand", "getRequiredFiles");
58                 exit(1);
59         }
60 }
61 //**********************************************************************************************************************
62 ParseFastaQCommand::ParseFastaQCommand(string option){
63         try {
64                 abort = false; calledHelp = false;   
65                 
66                 if(option == "help") {  help(); abort = true; calledHelp = true; }
67                 
68                 else {
69                         //valid paramters for this command
70                         string Array[] =  {"fastq", "outputdir", "inputdir"};
71                         vector<string> myArray (Array, Array+(sizeof(Array)/sizeof(string)));
72                         
73                         OptionParser parser(option);
74                         map<string,string> parameters = parser.getParameters();
75                         
76                         ValidParameters validParameter;
77                         map<string,string>::iterator it;
78
79                         //check to make sure all parameters are valid for command
80                         for (map<string,string>::iterator it = parameters.begin(); it != parameters.end(); it++) { 
81                                 if (validParameter.isValidParameter(it->first, myArray, it->second) != true) {  abort = true;  }
82                         }
83                         
84                         //initialize outputTypes
85                         vector<string> tempOutNames;
86                         outputTypes["fasta"] = tempOutNames;
87                         outputTypes["qual"] = tempOutNames;
88                         
89                         //if the user changes the input directory command factory will send this info to us in the output parameter 
90                         string inputDir = validParameter.validFile(parameters, "inputdir", false);              
91                         if (inputDir == "not found"){   inputDir = "";          }
92                         else {
93                                 string path;
94                                 it = parameters.find("fastq");
95                                 //user has given a template file
96                                 if(it != parameters.end()){ 
97                                         path = m->hasPath(it->second);
98                                         //if the user has not given a path then, add inputdir. else leave path alone.
99                                         if (path == "") {       parameters["fastq"] = inputDir + it->second;            }
100                                 }
101                         }
102                         
103                         //check for required parameters
104                         fastaQFile = validParameter.validFile(parameters, "fastq", true);
105                         if (fastaQFile == "not found") {        m->mothurOut("fastq is a required parameter for the fastq.info command.");      m->mothurOutEndLine();  abort = true;   }
106                         else if (fastaQFile == "not open")      {       fastaQFile = ""; abort = true;  }       
107                         
108                         //if the user changes the output directory command factory will send this info to us in the output parameter 
109                         outputDir = validParameter.validFile(parameters, "outputdir", false);   if (outputDir == "not found"){  outputDir = m->hasPath(fastaQFile);     }
110
111                 }               
112         }
113         catch(exception& e) {
114                 m->errorOut(e, "ParseFastaQCommand", "ParseFastaQCommand");
115                 exit(1);
116         }
117 }
118 //**********************************************************************************************************************
119
120 void ParseFastaQCommand::help(){
121         try {
122                 m->mothurOut("The fastq.info command reads a fastq file and creates a fasta and quality file.\n");
123                 m->mothurOut("The fastq.info command parameter is fastq, and it is required.\n");
124                 m->mothurOut("The fastq.info command should be in the following format: fastq.info(fastaq=yourFastaQFile).\n");
125                 m->mothurOut("Example fastq.info(fastaq=test.fastaq).\n");
126                 m->mothurOut("Note: No spaces between parameter labels (i.e. fastq), '=' and yourFastQFile.\n");
127                 m->mothurOutEndLine();
128         }
129         catch(exception& e) {
130                 m->errorOut(e, "ParseFastaQCommand", "help");
131                 exit(1);
132         }
133 }
134 //**********************************************************************************************************************
135
136 ParseFastaQCommand::~ParseFastaQCommand()       {       /*      do nothing      */      }
137
138 //**********************************************************************************************************************
139
140 int ParseFastaQCommand::execute(){
141         try {
142                 if (abort == true) { if (calledHelp) { return 0; }  return 2;   }
143                 
144                 //open Output Files
145                 string fastaFile = outputDir + m->getRootName(m->getSimpleName(fastaQFile)) + "fasta";
146                 string qualFile = outputDir + m->getRootName(m->getSimpleName(fastaQFile)) + "qual";
147                 ofstream outFasta, outQual;
148                 m->openOutputFile(fastaFile, outFasta);  outputNames.push_back(fastaFile); outputTypes["fasta"].push_back(fastaFile);
149                 m->openOutputFile(qualFile, outQual);   outputNames.push_back(qualFile);  outputTypes["qual"].push_back(qualFile);
150                 
151                 ifstream in;
152                 m->openInputFile(fastaQFile, in);
153                 
154                 while (!in.eof()) {
155                 
156                         //read sequence name
157                         string name = m->getline(in); m->gobble(in);
158                         if (name == "") {  m->mothurOut("[ERROR]: Blank fasta name."); m->mothurOutEndLine(); m->control_pressed = true; break; }
159                         else if (name[0] != '@') { m->mothurOut("[ERROR]: reading " + name + " expected a name with @ as a leading character."); m->mothurOutEndLine(); m->control_pressed = true; break; }
160                         else { name = name.substr(1); }
161                         
162                         //read sequence
163                         string sequence = m->getline(in); m->gobble(in);
164                         if (sequence == "") {  m->mothurOut("[ERROR]: missing sequence for " + name); m->mothurOutEndLine(); m->control_pressed = true; break; }
165                         
166                         //read sequence name
167                         string name2 = m->getline(in); m->gobble(in);
168                         if (name2 == "") {  m->mothurOut("[ERROR]: Blank quality name."); m->mothurOutEndLine(); m->control_pressed = true; break; }
169                         else if (name2[0] != '+') { m->mothurOut("[ERROR]: reading " + name2 + " expected a name with + as a leading character."); m->mothurOutEndLine(); m->control_pressed = true; break; }
170                         else { name2 = name2.substr(1);  }
171                         
172                         //read quality scores
173                         string qual = m->getline(in); m->gobble(in);
174                         if (qual == "") {  m->mothurOut("[ERROR]: missing quality for " + name2); m->mothurOutEndLine(); m->control_pressed = true; break; }
175                         
176                         //sanity check sequence length and number of quality scores match
177                         if (name2 != "") { if (name != name2) { m->mothurOut("[ERROR]: names do not match. read " + name + " for fasta and " + name2 + " for quality."); m->mothurOutEndLine(); m->control_pressed = true; break; } }
178                         if (qual.length() != sequence.length()) { m->mothurOut("[ERROR]: lengths do not match. read " + toString(sequence.length()) + " characters for fasta and " + toString(qual.length()) + " characters for quality scores."); m->mothurOutEndLine(); m->control_pressed = true; break; }
179                         
180                         //convert quality scores
181                         vector<int> qualScores = convertQual(qual);
182                         
183                         //print sequence info to files
184                         outFasta << ">" << name << endl << sequence << endl;
185                         
186                         outQual << ">" << name << endl;
187                         for (int i = 0; i < qualScores.size(); i++) { outQual << qualScores[i] << " "; }
188                         outQual << endl;
189                 }
190                 
191                 in.close();
192                 outFasta.close();
193                 outQual.close();
194                 
195                 if (m->control_pressed) { outputTypes.clear(); remove(fastaFile.c_str()); remove(qualFile.c_str()); return 0; }
196                 
197                 m->mothurOutEndLine();
198                 m->mothurOut("Output File Names: "); m->mothurOutEndLine();
199                 for (int i = 0; i < outputNames.size(); i++) {  m->mothurOut(outputNames[i]); m->mothurOutEndLine();    }
200                 m->mothurOutEndLine();
201
202                 return 0;
203         }
204         catch(exception& e) {
205                 m->errorOut(e, "ParseFastaQCommand", "execute");
206                 exit(1);
207         }
208 }
209 //**********************************************************************************************************************
210 vector<int> ParseFastaQCommand::convertQual(string qual) {
211         try {
212                 vector<int> qualScores;
213                 
214                 int controlChar = int('!');
215                 
216                 for (int i = 0; i < qual.length(); i++) { 
217                         int temp = int(qual[i]);
218                         temp -= controlChar;
219                         
220                         qualScores.push_back(temp);
221                 }
222                 
223                 return qualScores;
224         }
225         catch(exception& e) {
226                 m->errorOut(e, "ParseFastaQCommand", "convertQual");
227                 exit(1);
228         }
229 }
230 //**********************************************************************************************************************
231
232
233