/********************************************************************** * * cgiargs.cpp -- * Copyright (C) 1999 The New Zealand Digital Library Project * * A component of the Greenstone digital library software * from the New Zealand Digital Library Project at the * University of Waikato, New Zealand. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * *********************************************************************/ #include "cgiargs.h" #include "gsdlunicode.h" void cgiarg_t::clear () { value.clear(); source = program_arg; } cgiarg_t &cgiarg_t::operator=(const cgiarg_t &x) { value=x.value; source=x.source; return *this; } bool operator==(const cgiarg_t &x, const cgiarg_t &y) { return ((x.value == y.value) && (x.source == y.source)); } bool operator<(const cgiarg_t &x, const cgiarg_t &y) { return ((x.value < y.value) || ((x.value == y.value) && (x.source == y.source))); } // constructors cgiargsclass::cgiargsclass () { } // this returns NULL if there isn't an entry with a value of // 'key' already defined void cgiargsclass::setarg (const text_t &key, const text_t &value, cgiarg_t::source_t source) { cgiarg_t temparg; temparg.value = value; temparg.source = source; args[key] = temparg; } void cgiargsclass::setdefaultarg (const text_t &key, const text_t &value, cgiarg_t::source_t source) { if (getarg(key) == NULL) setarg (key, value, source); } void cgiargsclass::setintarg (const text_t &key, int value, cgiarg_t::source_t source) { setarg (key, value, source); } void cgiargsclass::setdefaultintarg (const text_t &key, int value, cgiarg_t::source_t source) { if (getarg(key) == NULL) setintarg (key, value, source); } void cgiargsclass::setcarg (const text_t &key, unsigned short c, cgiarg_t::source_t source) { text_t t; t.push_back(c); setarg(key,t, source); } void cgiargsclass::setdefaultcarg (const text_t &key, unsigned short c, cgiarg_t::source_t source) { if (getarg(key) == NULL) setcarg (key, c, source); } text_t *cgiargsclass::getarg (const text_t &key) { iterator here = args.find (key); if (here == args.end()) return NULL; return &((*here).second.value); } int cgiargsclass::getintarg (const text_t &key) { text_t *text = getarg (key); if (text == NULL) return 0; return text->getint(); } // stream operators to print cgi arguments for debugging purposes ostream &operator<<(ostream &outs, const cgiargsclass &args) { utf8outconvertclass text_t2utf8; cgiargsclass::const_iterator here = args.begin (); cgiargsclass::const_iterator end = args.end (); outs << "*** cgiargsclass\n"; while (here != end) { outs << text_t2utf8 << " \"" << (*here).first << "\"=\"" << (*here).second.value << "\"\n"; here++; } outs << "\n"; return outs; } cgiarginfo::cgiarginfo () { multiplechar = false; multiplevalue = false; defaultstatus = weak; argdefault.clear(); savedarginfo = can; } bool operator==(const cgiarginfo &x, const cgiarginfo &y) { return ((x.shortname == y.shortname) && (x.longname == y.longname) && (x.multiplechar == y.multiplechar) && (x.multiplevalue == y.multiplevalue) && (x.defaultstatus == y.defaultstatus) && (x.argdefault == y.argdefault) && (x.savedarginfo == y.savedarginfo)); } bool operator<(const cgiarginfo &x, const cgiarginfo &y) { return ((x.shortname < y.shortname) || ((x.shortname == y.shortname) && ((x.longname < y.longname) || ((x.longname == y.longname) && ((x.multiplevalue < y.multiplevalue) || ((x.multiplevalue == y.multiplevalue) && ((x.multiplechar < y.multiplechar) || ((x.multiplechar == y.multiplechar) && ((x.defaultstatus < y.defaultstatus) || ((x.defaultstatus == y.defaultstatus) && ((x.argdefault < y.argdefault) || ((x.argdefault == y.argdefault) && ((x.savedarginfo < y.savedarginfo)))))))))))))); } // constructor cgiargsinfoclass::cgiargsinfoclass () { } // addarginfo will combine the information with the present // information. If name clashes were detected then the information // will be written to logout and addarginfo will return false. No // processing with the arguments should be done if this happens // as the results will be meaningless. bool cgiargsinfoclass::addarginfo (ostream *logout, const cgiarginfo &info) { outconvertclass text_t2ascii; cgiarginfo *orginfo = getarginfo (info.shortname); if (orginfo == NULL) { argsinfo[info.shortname] = info; return true; // no clashes } if (orginfo->longname != info.longname) { if (logout != NULL) { (*logout) << text_t2ascii << "Error: cgi argument name clash for argument \"" << info.shortname << "\".\nOne long name was\n \"" << orginfo->longname << "\"\nand the other was\n \"" << info.longname << "\".\n\n"; } return false; // found a clash } if (orginfo->multiplevalue != info.multiplevalue) { if (logout != NULL) { (*logout) << text_t2ascii << "Error: cgi argument \"" << info.shortname << "\" was given as being a single value option\n" << "and a multiple value option.\n\n"; } return false; // found a clash } if (orginfo->multiplechar != info.multiplechar) { if (logout != NULL) { (*logout) << text_t2ascii << "Error: cgi argument \"" << info.shortname << "\" was given as being a single character option\n" << "and a multiple character option.\n\n"; } return false; // found a clash } if (!info.multiplechar && info.argdefault.size() > 1) { if (logout != NULL) { (*logout) << text_t2ascii << "Error: cgi argument \"" << info.shortname << "\" was defined as being a single character option\n" << "but a multiple character default was given.\n\n"; } return false; // found a problem } // make sure there is no clashes in the savedarginfo if ((orginfo->savedarginfo==cgiarginfo::mustnot && info.savedarginfo==cgiarginfo::must) || (orginfo->savedarginfo==cgiarginfo::must && info.savedarginfo==cgiarginfo::mustnot)) { if (logout != NULL) { (*logout) << text_t2ascii << "Error: it was specified that cgi argument \"" << info.shortname << "\" should be saved in the state\n" << "information and that it should not be save in the state information.\n\n"; } return false; // found a clash } // the only time orginfo->savedarginfo can change is when it is set // to "can" if (orginfo->savedarginfo == cgiarginfo::can) orginfo->savedarginfo = info.savedarginfo; if (orginfo->defaultstatus > info.defaultstatus) { return true; } orginfo->defaultstatus = info.defaultstatus; orginfo->argdefault = info.argdefault; return true; } bool cgiargsinfoclass::addarginfo (ostream *logout, const cgiargsinfoclass &info) { const_iterator here = info.begin (); const_iterator end = info.end (); while (here != end) { if (!addarginfo (logout, (*here).second)) return false; here++; } return true; // made it, no clashes } cgiarginfo *cgiargsinfoclass::getarginfo (const text_t &key) { iterator here = argsinfo.find (key); if (here == argsinfo.end()) return NULL; return &((*here).second); } const cgiarginfo *cgiargsinfoclass::getarginfo (const text_t &key) const { const_iterator here = argsinfo.find (key); if (here == argsinfo.end()) return NULL; return &((*here).second); }