| 1 | #include <stdio.h> |
|---|
| 2 | #include <stdlib.h> |
|---|
| 3 | #include <string.h> |
|---|
| 4 | // #include <malloc.h> |
|---|
| 5 | |
|---|
| 6 | char *TRS_map_file(const char *path,int writeable); |
|---|
| 7 | #define GB_map_file TRS_map_file |
|---|
| 8 | # include <cat_tree.hxx> |
|---|
| 9 | #undef GB_map_file |
|---|
| 10 | |
|---|
| 11 | #include "tree_lib.hxx" |
|---|
| 12 | #include "trs_proto.h" |
|---|
| 13 | |
|---|
| 14 | static void quit_with_error(char *error) __ATTR__NORETURN; |
|---|
| 15 | static void quit_with_error(char *error) { |
|---|
| 16 | fprintf(stdout,"%s\n",error); |
|---|
| 17 | exit(-1); |
|---|
| 18 | } |
|---|
| 19 | |
|---|
| 20 | static char *get_indata(int argc, char **argv) { |
|---|
| 21 | char *indata = 0; |
|---|
| 22 | char *request_method; |
|---|
| 23 | |
|---|
| 24 | request_method = getenv("REQUEST_METHOD"); |
|---|
| 25 | // GET means: contents are in variable QUERY_STRING |
|---|
| 26 | |
|---|
| 27 | if (request_method && argc<=1){ |
|---|
| 28 | printf("Content-type: text/html\n\n"); |
|---|
| 29 | if (!strcmp(request_method,"GET")) { |
|---|
| 30 | indata=strdup(getenv("QUERY_STRING")); |
|---|
| 31 | } else if (!strcmp(request_method,"POST")) { |
|---|
| 32 | char *temp; |
|---|
| 33 | if(!(temp=getenv("CONTENT_LENGTH"))) |
|---|
| 34 | quit_with_error(TRS_export_error("CONTENT_LENGTH not set")); |
|---|
| 35 | int len=atoi(temp); |
|---|
| 36 | indata=new char[len+1]; |
|---|
| 37 | indata[len]=0; |
|---|
| 38 | fread(indata,len,1,stdin); |
|---|
| 39 | } |
|---|
| 40 | } else { // read the command line |
|---|
| 41 | if (argc>1){ |
|---|
| 42 | indata = strdup(argv[1]); |
|---|
| 43 | }else{ |
|---|
| 44 | indata = 0; |
|---|
| 45 | } |
|---|
| 46 | } |
|---|
| 47 | |
|---|
| 48 | return indata; |
|---|
| 49 | } |
|---|
| 50 | |
|---|
| 51 | |
|---|
| 52 | static long convert_cgi_to_hash(char *indata){ // destroys indata |
|---|
| 53 | long hash = TRS_create_hash(10); |
|---|
| 54 | char *p; |
|---|
| 55 | for (p = strtok(indata,"&");p; p = strtok(0,"&")){ |
|---|
| 56 | char *out = strdup(p); |
|---|
| 57 | int i,j=0; |
|---|
| 58 | for ( i=0;p[i];i++ ){ |
|---|
| 59 | if (p[i]=='+'){ |
|---|
| 60 | out[j++] = ' '; |
|---|
| 61 | continue; |
|---|
| 62 | } |
|---|
| 63 | if (p[i] == '%'){ |
|---|
| 64 | int ch; |
|---|
| 65 | int save = p[i+3]; |
|---|
| 66 | p[i+3] = 0; |
|---|
| 67 | sscanf(p+i+1,"%x", &ch); |
|---|
| 68 | p[i+3] = save; |
|---|
| 69 | out[j++] = ch; |
|---|
| 70 | i+=2; |
|---|
| 71 | }else{ |
|---|
| 72 | out[j++] = p[i]; |
|---|
| 73 | } |
|---|
| 74 | } |
|---|
| 75 | out[j] = 0; |
|---|
| 76 | |
|---|
| 77 | char *eq = strchr(out,'='); |
|---|
| 78 | if (!eq) continue; |
|---|
| 79 | *(eq) = 0; |
|---|
| 80 | TRS_write_hash(hash,out,(long)(eq+1)); |
|---|
| 81 | } |
|---|
| 82 | return hash; |
|---|
| 83 | } |
|---|
| 84 | |
|---|
| 85 | /* |
|---|
| 86 | static long trs_show_hash(char *key,long val){ |
|---|
| 87 | printf("%s:%s\n",key,(char *)val); |
|---|
| 88 | return val; |
|---|
| 89 | } |
|---|
| 90 | */ |
|---|
| 91 | |
|---|
| 92 | int main(int argc, char **argv){ |
|---|
| 93 | char *data = get_indata(argc,argv); |
|---|
| 94 | char *error = 0; |
|---|
| 95 | if (!data){ |
|---|
| 96 | fprintf(stderr, |
|---|
| 97 | "Syntax: %s tree_name=xxx&tree_dir=yyyy&\n" |
|---|
| 98 | " query=tree get the tree structure of yyyy/xxxx.otb\n" |
|---|
| 99 | " query=branch_lengths get the branch lengths\n" |
|---|
| 100 | " query=node_names node Names\n" |
|---|
| 101 | " query=full_name1 First word of fullname\n" |
|---|
| 102 | " query=full_name2 Rest of fullname\n" |
|---|
| 103 | " getnames=RRRRR Get the names of the selected species\n" |
|---|
| 104 | " RRRR is genareted by the TrsTree\n" |
|---|
| 105 | " getnode=RRRRR Gets the name of the deepest nodes which\n" |
|---|
| 106 | " contains all selected\n" |
|---|
| 107 | " getfullnames=RRRRR Get the fullnames seperated by ####\n" |
|---|
| 108 | " getaccession=RRR Get the accession numbers \n" |
|---|
| 109 | " toOTF=name Translate stdin Lines like 'name#+#value' into otf\n" |
|---|
| 110 | " toOTF=fullname Translate stdin Lines like 'fullname#+#value' into otf\n" |
|---|
| 111 | " toOTF=accession Translate stdin Lines like 'accession#+#value' into otf\n" |
|---|
| 112 | "\n" |
|---|
| 113 | " toSelection=name Translate stdin Lines like 'name#+#' into compressed selection string\n" |
|---|
| 114 | " toSelection=fullname Translate stdin Lines like 'fullname#+#' into compressed selection string\n" |
|---|
| 115 | " toSelection=accession Translate stdin Lines like 'accession#+#' into compressed selection string\n" |
|---|
| 116 | "\n" |
|---|
| 117 | " toNewick=modified nodes Translate OTB format to newick, modified nodes comes from TrsTree\n" |
|---|
| 118 | " [stripNewick=grouped_nodes] Replace all grouped nodes by [GROUP=sizeofgroup]'name'\n" |
|---|
| 119 | " [prune=selected_nodes] Remove all nodes but selected, selected are from TrsTree\n" |
|---|
| 120 | ,argv[0]); |
|---|
| 121 | exit(0); |
|---|
| 122 | } |
|---|
| 123 | |
|---|
| 124 | |
|---|
| 125 | |
|---|
| 126 | long hash = convert_cgi_to_hash(strdup(data)); |
|---|
| 127 | //TRS_hash_do_loop(hash, trs_show_hash); |
|---|
| 128 | |
|---|
| 129 | char *tree_name = (char *)TRS_read_hash(hash,"tree_name"); |
|---|
| 130 | if (!tree_name){ |
|---|
| 131 | quit_with_error(TRS_export_error("No Parameter 'tree_name' found: '%s'",data)); |
|---|
| 132 | } |
|---|
| 133 | const char *tree_dir = (const char *)TRS_read_hash(hash,"tree_dir"); |
|---|
| 134 | if (!tree_dir) tree_dir = "."; |
|---|
| 135 | char *tree_path = (char *)calloc(strlen(tree_dir) + strlen(tree_name) + 10,1); // Look in ../irs_lib/%s.otb |
|---|
| 136 | sprintf(tree_path,"%s/%s.otb",tree_dir, tree_name); |
|---|
| 137 | |
|---|
| 138 | char *query = (char *)TRS_read_hash(hash,"query"); |
|---|
| 139 | if (query){ |
|---|
| 140 | if (!strcmp(query,"tree")){ |
|---|
| 141 | error = T2J_send_bit_coded_tree(tree_path,stdout); |
|---|
| 142 | }else if (!strcmp(query,"branch_lengths")){ |
|---|
| 143 | error = T2J_send_branch_lengths(tree_path,stdout); |
|---|
| 144 | }else if (!strcmp(query,"node_names")){ |
|---|
| 145 | error = T2J_transfer_group_names(tree_path,stdout); |
|---|
| 146 | }else if (!strcmp(query,"full_name1")){ |
|---|
| 147 | error = T2J_transfer_fullnames1(tree_path,stdout); |
|---|
| 148 | }else if (!strcmp(query,"full_name2")){ |
|---|
| 149 | error = T2J_transfer_fullnames2(tree_path,stdout); |
|---|
| 150 | } |
|---|
| 151 | } |
|---|
| 152 | |
|---|
| 153 | char *get_names = (char *)TRS_read_hash(hash,"getnames"); |
|---|
| 154 | if (!error && get_names){ |
|---|
| 155 | double relgroup; |
|---|
| 156 | char *selection = T2J_get_selection(tree_path,get_names,"",1,CAT_FIELD_NAME,0,0,&relgroup); |
|---|
| 157 | if (!selection) error = TRS_get_error(); |
|---|
| 158 | else printf("%s\n",selection); |
|---|
| 159 | } |
|---|
| 160 | char *get_fullnames = (char *)TRS_read_hash(hash,"getfullnames"); |
|---|
| 161 | if (!error && get_fullnames){ |
|---|
| 162 | double relgroup; |
|---|
| 163 | char *selection = T2J_get_selection(tree_path,get_fullnames,"",1,CAT_FIELD_FULL_NAME,0,0,&relgroup); |
|---|
| 164 | if (!selection) error = TRS_get_error(); |
|---|
| 165 | else printf("%s\n",selection); |
|---|
| 166 | } |
|---|
| 167 | |
|---|
| 168 | char *get_acc = (char *)TRS_read_hash(hash,"getaccession"); |
|---|
| 169 | if (!error && get_acc){ |
|---|
| 170 | double relgroup; |
|---|
| 171 | char *selection = T2J_get_selection(tree_path,get_acc,"",1,CAT_FIELD_ACC,0,0,&relgroup); |
|---|
| 172 | if (!selection) error = TRS_get_error(); |
|---|
| 173 | else printf("%s\n",selection); |
|---|
| 174 | } |
|---|
| 175 | |
|---|
| 176 | char *get_node = (char *)TRS_read_hash(hash,"getnode"); |
|---|
| 177 | if (!error && get_node){ |
|---|
| 178 | CAT_node_id focus; |
|---|
| 179 | char *nodename = 0; |
|---|
| 180 | double relgroup; |
|---|
| 181 | char *selection = T2J_get_selection(tree_path,get_node,"",1,CAT_FIELD_ACC,&focus,&nodename,&relgroup); |
|---|
| 182 | if (!selection) error = TRS_get_error(); |
|---|
| 183 | else printf("%s:%G\n",nodename,relgroup); |
|---|
| 184 | } |
|---|
| 185 | int otf = 1; |
|---|
| 186 | char *toOTF = (char *)TRS_read_hash(hash,"toOTF"); |
|---|
| 187 | if (! toOTF){ |
|---|
| 188 | otf = 0; // not otf format |
|---|
| 189 | toOTF = (char *)TRS_read_hash(hash,"toSelection"); |
|---|
| 190 | } |
|---|
| 191 | if (!error && toOTF){ |
|---|
| 192 | CAT_FIELDS catfield; |
|---|
| 193 | if (!strcmp(toOTF,"name")) catfield = CAT_FIELD_NAME; |
|---|
| 194 | else if (!strcmp(toOTF,"fullname")) catfield = CAT_FIELD_FULL_NAME; |
|---|
| 195 | else if (!strcmp(toOTF,"accession")) catfield = CAT_FIELD_ACC; |
|---|
| 196 | else { |
|---|
| 197 | error = TRS_export_error("Sorry: invalid toOTF Value:\n" |
|---|
| 198 | " only name,fullname,accession is allowed"); |
|---|
| 199 | goto end; |
|---|
| 200 | } |
|---|
| 201 | char *dat = TRS_read_file("-"); |
|---|
| 202 | struct T2J_transfer_struct *transfer = T2J_read_query_result_from_data(dat,catfield); |
|---|
| 203 | if (!transfer){ |
|---|
| 204 | error = TRS_get_error(); |
|---|
| 205 | goto end; |
|---|
| 206 | } |
|---|
| 207 | if ( otf != 0 ){ |
|---|
| 208 | error = T2J_transform(1,tree_path,transfer,0,stdout); |
|---|
| 209 | }else{ |
|---|
| 210 | error = T2J_transform(0,tree_path,transfer,0,stdout); |
|---|
| 211 | } |
|---|
| 212 | } |
|---|
| 213 | { |
|---|
| 214 | char *toNewick = (char *)TRS_read_hash(hash,"toNewick"); |
|---|
| 215 | if (!error && toNewick){ |
|---|
| 216 | char *stripNewick = (char *)TRS_read_hash(hash,"stripNewick"); |
|---|
| 217 | char *prune = (char *)TRS_read_hash(hash,"prune"); |
|---|
| 218 | error = T2J_send_newick_tree(tree_path,toNewick,prune,stripNewick,stdout); |
|---|
| 219 | } |
|---|
| 220 | } |
|---|
| 221 | |
|---|
| 222 | end: |
|---|
| 223 | if (error) { |
|---|
| 224 | quit_with_error(error); |
|---|
| 225 | } |
|---|
| 226 | return 0; |
|---|
| 227 | } |
|---|