root/gsdl/trunk/runtime-src/src/recpt/wizardaction.cpp @ 19062

Revision 19062, 23.5 KB (checked in by kjdon, 10 years ago)

all gdbm files (key, users, history, argdb) now use gdb extension instead of db

  • Property svn:keywords set to Author Date Id Revision
Line 
1/**********************************************************************
2 *
3 * wizardaction.cpp --
4 * Copyright (C) 2000  The New Zealand Digital Library Project
5 *
6 * A component of the Greenstone digital library software
7 * from the New Zealand Digital Library Project at the
8 * University of Waikato, New Zealand.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 *
24 *********************************************************************/
25
26#include "gsdl_modules_cfg.h"
27
28// note that the wizardaction relies on having direct access to a
29// collections configuration file. this breaks the separation between
30// receptionist and collection server and so is not suitable (at least
31// in its current form) for use when collection servers are separate
32// from the receptionist (e.g. when using the CORBA protocol).
33
34// following line required to get fstream.filedesc() on darwin (Mac OS X)
35#define _STREAM_COMPAT  1
36// required for utsname on solaris???
37#define _XOPEN_SOURCE 1
38#define _XOPEN_SOURCE_EXTENDED 1
39
40#include "wizardaction.h"
41#include "OIDtools.h"
42#include "fileutil.h"
43#include "cfgread.h"
44#include "gsdltools.h"
45#include "gsdltimes.h"
46#include "argdb.h"
47#include "cgiutils.h"
48#include <stdio.h>
49#include <fcntl.h>
50
51#if !defined (__WIN32__)
52#include <sys/utsname.h>
53#include <unistd.h>
54#endif
55
56wizardaction::wizardaction () {
57
58  recpt = NULL;
59  disabled = true;
60
61  macro_prefix = "";
62}
63
64wizardaction::~wizardaction () {
65}
66
67void wizardaction::configure (const text_t &key, const text_tarray &cfgline) {
68 
69  const text_t& action_name = get_action_name();
70
71  if ((key == action_name) && (cfgline.size() == 1) &&
72      (cfgline[0] == "true" || cfgline[0] == "on" || cfgline[0] == "enabled")) {
73    disabled = false;
74  } else {
75    // call the parent class to deal with the things which
76    // are not dealt with here
77    action::configure (key, cfgline);
78  }
79}
80
81
82bool wizardaction::init (ostream & /*logout*/) {
83
84  return set_gsdl_env_vars(gsdlhome);
85}
86
87
88void wizardaction::get_cgihead_info (cgiargsclass &/*args*/, recptprotolistclass * /*protos*/,
89                    response_t &response,text_t &response_data,
90                    ostream &/*logout*/) {
91  response = content;
92  response_data = "text/html";
93}
94
95
96bool wizardaction::check_cgiargs (cgiargsinfoclass &argsinfo, cgiargsclass &args,
97                     recptprotolistclass * /*protos*/, ostream &logout) {
98 
99  text_t current_page = args["p"];
100
101  if (current_page != "intro" &&
102      current_page != "bildframe1" && current_page != "new" && current_page != "select") {
103    // update arguments that were saved to the harddrive
104    text_tmap saved_args;
105   
106    // update the argdb database with any arguments that were set
107    // by previous page as denoted by prefix (eg. di1 or bc1)
108
109    cgiargsclass::const_iterator args_here = args.begin();
110    cgiargsclass::const_iterator args_end = args.end();
111
112    while (args_here != args_end) {
113      text_t args_name = (*args_here).first;
114     
115      int prefix_len = macro_prefix.size();
116     
117      text_t args_prefix = substr(args_name.begin(),args_name.begin()+prefix_len);
118     
119      if (args_prefix == macro_prefix) {
120    saved_args[args_name] = args[args_name];
121      }
122      ++args_here;
123    }
124     
125    text_t argfile = filename_cat(gsdlhome, "tmp", args[macro_prefix+"tmp"], "argdb.gdb");
126    argdb *args_on_disk = new argdb(argfile);
127    if (!args_on_disk->update_args(saved_args)) {
128      // error
129      logout << "wizardaction: argdb::update_args failed (" << argfile << ")\n";
130    }
131   
132    // update args from argdb
133    saved_args.erase(saved_args.begin(), saved_args.end());
134    if (!args_on_disk->get_args(saved_args)) {
135      // error
136      logout << "wizardaction: argdb::get_args failed (" << argfile << ")\n";
137    }
138    delete args_on_disk;
139   
140    text_tmap::iterator sa_here = saved_args.begin();
141    text_tmap::iterator sa_end = saved_args.end();
142    while (sa_here != sa_end) {
143      if (!(*sa_here).second.empty()) {
144    args[(*sa_here).first] = (*sa_here).second;
145      }
146      ++sa_here;
147    }  bool first = true;
148
149  }
150
151  return true;
152}
153
154// tests if collection is write protected (currently just checks if
155// collect.cfg file is writable
156bool wizardaction::collection_protected (const text_t &collection) {
157  text_t cfgfile = filename_cat(collecthome, collection, "etc", "collect.cfg");
158  if (file_writable(cfgfile)) return false;
159  return true;
160}
161
162// set the _statusline_ macro
163void wizardaction::set_statusline (displayclass &disp, cgiargsclass &args, ostream & /*logout*/) {
164
165  // the build command creates .bld.download, .bld.import, and .bld.build files (in that
166  // order) and deletes them (also in that order) when each stage is complete. the .bld
167  // file is the concatenation of all these files.
168  text_t bld_file = filename_cat (gsdlhome, "tmp", args[macro_prefix+"tmp"], args[macro_prefix+"dirname"] + ".bld");
169  text_t statusline;
170
171  if (file_exists (bld_file + ".download")) {
172    statusline = "_collector:textdownloadingfiles_<br>\n";
173    statusline += dm_safe(file_tail(bld_file + ".download", 1, 0));
174  } else if (file_exists (bld_file + ".import")) {
175    statusline = "_collector:textimportingcollection_<br>\n";
176    statusline += dm_safe(file_tail(bld_file + ".import", 1, 0));
177  } else if (file_exists (bld_file + ".build")) {
178    statusline = "_collector:textbuildingcollection_<br>\n";
179    statusline += dm_safe(file_tail(bld_file + ".build", 1, 0));
180  } else {
181    statusline += "_collector:textcreatingcollection_<br>\n";
182    statusline += dm_safe(file_tail(bld_file, 1, 0));
183  }
184
185  disp.setmacro ("statusline", "collector", statusline);
186  disp.setmacro ("statusline", "depositor", statusline);
187}
188
189
190// if sw = 0 replace all carriage returns in intext with the string "\n"
191// else replace all occurances of "\n" with a carriage return
192text_t wizardaction::carriage_replace (const text_t &intext, int sw) {
193   
194  text_t outtext;
195  text_t::const_iterator here = intext.begin();
196  text_t::const_iterator end = intext.end();
197  while (here != end) {
198    if (sw == 0) {
199      if (*here == '\n') {
200    if ((here+1) != end && *(here+1) == '\r') ++here;
201    outtext += "\\n";
202      } else if (*here == '\r') {
203    if ((here+1) != end && *(here+1) == '\n') ++here;
204    outtext += "\\n";
205      } else {
206    outtext.push_back (*here);
207      }
208    } else if (*here == '\\' && (here+1) != end && *(here+1) == 'n') {
209      outtext.push_back ('\n');
210      ++here;
211    } else {
212      outtext.push_back (*here);
213    }
214    ++here;
215  }
216  return outtext;
217}
218
219
220// create a short directory name from fullname
221text_t wizardaction::get_directory_name (const text_t &fullname) {
222
223  text_t shortname;
224  if (fullname.empty()) {
225    shortname = "coll";
226
227  } else {
228   
229    // first make all lowercase and remove any dodgy characters
230    // (i.e. anything not [a-z]
231    text_t::const_iterator here = fullname.begin();
232    text_t::const_iterator end = fullname.end();
233    while (here != end) {
234      if ((*here >= 'A' && *here <= 'Z') || (*here >= 'a' && *here <= 'z') ||
235      (*here == ' ')) {
236    if (*here >= 'A' && *here <= 'Z') shortname.push_back (*here+32);
237    else if (*here == ' ') {
238      while ((*(here+1)) == ' ') ++here;
239      shortname.push_back (*here);
240    } else shortname.push_back (*here);
241      }
242      ++here;
243    }
244
245    text_tarray words;
246    splitchar (shortname.begin(), shortname.end(), ' ', words);
247    int num_words = words.size();
248
249    if (num_words == 0) {
250      shortname = "coll";
251
252    } else {
253
254      shortname.clear();
255      int use_words = (num_words <= 6) ? num_words : 6;
256      unsigned int substr_len = 6 / use_words;
257     
258      for (int i = 0; i < use_words; ++i) {
259    if (words[i].size() < substr_len) shortname += words[i];
260    else shortname += substr (words[i].begin(), words[i].begin()+substr_len);
261      }
262    }
263  }
264
265  // check to see if shortname is unique
266  text_t fulldirname = filename_cat (collecthome, shortname);
267  if (directory_exists (fulldirname)) {
268    int version = 0;
269    text_t newname;
270    do {
271      ++version;
272      newname = shortname;
273      newname.push_back ('v');
274      newname.appendint (version);
275      fulldirname = filename_cat (collecthome, newname);
276    } while (directory_exists (fulldirname));
277
278    shortname = newname;
279  }
280 
281  return shortname;
282}
283
284// assigns a temporary directory name for this collector session
285// and creates temporary directory
286// returns false if it couldn't create the directory
287bool wizardaction::assign_tmpname (cgiargsclass &args, ostream &logout) {
288
289  int i = 0;
290  text_t tmpname = "tbuild";
291  while (directory_exists (filename_cat (gsdlhome, "tmp", tmpname + text_t(i)))) {
292    ++i;
293  }
294  tmpname.appendint (i);
295
296  text_t fulltmpdir = filename_cat (gsdlhome, "tmp", tmpname);
297  if (!mk_dir (fulltmpdir)) {
298    outconvertclass text_t2ascii;
299    logout << text_t2ascii << "wizardaction::assign_tmpname unable to create directory ("
300       << fulltmpdir << ")\n";
301    return false;
302  }
303
304  args[macro_prefix + "tmp"] = tmpname;
305  return true;
306}
307
308// set the _fullnamemenu_ macro (and _warnindex_ and _selectedindex_ if
309// we're on the "srce" page)
310void wizardaction::set_fullnamemenu (displayclass &disp, cgiargsclass &args,
311                    recptprotolistclass *protos, ostream &logout) {
312
313  if (recpt == NULL) {
314    logout << "ERROR (wizardaction::set_fullnamemenu): This action does not contain\n"
315       << "       information about any receptionists. The method set_receptionist was\n"
316       << "       probably not called from the module which instantiated this action.\n";
317    return;
318  }
319
320  text_t &current_page = args["p"];
321  text_t currentname = args[macro_prefix+"dirname"];
322  if (current_page == "srce") currentname = args[macro_prefix + "clonecol"];
323
324  text_tarray dirnames;
325  text_tarray fullnames;
326  vector<bool> write_protected;
327  text_tarray  build_type;
328
329  bool is_selected = false;
330  int selected_index = 0;
331  int index = 0;
332
333  recptprotolistclass::iterator rprotolist_here = protos->begin();
334  recptprotolistclass::iterator rprotolist_end = protos->end();
335  while (rprotolist_here != rprotolist_end) {
336    if ((*rprotolist_here).p != NULL) {
337
338      // don't include z39.50 collections
339      comerror_t err = noError;
340      if ((*rprotolist_here).p->get_protocol_name (err) == "z3950proto") {
341    ++rprotolist_here;
342    continue;
343      }
344
345      text_tarray collist;
346      (*rprotolist_here).p->get_collection_list (collist, err, logout);
347      if (err == noError) {
348    text_tarray::iterator collist_here = collist.begin();
349    text_tarray::iterator collist_end = collist.end();
350    while (collist_here != collist_end) {
351      ColInfoResponse_t *cinfo = recpt->get_collectinfo_ptr ((*rprotolist_here).p, *collist_here, logout);
352      if (cinfo != NULL) {
353        text_t collectionname = cinfo->get_collectionmeta("collectionname", args["l"]);
354        if (collectionname.empty()) {
355          collectionname = *collist_here;
356        }
357        dirnames.push_back(*collist_here);
358        fullnames.push_back(collectionname);
359        // check to see if the collection is writable
360        if (collection_protected (*collist_here)) write_protected.push_back(true);
361        else write_protected.push_back(false);
362
363        // remember build type for collection (mg, mgpp, lucene, ...)
364        // used to determine cgi arg 'ct' later on and minus option to 'build'
365        build_type.push_back(cinfo->buildType);
366
367        if (*collist_here == currentname) {
368          is_selected = true;
369          selected_index = index;       
370        }
371        ++index;
372      }
373      ++collist_here;
374    }
375      }
376    }
377    ++rprotolist_here;
378  }
379
380  bool first = true;
381
382  text_t warnindex;
383  text_t fullnamemenu = "<select name=\""+macro_prefix+"dirname\" onChange=\"menuchange();\">\n";
384  text_t buildtype_jsarray = "var buildtype = new Array(";
385
386  fullnamemenu += "<option value=\"\">_textselectoption_</option>\n";
387  buildtype_jsarray += "\"\" ";
388
389  for (int i = 0; i < index; ++i) {
390    // don't want write protected collections in list on "change existing
391    // collection" page
392    if (write_protected[i] && current_page == "existing") continue;
393    fullnamemenu += "<option value=\"" + dirnames[i] + "\"";
394    if (is_selected && i == selected_index) {
395      fullnamemenu += " selected";
396      ++selected_index;
397      is_selected = false;
398    }
399    fullnamemenu.push_back ('>');
400    fullnamemenu += fullnames[i] + " ("+dirnames[i]+")";
401    fullnamemenu.push_back ('\n');
402
403    buildtype_jsarray += ", \"" + build_type[i] + "\"";
404   
405    first = false;
406  }
407  fullnamemenu += "</select>\n";
408
409  buildtype_jsarray += ");";
410
411  text_t action_name = get_action_name();
412  disp.setmacro ("fullnamemenu", action_name, fullnamemenu);
413  disp.setmacro ("buildtypearray", action_name, buildtype_jsarray);
414}
415
416// checks to see if any of the plugins in pluginset occur in
417// collections configuration file
418bool wizardaction::uses_weird_plugin (const text_t &collection) {
419
420  text_tset pluginset;
421  pluginset.insert ("HBPlug");
422
423  text_t cfgfile_content;
424  text_t cfgfile_name = filename_cat (collecthome, collection, "etc", "collect.cfg");
425  text_t pluginstr, pluginname;
426
427  if (read_file (cfgfile_name, cfgfile_content)) {
428    text_t::const_iterator here = cfgfile_content.begin();
429    text_t::const_iterator end = cfgfile_content.end();
430    while (here != end) {
431      here = findchar (here, end, 'p');
432      if (here == end) break;
433      if ((here+6 < end) && (substr (here, here+6) == "plugin")) {
434    getdelimitstr (here+6, end, '\n', pluginstr);
435    text_t::const_iterator hp = pluginstr.begin();
436    text_t::const_iterator ep = pluginstr.end();
437    bool found = false;
438    // remove any leading whitespace, trailing options etc.
439    while (hp != ep) {
440      if (*hp == '\t' || *hp == ' ' || *hp == '\n') {
441        if (found) break;
442      } else {
443        pluginname.push_back (*hp);
444        found = true;
445      }
446      ++hp;
447    }
448    text_tset::const_iterator it = pluginset.find (pluginname);
449    if (it != pluginset.end()) return true; // found matching plugin
450    pluginname.clear();
451      }
452      ++here;
453    }
454  }
455  return false;
456}
457
458void wizardaction::gsdl_build (cgiargsclass &args, ostream &logout) {
459
460  outconvertclass text_t2ascii;
461
462  //check to see if the tbuild directory exists
463  text_t tmpdir = filename_cat (gsdlhome, "tmp", args[macro_prefix+"tmp"]);
464  if (!directory_exists (tmpdir)) {
465    message = "tmpfail";
466    return;
467  }
468 
469  //check to see if collection name specified
470  text_t &collection = args[macro_prefix+"dirname"];
471  if (collection.empty()) {
472    message = "nocollection";
473    return;
474  }
475
476  // check for a .build file - if it exists then we've already built
477  // the collection (or are in the process of building it)
478  text_t buildfile = filename_cat (tmpdir, ".build");
479  if (file_exists (buildfile)) {
480    return;
481  } else {
482    // create the .build file (this file is just a place holder to let any future
483    // pages know that we've already been here)
484    char *buildfilec = buildfile.getcstr();
485    ofstream bfile_out (buildfilec);
486    delete []buildfilec;
487    if (bfile_out) {
488      bfile_out << "collection building\n";
489      bfile_out.close();
490    } else {
491      message = "tmpfail";
492      return;
493    }
494  }
495
496  //FLAG!
497  const recptconf &rcinfo = recpt->get_configinfo ();
498
499  // create the event header file if LogEvents, EmailEvents or
500  // EmailUserEvents options are turned on.
501  bool logevents =
502    (rcinfo.LogEvents == CollectorEvents || rcinfo.LogEvents == AllEvents ||
503     rcinfo.EmailEvents == CollectorEvents || rcinfo.EmailEvents == AllEvents ||
504     rcinfo.EmailUserEvents);
505  text_t ehead_file = filename_cat (tmpdir, "ehead.txt");
506  if (logevents) {
507    if (!create_event_header_file (ehead_file, args, logout)) {
508      logevents = false;
509    }
510  }
511   
512  text_t collectdir = get_collectdir (args);
513
514  // set up build options
515  //text_t options = "-make_writable -remove_import -out \"";
516  text_t options = "-make_writable  -out \"";
517  options += filename_cat (tmpdir, collection + ".bld");
518  options += "\" -collectdir \"" + collectdir + "\" -statsfile \"";
519  options += filename_cat(collectdir, collection, "etc", "import.log") + "\"";
520
521  if (args[macro_prefix+"esrce"] == 1) {
522    // we're adding data to an existing collection
523    options += " -save_archives -append -manifest";
524  }
525
526  text_tarray inputvalues, inputtypes;
527  splitchar (args[macro_prefix+"input"].begin(), args[macro_prefix+"input"].end(), ',', inputvalues);
528  splitchar (args[macro_prefix+"inputtype"].begin(), args[macro_prefix+"inputtype"].end(), ',', inputtypes);
529  int numvalues = inputvalues.size();
530  int numtypes = inputtypes.size();
531  for (int i = 0; i < numvalues; ++i) {
532    if (!inputvalues[i].empty()) {
533      text_t type = "file://"; // default
534      if (i < numtypes) type = inputtypes[i];
535      options += " -download \"" +
536    remove_trailing_slashes(type + format_url(decode_commas(inputvalues[i]))) + "\"";
537    }
538  }
539
540  if (logevents) {
541    if (rcinfo.LogEvents == CollectorEvents || rcinfo.LogEvents == AllEvents)
542      options += " -log_events";
543    if (rcinfo.EmailEvents == CollectorEvents || rcinfo.EmailEvents == AllEvents) {
544      options += " -mail_server " + rcinfo.MailServer;
545      options += " -email_events " + rcinfo.maintainer;
546      if (rcinfo.EmailUserEvents) options += "," + args[macro_prefix+"contactemail"];
547    } else if (rcinfo.EmailUserEvents) {
548      options += " -mail_server " + rcinfo.MailServer;
549      options += " -email_events " + args[macro_prefix+"contactemail"];
550    }
551    options += " -event_header " + ehead_file;
552  }
553
554  text_t indextype = args[macro_prefix+"buildtype"];
555  if(indextype == "") {
556    indextype = "mg";
557  }
558  options += " -indextype \"" + indextype + "\"";
559
560  text_t optionfile = filename_cat (tmpdir, "build.opt");
561  char *optionfilec = optionfile.getcstr();
562  ofstream ofile_out (optionfilec);
563  delete []optionfilec;
564  if (!ofile_out) {
565    message = "tmpfail";
566    return;
567  }
568  ofile_out << text_t2ascii << options << "\n";
569  ofile_out.close();
570
571  // if we're altering an existing collection we need to kill off
572  // the existing collection server - we do this for the local library
573  // (and any other persistent version of the library) as the existing
574  // database file can't be deleted while the collection server holds it open
575  if ((args[macro_prefix+"econf"] == 1) || (args[macro_prefix+"esrce"] == 1)) {
576    remove_colservr (collection, logout);
577  }   
578
579  // set up the build command - build.bat has some issues with quoting
580  // on win2k when gsdlhome contains spaces so we'll avoid using
581  // "perl -S" here in favor of calling the "build" perl script explicitly
582  text_t build_cmd = "perl \"" + filename_cat (gsdlhome, "bin", "script", "build");
583  build_cmd += "\" -optionfile \"" + optionfile + "\" " + collection;
584
585  // run build command in background (i.e. asynchronously)
586  gsdl_system (build_cmd, false, logout);
587
588}
589
590void wizardaction::gsdl_cancel_build (cgiargsclass &args, ostream &logout) {
591  // I really wanted to do what this perl script does from within the library
592  // c++ code. I ran into some problems though (like how do you write a portable
593  // "rm -r" in c++?). One day I'll spend some time sorting it out ... maybe.
594  text_t cancel_cmd = "perl -S cancel_build.pl -collectdir \"";
595  cancel_cmd += filename_cat (gsdlhome, "tmp", args[macro_prefix+"tmp"]) + "\" ";
596  cancel_cmd += args[macro_prefix+"dirname"];
597  // To be on the safe side we'll make this a synchronous call
598  // so that all tidying up is done before the user has a chance
599  // to do anything else (like start rebuilding their collection).
600  // This means that for a big collection where there's lots of
601  // stuff to delete etc. it might take a while before the "build
602  // cancelled" page appears.
603  gsdl_system (cancel_cmd, true, logout);
604}
605
606text_t wizardaction::get_collectdir (cgiargsclass &args)
607{
608  if ((args[macro_prefix+"econf"] == 1) || (args[macro_prefix+"esrce"] == 1)) {
609    // we're adding to a collection in place
610    return collecthome;
611  }
612  else {
613    return filename_cat (gsdlhome, "tmp", args[macro_prefix+"tmp"]);
614  }
615}
616
617// create and initialize a new collection server and
618// add it to the null protocol.
619void wizardaction::create_colserver (const text_t &collection, ostream &logout) {
620
621  recptprotolistclass *protos = recpt->get_recptprotolist_ptr();
622  recptprotolistclass::iterator rprotolist_here = protos->begin();
623  recptprotolistclass::iterator rprotolist_end = protos->end();
624  while (rprotolist_here != rprotolist_end) {
625    comerror_t err = noError;
626    if ((*rprotolist_here).p != NULL) {
627      if ((*rprotolist_here).p->get_protocol_name (err) == "nullproto") {
628    // create collection server and add it to nullproto
629    (*rprotolist_here).p->add_collection (collection, recpt, gsdlhome, collecthome, dbhome);
630    // make sure gsdlhome is configured
631    text_tarray tmp;
632    tmp.push_back (gsdlhome);
633    (*rprotolist_here).p->configure ("gsdlhome", tmp, err);
634    // re-initialize the null protocol
635    if (!(*rprotolist_here).p->init (err, logout)) {
636      logout << "wizardaction::create_colserver: nullproto init failed\n";
637    }
638    return;
639      }
640    }
641    ++rprotolist_here;
642  }
643
644  logout << "wizardaction::create_colserver: no valid nullproto found\n";
645}
646
647// delete a collection server from the null protocol
648void wizardaction::remove_colservr (const text_t &collection, ostream &logout) {
649
650  recpt->uncache_collection (collection);
651
652  recptprotolistclass *protos = recpt->get_recptprotolist_ptr();
653  recptprotolistclass::iterator rprotolist_here = protos->begin();
654  recptprotolistclass::iterator rprotolist_end = protos->end();
655  while (rprotolist_here != rprotolist_end) {
656    comerror_t err = noError;
657    if ((*rprotolist_here).p != NULL) {
658      if ((*rprotolist_here).p->get_protocol_name (err) == "nullproto") {
659    (*rprotolist_here).p->remove_collection (collection, logout);
660    return;
661      }
662    }
663    ++rprotolist_here;
664  }
665
666  logout << "wizardaction::create_colserver: no valid nullproto found\n";
667}
668
669bool wizardaction::create_event_header_file (const text_t &filename, cgiargsclass &args,
670                        ostream &logout) {
671
672  outconvertclass text_t2ascii;
673  char *filenamec = filename.getcstr();
674  ofstream eheadfile (filenamec);
675  delete []filenamec;
676
677  if (eheadfile) {
678    eheadfile << text_t2ascii << get_event_header (args);
679    eheadfile.close();
680    return true;
681  }
682   
683  logout << text_t2ascii << "wizardaction::create_event_header ERROR: Couldn't create "
684     << "Event Header file " << filename << ". Event logging disabled\n";
685  return false;
686}
687
688text_t wizardaction::get_event_header (cgiargsclass &args) {
689  text_t header = "Greenstone Username: " + args["un"] + "\n";
690  header += "Collection: " + args[macro_prefix+"dirname"] + "\n";
691  header += "Collection Creator: " + args[macro_prefix+"contactemail"] + "\n";
692  header += "GSDLHOME: " + gsdlhome + "\n";
693  header += "Build Location: " + get_collectdir(args) + "\n";
694
695  return header;
696}
697
698
699// format_url simply strips "http://", "ftp://", or "file://" off the
700// beginning of url if they're there
701text_t wizardaction::format_url (const text_t &url) {
702  text_t::const_iterator begin = url.begin();
703  text_t::const_iterator end = url.end();
704
705  if (url.size() >= 7) {
706    text_t prefix = substr(begin, begin+7);
707    if (prefix == "http://" || prefix == "file://") {
708      return substr(begin+7, end);
709    }
710  }
711  if (url.size() >= 6) {
712    if (substr(begin, begin+6) == "ftp://") {
713      return substr(begin+6, end);
714    }
715  }
716  return url;
717}
718
719text_t wizardaction::remove_trailing_slashes (text_t str) {
720
721  while (*(str.end()-1) == '\\') {
722    str.pop_back();
723  }
724  return str;
725}
726
Note: See TracBrowser for help on using the browser.