diff --git a/.gitignore b/.gitignore new file mode 100644 index 00000000..3efef7f1 --- /dev/null +++ b/.gitignore @@ -0,0 +1,9 @@ +.DS_Store +.DS_Store? +._* +.Spotlight-V100 +.Trashes +Icon? +ehthumbs.db +Thumbs.db + diff --git a/DocDB/cgi/AddFiles b/DocDB/cgi/AddFiles index 9d4e17d6..f1d2d311 100755 --- a/DocDB/cgi/AddFiles +++ b/DocDB/cgi/AddFiles @@ -8,7 +8,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -27,6 +27,7 @@ use Benchmark; use CGI; +use CGI::Untaint; use DBI; $StartTime = new Benchmark; @@ -40,6 +41,7 @@ require "MiscSQL.pm"; require "FSUtilities.pm"; require "WebUtilities.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "FileUtilities.pm"; require "Security.pm"; @@ -61,7 +63,7 @@ $dbh = DBI -> connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rwuser,$db_rwpass ### Set up, give user initial information -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("$Project File Addition Results","File Addition Results"); @@ -73,12 +75,12 @@ print $query -> header( -charset => $HTTP_ENCODING ); ### Get document and revision ID -my $DocumentID = $params{docid}; -my $Version = $params{version}; -my $Replace = $params{replace}; -my $MaxFiles = $params{maxfiles}; -my $SubmitAgree = $params{submitagree}; -my $PreserveSigs = $params{preservesigs}; +my $DocumentID = $Untaint -> extract(-as_integer => "docid") || 0; +my $Version = $Untaint -> extract(-as_integer => "version") || 0; +my $Replace = $Untaint -> extract(-as_printable => "replace") || ""; +my $MaxFiles = $Untaint -> extract(-as_integer => "maxfiles") || 0; +my $SubmitAgree = $Untaint -> extract(-as_printable => "submitagree") || ""; +my $PreserveSigs = $Untaint -> extract(-as_printable => "preservesigs") || ""; my $DocRevID; @@ -86,20 +88,17 @@ my $DocRevID; if ($DocumentID && $Version) { $DocRevID = &FetchRevisionByDocumentAndVersion($DocumentID,$Version); - unless ($DocRevID) { - push @ErrorStack,"No such document exists."; - } - unless (&CanModify($DocumentID,$Version)) { - push @ErrorStack,"You are not authorized to modify this document."; + unless ($DocRevID && CanModify($DocumentID,$Version)) { + push @ErrorStack,"You are not authorized to modify this document or it does not exist."; } } else { push @ErrorStack,"You must supply document and version numbers to add files."; } if ($Preferences{Options}{SubmitAgree} && !$SubmitAgree) { - push @ErrorStack,'You must check the box near with this statement:
'. + push @ErrorStack,'You must check the box near with this statement: \n'. $Preferences{Options}{SubmitAgree}. - '
to add files to the document.'; + '\nto add files to the document.'; } if ($PreserveSigs && !CanPreserveSigs()) { @@ -110,6 +109,8 @@ if ($PreserveSigs && !CanPreserveSigs()) { my $UpdateLink = $DocumentAddForm."?mode=update&docid=$DocumentID"; # Fill in file hash +my $HttpUser = $Untaint -> extract(-as_printable => "http_user") || ""; +my $HttpPass = $Untaint -> extract(-as_printable => "http_pass") || ""; my %Files = (); my $NeedURLs = 0; @@ -117,9 +118,13 @@ my $AddNewFile = 0; for (my $i = 1; $i<= $MaxFiles; ++$i) { my $Key = $i; # Probably something better later - if ($params{"upload$i"}) { + my $UploadI = $query -> param("upload$i"); + my $UrlI = $Untaint -> extract(-as_printable => "url$i") || ""; + my $MainI = $Untaint -> extract(-as_printable => "main$i") || ""; + my $DescriptionI = $Untaint -> extract(-as_safehtml => "filedesc$i") || ""; + if ($UploadI) { $AddNewFile = 1; - $Files{$Key}{File} = $query -> param("upload$i"); + $Files{$Key}{File} = $UploadI; if (&ExistsUpload($DocRevID,$Files{$Key}{File})) { if ($Replace) { push @WarnStack,"The file $short_file already existed and has been @@ -131,12 +136,12 @@ for (my $i = 1; $i<= $MaxFiles; ++$i) { document, not add files."; } } - } elsif ($params{"url$i"}) { + } elsif ($UrlI) { $NeedURLs = 1; $AddNewFile = 1; - $Files{$Key}{URL} = $params{"url$i"}; - $Files{$Key}{User} = $params{http_user}; - $Files{$Key}{Pass} = $params{http_pass}; + $Files{$Key}{URL} = $UrlI; + $Files{$Key}{User} = $HttpUser; + $Files{$Key}{Pass} = $HttpPass; if (&ExistsURL($DocRevID,$Files{$Key}{URL})) { if ($Replace) { push @WarnStack,"The file $short_file already existed and has been @@ -150,13 +155,13 @@ for (my $i = 1; $i<= $MaxFiles; ++$i) { } } - if ($params{"main$i"}) { + if ($MainI) { $Files{$Key}{Main} = 1; } else { $Files{$Key}{Main} = 0; } - $Files{$Key}{Description} = $params{"filedesc$i"}; + $Files{$Key}{Description} = $DescriptionI; } unless ($AddNewFile) { diff --git a/DocDB/cgi/AddFilesForm b/DocDB/cgi/AddFilesForm index b05abade..991469e1 100755 --- a/DocDB/cgi/AddFilesForm +++ b/DocDB/cgi/AddFilesForm @@ -9,7 +9,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -27,6 +27,7 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI qw(-nosticky); +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -45,20 +46,21 @@ require "FileHTML.pm"; require "Cookies.pm"; require "Defaults.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "Scripts.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); &GetSecurityGroups; &GetPrefsCookie; -%params = $query -> Vars; - -$DocumentID = $params{docid}; -$Upload = $params{upload}; -$NumberUploads = $params{numfile}; -#$Version done later +my $DocumentID = $Untaint -> extract(-as_integer => "docid") || 0; +my $Upload = $Untaint -> extract(-as_safehtml => "upload") || undef; +my $NumberUploads = $Untaint -> extract(-as_integer => "numfile") || 0; # Global since not passed (oversight) +my $InputVersion = $Untaint -> extract(-as_integer => "version") || undef; # Set defaults @@ -76,11 +78,11 @@ unless ($DocumentID) { &FetchDocument($DocumentID); -if ($params{version} eq "0") { +if ($InputVersion eq "0") { $Version = 0; } else { - if ($params{version}) { - $Version = $params{version}; + if ($InputVersion) { + $Version = $InputVersion; } else { $Version = $Documents{$DocumentID}{NVersions}; } diff --git a/DocDB/cgi/AdministerElements.pm b/DocDB/cgi/AdministerElements.pm index 2d8eaef1..ab523199 100644 --- a/DocDB/cgi/AdministerElements.pm +++ b/DocDB/cgi/AdministerElements.pm @@ -1,5 +1,5 @@ # Name: $RCSfile$ -# Description: Various routines which supply input forms for adminstrative +# Description: Various routines which supply input forms for administrative # functions # # Revision: $Revision$ @@ -7,7 +7,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/AdministerForm b/DocDB/cgi/AdministerForm index 727d7b96..f9f53a83 100755 --- a/DocDB/cgi/AdministerForm +++ b/DocDB/cgi/AdministerForm @@ -9,7 +9,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -49,9 +49,11 @@ require "MiscSQL.pm"; require "ResponseElements.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "Sorts.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI -> connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); &GetSecurityGroups; diff --git a/DocDB/cgi/AdministerHome b/DocDB/cgi/AdministerHome index f2036d1a..96400731 100755 --- a/DocDB/cgi/AdministerHome +++ b/DocDB/cgi/AdministerHome @@ -1,9 +1,12 @@ #! /usr/bin/env perl # +# Name: AdministerHome +# Description: A "home page" for the various administration pages +# # Author: Lynn Garren (garren@fnal.gov) # Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -30,13 +33,12 @@ require "Scripts.pm"; require "ResponseElements.pm"; require "FormElements.pm"; require "Messages.pm"; -#require "Cookies.pm"; require "Security.pm"; require "SecuritySQL.pm"; require "SecurityHTML.pm"; -#require "MeetingSecurityUtilities.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); GetSecurityGroups(); diff --git a/DocDB/cgi/AdministerIntructions.pm b/DocDB/cgi/AdministerIntructions.pm index 5e9320a0..ac103260 100644 --- a/DocDB/cgi/AdministerIntructions.pm +++ b/DocDB/cgi/AdministerIntructions.pm @@ -6,7 +6,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/AdvancedInstructions.pm b/DocDB/cgi/AdvancedInstructions.pm index ae40ca23..72327e83 100644 --- a/DocDB/cgi/AdvancedInstructions.pm +++ b/DocDB/cgi/AdvancedInstructions.pm @@ -1,17 +1,17 @@ -# Description: The generic instructions for DocDB. This is mostly HTML, but making +# Description: The generic instructions for DocDB. This is mostly HTML, but making # it a script allows us to eliminate parts of it that we don't want # and get it following everyone's style, and allows groups to add # to it with ProjectMessages. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -61,7 +61,7 @@ sub AdvancedInstructionsBody {

You can also construct URL's that link to your document. The URL is of the form $ShowDocument?docid=XXXX&version=XX, where the X's represent just the numbers of the document and version. - (I.e. leave off the ``$ShortProject-doc-'' and ``-v.'') As above, you can leave off the + (I.e. leave off the $ShortProject-doc- and -v.) As above, you can leave off the &version=XX to refer to the latest version.

Using "as of" instead of version number: Instead of specifying a version @@ -70,11 +70,11 @@ sub AdvancedInstructionsBody {

Linking to files in a document

-

There is a script interface which fetches files from DocDB. The URL is +

There is a script interface which fetches files from DocDB. The URL is $RetrieveFile?docid=XXXX&version=XX&filename=xxxxxx. The version number can be left off to get files from the latest version number. The filename can also be left off. If there is only one file marked Main - that file will be retrieved. + that file will be retrieved. An alternate form is $RetrieveFile?docid=XXXX&version=XX&extension=xxx, so for instance you can specify PDF as the extension to retrieve the PDF file @@ -94,16 +94,16 @@ sub AdvancedInstructionsBody { The most useful searches are by author, topic, keyword, or events.

- To link to a topic, you must first find out the topic ID number. - The easiest way to do this is to simply click on that topic from the + To link to a topic, you must first find out the topic ID number. + The easiest way to do this is to simply click on that topic from the list by topic page. - The URL for a single topic will be - $ListBy?topicid=xxx. - Similarly, links to documents by authors are most easily found by the + The URL for a single topic will be + $ListBy?topicid=xxx. + Similarly, links to documents by authors are most easily found by the list by author page.

- Use the search form to link to a keyword: + Use the search form to link to a keyword: $Search?keywordsearchmode=anysub&keywordsearch=xxxxxxx.

@@ -126,7 +126,7 @@ sub AdvancedInstructionsBody { have values of AND and OR. For instance, if you specify two authors, innerlogic=OR will return documents by either author while AND will require the document to be authored by both people. To understand - outerlogic, take the example of searching for an author and a topic. + outerlogic, take the example of searching for an author and a topic. outerlogic=OR will require a document to either have the correct author or the correct topic, while AND will require both. Both options can be specified at the same time. outerlogic defaults to AND and innerlogic defaults @@ -161,7 +161,7 @@ sub AdvancedInstructionsBody { more than one are specified, only one word must be found

  • searchmode=allsub as above, but all words must be found
  • searchmode=anyword or allword like above, but the word must be found surrounded by spaces
  • - +

    More modes can be added if required. To search for more than one word, place the code for a space (%20) between them.

    @@ -182,13 +182,13 @@ sub AdvancedInstructionsBody {

    XML Interface

    -

    An XML interface for retrieving information from and submiting information to DocDB is +

    An XML interface for retrieving information from and submiting information to DocDB is partially complete. It is not fully complete, but it may satisfy the most common needs.

    - +

    XML Downloads

    -

    Any link to Search or ShowDocument described above will generate XML +

    Any link to Search or ShowDocument described above will generate XML output if &outformat=xml is added to the parameter list. Search returns a summary of the found documents while ShowDocument returns all the meta-info for the document.

    @@ -198,7 +198,7 @@ sub AdvancedInstructionsBody { the XML output). Future improvements to the XML facilities of DocDB may include XML output from ListBy, XML output of events, and XML output of topic, author and other lists. If any of these enhancements would be useful to you, please contact your administrator or - the developers.

    + the developers.

    XML Uploads

    @@ -206,9 +206,9 @@ sub AdvancedInstructionsBody {

    Since version 8.4 DocDB has supported uploads of XML data describing documents. This is done with the XMLUpload script. The XML output of ShowDocument described above can be used almost directly to create a new document. One new XML element - must be added to such an XMLFile and a second element is optional. Both elements must be + must be added to such an XMLFile and a second element is optional. Both elements must be added as children of <docdb> (at the same level as <document>).

    - +

    The first XML element is control which has two parameters: mode and usedate. mode must be one of three values, new, bump, or updatedb. New ignores the document ID in the uploaded XML and creates a new document with the included @@ -223,25 +223,25 @@ sub AdvancedInstructionsBody { <mode>new</mode> <usedate>yes</usedate> </control> - +

    The second element XML element (which is optional) is authentication which contains the username and password needed to download the file(s) in the document from the remote source. It will look like this:

    - +
          <authentication>
            <username>http-basic-username</username>
            <password>http-basic-password</password>
          </authentication>
    -     
    - -

    Generally speaking, when DocDB is processing an XML file, the id numbers describing + + +

    Generally speaking, when DocDB is processing an XML file, the id numbers describing things like topics, events, etc. are used and the names of those things shown in the XML file are ignored. Also, not all information about a document van be uploaded via XML. This can be changed if there is a need for it.

    -

    If the id numbers are missing, DocDB attempts a text match for the following +

    If the id numbers are missing, DocDB attempts a text match for the following information:

    -

    Finally, you will notice that there is no provision for adding files via XML. +

    Finally, you will notice that there is no provision for adding files via XML. This could be added but was not needed at the moment.

    - +

    Programatic Interface

    diff --git a/DocDB/cgi/AuthorAdd b/DocDB/cgi/AuthorAdd index 652eedba..29c33ad3 100755 --- a/DocDB/cgi/AuthorAdd +++ b/DocDB/cgi/AuthorAdd @@ -1,18 +1,19 @@ #! /usr/bin/env perl # -# Description: Adds an author into the DB list of authors. -# Called by submission from AddAuthorForm +# Name: AuthorAdd +# Description: Adds an author into the DB list of authors. +# Called by submission from AddAuthorForm # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: Eric Vaandering (ewv@fnal.gov) # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -25,6 +26,7 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -32,18 +34,19 @@ require "ResponseElements.pm"; require "SecuritySQL.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; $query = new CGI; # Global for subroutines $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rwuser,$db_rwpass); GetSecurityGroups(); -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); -$InstitutionID = $params{inst}; -$FirstName = $params{first}; -$MiddleInitials = $params{middle}; -$LastName = $params{lastname}; +my $InstitutionID = $Untaint -> extract(-as_integer => "inst") || 0; +my $FirstName = $Untaint -> extract(-as_safehtml => "first") || 0; +my $MiddleInitials = $Untaint -> extract(-as_safehtml => "middle") || 0; +my $LastName = $Untaint -> extract(-as_safehtml => "lastname") || 0; print $query -> header( -charset => $HTTP_ENCODING ); DocDBHeader("Author Addition Results"); @@ -57,24 +60,24 @@ unless (CanCreate()) { } unless ($InstitutionID && $FirstName && $LastName) { push @ErrorStack,"You must supply a first and last name and an institution."; -} - +} + EndPage(@ErrorStack); my $AuthorInsert = $dbh->prepare( "insert into Author ". - "(AuthorID, FirstName, MiddleInitials, LastName, InstitutionID,Active) ". + "(AuthorID, FirstName, MiddleInitials, LastName, InstitutionID,Active) ". "values (0, ?, ?, ?, ?, 1)"); - + $AuthorInsert -> execute($FirstName,$MiddleInitials,$LastName,$InstitutionID); my $AuthorID = $AuthorInsert -> {mysql_insertid}; # Works with MySQL only - + if ($AuthorID) { - push @ActionStack,"$FirstName $MiddleInitials $LastName has been added as an author. You can
    add another author."; + push @ActionStack,"$FirstName $MiddleInitials $LastName has been added as an author."; } else { unless (@ErrorStack) { push @ErrorStack,"Something unknown went wrong. Contact an administrator."; - } + } } ActionReport(); diff --git a/DocDB/cgi/AuthorAddForm b/DocDB/cgi/AuthorAddForm index 8ce3eeb8..0eca817d 100755 --- a/DocDB/cgi/AuthorAddForm +++ b/DocDB/cgi/AuthorAddForm @@ -1,17 +1,18 @@ #! /usr/bin/env perl # -# Description: A simple for to allow new author addition (no changes possible) +# Description: A simple script to allow new author addition (no changes possible) # +# Name: AuthorAddForm # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: Eric Vaandering (ewv@fnal.gov) # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -24,7 +25,7 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI qw(-nosticky); +use CGI qw(-nosticky); use DBI; require "DocDBGlobals.pm"; @@ -36,6 +37,7 @@ require "HTMLUtilities.pm"; require "Sorts.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI -> connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); GetInstitutions(); @@ -50,10 +52,10 @@ print $query -> start_multipart_form('POST',"$AuthorAdd"); print "

    You are about to add an author to the $Project document database. Anyone is allowed to add authors. Please be careful and make sure to put the authors first name, last name, and -middle initials (with periods) in the right place. If you make a mistake, +middle initials (with periods) in the right place. If you make a mistake, DO NOT enter the author again. Contact an -adminstrator and explain the problem. -Required fields are denoted by $RequiredMark. Click any +administrator and explain the problem. +Required fields are denoted by $RequiredMark. Click any highlighted link for quick help.

    \n"; print "\n"; diff --git a/DocDB/cgi/AuthorAdminister b/DocDB/cgi/AuthorAdminister index f5d4a587..b61036a0 100755 --- a/DocDB/cgi/AuthorAdminister +++ b/DocDB/cgi/AuthorAdminister @@ -9,7 +9,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -28,34 +28,38 @@ use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "AuthorSQL.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); @ErrorStack = (); @WarnStack = (); # Parameters to script -$Password = $params{password}; -my $Username = $params{admuser}; -$Action = $params{admaction}; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; -my $AuthorID = $params{authors}; -my $ConsolidateID = $params{targetauthor}; -$FirstName = $params{first}; -$Middle = $params{middle}; -$LastName = $params{lastname}; -$InstitutionID = $params{inst}; +my $AuthorID = $Untaint -> extract(-as_integer => "authors") || 0; +my $ConsolidateID = $Untaint -> extract(-as_integer => "targetauthor") || 0; +my $InstitutionID = $Untaint -> extract(-as_integer => "inst") || 0; + +my $FirstName = $Untaint -> extract(-as_safehtml => "first") || 0; +my $Middle = $Untaint -> extract(-as_safehtml => "middle") || 0; +my $LastName = $Untaint -> extract(-as_safehtml => "lastname") || 0; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); diff --git a/DocDB/cgi/AuthorHTML.pm b/DocDB/cgi/AuthorHTML.pm index 9e7316f7..fea0f5bd 100644 --- a/DocDB/cgi/AuthorHTML.pm +++ b/DocDB/cgi/AuthorHTML.pm @@ -1,11 +1,12 @@ +# Name: AuthorHTML.pm # # Description: Routines to create HTML elements for authors and institutions # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: Eric Vaandering (ewv@fnal.gov) # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -22,6 +23,8 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +require "HTMLUtilities.pm"; + sub FirstAuthor ($;$) { my ($DocRevID,$ArgRef) = @_; my $Institution = exists $ArgRef->{-institution} ? $ArgRef->{-institution} : $FALSE; @@ -41,7 +44,7 @@ sub FirstAuthor ($;$) { if ($Institution) { FetchInstitution($Authors{$FirstID}{InstitutionID}); $AuthorLink .= "
    ". - $Institutions{$Authors{$FirstID}{InstitutionID}}{SHORT}. + SmartHTML({-text=>$Institutions{$Authors{$FirstID}{InstitutionID}}{SHORT}}). ""; } return $AuthorLink; @@ -152,6 +155,7 @@ sub AuthorLink ($;%) { FetchAuthor($AuthorID); FetchInstitution($Authors{$AuthorID}{InstitutionID}); my $InstitutionName = $Institutions{$Authors{$AuthorID}{InstitutionID}}{LONG}; + $InstitutionName = SmartHTML( {-text => $InstitutionName,} ); unless ($Authors{$AuthorID}{FULLNAME}) { return "Unknown"; } @@ -165,9 +169,9 @@ sub AuthorLink ($;%) { my $Link; $Link = ""; if ($Format eq "full") { - $Link .= $Authors{$AuthorID}{FULLNAME}; + $Link .= SmartHTML( {-text => $Authors{$AuthorID}{FULLNAME}, } ); } elsif ($Format eq "formal") { - $Link .= $Authors{$AuthorID}{Formal}; + $Link .= SmartHTML( {-text => $Authors{$AuthorID}{Formal}, } ); } $Link .= ""; @@ -185,7 +189,7 @@ sub PrintAuthorInfo { print "$link\n"; print " of "; - print $Institutions{$Authors{$AuthorID}{InstitutionID}}{LONG}; + print SmartHTML( {-text => $Institutions{$Authors{$AuthorID}{InstitutionID}}{LONG}, } ); } sub AuthorsByInstitution { @@ -306,7 +310,7 @@ sub AuthorScroll (%) { my @ActiveIDs = (); foreach my $ID (@AuthorIDs) { if ($Authors{$ID}{ACTIVE} || $All) { - $AuthorLabels{$ID} = $Authors{$ID}{Formal}; + $AuthorLabels{$ID} = SmartHTML({-text=>$Authors{$ID}{Formal}}); push @ActiveIDs,$ID; } } @@ -343,7 +347,7 @@ sub AuthorTextEntry ($;@) { foreach $AuthorID (@Defaults) { FetchAuthor($AuthorID); - $AuthorManDefault .= "$Authors{$AuthorID}{FULLNAME}\n" ; + $AuthorManDefault .= SmartHTML({-text=>$Authors{$AuthorID}{FULLNAME}})."\n" ; } print FormElementTitle(-helplink => $HelpLink, -helptext => $HelpText, diff --git a/DocDB/cgi/AuthorSQL.pm b/DocDB/cgi/AuthorSQL.pm index d65222e0..f98aa382 100644 --- a/DocDB/cgi/AuthorSQL.pm +++ b/DocDB/cgi/AuthorSQL.pm @@ -5,7 +5,7 @@ # Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -143,6 +143,12 @@ sub GetInstitutions { # Creates/fills a hash $Institutions{$InstitutionID}{} wit $HaveAllInstitutions = 1; } +sub ClearInstitutions { + %Institutions = (); + $HaveAllInstitutions = 0; + return; +} + sub FetchInstitution { # Creates/fills a hash $Institutions{$InstitutionID}{} with all Institutions my ($InstitutionID) = @_; if ($Institutions{$InstitutionID}{InstitutionID}) { diff --git a/DocDB/cgi/AuthorUtilities.pm b/DocDB/cgi/AuthorUtilities.pm index 3ddb8891..c93d567a 100644 --- a/DocDB/cgi/AuthorUtilities.pm +++ b/DocDB/cgi/AuthorUtilities.pm @@ -4,7 +4,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/BulkCertificateInsert b/DocDB/cgi/BulkCertificateInsert index 16ad462a..a3e6acb0 100755 --- a/DocDB/cgi/BulkCertificateInsert +++ b/DocDB/cgi/BulkCertificateInsert @@ -3,9 +3,9 @@ # Description: Allows an administrator to create entries for certificate users in EmailUser # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -36,23 +36,24 @@ require "Messages.pm"; require "DBUtilities.pm"; require "DBColumnSizes.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "SecuritySQL.pm"; require "SecurityHTML.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); # Parameters to script my $Untaint = CGI::Untaint -> new($query -> Vars); -my %CGIParams = $query -> Vars; my $Password = $Untaint -> extract (-as_printable => "password") || ""; my $Username = $Untaint -> extract (-as_printable => "admuser") || ""; my $Action = $Untaint -> extract (-as_printable => "admaction") || ""; my $Force = $Untaint -> extract (-as_printable => "admforce") || ""; my $CanSign = $Untaint -> extract (-as_printable => "CanSign") || ""; -my @GroupIDs = split /\0/,$CGIParams{group}; +my @GroupIDs = @{ $Untaint -> extract(-as_listofint => "group") || undef }; if ($CanSign) {$CanSign = $TRUE;} @@ -95,22 +96,21 @@ if ($Action eq "Insert") { my $UsersGroupInsert = $dbh -> prepare("insert into UsersGroup (UsersGroupID,EmailUserID,GroupID) values (0,?,?)"); foreach my $Row (1..$MaxUsers) { - my $Name = $Untaint -> extract (-as_printable => "name$Row") || ""; + my $Username = $Untaint -> extract (-as_printable => "name$Row") || ""; + my $Name = $Untaint -> extract (-as_safehtml => "commonname$Row") || ""; my $Email = $Untaint -> extract (-as_printable => "email$Row") || ""; - my $Username = $Name; - $Username =~ s/\W//g; if ($Username) { if ($Usernames{$Username}) { push @WarnStack,"The user $Name already exists. Not inserted."; next; } - unless ($Email) { - push @WarnStack,"You must supply a name and e-mail address for the user $Name. Not inserted."; + unless ($Email && $Name) { + push @WarnStack,"You must supply a name and e-mail address for the user. Not inserted."; next; } unless (@GroupIDs) { - push @WarnStack,"You did not specify any groups. $Name inserted with membership in no groups."; + push @WarnStack,"You did not specify any groups. The users was inserted with membership in no groups."; } $UserInsert -> execute($Username,$Name,$Email,$CanSign); my $EmailUserID = $UserInsert -> {mysql_insertid}; # Works with MySQL only @@ -157,20 +157,24 @@ if ($UseSignoffs) { print "\n"; print "\n"; foreach my $Row (1..$MaxUsers) { print "\n"; } -print '\n"; diff --git a/DocDB/cgi/CalendarHTML.pm b/DocDB/cgi/CalendarHTML.pm index a0e84444..ae32f596 100644 --- a/DocDB/cgi/CalendarHTML.pm +++ b/DocDB/cgi/CalendarHTML.pm @@ -8,7 +8,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -70,7 +70,7 @@ sub PrintCalendar { my $DaysInMonth = DateTime -> last_day_of_month(year => $Year, month => $Month) -> day(); my $FirstDay = DateTime -> new(year => $Year, month => $Month, day => 1); my $MonthName = $FirstDay -> month_name(); - my $Today = DateTime ->today(time_zone => 'local'); + my $Today = DateTime ->today(time_zone => $LocalTimezone); my $Class = "ByMonth"; if ($Type eq "year") { diff --git a/DocDB/cgi/CertificateApplyForm b/DocDB/cgi/CertificateApplyForm index 7d8179de..d67f1efa 100755 --- a/DocDB/cgi/CertificateApplyForm +++ b/DocDB/cgi/CertificateApplyForm @@ -2,12 +2,12 @@ # # Author Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -37,8 +37,6 @@ require "CertificateUtilities.pm"; $query = new CGI; # Global for subroutines -%params = $query -> Vars; - $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); ### Start HTML @@ -52,6 +50,9 @@ print $query -> header( -charset => $HTTP_ENCODING ); my $CertificateStatus = &CertificateStatus(); my $CertEmail = $ENV{SSL_CLIENT_S_DN_Email}; my $CertCN = $ENV{SSL_CLIENT_S_DN_CN}; +my $CertDN = $ENV{SSL_CLIENT_S_DN}; + +push @DebugStack, "DN is $CertDN, CN is $CertCN"; if ($CertificateStatus eq "verified") { print "Your certificate has been verified and you have access to documents from these groups:"; @@ -63,37 +64,32 @@ if ($CertificateStatus eq "verified") { print "
  • ",$SecurityGroups{$GroupID}{NAME},"
  • \n"; } } else { - print "
  • None. Contact an adminstrator if this is incorrect
  • \n"; - } + print "
  • None. Contact an administrator if this is incorrect
  • \n"; + } print "\n"; -} elsif ($CertificateStatus eq "unverified") { - print "Your certificate is valid and you have applied for access to documents. +} elsif ($CertificateStatus eq "unverified") { + print "Your certificate is valid and you have applied for access to documents. If you believe your request has been misplaced or neglected, contact an administator.

    "; print "The following information may be helpful:
    \n"; + print "Certificate Distinguished Name (DN): $CertDN
    \n"; print "Certificate Common Name (CN): $CertCN
    \n"; print "Certificate E-mail Address: $CertEmail
    \n"; -} elsif ($CertificateStatus eq "mismatch") { - print "Your certificate is valid but a similar certificate already exists - for either your e-mail address or your name (CN). Only one - certificate is allowed per person. Contact an administrator if you - don't know what to do.

    "; - print "The following information may be helpful:
    \n"; - print "Certificate Common Name (CN): $CertCN
    \n"; - print "Certificate E-mail Address: $CertEmail
    \n"; -} elsif ($CertificateStatus eq "nocert") { +} elsif ($CertificateStatus eq "nocert") { print "You didn't present a certificate. Make sure your browser is supplying one and contact an administrator if are supplying one.

    "; } elsif ($CertificateStatus eq "noapp") { require "SecurityHTML.pm"; require "FormElements.pm"; print "

    Your certificate is valid but you have never applied for access to - documents.
    Fill out the form below to apply for access. - Select the groups which you think you belong to from the list. + documents.
    Fill out the form below to apply for access. + Select the groups which you think you belong to from the list. Your selection(s) will be verified by an administrator.

    "; print "
    \n"; print $query -> start_multipart_form('POST',$UserAccessApply); print "
    "; -print FormElementTitle(-helplink => 'certname', -helptext => 'Certificate CN'); +print FormElementTitle(-helplink => 'usersname', -helptext => "User's Name"); +print ""; +print FormElementTitle(-helplink => 'certname', -helptext => 'Certificate DN'); print ""; print FormElementTitle(-helplink => 'certemail', -helptext => 'E-mail Address'); print "
    \n"; - TextField(-name => "name$Row", -size => 40, -maxlength => $DBColumnSize{EmailUser}{Name} ); + TextField(-name => "commonname$Row", -size => 40, -maxlength => $DBColumnSize{EmailUser}{Name} ); + print "\n"; + TextField(-name => "name$Row", -size => 40, -maxlength => 2048); print "\n"; TextField(-name => "email$Row", -size => 30, -maxlength => $DBColumnSize{EmailUser}{EmailAddress}); print "
    '; +print '
    '; print $query -> submit (-value => "Insert Users"); print "
    \n"; print "\n"; - print "\n"; + print "\n"; @@ -104,14 +100,14 @@ if ($CertificateStatus eq "verified") { print "\n"; print "\n"; print ""; print ""; - print "
    Your name (Certificate CN):
      $CertCN

    \n"; + print "

    Your certificate DN:
      $CertDN

    \n"; + print "

    Your name (certificate CN):
      $CertCN

    \n"; TextField(-name => "email", -helplink => "email", -helptext => "Your E-mail", -size => 20, -maxlength => 64, -default => $CertEmail); print "

    \n"; - TextArea(-helplink => "certnote", -helptext => "Notes", + TextArea(-helplink => "certnote", -helptext => "Notes", -extratext => "(Identify yourself or other notes if needed.)", - -name => "certnote"); + -name => "certnote"); print "
    \n"; print $query -> submit (-value => "Apply for access"); print "
    \n"; + print "\n"; print "\n"; } diff --git a/DocDB/cgi/CertificateInstructions.pm b/DocDB/cgi/CertificateInstructions.pm index 50e40a0a..9cf705b5 100644 --- a/DocDB/cgi/CertificateInstructions.pm +++ b/DocDB/cgi/CertificateInstructions.pm @@ -11,7 +11,7 @@ # is set, there may be some issues. Please feel free to send patches if you find # FNAL specific information remaining. -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/CertificateUtilities.pm b/DocDB/cgi/CertificateUtilities.pm index b343ff5a..ba52c9e3 100644 --- a/DocDB/cgi/CertificateUtilities.pm +++ b/DocDB/cgi/CertificateUtilities.pm @@ -1,14 +1,14 @@ -# Description: Various routines to deal with certificates +# Description: Various routines to deal with certificates # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -21,15 +21,15 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA sub FetchSecurityGroupsByCert (%) { - require "SecuritySQL.pm"; + require "SecuritySQL.pm"; my %Params = @_; my $EmailUserID = FetchEmailUserIDByCert(%Params); if ($EmailUser{$EmailUserID}{Verified} != 1) { push @DebugStack,"User is not verified"; - push @WarnStack,"You have a valid certificate, but have are not yet allowed to access to DocDB. + push @WarnStack,"You have a valid certificate, but are not yet allowed to access to DocDB. Apply for access."; return; - } + } my @UserGroupIDs = FetchUserGroupIDs($EmailUserID); return @UserGroupIDs; } @@ -38,37 +38,35 @@ sub FetchEmailUserIDByCert (%) { my %Params = @_; my $IgnoreVerification = $Params{-ignoreverification}; - - require "SecuritySQL.pm"; - require "NotificationSQL.pm"; + + require "SecuritySQL.pm"; + require "NotificationSQL.pm"; my $CertEmail = $ENV{SSL_CLIENT_S_DN_Email}; my $CertCN = $ENV{SSL_CLIENT_S_DN_CN}; - - $CertificateCN = $CertCN; - $CertificateEmail = $CertEmail; - - push @DebugStack,"Finding EmailUserID by certificate $CertCN"; + my $CertDN = $ENV{SSL_CLIENT_S_DN}; # If we do http basic with users, this routine will function with minor modifications my $EmailUserSelect; + + push @DebugStack, "Finding EmailUserID and groups by DN $CertDN"; if ($IgnoreVerification) { $EmailUserSelect = $dbh->prepare("select EmailUserID from EmailUser ". - "where Name=?"); - } else { + "where Username=?"); + } else { $EmailUserSelect = $dbh->prepare("select EmailUserID from EmailUser ". - "where Verified=1 and Name=?"); + "where Verified=1 and Username=?"); } - $EmailUserSelect -> execute($CertCN); + $EmailUserSelect -> execute($CertDN); - my ($EmailUserID) = $EmailUserSelect -> fetchrow_array; + my ($EmailUserID) = $EmailUserSelect -> fetchrow_array; push @DebugStack,"Found e-mail user: $EmailUserID"; if ($EmailUserID) { FetchEmailUser($EmailUserID) } - + return $EmailUserID; } @@ -83,37 +81,37 @@ sub CertificateStatus () { # nocert -- no certificate was presented (not sure if this can work) my $CertificateStatus = ""; - + my $CertEmail = $ENV{SSL_CLIENT_S_DN_Email}; my $CertCN = $ENV{SSL_CLIENT_S_DN_CN}; - - push @DebugStack,"Finding Status by certificate"; + my $CertDN = $ENV{SSL_CLIENT_S_DN}; unless ($CertCN) { $CertificateStatus = "nocert"; push @DebugStack,"Certificate Status: $CertificateStatus"; return $CertificateStatus; - } - + } + my $EmailUserSelect; + push @DebugStack, "Finding status by DN $CertDN"; $EmailUserSelect = $dbh->prepare("select EmailUserID,Verified from EmailUser ". - "where Name=?"); - $EmailUserSelect -> execute($CertCN); - my ($EmailUserID,$Verified) = $EmailUserSelect -> fetchrow_array; - push @DebugStack,"Checking user $CertCN by CN"; + "where Username=?"); + $EmailUserSelect -> execute($CertDN); + my ($EmailUserID,$Verified) = $EmailUserSelect -> fetchrow_array; + if ($Verified) { $CertificateStatus = "verified"; push @DebugStack,"Certificate Status: $CertificateStatus"; return $CertificateStatus; - } - + } + if ($EmailUserID) { $CertificateStatus = "unverified"; push @DebugStack,"Certificate Status: $CertificateStatus"; return $CertificateStatus; - } - + } + $CertificateStatus = "noapp"; push @DebugStack,"Certificate Status: $CertificateStatus"; return $CertificateStatus; diff --git a/DocDB/cgi/ConfigSQL.pm b/DocDB/cgi/ConfigSQL.pm index 0ebdfb36..e9ec1dfd 100644 --- a/DocDB/cgi/ConfigSQL.pm +++ b/DocDB/cgi/ConfigSQL.pm @@ -4,7 +4,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/ConfirmTalkHint b/DocDB/cgi/ConfirmTalkHint index 296fe414..aae9a1e9 100755 --- a/DocDB/cgi/ConfirmTalkHint +++ b/DocDB/cgi/ConfirmTalkHint @@ -1,18 +1,18 @@ #! /usr/bin/env perl # -# Description: Script to confirm a match between a talk entered in the agenda +# Description: Script to confirm a match between a talk entered in the agenda # and a document # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: Eric Vaandering (ewv@fnal.gov) # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,6 +26,7 @@ use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -41,31 +42,28 @@ require "MeetingSecurityUtilities.pm"; require "FSUtilities.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "Security.pm"; require "SQLChecks.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); @ErrorStack = (); @WarnStack = (); -$DocumentID = $params{documentid}; -$SessionTalkID = $params{sessiontalkid}; - -$DocumentID =~ s/^\s+//; # Remove leading and trailing spaces -$DocumentID =~ s/\s+$//; -$SessionTalkID =~ s/^\s+//; -$SessionTalkID =~ s/\s+$//; +my $DocumentID = $Untaint -> extract(-as_typedint => "documentid") || 0; +my $SessionTalkID = $Untaint -> extract(-as_typedint => "sessiontalkid") || 0; unless ($DocumentID) { push @ErrorStack,"You are must supply a document number!"; -} +} unless ($SessionTalkID) { push @ErrorStack,"You are must supply a Session Number!"; -} +} print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("Confirming document match","",-nobody => $TRUE); @@ -73,7 +71,7 @@ print $query -> header( -charset => $HTTP_ENCODING ); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rwuser,$db_rwpass); unless ($dbh) { push @ErrorStack,$Msg_NoConnect; -} +} &EndPage(@ErrorStack); &FetchDocument($DocumentID); @@ -105,9 +103,9 @@ my $RevisionEventCheck = $dbh -> prepare("select RevEventID from RevisionEvent w $RevisionEventCheck -> execute($DocRevID,$ConferenceID); my ($RevisionEventID) = $RevisionEventCheck -> fetchrow_array; unless ($RevisionEventID) { - my $Insert = $dbh -> prepare("insert into RevisionEvent (RevEventID,DocRevID,ConferenceID) values (0,?,?)"); + my $Insert = $dbh -> prepare("insert into RevisionEvent (RevEventID,DocRevID,ConferenceID) values (0,?,?)"); $Insert -> execute($DocRevID,$ConferenceID); -} +} print "

    The match has been confirmed.
    Press the button below to reload the original page.

    \n"; diff --git a/DocDB/cgi/Cookies.pm b/DocDB/cgi/Cookies.pm index ac63afb4..e1f88d0b 100644 --- a/DocDB/cgi/Cookies.pm +++ b/DocDB/cgi/Cookies.pm @@ -5,7 +5,7 @@ # Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/CustomListForm b/DocDB/cgi/CustomListForm index e9dd03b3..e37afa3f 100755 --- a/DocDB/cgi/CustomListForm +++ b/DocDB/cgi/CustomListForm @@ -9,7 +9,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -28,6 +28,7 @@ use CGI qw(-nosticky); +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -42,6 +43,7 @@ require "DocDBFields.pm"; require "DBUtilities.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "MeetingSecurityUtilities.pm"; require "ConfigSQL.pm"; @@ -55,16 +57,17 @@ require "MeetingHTML.pm"; require "TopicHTML.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); -my $Scope = $params{scope}; -my @EventGroupIDs = split /\0/,$params{eventgroups}; -my @EventIDs = split /\0/,$params{events}; -my @Defaults = split /\0/,$params{defaultlists}; -my @TopicIDs = split /\0/,$params{topics}; -my @DocTypeIDs = split /\0/,$params{doctype}; -my $DefaultEventID = $params{eventid}; +my $Scope = $Untaint -> extract(-as_printable => "scope") || ""; +my @EventGroupIDs = @{ $Untaint -> extract(-as_listofint => "eventgroups") || undef }; +my @EventIDs = @{ $Untaint -> extract(-as_listofint => "events") || undef }; +my @Defaults = @{ $Untaint -> extract(-as_listofwords => "defaultlists") || undef }; +my @TopicIDs = @{ $Untaint -> extract(-as_listofint => "topics") || undef }; +my @DocTypeIDs = @{ $Untaint -> extract(-as_listofint => "doctype") || undef }; +my $DefaultEventID = $Untaint -> extract(-as_integer => "eventid") || 0; my $MaxFields = 15; my @Cookies = (); @@ -98,13 +101,13 @@ if (CanAdminister()) { my %FieldList = (); foreach my $FieldCount (1..$MaxFields) { - my $Field = $params{"field$FieldCount"}; + my $Field = $Untaint -> extract(-as_printable => "field$FieldCount") || ""; if ($Field && $Field ne "xxxx") { push @ActionStack,"Field \"$Field\" added to the display"; - $FieldList{$Field}{Row} = $params{"row$FieldCount"}; - $FieldList{$Field}{Column} = $params{"col$FieldCount"}; - $FieldList{$Field}{RowSpan} = $params{"rowspan$FieldCount"}; - $FieldList{$Field}{ColSpan} = $params{"colspan$FieldCount"}; + $FieldList{$Field}{Row} = $Untaint -> extract(-as_integer => "row$FieldCount") || 0; + $FieldList{$Field}{Column} = $Untaint -> extract(-as_integer => "col$FieldCount") || 0; + $FieldList{$Field}{RowSpan} = $Untaint -> extract(-as_integer => "rowspan$FieldCount") || 0; + $FieldList{$Field}{ColSpan} = $Untaint -> extract(-as_integer => "colspan$FieldCount") || 0; } } diff --git a/DocDB/cgi/DBColumnSizes.pm b/DocDB/cgi/DBColumnSizes.pm index 3ec49b86..f7d82124 100644 --- a/DocDB/cgi/DBColumnSizes.pm +++ b/DocDB/cgi/DBColumnSizes.pm @@ -7,7 +7,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/DBUtilities.pm b/DocDB/cgi/DBUtilities.pm index d6e34ac8..a589e925 100644 --- a/DocDB/cgi/DBUtilities.pm +++ b/DocDB/cgi/DBUtilities.pm @@ -5,7 +5,7 @@ # Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/Debug.pm b/DocDB/cgi/Debug.pm index 0af275d0..f127fed5 100644 --- a/DocDB/cgi/Debug.pm +++ b/DocDB/cgi/Debug.pm @@ -1,5 +1,5 @@ -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/Defaults.pm b/DocDB/cgi/Defaults.pm index 5a4f89e6..557d8f46 100644 --- a/DocDB/cgi/Defaults.pm +++ b/DocDB/cgi/Defaults.pm @@ -4,20 +4,20 @@ # (in that order) # # Functions in this file: -# +# # SetAuthorMode: Selectable list or free-form text field -# SetTopicMode: Single or multiple selectable lists +# SetTopicMode: Single or multiple selectable lists # SetUploadMethod: File upload or HTTP fetch -# SetDateOverride: Allows over-riding modification date -# SetAuthorDefault: Sets Author and Requester defaults to cookie value +# SetDateOverride: Allows over-riding modification date +# SetAuthorDefault: Sets Author and Submitter defaults to cookie value # SetFileOptions: Sets archive mode and number of uploads -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -29,75 +29,88 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +use CGI::Untaint; sub SetAuthorMode { - if ($params{authormode}) { - $AuthorMode = $params{authormode}; + my $Untaint = CGI::Untaint -> new($query -> Vars); + my $Param = $Untaint -> extract(-as_safehtml => "authormode") || ""; + if ($Param) { + $AuthorMode = $Param; } else { $AuthorMode = $AuthorModePref; - } + } if ($AuthorMode ne "list" && $AuthorMode ne "field") { $AuthorMode = "list"; } } sub SetTopicMode { - if ($params{topicmode}) { - $TopicMode = $params{topicmode}; + my $Untaint = CGI::Untaint -> new($query -> Vars); + my $Param = $Untaint -> extract(-as_safehtml => "topicmode") || ""; + if ($Param) { + $TopicMode = $Param; } else { $TopicMode = $TopicModePref; } if ($TopicMode ne "single" && $TopicMode ne "multi") { $TopicMode = "multi"; - } + } } sub SetUploadMethod { - if ($params{upload}) { - $Upload = $params{upload}; + my $Untaint = CGI::Untaint -> new($query -> Vars); + my $Param = $Untaint -> extract(-as_safehtml => "upload") || ""; + if ($Param) { + $Upload = $Param; } else { $Upload = $UploadMethodPref; - } + } if ($Upload ne "http" && $Upload ne "file") { $Upload = "file"; - } + } } sub SetDateOverride { - if ($params{overdate}) { - $Overdate = $params{overdate}; + my $Untaint = CGI::Untaint -> new($query -> Vars); + my $Param = $Untaint -> extract(-as_safehtml => "overdate") || ""; + if ($Param) { + $Overdate = $Param; } else { $Overdate = $DateOverridePref; - } + } } sub SetFileOptions { my ($DocRevID) = @_; - if ($params{archive}) { - $Archive = $params{archive}; + my $Untaint = CGI::Untaint -> new($query -> Vars); + my $InputArchive = $Untaint -> extract(-as_safehtml => "archive") || ""; + my $InputNumFile = $Untaint -> extract(-as_safehtml => "numfile") || ""; + + if ($InputArchive) { + $Archive = $InputArchive; } else { $Archive = $UploadTypePref - } + } if ($Archive eq "single") {$NumberUploads = 3;} # Make sure if ($Archive eq "multi") {$Archive = "single";} # No real difference if ($Archive ne "archive" && $Archive ne "single") { $Archive = "single"; - } - - if ($params{numfile}) { # User has selected - $NumberUploads = $params{numfile}; + } + + if ($InputNumFile) { # User has selected + $NumberUploads = $InputNumFile; } elsif ($NumFilesPref && $mode ne "update") { # User has a pref if ($Meeting || $OtherMeeting) { if ($NumFilesPref < 3) { $NumberUploads = 3; - } else { + } else { $NumberUploads = $NumFilesPref; - } - } else { + } + } else { $NumberUploads = $NumFilesPref; - } + } } else { # No selection, no pref if ($Meeting || $OtherMeeting) { $NumberUploads = 3; @@ -106,10 +119,10 @@ sub SetFileOptions { $NumberUploads = @DocFiles; # FIXME: One line with scalar unless ($NumberUploads) { # Gyrations to handle docs that have 0 files $NumberUploads = 3; - } + } } else { $NumberUploads = 3; - } + } } } diff --git a/DocDB/cgi/DeleteConfirm b/DocDB/cgi/DeleteConfirm index 6b7c9c8e..c9ccd7ee 100755 --- a/DocDB/cgi/DeleteConfirm +++ b/DocDB/cgi/DeleteConfirm @@ -8,7 +8,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -26,6 +26,7 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -36,21 +37,21 @@ require "DocumentSQL.pm"; require "RevisionSQL.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "AdministerElements.pm"; require "Security.pm"; require "RevisionHTML.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); &GetSecurityGroups; -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); -$DocumentID = $params{docid}; -$DocumentID =~ s/^\s+//; # Remove leading and trailing spaces -$DocumentID =~ s/\s+$//; +my $DocumentID = $Untaint -> extract(-as_typedint => "docid") || 0; @ErrorStack = (); @@ -58,7 +59,7 @@ unless ($DocumentID) { push @ErrorStack,"You are must supply a document number to delete."; } unless (&CanAdminister) { - push @ErrorStack,"You must be logged in as the adminstrator to delete + push @ErrorStack,"You must be logged in as the administrator to delete documents"; } @@ -80,7 +81,7 @@ unless ($DocRevID) { EndPage(@ErrorStack); -print "

    To delete this document, you must supply the adminstrator +print "

    To delete this document, you must supply the administrator username and password:"; print $query -> startform('POST',$DeleteDocument); diff --git a/DocDB/cgi/DeleteDocument b/DocDB/cgi/DeleteDocument index 86218712..a228a97f 100755 --- a/DocDB/cgi/DeleteDocument +++ b/DocDB/cgi/DeleteDocument @@ -1,18 +1,18 @@ #! /usr/bin/env perl # # Description: This script is called by DeleteConfirm to actually delete -# the requested document, all associated entries in the DB, -# and the actual files as well. +# the requested document, all associated entries in the DB, +# and the actual files as well. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -25,6 +25,7 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -32,17 +33,15 @@ require "ResponseElements.pm"; require "Security.pm"; require "FSUtilities.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -%params = $query -> Vars; - -$DocumentID = $params{docid}; -$DocumentID =~ s/^\s+//; # Remove leading and trailing spaces -$DocumentID =~ s/\s+$//; - -my $Password = $params{password}; -my $Username = $params{admuser}; +my $DocumentID = $Untaint -> extract(-as_typedint => "docid") || 0; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; @ErrorStack = (); @@ -50,7 +49,7 @@ $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,"Unable to connect to the database. Check the password."; -} +} print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("Deleting Document $DocumentID"); @@ -59,11 +58,11 @@ EndPage(@ErrorStack); unless ($DocumentID) { push @ErrorStack,"You are must supply a document number to delete."; -} +} unless (&CanAdminister) { - push @ErrorStack,"You must be logged in as the adminstrator to delete + push @ErrorStack,"You must be logged in as the administrator to delete documents"; -} +} EndPage(@ErrorStack); @@ -92,10 +91,10 @@ my @Revisions = keys %Revision; unless (@Revisions) { print "Document $DocumentID does not exist.\n"; exit; -} - -# Delete stuff from files and linking tables - +} + +# Delete stuff from files and linking tables + foreach $RevisionID (@Revisions) { $author_delete -> execute($RevisionID); $topic_delete -> execute($RevisionID); @@ -107,16 +106,16 @@ foreach $RevisionID (@Revisions) { $document_delete -> execute($DocumentID); $revision_delete -> execute($DocumentID); - + # Delete stuff from file system $command = "rm -rf $Directory/*"; system ($command); - + print "Document $DocumentID has been deleted.

    "; &DocDBNavBar; &DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/DisplayMeeting b/DocDB/cgi/DisplayMeeting index 2259e97e..91b75411 100755 --- a/DocDB/cgi/DisplayMeeting +++ b/DocDB/cgi/DisplayMeeting @@ -8,7 +8,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -27,6 +27,7 @@ use Benchmark; use CGI; +use CGI::Untaint; use DBI; $StartTime = new Benchmark; @@ -35,6 +36,7 @@ require "DocDBGlobals.pm"; require "Messages.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "ResponseElements.pm"; require "Sorts.pm"; require "Scripts.pm"; @@ -53,12 +55,12 @@ require "EventUtilities.pm"; require "Utilities.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -%params = $query -> Vars; - -my $SessionID = $params{sessionid}; -my $SessionSeparatorID = $params{sessionseparatorid}; -my $EventID = $params{conferenceid}; +my $SessionID = $Untaint -> extract(-as_integer => "sessionid") || 0; +my $SessionSeparatorID = $Untaint -> extract(-as_integer => "sessionseparatorid") || 0; +my $EventID = $Untaint -> extract(-as_integer => "conferenceid") || 0; @ErrorStack = (); @WarnStack = (); diff --git a/DocDB/cgi/DocDBFields.pm b/DocDB/cgi/DocDBFields.pm index d09622b7..c11dd1c0 100644 --- a/DocDB/cgi/DocDBFields.pm +++ b/DocDB/cgi/DocDBFields.pm @@ -6,7 +6,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/DocDBGlobals.pm b/DocDB/cgi/DocDBGlobals.pm index c3aecf41..d4e897ac 100644 --- a/DocDB/cgi/DocDBGlobals.pm +++ b/DocDB/cgi/DocDBGlobals.pm @@ -1,4 +1,4 @@ -# +# Name: $RCSfile$ # Description: Configuration file for the DocDB. Sets default # values and script names. Do not change this file, # specific local settings are in ProjectGlobals.pm. @@ -7,7 +7,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -26,6 +26,8 @@ # Constants +use DateTime; +$LocalTimezone = DateTime::TimeZone->new(name => 'local'); $TRUE = 1; $FALSE = 0; @@ -89,13 +91,20 @@ $Preferences{Security}{Certificates}{FNALKCA} = $FALSE; # TRUE or FALSE - s $Preferences{Security}{Certificates}{DOEGrids} = $FALSE; # TRUE or FALSE - show DOEgrid certificate instructions $Preferences{Security}{Certificates}{ShowCertInstructions} = $FALSE; # TRUE or FALSE - show certificate instructions even on non-cert version +$Preferences{Security}{AuthName} = ""; # Set to override default AuthName of group1 or group2, etc. + $Preferences{Options}{DynamicFullList}{Private} = $FALSE; # Generate Full document list by dynamically for private db $Preferences{Options}{DynamicFullList}{Public} = $FALSE; # Generate Full document list by dynamically for public db $Preferences{Options}{AlwaysRetrieveFile} = $FALSE; # Always use RetrieveFile instead of File Links +@{$Preferences{Options}{FileEndingsForAttachment}} = ("doc","docx","xls","xlsx","ppt","pptx","pps","ppsx"); $Preferences{Options}{SubmitAgree} = ""; # "Put text here to make users agree to a privacy statement or some-such.
    I agree:" +# On updates of documents, require an entry in the note field and/or zero out the submitter and require a new entry +$Preferences{Options}{Update}{RequireNote} = $FALSE; +$Preferences{Options}{Update}{RequireSubmitter} = $FALSE; + $Preferences{Components}{iCal} = $TRUE; # Display links to iCal calendars $Preferences{Topics}{MinLevel}{Document} = 1; diff --git a/DocDB/cgi/DocDBHelp b/DocDB/cgi/DocDBHelp index 86e89f33..fc779e66 100755 --- a/DocDB/cgi/DocDBHelp +++ b/DocDB/cgi/DocDBHelp @@ -1,17 +1,17 @@ #! /usr/bin/env perl # # Description: Usually called as a pop-up, this looks up in docdb.hlp -# the information on a specific topic. +# the information on a specific topic. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -23,7 +23,8 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI; +use CGI; +use CGI::Untaint; use XML::Parser::PerlSAX; use XML::PatAct::MatchName; use XML::PatAct::ToObjects; @@ -32,6 +33,7 @@ use XML::Grove::AsCanonXML; require "DocDBGlobals.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; my $DefaultPatterns = [ 'helpfile' => [ qw{ -holder } ], @@ -51,7 +53,7 @@ my $ProjectPatterns = [ if (-e "ProjectHelp.xml") { $ProjectHelp = 1; -} +} my $DefaultMatcher = XML::PatAct::MatchName -> new(Patterns => $DefaultPatterns); my $DefaultHandler = XML::PatAct::ToObjects -> new(Patterns => $DefaultPatterns, @@ -70,12 +72,13 @@ if ($ProjectHelp) { # Start page -$query = new CGI; +$query = new CGI; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("$Project DocDB Help","",-nobody => $TRUE); -%params = $query -> Vars; -$helpterm = $params{term}; # Extract term user wants help for +$helpterm = $Untaint -> extract(-as_safehtml => "term") || ""; # Parse XML into hashes, pull out desired text @@ -127,6 +130,6 @@ if ($DefaultText || $ProjectText) { } } else { print "No help available on this topic.

    \n"; -} +} &DocDBFooter($DBWebMasterEmail,$DBWebMasterName,-nobody => $TRUE); diff --git a/DocDB/cgi/DocDBHelp.xml b/DocDB/cgi/DocDBHelp.xml index 45fa90ba..fa35bd13 100644 --- a/DocDB/cgi/DocDBHelp.xml +++ b/DocDB/cgi/DocDBHelp.xml @@ -10,7 +10,7 @@ Author: Eric Vaandering (ewv@fnal.gov) - Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant + Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant This file is part of DocDB. @@ -1248,14 +1248,23 @@ or may not be the same as the web username and password. certname - Certificate Common Name (CN) + Certificate Distinguished Name (DN) - This is a unique identifier in the user's client certificate. It is usually - the user's name or login. It must be entered exactly or the user will not be + This is the unique identifier (subject or DN) in the user's client certificate. + It must be entered exactly or the user will not be authenticated when they present their client certificate to DocDB. + + usersname + User's Name (CN) + + Enter the user's common name. Often this is present in a CN section of the certificate DN, but it need + not be entered exactly; it is not used for authentication. + + + certemail E-Mail Address for Certificate User diff --git a/DocDB/cgi/DocDBInstructions b/DocDB/cgi/DocDBInstructions index 45c4cdfe..780d1667 100755 --- a/DocDB/cgi/DocDBInstructions +++ b/DocDB/cgi/DocDBInstructions @@ -1,19 +1,19 @@ #! /usr/bin/env perl # -# Description: The instructions for DocDB. This is mostly HTML, but making +# Description: The instructions for DocDB. This is mostly HTML, but making # it a script allows us to eliminate parts of it that we don't want # and get it following everyone's style, and allows groups to add # to it with ProjectMessages. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -25,22 +25,26 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI; -use DBI; +use CGI; +use CGI::Untaint; +use DBI; require "DocDBGlobals.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "Messages.pm"; require "SecuritySQL.pm"; require "Security.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); &GetSecurityGroups; -%params = $query -> Vars; -$InstructionSet = $params{set} || "general"; +my $Untaint = CGI::Untaint -> new($query -> Vars); + +my $InstructionSet = $Untaint -> extract(-as_printable => "set") || "general"; # Title @@ -77,7 +81,7 @@ if ($InstructionSet eq "general") { $PageTitle = "Advanced Users & XML Interface"; $HTMLTitle = $PageTitle; } elsif ($InstructionSet eq "admin") { - $PageTitle = "Adminstration Instructions"; + $PageTitle = "Administration Instructions"; $HTMLTitle = $PageTitle; } print $query->header( -charset => $HTTP_ENCODING ); diff --git a/DocDB/cgi/DocDBVersion.pm b/DocDB/cgi/DocDBVersion.pm index 88dd2b4c..7abfc308 100644 --- a/DocDB/cgi/DocDBVersion.pm +++ b/DocDB/cgi/DocDBVersion.pm @@ -3,7 +3,7 @@ # Revision: $Revision$ # Modified: $Author$ on $Date$ # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -20,6 +20,6 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -$DocDBVersion = "8.7.10"; +$DocDBVersion = "8.7.20rc6"; 1; diff --git a/DocDB/cgi/DocTypeAdminister b/DocDB/cgi/DocTypeAdminister index 4eff62cb..ee27234d 100755 --- a/DocDB/cgi/DocTypeAdminister +++ b/DocDB/cgi/DocTypeAdminister @@ -1,19 +1,19 @@ #! /usr/bin/env perl # # Name: DocTypeAdminister.pm -# Description: This script is called by AdministerForm and does administration +# Description: This script is called by AdministerForm and does administration # on document types in the DB. This script adds, modifies and # deletes document types. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,35 +26,37 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "MiscSQL.pm"; require "DocTypeHTML.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -%params = $query -> Vars; +# Parameters to script -# Parameters to script +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; -$Password = $params{password}; -my $Username = $params{admuser}; -$Action = $params{admaction}; - -my $DocTypeID = $params{doctype}; -my $ShortName = $params{name}; -my $LongName = $params{longdesc}; +my $DocTypeID = $Untaint -> extract(-as_integer => "doctype") || 0; +my $ShortName = $Untaint -> extract(-as_safehtml => "name") || 0; +my $LongName = $Untaint -> extract(-as_safehtml => "longdesc") || 0; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,$Msg_AdminNoConnect; -} +} EndPage(); print $query -> header( -charset => $HTTP_ENCODING ); @@ -62,7 +64,7 @@ DocDBHeader("Modified List of Document Types"); unless (CanAdminister()) { push @ErrorStack,$Msg_AdminNoLogin; -} +} EndPage(); GetDocTypes(); @@ -81,14 +83,14 @@ if ($Action eq "Delete") { # Delete institutions } EndPage(); -# Deal with name changes +# Deal with name changes - if ($ShortName) { + if ($ShortName) { push @ActionStack,"Changed document type's short name to $ShortName"; my $DocTypeUpdate = $dbh->prepare("update DocumentType set ShortType=? where DocTypeID=?"); $DocTypeUpdate -> execute($ShortName,$DocTypeID); } - if ($LongName) { + if ($LongName) { push @ActionStack,"Changed document type's long name to $LongName"; my $DocTypeUpdate = $dbh -> prepare("update DocumentType set LongType=? where DocTypeID=?"); $DocTypeUpdate -> execute($LongName,$DocTypeID); @@ -100,7 +102,7 @@ if ($Action eq "Delete") { # Delete institutions $DocTypeID = $DocTypeInsert -> {mysql_insertid}; # Works with MySQL only } else { push @ErrorStack,"No valid action was specified."; -} +} # For modify or new fetch institution information and display. @@ -109,5 +111,5 @@ EndPage(); DocDBNavBar(); DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/DocTypeHTML.pm b/DocDB/cgi/DocTypeHTML.pm index 68fae91d..8f2c3ec3 100644 --- a/DocDB/cgi/DocTypeHTML.pm +++ b/DocDB/cgi/DocTypeHTML.pm @@ -1,17 +1,17 @@ -# +# # Name: DocTypeHTML.pm -# Description: Routines with form elements and other HTML generating +# Description: Routines with form elements and other HTML generating # code pertaining to DocumentTypes. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -30,48 +30,50 @@ sub DocTypeSelect (;%) { # Scrolling selectable list for doc type search my $Format = exists $ArgRef->{-format} ? $ArgRef->{-format} : "full"; # my $HelpLink = exists $ArgRef->{-helplink} ? $ArgRef->{-helplink} : ""; # my $HelpText = exists $ArgRef->{-helptext} ? $ArgRef->{-helptext} : " my (%Params) = @_; - + my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } - + } + my %DocTypeLabels = (); foreach my $DocTypeID (keys %DocumentTypes) { + my $LongName = SmartHTML({-text => $DocumentTypes{$DocTypeID}{LONG}},); + my $ShortName = SmartHTML({-text => $DocumentTypes{$DocTypeID}{SHORT}},); if ($Format eq "short") { - $DocTypeLabels{$DocTypeID} = "$DocumentTypes{$DocTypeID}{SHORT}"; + $DocTypeLabels{$DocTypeID} = $ShortName; } elsif ($Format eq "full") { - $DocTypeLabels{$DocTypeID} = "$DocumentTypes{$DocTypeID}{SHORT} [$DocumentTypes{$DocTypeID}{LONG}]"; + $DocTypeLabels{$DocTypeID} = "$ShortName [$LongName]"; } - } - print FormElementTitle(-helplink => "doctype", -helptext => "Document type"); - print $query -> scrolling_list(-size => 10, -name => "doctype", -multiple => $Multiple, + } + print FormElementTitle(-helplink => "doctype", -helptext => "Document type"); + print $query -> scrolling_list(-size => 10, -name => "doctype", -multiple => $Multiple, -values => \%DocTypeLabels, $Booleans); }; sub DocTypeEntryBox (;%) { my (%Params) = @_; - + my $Disabled = $Params{-disabled} || "0"; - + my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } - + } + print "\n"; print "\n"; print "\n"; print "\n"; diff --git a/DocDB/cgi/DocumentAddForm b/DocDB/cgi/DocumentAddForm index f9253771..2938cd93 100755 --- a/DocDB/cgi/DocumentAddForm +++ b/DocDB/cgi/DocumentAddForm @@ -1,14 +1,12 @@ #! /usr/bin/env perl # -# Name: $RCSfile$ +# Name: DocumentAddForm # Description: The main form to add or modify documents or metadata # -# Revision: $Revision$ -# Modified: $Author$ on $Date$ -# # Author: Eric Vaandering (ewv@fnal.gov) +# Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -26,6 +24,7 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI qw(-nosticky); +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -45,6 +44,7 @@ require "TopicSQL.pm"; require "ResponseElements.pm"; require "FormElements.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "Utilities.pm"; require "Defaults.pm"; require "Security.pm"; @@ -61,22 +61,27 @@ require "SignoffHTML.pm"; require "TalkHTML.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); +@ErrorStack = (); +@WarnStack = (); + &GetAuthors; &GetTopics; &GetSecurityGroups; &GetDocTypes; &GetPrefsCookie; -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); -my $DocumentID = $params{docid}; -my $ConferenceID = $params{conferenceid}; -my $SessionID = $params{sessionid}; -my $Version = $params{version}; -my @PreTopics = $query -> param('pretopic'); - $mode = $params{mode}; # FIXME: Can't be my since used in subroutines +my $DocumentID = $Untaint -> extract(-as_integer => "docid") || 0; +my $ConferenceID = $Untaint -> extract(-as_integer => "conferenceid") || undef; +my $SessionID = $Untaint -> extract(-as_integer => "sessionid") || undef; +my $Version = $Untaint -> extract(-as_integer => "version") || undef; +my $InputVersion = $Untaint -> extract(-as_integer => "version") || undef; +my @PreTopics = @{ $Untaint -> extract(-as_listofint => "pretopic") || undef }; + $mode = $Untaint -> extract(-as_safehtml => "mode") || ""; # FIXME: Can't be "my" since used in subroutines if ($mode ne "add" && $mode ne "reserve" && $mode ne "update" && $mode ne "updatedb") { @@ -98,14 +103,11 @@ if ($mode eq "add") { DocDBHeader("$Project Document Update", "Document Update", -scripts => \@Scripts); } -@ErrorStack = (); -@WarnStack = (); - unless (CanCreate()) { push @ErrorStack,"You are not allowed to modify or create documents."; } if ($mode eq "update" || $mode eq "updatedb") { - unless ($params{docid}) { + unless ($DocumentID) { push @ErrorStack,"You must supply a document number to modify a document."; } } @@ -140,6 +142,10 @@ if ($mode eq "reserve") { $RequiredEntries{Abstract} = 0; } +if ($Preferences{Options}{Update}{RequireNote} && ($mode eq "update" || $mode eq "updatedb")){ + $RequiredEntries{Note} = 1; +} + my $DocRevID; if ($mode eq "update" || $mode eq "updatedb") { @@ -177,11 +183,16 @@ if ($mode eq "update" || $mode eq "updatedb") { # Need to read in last version v $TitleDefault = $DocRevisions{$DocRevID}{Title}; $PubInfoDefault = $DocRevisions{$DocRevID}{PUBINFO}; $AbstractDefault = $DocRevisions{$DocRevID}{Abstract}; - $RequesterDefault = $DocRevisions{$DocRevID}{Submitter}; + if (not $Preferences{Options}{Update}{RequireSubmitter}) { + $RequesterDefault = $DocRevisions{$DocRevID}{Submitter}; + } $KeywordsDefault = $DocRevisions{$DocRevID}{Keywords}; $RevisionNoteDefault = $DocRevisions{$DocRevID}{Note}; $DocTypeIDDefault = $DocRevisions{$DocRevID}{DocTypeID}; @SecurityDefaults = GetRevisionSecurityGroups($DocRevID); + unless (@SecurityDefaults) { + @SecurityDefaults = (0); + } my @AuthorRevIDs = GetRevisionAuthors($DocRevID); @AuthorRevIDs = sort AuthorRevIDsByOrder @AuthorRevIDs; $AuthorListOrdered = IsAuthorListOrdered({ -authorrevids => \@AuthorRevIDs, }); @@ -276,12 +287,12 @@ print $query -> hidden(-name => 'docid', -default => $DocumentID); print $query -> hidden(-name => 'oldversion',-default => $Version); # Generate unique ID to disallow multiple posting -srand (time ^ $$ ^ unpack "%32L*", `ps axww`); +srand (time ^ $$ ^ unpack "%32L*", `ps -eaf`); my $UniqueID = time."-".(int rand (2**31-1)); print $query -> hidden(-name => 'uniqueid', -default => $UniqueID); if ($mode eq "updatedb") { - if (defined $params{version}) { + if (defined $InputVersion) { print $query -> hidden(-name => 'version', -default => $Version); } } @@ -514,7 +525,7 @@ print "\n"; print "\n"; diff --git a/DocDB/cgi/DocumentDatabase b/DocDB/cgi/DocumentDatabase index 8122aa48..2c1439a9 100755 --- a/DocDB/cgi/DocumentDatabase +++ b/DocDB/cgi/DocumentDatabase @@ -11,7 +11,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -47,6 +47,7 @@ require "XRefSQL.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); GetSecurityGroups(); @@ -56,8 +57,6 @@ if ($UserValidation eq "certificate") { $CertificateStatus = CertificateStatus(); } -# %params = $query -> Vars; # No parameters (yet?) - print $query->header( -charset => $HTTP_ENCODING ); if ($UserValidation eq "certificate" && $CertificateStatus ne "verified") { DocDBHeader("$Project Document Database","Document Database", -scripts => ["PopUps"], -refresh => "5;url=$CertificateApplyForm"); diff --git a/DocDB/cgi/DocumentHTML.pm b/DocDB/cgi/DocumentHTML.pm index e1f53144..25d214a1 100644 --- a/DocDB/cgi/DocumentHTML.pm +++ b/DocDB/cgi/DocumentHTML.pm @@ -6,7 +6,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -23,6 +23,8 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +require "HTMLUtilities.pm"; + sub DocumentTable (%) { require "DocumentSQL.pm"; require "RevisionSQL.pm"; @@ -41,6 +43,7 @@ sub DocumentTable (%) { my $MaxDocs = $Params{-maxdocs}; my $NoneBehavior = $Params{-nonebehavior} || "skip"; # skip| my $TalkID = $Params{-talkid} || 0; + my $SkipVersions = $Params{-skipversions} || $False; my @DocumentIDs = @{$Params{-docids}}; my @SessionOrderIDs = @{$Params{-sessionorderids}}; my %FieldList = %{$Params{-fieldlist}}; @@ -263,10 +266,10 @@ sub DocumentTable (%) { } elsif ($Field eq "Abstract") { # Abstract PrintAbstract($DocRevisions{$DocRevID}{Abstract}, {-format => "bare"} ); } elsif ($Field eq "DocNotes") { # Notes and Changes - print AddLineBreaks(URLify($DocRevisions{$DocRevID}{Note})); + print SmartHTML({-text=>$DocRevisions{$DocRevID}{Note}, -addLineBreaks=>$TRUE, -makeURLs=>$TRUE}); } elsif ($Field eq "Files") { # Files in document require "FileHTML.pm"; - ShortFileListByRevID($DocRevID); + ShortFileListByRevID($DocRevID, $SkipVersions); } elsif ($Field eq "Confirm") { print $query -> start_multipart_form('POST',$ConfirmTalkHint); print "
    \n"; @@ -294,9 +297,9 @@ sub DocumentTable (%) { } } elsif ($Field eq "TalkNotes") { if ($SessionTalkID) { - print URLify( AddLineBreaks($SessionTalks{$SessionTalkID}{Note}) ); + print SmartHTML({-text=>$SessionTalks{$SessionTalkID}{Note}, -addLineBreaks=>$TRUE, -makeURLs=>$TRUE}); } elsif ($TalkSeparatorID) { - print URLify( AddLineBreaks($TalkSeparators{$TalkSeparatorID}{Note}) ); + print SmartHTML({-text=>$TalkSeparators{$TalkSeparatorID}{Note}, -addLineBreaks=>$TRUE, -makeURLs=>$TRUE}); } } elsif ($Field eq "Edit") { if ($SessionOrderID) { @@ -382,14 +385,21 @@ sub DocumentLink (%) { $Link .= $DocumentID."-v".$Version; $Link .= $EndElement; } elsif ($TitleLink) { # Use the document Title - $Link .= $DocRevisions{$DocRevID}{Title}; + $Link .= SmartHTML({-text => $DocRevisions{$DocRevID}{Title} }); $Link .= $EndElement; if ($UseSignoffs && !$NoApprovalStatus) { # Put document status on next line require "SignoffUtilities.pm"; + require "SignoffSQL.pm"; + require "SQLUtilities.pm"; my ($ApprovalStatus,$LastApproved) = RevisionStatus($DocRevID); unless ($ApprovalStatus eq "Unmanaged") { $Link .= "
    ($ApprovalStatus"; - if ($ApprovalStatus eq "Unapproved") { + if($ApprovalStatus eq "Approved") { + my $LastApproved = RevisionSignoffDate($DocRevID); + my $ApprovalDateTime = ConvertToDateTime({-MySQLTimeStamp => $LastApproved, }); + my $ApprovalTime = DateTimeString({ -DateTime => $ApprovalDateTime, -ShowTime => $FALSE, }); + $Link .= " - $ApprovalTime"; + } elsif ($ApprovalStatus eq "Unapproved") { if (defined $LastApproved) { my $DocumentID = $DocRevisions{$LastApproved}{DOCID}; my $Version = $DocRevisions{$LastApproved}{Version}; diff --git a/DocDB/cgi/DocumentSQL.pm b/DocDB/cgi/DocumentSQL.pm index 1b2591be..7f8fc7d3 100644 --- a/DocDB/cgi/DocumentSQL.pm +++ b/DocDB/cgi/DocumentSQL.pm @@ -1,5 +1,5 @@ -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/DocumentUtilities.pm b/DocDB/cgi/DocumentUtilities.pm index 0b34f677..beb0d086 100644 --- a/DocDB/cgi/DocumentUtilities.pm +++ b/DocDB/cgi/DocumentUtilities.pm @@ -8,7 +8,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/EditTalkInfo b/DocDB/cgi/EditTalkInfo index a84e4f00..04f01b5b 100755 --- a/DocDB/cgi/EditTalkInfo +++ b/DocDB/cgi/EditTalkInfo @@ -5,14 +5,14 @@ # and display it since it could get crowded in the normal table. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,7 +26,8 @@ # FIXME: XHTML -use CGI qw(-nosticky); +use CGI qw(-nosticky); +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -36,37 +37,29 @@ require "ResponseElements.pm"; require "Security.pm"; require "MeetingSecurityUtilities.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "DBUtilities.pm"; -#require "DocumentSQL.pm"; -#require "RevisionSQL.pm"; require "TalkSQL.pm"; require "MeetingSQL.pm"; require "TalkHintSQL.pm"; -#require "TalkHintUtilities.pm"; -#require "DocumentUtilities.pm"; -#require "FormElements.pm"; - -#require "DocumentHTML.pm"; -#require "TalkHTML.pm"; -#require "AuthorHTML.pm"; -#require "TopicHTML.pm"; - -$query = new CGI; -my %Params = $query -> Vars; - -my $SessionOrderID = $Params{sessionorderid}; -my $Title = $Params{talktitle}; -my $DocumentID = $Params{docid}; -my $Confirmed = $Params{talkconfirm}; -my $Length = $Params{talktime}; -my $Note = $Params{talknote}; -my @AuthorHints = split /\0/,$Params{authors}; -my @TopicHints = split /\0/,$Params{topics}; + +$query = new CGI; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); + +my $SessionOrderID = $Untaint -> extract(-as_integer => "sessionorderid") || 0; +my $Title = $Untaint -> extract(-as_safehtml => "talktitle") || ""; +my $DocumentID = $Untaint -> extract(-as_integer => "docid") || 0; +my $Confirmed = $Untaint -> extract(-as_safehtml => "talkconfirm") || ""; +my $Length = $Untaint -> extract(-as_safehtml => "talktime") || ""; +my $Note = $Untaint -> extract(-as_safehtml => "talknote") || ""; +my @AuthorHints = @{ $Untaint -> extract(-as_listofint => "authors") || undef }; +my @TopicHints = @{ $Untaint -> extract(-as_listofint => "topics") || undef }; if ($Confirmed) { $Confirmed = $TRUE; } - + CreateConnection(-type => "rw"); EndPage(-startpage => $TRUE); @@ -99,14 +92,14 @@ EndPage(-startpage => $TRUE); if ($TalkSeparatorID) { # Modify a talk separator my $TalkSeparatorUpdate = $dbh -> prepare( "update TalkSeparator set ". - "Time=?, Title=?, Note=? ". + "Time=?, Title=?, Note=? ". "where TalkSeparatorID=?"); $TalkSeparatorUpdate -> execute($Length,$Title,$Note,$TalkSeparatorID); push @ActionStack,"Modified break: $Title"; } elsif ($SessionTalkID) { # Modify a talk my $SessionTalkUpdate = $dbh -> prepare( "update SessionTalk set ". - "DocumentID=?, Confirmed=?, Time=?, HintTitle=?, Note=? ". + "DocumentID=?, Confirmed=?, Time=?, HintTitle=?, Note=? ". "where SessionTalkID=?"); $SessionTalkUpdate -> execute($DocumentID,$Confirmed,$Length,$Title,$Note,$SessionTalkID); if ($Confirmed) { @@ -116,7 +109,7 @@ if ($TalkSeparatorID) { # Modify a talk separator InsertAuthorHints($SessionTalkID,@AuthorHints); push @ActionStack,"Modified talk: $Title"; } - + # Start page print $query -> header( -charset => $HTTP_ENCODING ); diff --git a/DocDB/cgi/EmailAdminister b/DocDB/cgi/EmailAdminister index c7765775..e89a3fc4 100755 --- a/DocDB/cgi/EmailAdminister +++ b/DocDB/cgi/EmailAdminister @@ -1,23 +1,23 @@ #! /usr/bin/env perl # -# Name: EmailAdminister -# Description: This script is called by EmailAdministerForm and does +# Name: EmailAdminister +# Description: This script is called by EmailAdministerForm and does # administration on users who have signed up for email from the # DB. Since users can change almost everything, it really just # deletes users and changes their passwords in case they forget. -# It also displays all the users and their notification +# It also displays all the users and their notification # preferences. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -30,40 +30,44 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "SecuritySQL.pm"; require "NotificationSQL.pm"; require "Messages.pm"; require "EmailUserHTML.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -# Parameters to script +# Parameters to script -%params = $query -> Vars; -my $Password = $params{password}; -my $Username = $params{admuser}; -my $Action = $params{admaction}; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; -my $EmailUserID = $params{emailuserid}; -my $SingleUser = $params{singleuser}; -my $NewPassword = $params{resetpw}; -my $ClearGroups = ($params{cleargroups} eq "on"); -my $ClearUser = ($params{clearuser} eq "on"); -my $UserSign = ($params{usersign} eq "on"); -my $VerifyUser = ($params{verifyuser} eq "on"); -my @UsersGroupIDs = split /\0/,$params{usergroups}; +my $EmailUserID = $Untaint -> extract(-as_integer => "emailuserid") || 0; +my $SingleUser = $Untaint -> extract(-as_safehtml => "singleuser") || ""; +my $NewPassword = $Untaint -> extract(-as_printable => "resetpw") || ""; + +my $ClearGroups = ($Untaint -> extract(-as_printable => "cleargroups") eq "on"); +my $ClearUser = ($Untaint -> extract(-as_printable => "clearuser") eq "on"); +my $UserSign = ($Untaint -> extract(-as_printable => "usersign") eq "on"); +my $VerifyUser = ($Untaint -> extract(-as_printable => "verifyuser") eq "on"); +my @UsersGroupIDs = @{ $Untaint -> extract(-as_listofint => "usergroups") || undef }; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,$Msg_AdminNoConnect; -} +} print $query -> header( -charset => $HTTP_ENCODING ); DocDBHeader("Modified E-mail Users"); @@ -73,7 +77,7 @@ GetSecurityGroups(); unless (CanAdminister()) { push @ErrorStack,$Msg_AdminNoLogin; -} +} EndPage(); if ($Action eq "Delete") { # Delete user @@ -94,21 +98,21 @@ if ($Action eq "Delete") { # Delete user my $Table = "Email$NotifyType$NotifyTime"; my $NotifyDelete = $dbh -> prepare("delete from $Table where EmailUserID=?"); $NotifyDelete -> execute($EmailUserID); - } + } } push @ActionStack,"The user was deleted."; } ActionReport(); -} elsif ($Action eq "Modify") { - unless ($EmailUserID) { # Deal with password changes +} elsif ($Action eq "Modify") { + unless ($EmailUserID) { # Deal with password changes push @ErrorStack,$Msg_ModEUserEmpty; } EndPage(); FetchEmailUser($EmailUserID); - if ($NewPassword) { - srand (time ^ $$ ^ unpack "%32L*", `ps axww`); + if ($NewPassword) { + srand (time ^ $$ ^ unpack "%32L*", `ps -eaf`); my $Salt = ((0..9,'a'..'z','A'..'Z','.','/')[(int rand (64))]). ((0..9,'a'..'z','A'..'Z','.','/')[(int rand (64))]); @@ -126,9 +130,9 @@ if ($Action eq "Delete") { # Delete user if ($ClearUser || $SingleUser) { my $UserUpdate = $dbh -> prepare("update EmailUser set CanSign=0,Verified=0 where EmailUserID=?"); $UserUpdate -> execute($EmailUserID); - unless ($SingleUser) { + unless ($SingleUser) { push @ActionStack,"The user is no longer verified and cannot sign documents."; - } + } } if ($UserSign) { my $UserUpdate = $dbh -> prepare("update EmailUser set CanSign=1 where EmailUserID=?"); @@ -139,13 +143,13 @@ if ($Action eq "Delete") { # Delete user my $UserUpdate = $dbh -> prepare("update EmailUser set Verified=1 where EmailUserID=?"); $UserUpdate -> execute($EmailUserID); push @ActionStack,"The user is verified."; - + if ($MailInstalled && $UserValidation eq "certificate") { require "EmailUtilities.pm"; my @To = ($EmailUser{$EmailUserID}{EmailAddress},$DBWebMasterEmail); my $Subject = "DocDB account for $EmailUser{$EmailUserID}{Name} activated"; - my $Body = "An adminstrator has approved the request for "; + my $Body = "An administrator has approved the request for "; $Body .= "$EmailUser{$EmailUserID}{Name} for access to $Project DocDB. "; $Body .= "If you did not request access to $Project DocDB, "; $Body .= "please contact $DBWebMasterEmail immediately."; @@ -154,35 +158,35 @@ if ($Action eq "Delete") { # Delete user } foreach my $UsersGroupID (@UsersGroupIDs) { my $UsersGroupSelect = $dbh -> prepare("select UsersGroupID from UsersGroup where EmailUserID=? and GroupID=?"); - $UsersGroupSelect -> execute($EmailUserID,$UsersGroupID); + $UsersGroupSelect -> execute($EmailUserID,$UsersGroupID); my ($ComboExists) = $UsersGroupSelect -> fetchrow_array; - unless ($ComboExists) { + unless ($ComboExists) { my $UsersGroupUpdate = $dbh -> prepare("insert into UsersGroup (UsersGroupID,EmailUserID,GroupID) ". " values (0,?,?)"); - $UsersGroupUpdate -> execute($EmailUserID,$UsersGroupID); + $UsersGroupUpdate -> execute($EmailUserID,$UsersGroupID); FetchSecurityGroup($UsersGroupID); push @ActionStack,"Added user to $SecurityGroups{$UsersGroupID}{NAME}"; - } - } - + } + } + ClearEmailUsers(); FetchEmailUser($EmailUserID); ActionReport(); - + print "

    The user now has the following information:

    "; print "
    \n"; print FormElementTitle(-helplink => "doctypeentry", -helptext => "Short Description"); - print $query -> textfield (-name => 'name', + print $query -> textfield (-name => 'name', -size => 20, -maxlength => 32, $Booleans); print "
    \n"; print FormElementTitle(-helplink => "doctypeentry", -helptext => "Long Description"); - print $query -> textfield (-name => 'longdesc', + print $query -> textfield (-name => 'longdesc', -size => 40, -maxlength => 255, $Booleans); print "
    \n"; TextField(-name => 'xrefs', -size => 40, - -default => $XRefDefault, + -default => $XRefDefault, -maxlength => 2048, -helplink => 'xrefentry', -helptext => 'Related Documents'); print "
    \n"; PrintEmailUserInfo($EmailUserID); print "
    \n"; -} elsif ($Action eq "New") { +} elsif ($Action eq "New") { push @ErrorStack,"You can't create new users here. Do it the normal way."; } else { push @ErrorStack,"No valid action was specified."; -} +} EndPage(); WarnPage(); DocDBNavBar(); DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/EmailAdministerForm b/DocDB/cgi/EmailAdministerForm index ae879737..55d254b4 100755 --- a/DocDB/cgi/EmailAdministerForm +++ b/DocDB/cgi/EmailAdministerForm @@ -10,7 +10,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -28,6 +28,7 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI qw(-nosticky); +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -35,6 +36,7 @@ require "Scripts.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "AdministerElements.pm"; require "EmailUserHTML.pm"; require "SecurityHTML.pm"; @@ -45,11 +47,12 @@ require "SecuritySQL.pm"; require "NotificationSQL.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI -> connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); -my $EmailUserID = $params{emailuserid} || 0; +my $EmailUserID = $Untaint -> extract(-as_integer => "emailuserid") || 0; GetSecurityGroups(); @@ -65,6 +68,11 @@ unless (CanAdminister()) { EndPage(); +my $UsernameHeader = "Username"; +if ($UserValidation eq "certificate") { + $UsernameHeader = "Certificate DN" +} + if ($EmailUserID) { print "

    This form allows you to delete the user, change which groups the user belongs to, "; @@ -121,7 +129,7 @@ print "\n"; print "\n"; print "\n"; - EmailUserSelect(-disabled => $TRUE, -default => [$EmailUserID]); + EmailUserSelect(-disabled => $TRUE, -default => [$EmailUserID], -helptext => $UsernameHeader); print "\n"; print "\n"; @@ -195,7 +203,7 @@ if ($EmailUserID) { my @EmailUserIDs = sort EmailUserIDsByName GetEmailUserIDs(); print "\n"; - print "\n"; + print "\n"; #print "\n"; my $Row = 0; @@ -231,8 +239,8 @@ if ($EmailUserID) { my $Link = $EmailAdministerForm."?emailuserid=$EmailUserID"; print "\n"; - print "\n"; - print "\n"; + print "\n"; + print "\n"; print "\n"; print "\n"; print "\n"; @@ -251,7 +259,7 @@ if ($EmailUserID) { print "

    $SecurityGroup has these members:

    \n
      \n"; foreach my $EmailUserID (@EmailUserIDs) { if ($EmailUser{$EmailUserID}{Name}) { - print "
    • $EmailUser{$EmailUserID}{Name} ($EmailUser{$EmailUserID}{Username}, $EmailUser{$EmailUserID}{EmailAddress})
    • \n"; + print "
    • ".SmartHTML({-text => "$EmailUser{$EmailUserID}{Name} ($EmailUser{$EmailUserID}{Username}, $EmailUser{$EmailUserID}{EmailAddress})"})."
    • \n"; } else { print "
    • Unknown (ID: $EmailUserID)
    • \n"; } diff --git a/DocDB/cgi/EmailCreate b/DocDB/cgi/EmailCreate index daaba2ec..455bf4de 100755 --- a/DocDB/cgi/EmailCreate +++ b/DocDB/cgi/EmailCreate @@ -3,15 +3,15 @@ # Description: Creates a new e-mail notification account # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -23,24 +23,27 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI; +use CGI; +use CGI::Untaint; use DBI; - + require "DocDBGlobals.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "ResponseElements.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rwuser,$db_rwpass); @ErrorStack = (); -%params = $query -> Vars; +my $Untaint = CGI::Untaint -> new($query -> Vars); # Collect parameters -my $UserName = $params{username}; -my $Password = $params{password}; -my $PassConf = $params{passconf}; +my $UserName = $Untaint -> extract(-as_safehtml => "username") || ""; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $PassConf = $Untaint -> extract(-as_printable => "passconf") || ""; $UserName =~ s/\s+//g; $Password =~ s/\s+//g; $PassConf =~ s/\s+//g; @@ -65,15 +68,15 @@ if ($UserExists) { } # Start the page - + print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("Notification Account Creation"); # Everything is OK, create the account unless (@ErrorStack) { - srand (time ^ $$ ^ unpack "%32L*", `ps axww`); - + srand (time ^ $$ ^ unpack "%32L*", `ps -eaf`); + my $Salt = ((0..9,'a'..'z','A'..'Z','.','/')[(int rand (64))]). ((0..9,'a'..'z','A'..'Z','.','/')[(int rand (64))]); @@ -81,10 +84,10 @@ unless (@ErrorStack) { my $UserInsert = $dbh -> prepare( "insert into EmailUser (EmailUserID,Username,Password) ". "values (0, ?, ?)"); - $UserInsert -> execute($UserName,$EncryptedPassword); - + $UserInsert -> execute($UserName,$EncryptedPassword); + print "User $UserName created. Do not forget your password, there is no way to - retrieve it.

      \n"; + retrieve it.

      \n"; } EndPage(@ErrorStack); diff --git a/DocDB/cgi/EmailLogin b/DocDB/cgi/EmailLogin index 7f9ee8ea..49c5cd7b 100755 --- a/DocDB/cgi/EmailLogin +++ b/DocDB/cgi/EmailLogin @@ -6,7 +6,7 @@ # Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -32,6 +32,7 @@ require "ResponseElements.pm"; require "EmailSecurity.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); diff --git a/DocDB/cgi/EmailSecurity.pm b/DocDB/cgi/EmailSecurity.pm index bdbad545..4c1f3dde 100644 --- a/DocDB/cgi/EmailSecurity.pm +++ b/DocDB/cgi/EmailSecurity.pm @@ -8,7 +8,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -77,9 +77,9 @@ sub UserPrefForm ($) { print "

    \n"; + print "Username:\n"; } elsif ($UserValidation eq "certificate") { - print "\n"; + print "\n"; } else { print "\n\n\n"; print "\n\n"; } else { print "\n\n"; print "\n\n"; print "\n\n"; } diff --git a/DocDB/cgi/EmailUserHTML.pm b/DocDB/cgi/EmailUserHTML.pm index 2a046d3d..76879385 100644 --- a/DocDB/cgi/EmailUserHTML.pm +++ b/DocDB/cgi/EmailUserHTML.pm @@ -1,10 +1,10 @@ -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -18,49 +18,49 @@ sub PrintEmailUserInfo ($) { my ($EmailUserID) = @_; - + require "NotificationSQL.pm"; require "SecuritySQL.pm"; require "MailNotification.pm"; - - FetchEmailUser($EmailUserID); - + + FetchEmailUser($EmailUserID); + print "\n"; print "\n"; + print "\n"; print "\n"; } diff --git a/DocDB/cgi/EmailUtilities.pm b/DocDB/cgi/EmailUtilities.pm index b02de41f..aecf3c95 100644 --- a/DocDB/cgi/EmailUtilities.pm +++ b/DocDB/cgi/EmailUtilities.pm @@ -1,9 +1,9 @@ -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -15,32 +15,34 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +use HTML::Entities; + sub SendEmail (%) { unless ($MailInstalled) { return 0; - } + } require Mail::Send; #FIXME: Why not use? require Mail::Mailer; my (%Params) = @_; - + my %Headers = (); my @Addressees = @{$Params{-to}}; my $From = $Params{-from} || "$Project Document Database <$DBWebMasterEmail>"; my $Subject = $Params{-subject} || "$Project Document Database"; my $Body = $Params{-body} || ""; - + my %Headers = (); - + if (@Addressees) { print "Sending mail to: ",join ", ",@Addressees,"
    \n"; my $Mailer = new Mail::Mailer 'smtp', Server => $MailServer; $Headers{To} = \@Addressees; $Headers{From} = $From; - $Headers{Subject} = $Subject; - + $Headers{Subject} = HTML::Entities::decode_entities($Subject); + $Mailer -> open(\%Headers); # Start mail with headers - print $Mailer $Body; + print $Mailer HTML::Entities::decode_entities($Body); $Mailer -> close; # Complete the message and send it } return int(@Addressees); diff --git a/DocDB/cgi/EventAdministerForm b/DocDB/cgi/EventAdministerForm index 153824ee..dd91d814 100755 --- a/DocDB/cgi/EventAdministerForm +++ b/DocDB/cgi/EventAdministerForm @@ -9,7 +9,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -28,6 +28,7 @@ use CGI qw(-nosticky); +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -40,6 +41,7 @@ require "Sorts.pm"; require "DBUtilities.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "MeetingSQL.pm"; require "SecuritySQL.pm"; @@ -48,19 +50,19 @@ require "MeetingHTML.pm"; require "TopicHTML.pm"; # For description boxes $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -%params = $query -> Vars; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; +my $Force = $Untaint -> extract(-as_printable => "admforce") || ""; -my $Password = $params{password}; -my $Username = $params{admuser}; -my $Action = $params{admaction}; -my $Force = $params{admforce}; - -my $SubForm = $params{subform}; -my $EventGroupID = int($params{eventgroups}); -my $EventID = int($params{events}); -my $ShortDescription = $params{shortdesc}; -my $LongDescription = $params{longdesc}; +my $SubForm = $Untaint -> extract(-as_printable => "subform") || ""; +my $EventGroupID = $Untaint -> extract(-as_integer => "eventgroups") || 0; +my $EventID = $Untaint -> extract(-as_integer => "events") || 0; +my $ShortDescription = $Untaint -> extract(-as_safehtml => "shortdesc") || ""; +my $LongDescription = $Untaint -> extract(-as_safehtml => "longdesc") || ""; $query -> delete_all(); @@ -94,18 +96,19 @@ if ($SubForm eq "eventgroup") { if ($Action eq "Delete") { &DeleteEventGroup(-eventgroupid => $EventGroupID, -force => $Force); } elsif ($Action eq "Modify") { + my $OldShortDescription = SmartHTML({-text => $EventGroups{$EventGroupID}{ShortDescription}},); if ($ShortDescription) { - push @ActionStack,"Updated short description of $EventGroups{$EventGroupID}{ShortDescription}"; + push @ActionStack,"Updated short description of $OldShortDescription"; my $Update = $dbh->prepare("update EventGroup set ShortDescription=? where EventGroupID=?"); $Update -> execute($ShortDescription,$EventGroupID); } if ($LongDescription) { - push @ActionStack,"Updated long description of $EventGroups{$EventGroupID}{ShortDescription}"; + push @ActionStack,"Updated long description of $OldShortDescription"; my $Update = $dbh->prepare("update EventGroup set LongDescription=? where EventGroupID=?"); $Update -> execute($LongDescription,$EventGroupID); } } elsif ($Action eq "New") { - push @ActionStack,"New event group with description $ShortDescription inserted"; + push @ActionStack,"New event group with description $ShortDescription inserted"; my $Insert = $dbh -> prepare("insert into EventGroup (ShortDescription,LongDescription) values (?,?)"); $Insert -> execute($ShortDescription,$LongDescription); } else { @@ -115,7 +118,7 @@ if ($SubForm eq "eventgroup") { if ($Action eq "Delete") { &DeleteEvent(-eventid => $EventID, -force => $Force); } else { - push @WarnStack,"Only \"Delete\" is a valid action"; + push @WarnStack,"Only \"Delete\" is a valid action for events."; } } diff --git a/DocDB/cgi/EventInstructions.pm b/DocDB/cgi/EventInstructions.pm index d7f289fa..2b727c65 100644 --- a/DocDB/cgi/EventInstructions.pm +++ b/DocDB/cgi/EventInstructions.pm @@ -6,7 +6,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/EventUtilities.pm b/DocDB/cgi/EventUtilities.pm index 42cf87fe..22eea1c6 100644 --- a/DocDB/cgi/EventUtilities.pm +++ b/DocDB/cgi/EventUtilities.pm @@ -7,7 +7,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/ExternalDocDBAdministerForm b/DocDB/cgi/ExternalDocDBAdministerForm index 0170b727..0929a523 100755 --- a/DocDB/cgi/ExternalDocDBAdministerForm +++ b/DocDB/cgi/ExternalDocDBAdministerForm @@ -1,18 +1,18 @@ #! /usr/bin/env perl # # Name: ExternalDocDBAdministerForm -# Description: Allows the administrator to add knowledge of other DocDBs. +# Description: Allows the administrator to add knowledge of other DocDBs. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,6 +26,7 @@ use CGI qw(-nosticky); +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -38,27 +39,28 @@ require "Sorts.pm"; require "DBUtilities.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "SecuritySQL.pm"; require "XRefHTML.pm"; require "XRefSQL.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -%params = $query -> Vars; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; +my $Force = $Untaint -> extract(-as_printable => "admforce") || ""; -my $Password = $params{password}; -my $Username = $params{admuser}; -my $Action = $params{admaction}; -my $Force = $params{admforce}; +my $SubForm = $Untaint -> extract(-as_printable => "subform") || ""; -my $SubForm = $params{subform}; - -my $ExternalDocDBID = $params{externaldocdbs}; -my $ProjectName = $params{project}; -my $Description = $params{desc}; -my $PublicURL = $params{puburl}; -my $PrivateURL = $params{privurl}; +my $ExternalDocDBID = $Untaint -> extract(-as_integer => "externaldocdbs") || 0; +my $ProjectName = $Untaint -> extract(-as_safehtml => "project") || ""; +my $Description = $Untaint -> extract(-as_safehtml => "desc") || ""; +my $PublicURL = $Untaint -> extract(-as_safehtml => "puburl") || ""; +my $PrivateURL = $Untaint -> extract(-as_safehtml => "privurl") || ""; $query -> delete_all(); @@ -75,7 +77,7 @@ GetSecurityGroups(); print $query -> header( -charset => $HTTP_ENCODING ); DocDBHeader("Administer External DocDBs","", - -scripts => ["PopUps","ExternalDocDBAdminDisable"]); + -scripts => ["PopUps","ExternalDocDBAdminDisable"]); unless (CanAdminister()) { push @ErrorStack,"You are not allowed to access administrative functions."; @@ -95,40 +97,40 @@ if ($SubForm eq "externaldocdb") { $Delete -> execute($ExternalDocDBID); push @ActionStack,"Deleted reference to external DocDB"; } elsif ($Action eq "Modify") { - if ($ProjectName) { - push @ActionStack,"Updated project name of $ExternalDocDBs{$ExternalDocDBID}{Project}"; + if ($ProjectName) { + push @ActionStack,"Updated the project name."; my $Update = $dbh->prepare("update ExternalDocDB set Project=? where ExternalDocDBID=?"); $Update -> execute($ProjectName,$ExternalDocDBID); } - if ($Description) { - push @ActionStack,"Updated description of $ExternalDocDBs{$ExternalDocDBID}{Project}"; + if ($Description) { + push @ActionStack,"Updated the description."; my $Update = $dbh->prepare("update ExternalDocDB set Description=? where ExternalDocDBID=?"); $Update -> execute($Description,$ExternalDocDBID); } - if ($PrivateURL) { - push @ActionStack,"Updated private URL of $ExternalDocDBs{$ExternalDocDBID}{Project}"; + if ($PrivateURL) { + push @ActionStack,"Updated the private URL."; my $Update = $dbh->prepare("update ExternalDocDB set PrivateURL=? where ExternalDocDBID=?"); $Update -> execute($PrivateURL,$ExternalDocDBID); } - if ($PublicURL) { - push @ActionStack,"Updated public URL of $ExternalDocDBs{$ExternalDocDBID}{Project}"; + if ($PublicURL) { + push @ActionStack,"Updated the public URL."; my $Update = $dbh->prepare("update ExternalDocDB set PublicURL=? where ExternalDocDBID=?"); $Update -> execute($PublicURL,$ExternalDocDBID); } - } elsif ($Action eq "New") { - push @ActionStack,"New external DocDB for $ProjectName added"; - my $Insert = $dbh -> prepare("insert into ExternalDocDB (Project,Description,PrivateURL,PublicURL) values (?,?,?,?)"); + } elsif ($Action eq "New") { + push @ActionStack,"New external DocDB for $ProjectName added"; + my $Insert = $dbh -> prepare("insert into ExternalDocDB (Project,Description,PrivateURL,PublicURL) values (?,?,?,?)"); $Insert -> execute($ProjectName,$Description,$PrivateURL,$PublicURL); } else { push @WarnStack,"No valid action was specified."; - } + } } - -if (@ActionStack) { + +if (@ActionStack) { ClearExternalDocDBs(); GetAllExternalDocDBs(); ActionReport(); -} +} EndPage(); @@ -157,7 +159,7 @@ print $query -> start_multipart_form('POST',"$ExternalDocDBAdministerForm", "name=\"externaldocdb\" id=\"externaldocdb\""); print "
    NameUsernameVerified?Can Sign?Groups
    Name$UsernameHeaderVerified?Can Sign?Groups
    Notifications
    $EmailUser{$EmailUserID}{Name} $EmailUser{$EmailUserID}{Username}".SmartHTML({-text => $EmailUser{$EmailUserID}{Name}})."".SmartHTML({-text => $EmailUser{$EmailUserID}{Username}})."$Verified$CanSign$Groups
    \n"; print $query -> hidden(-name => 'username', -default => $Username); print $query -> hidden(-name => 'digest', -default => $Digest); - print "Username:$Username
    ".SmartHTML({-text => $Username})."
    Username:$Username
    Username:".SmartHTML({-text => $Username})."
    Username:"; print $query -> textfield(-name => 'username', -default => $Username, @@ -94,16 +94,16 @@ sub UserPrefForm ($) { if ($UserValidation eq "certificate") { print "
    Real name:$Name
    E-mail address:"; - print $query -> textfield(-name => 'email', -default => $EmailAddress, + print $query -> textfield(-name => 'email', -default => SmartHTML({-text => $EmailAddress}), -size => 24, -maxlength => 64); print "
    Real name:"; - print $query -> textfield(-name => 'name', -default => $Name, + print $query -> textfield(-name => 'name', -default => SmartHTML({-text => $Name}), -size => 24, -maxlength => 128); print "
    E-mail address:"; - print $query -> textfield(-name => 'email', -default => $EmailAddress, + print $query -> textfield(-name => 'email', -default => SmartHTML({-text => $EmailAddress}), -size => 24, -maxlength => 64); print "
    New password:"; @@ -129,7 +129,7 @@ sub UserPrefForm ($) { my @UserGroupIDs = &FetchUserGroupIDs($EmailUserID); foreach my $UserGroupID (@UserGroupIDs) { &FetchSecurityGroup($UserGroupID); - print "
  • $SecurityGroups{$UserGroupID}{NAME}
  • \n"; + print "
  • ".SmartHTML({-text => $SecurityGroups{$UserGroupID}{NAME}})."
  • \n"; } print "
    \n"; print "\n"; print "\n"; - print "\n"; + print "\n"; print "\n"; - print "\n"; + print "\n"; print "\n"; - print "\n"; + print "\n"; print "\n"; print ""; - print "\n"; + print "\n"; print "\n"; print ""; - print "\n"; + print "\n"; print "\n"; print ""; - print "\n"; + print "\n"; print "\n"; - + # Groups user belongs (or wants to belong to) - + print ""; - print "\n"; print "\n"; print "
    Username:$EmailUser{$EmailUserID}{Username}Username:".SmartHTML({-text => $EmailUser{$EmailUserID}{Username}})."
    Name:$EmailUser{$EmailUserID}{Name}Name:".SmartHTML({-text => $EmailUser{$EmailUserID}{Name}})."
    E-mail:$EmailUser{$EmailUserID}{EmailAddress}E-mail:".SmartHTML({-text => $EmailUser{$EmailUserID}{EmailAddress}})."
    Verified:".("No","Yes")[$EmailUser{$EmailUserID}{Verified}]."".("No","Yes")[$EmailUser{$EmailUserID}{Verified}]."
    HTML:".("No","Yes")[$EmailUser{$EmailUserID}{PreferHTML}]."".("No","Yes")[$EmailUser{$EmailUserID}{PreferHTML}]."
    Can Sign:".("No","Yes")[$EmailUser{$EmailUserID}{CanSign}]."".("No","Yes")[$EmailUser{$EmailUserID}{CanSign}]."
    Groups:\n"; + print "\n"; my @UserGroupIDs = FetchUserGroupIDs($EmailUserID); if (@UserGroupIDs) { print "
      \n"; foreach my $UserGroupID (@UserGroupIDs) { FetchSecurityGroup($UserGroupID); - print "
    • $SecurityGroups{$UserGroupID}{NAME}
    • \n"; + print "
    • ".SmartHTML({-text => $SecurityGroups{$UserGroupID}{NAME}})."
    • \n"; } print "
    \n"; } else { print " \n"; - } + } print "
    \n"; @@ -76,7 +76,7 @@ sub PrintEmailUserInfo ($) { print "
    \n"; DisplayNotification($EmailUserID,"Weekly"); - print "
    \n"; print "\n"; -print "\n"; @@ -165,33 +167,33 @@ print "\n"; print "\n"; print "\n"; -print "\n"; +print "\n"; print "\n"; print "\n"; -print "\n"; print "\n"; print "\n"; -print "\n"; print "\n"; print "\n"; -print "\n"; print "\n"; print "\n"; -print "\n"; print "\n"; diff --git a/DocDB/cgi/FSUtilities.pm b/DocDB/cgi/FSUtilities.pm index fd98d3a0..db10e269 100644 --- a/DocDB/cgi/FSUtilities.pm +++ b/DocDB/cgi/FSUtilities.pm @@ -5,7 +5,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -162,6 +162,9 @@ sub ProtectDirectory { # Write (or delete) correct .htaccess file in directory } my $AuthName = join ' or ',@users; + if ($Preferences{Security}{AuthName}) { + $AuthName = $Preferences{Security}{AuthName}; + } my $directory = &GetDirectory($documentID,$version); if (@users) { @@ -257,7 +260,7 @@ sub ExtractArchive { system ($Command); } else { print "Could not unpack the archive; contact an - adminstrator.
    \n"; + administrator.
    \n"; } chdir $current_dir; } @@ -281,7 +284,7 @@ sub DownloadURLs (%) { if ($Files{$FileKey}{URL}) { my $URL = $Files{$FileKey}{URL}; unless (&ValidFileURL($URL)) { - push @ErrorStack,"The URL $URL is not well formed. Don't forget ". + push @ErrorStack,"The URL $URL is not well formed. Don't forget ". "http:// on the front and a file name after the last /."; } my @Options = (); @@ -332,7 +335,7 @@ sub DownloadURLs (%) { } sub MakeTmpSubDir { - my $TmpSubDir = $TmpDir."/".(time ^ $$ ^ unpack "%32L*", `ps axww`); + my $TmpSubDir = $TmpDir."/".(time ^ $$ ^ unpack "%32L*", `ps -eaf`); mkdir $TmpSubDir, oct 755 or die "Could not make temporary directory"; return $TmpSubDir; } diff --git a/DocDB/cgi/FileHTML.pm b/DocDB/cgi/FileHTML.pm index 4c999a79..653003ca 100644 --- a/DocDB/cgi/FileHTML.pm +++ b/DocDB/cgi/FileHTML.pm @@ -1,17 +1,17 @@ +# Name: FileHTML.pm # -# Description: Subroutines to provide links for files, groups of +# Description: Subroutines to provide links for files, groups of # files and archives. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: -# +# Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -23,6 +23,7 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +require "HTMLUtilities.pm"; sub FileListByRevID { require "MiscSQL.pm"; @@ -44,22 +45,22 @@ sub FileListByRevID { push @RootFiles,$FileID; } else { push @OtherFiles,$FileID; - } + } } if (@RootFiles) { print "
    \n"; &FileListByFileID(@RootFiles); print "
    \n"; - } + } if (@OtherFiles) { print "
    Other Files:\n"; &FileListByFileID(@OtherFiles); print "
    \n"; - } - unless ($Public) { + } + unless ($Public) { my $ArchiveLink = &ArchiveLink($DocumentID,$Version); print "
    $ArchiveLink
    \n"; - } + } } else { print "
    None
    \n"; } @@ -69,7 +70,7 @@ sub FileListByRevID { sub ShortFileListByRevID { require "MiscSQL.pm"; - my ($DocRevID) = @_; + my ($DocRevID, $SkipVersions) = @_; my @FileIDs = &FetchDocFiles($DocRevID); my $DocumentID = $DocRevisions{$DocRevID}{DOCID}; @@ -79,10 +80,10 @@ sub ShortFileListByRevID { foreach $File (@FileIDs) { if ($DocFiles{$File}{ROOT}) { push @RootFiles,$File - } + } } if (@RootFiles) { - &ShortFileListByFileID(@RootFiles); + ShortFileListByFileID({-files => \@RootFiles, -skipversions => $SkipVersions, }); } else { print "None
    \n"; } @@ -90,14 +91,14 @@ sub ShortFileListByRevID { sub FileListByFileID { require "Sorts.pm"; - + my (@Files) = @_; unless (@Files) { return; - } - + } + @Files = sort FilesByDescription @Files; - + print "
      \n"; foreach my $FileID (@Files) { my $DocRevID = $DocFiles{$FileID}{DOCREVID}; @@ -107,31 +108,33 @@ sub FileListByFileID { -shortname => $DocFiles{$FileID}{NAME}, -description => $DocFiles{$FileID}{DESCRIPTION}} ); print "
    • $Link
    • \n"; - } + } print "
    \n"; } sub ShortFileListByFileID { # FIXME: Make special case of FileListByFileID require "Sorts.pm"; - - my (@Files) = @_; - + + my ($ArgRef) = @_; + my @Files = exists $ArgRef->{-files} ? @{$ArgRef->{-files}} : (); + my $SkipVersions = exists $ArgRef->{-skipversions} ? $ArgRef->{-skipversions} : $FALSE; + @Files = sort FilesByDescription @Files; - + foreach my $FileID (@Files) { my $DocRevID = $DocFiles{$FileID}{DOCREVID}; my $Version = $DocRevisions{$DocRevID}{VERSION}; my $DocumentID = $DocRevisions{$DocRevID}{DOCID}; my $Link = FileLink( {-maxlength => 20, -format => "short", -docid => $DocumentID, -version => $Version, - -shortname => $DocFiles{$FileID}{NAME}, + -shortname => $DocFiles{$FileID}{NAME}, -skipversions => $SkipVersions, -description => $DocFiles{$FileID}{DESCRIPTION}} ); print "$Link
    \n"; - } + } } sub FileLink ($) { my ($ArgRef) = @_; - + my $DocumentID = exists $ArgRef->{-docid} ? $ArgRef->{-docid} : 0; my $Version = exists $ArgRef->{-version} ? $ArgRef->{-version} : 0; my $ShortName = exists $ArgRef->{-shortname} ? $ArgRef->{-shortname} : ""; @@ -139,6 +142,7 @@ sub FileLink ($) { my $MaxLength = exists $ArgRef->{-maxlength} ? $ArgRef->{-maxlength} : 60; my $MaxExt = exists $ArgRef->{-maxext} ? $ArgRef->{-maxext} : 4; my $Format = exists $ArgRef->{-format} ? $ArgRef->{-format} : "long"; + my $SkipVersions = exists $ArgRef->{-skipversions} ? $ArgRef->{-skipversions} : $FALSE; require "FSUtilities.pm"; require "FileUtilities.pm"; @@ -148,20 +152,28 @@ sub FileLink ($) { my $FileSize = FileSize(FullFile($DocumentID,$Version,$ShortName)); $FileSize =~ s/^\s+//; # Chop off leading spaces - - my $PrintedName = $ShortName; - if ($MaxLength) { + + my $PrintedName = $ShortName; + if ($MaxLength) { $PrintedName = AbbreviateFileName(-filename => $ShortName, -maxlength => $MaxLength, -maxext => $MaxExt); - } + } my $URL = $BaseURL.$ShortFile; - if ($UserValidation eq "certificate" || $Preferences{Options}{AlwaysRetrieveFile}) { - $URL = $RetrieveFile."?docid=".$DocumentID."&version=".$Version."&filename=".$ShortFile; + if ($UserValidation eq "certificate" || $Preferences{Options}{AlwaysRetrieveFile}) { + $URL = $RetrieveFile."?docid=".$DocumentID.";filename=".$ShortFile; + unless ($SkipVersions) { + $URL .= ";version=".$Version; + } } - + my $Link = ""; - + + # Sanitize output + $ShortName = SmartHTML( {-text => $ShortName, } ); + $Description = SmartHTML( {-text => $Description, } ); + $PrintedName = SmartHTML( {-text => $PrintedName, } ); + if ($Format eq "short") { if ($Description) { return "$Description"; @@ -179,25 +191,25 @@ sub FileLink ($) { sub ArchiveLink { my ($DocumentID,$Version) = @_; - + my @Types = ("tar.gz"); if ($Zip) {push @Types,"zip";} - + @Types = sort @Types; - + my $link = "Get all files as \n"; @LinkParts = (); foreach my $Type (@Types) { push @LinkParts,"$Type"; - } + } $link .= join ', ',@LinkParts; $link .= "."; - + return $link; } sub FileUploadBox (%) { - my (%Params) = @_; + my (%Params) = @_; my $Type = $Params{-type} || "file"; my $DescOnly = $Params{-desconly} || 0; @@ -208,16 +220,16 @@ sub FileUploadBox (%) { my $Required = $Params{-required} || 0; my $FileSize = $Params{-filesize} || 60; my $FileMaxSize = $Params{-filemaxsize} || 250; - + my @FileIDs = @{$Params{-fileids}}; - + require "Sorts.pm"; - + if ($DocRevID) { require "MiscSQL.pm"; @FileIDs = &FetchDocFiles($DocRevID); } - + my @RootFiles = (); my @OtherFiles = (); @@ -226,9 +238,9 @@ sub FileUploadBox (%) { push @RootFiles,$FileID; } else { push @OtherFiles,$FileID; - } + } } - + @RootFiles = sort FilesByDescription @RootFiles; @OtherFiles = sort FilesByDescription @OtherFiles; @FileIDs = (@RootFiles,@OtherFiles); @@ -236,22 +248,22 @@ sub FileUploadBox (%) { unless ($MaxFiles) { if (@FileIDs) { $MaxFiles = @FileIDs + $AddFiles; - + } elsif ($NumberUploads) { - $MaxFiles = $NumberUploads; + $MaxFiles = $NumberUploads; } elsif ($UserPreferences{NumFiles}) { $MaxFiles = $UserPreferences{NumFiles}; } else { - $MaxFiles = 1; - } - } + $MaxFiles = 1; + } + } print "
    \n"; print $query -> hidden(-name => 'maxfiles', -default => $MaxFiles); print "
    \n"; print "
    \n"; +print "\n"; AdministerActions(-form => "externaldocdb"); print $query -> hidden(-name => "subform", -default => "externaldocdb"); print "
    \n"; - ExternalDocDBSelect(-disabled => true, -format => "full"); -print "\n"; + ExternalDocDBSelect(-disabled => true, -format => "full"); +print "\n"; TextField(-name => "project", -disabled => "true", -helptext => "Project", -helplink => "extdocdb"); print "
    \n"; +print "\n"; TextField(-name => "desc", -disabled => "true", -helptext => "Description", -helplink => "extdocdb"); print "
    \n"; +print "\n"; TextField(-name => "puburl", -disabled => "true", -helptext => "Public URL", -helplink => "extdocdb"); print "
    \n"; +print "\n"; TextField(-name => "privurl", -disabled => "true", -helptext => "Private URL", -helplink => "extdocdb"); print "
    \n"; +print "\n"; AdminRegardless(); print "
    \n"; - + my ($HelpLink,$HelpText,$FileHelpLink,$FileHelpText,$DescHelpLink,$DescHelpText); if ($Type eq "file") { $HelpLink = "fileupload"; @@ -264,21 +276,21 @@ sub FileUploadBox (%) { $FileHelpLink = "remoteurl"; $FileHelpText = "URL"; } - + if ($DescOnly) { $HelpLink = "filechar"; $HelpText = "Update File Characteristics"; } - + $DescHelpLink = "description"; $DescHelpText = "Description"; - + my $BoxTitle = FormElementTitle(-helplink => $HelpLink, -helptext => $HelpText, -required => $Required); - print '\n"; - + for (my $i = 1; $i <= $MaxFiles; ++$i) { my $FileID = shift @FileIDs; my $ElementName = "upload$i"; @@ -288,13 +300,13 @@ sub FileUploadBox (%) { my $CopyName = "copyfile$i"; my $URLName = "url$i"; my $NewName = "newname$i"; - + my $FileHelp = FormElementTitle(-helplink => $FileHelpLink, -helptext => $FileHelpText); my $DescriptionHelp = FormElementTitle(-helplink => $DescHelpLink, -helptext => $DescHelpText); my $NewNameHelp = FormElementTitle(-helplink => "newfilename", -helptext => "New Filename"); my $MainHelp = FormElementTitle(-helplink => "main", -helptext => "Main?", -nocolon => $TRUE, -nobold => $TRUE); my $DefaultDesc = $DocFiles{$FileID}{DESCRIPTION}; - + if ($DescOnly) { print "\n"; print ""; @@ -313,29 +325,29 @@ sub FileUploadBox (%) { print $query -> filefield(-name => $ElementName, -size => $FileSize, -maxlength => $FileMaxSize); } elsif ($Type eq "http") { - print $query -> textfield(-name => $URLName, -size => $FileSize, + print $query -> textfield(-name => $URLName, -size => $FileSize, -maxlength => $FileMaxSize); } print "\n"; print "\n"; - + if ($Type eq "http") { print "\n"; print "\n"; print "\n"; } - } + } print "\n"; print "\n"; if ($FileID && $AllowCopy && !$DescOnly) { @@ -352,13 +364,13 @@ sub FileUploadBox (%) { print $query -> hidden(-name => $FileIDName, -value => $FileID); print $query -> checkbox(-name => $CopyName, -label => ''); print "\n"; - } + } print "\n"; } if ($AllowCopy && $NOrigFiles) { - print '\n"; } @@ -372,10 +384,10 @@ sub FileUploadBox (%) { } print "
    '; + print '
    '; print $BoxTitle; print "
    Filename:
    \n"; print $NewNameHelp; print "\n"; - print $query -> textfield(-name => $NewName, -size => $FileSize, + print $query -> textfield(-name => $NewName, -size => $FileSize, -maxlength => $FileMaxSize); print "
    \n"; print $DescriptionHelp; print "\n"; - print $query -> textfield (-name => $DescName, -size => 60, + print $query -> textfield (-name => $DescName, -size => 60, -maxlength => 128, -default => $DefaultDesc); if ($DocFiles{$FileID}{ROOT} || !$FileID) { @@ -343,7 +355,7 @@ sub FileUploadBox (%) { } else { print $query -> checkbox(-name => $MainName, -label => ''); } - + print $MainHelp; print "
    '; - print $query -> checkbox(-name => 'LessFiles', -label => ''); - print FormElementTitle(-helplink => "LessFiles", -helptext => "New version has fewer files", + print '
    '; + print $query -> checkbox(-name => 'LessFiles', -label => ''); + print FormElementTitle(-helplink => "LessFiles", -helptext => "New version has fewer files", -nocolon => $TRUE, -nobold => $TRUE);; print "
    \n"; } - + sub ArchiveUploadBox (%) { - my (%Params) = @_; - + my (%Params) = @_; + my $Required = $Params{-required} || 0; # short, long, full print "\n"; diff --git a/DocDB/cgi/FileSQL.pm b/DocDB/cgi/FileSQL.pm index 174e08f6..fb9660bd 100644 --- a/DocDB/cgi/FileSQL.pm +++ b/DocDB/cgi/FileSQL.pm @@ -1,6 +1,6 @@ # FIXME: Should grab stuff from MiscSQL.pm -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/FileUtilities.pm b/DocDB/cgi/FileUtilities.pm index edc9278c..146b1241 100644 --- a/DocDB/cgi/FileUtilities.pm +++ b/DocDB/cgi/FileUtilities.pm @@ -1,5 +1,5 @@ -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -188,20 +188,34 @@ sub StreamFile (%) { my $Size = (stat $File)[7]; $MimeType = mimetype($File); # Try Mime-info first + unless ($MimeType) { - $MimeType = `$FileMagic -ib \"$File\"`; # Use magic as a backup - chomp $MimeType; - print STDERR "DocDB: MIME info not found, defaulting to \"magic\" which says: $MimeType\n"; + # This is unsafe. Until we can figure out a way to do this, comment it out. Could use IPC::Run if we had it + # $MimeType = `$FileMagic -ib \"$File\"`; # Use magic as a backup + # chomp $MimeType; + # print STDERR "DocDB: MIME info not found, defaulting to \"magic\" which says: $MimeType\n"; + $MimeType = 'binary/octet-stream'; + print STDERR "DocDB: MIME info not found, defaulting to binary/octet-stream\n"; } my @Parts = split /\//,$File; my $ShortFile = pop @Parts; - select STDOUT; - $| = 1; + my $AttachmentString = ""; + if (defined($Preferences{Options}{FileEndingsForAttachment})) { + my $Search = $ShortFile; + my $AttachRegex = join "|", @{$Preferences{Options}{FileEndingsForAttachment}}; + if ($Search =~ m/\.($AttachRegex)$/i) { + $AttachmentString = "attachment;"; + } + } + print "Content-Type: $MimeType\n", # Print header - "Content-Disposition: filename=\"$ShortFile\"\n", + "Content-Disposition: $AttachmentString filename=\"$ShortFile\"\n", "Content-Length: $Size\n\n"; + select STDOUT; + $| = 1; + open OUT, "<$File" or die "Cannot open File\n"; binmode OUT if -B $File; my $BlockSize = (stat OUT)[11] || 16384; @@ -210,17 +224,21 @@ sub StreamFile (%) { next unless defined $Length; my $Offset = 0; - while ($Length) { - my $Written = syswrite STDOUT, $Buffer, $Length, $Offset; + my $Written= 1; + while ($Length && $Written > 0) { + print STDOUT $Buffer; + $Written = $Length; + last unless defined($Written); $Length -= $Written; $Offset += $Written; } + last unless defined($Written); } close OUT; } else { print $query -> header( -charset => $HTTP_ENCODING ); print $query -> start_html, - "There was a problem. File $File does not exist.", + "There was a problem. The file does not exist.", $query -> end_html; } } diff --git a/DocDB/cgi/FormElements.pm b/DocDB/cgi/FormElements.pm index 615cf226..9c68bf60 100644 --- a/DocDB/cgi/FormElements.pm +++ b/DocDB/cgi/FormElements.pm @@ -1,19 +1,19 @@ # # Name: FormElements.pm -# Description: Various routines which supply input forms for document -# addition, etc. This file is deprecated. Routines are +# Description: Various routines which supply input forms for document +# addition, etc. This file is deprecated. Routines are # being moved out into the various *HTML.pm files. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -29,9 +29,9 @@ require "TopicHTML.pm"; sub DaysPulldown (;$) { my ($DefaultDays) = @_; - unless ($DefaultDays) { + unless ($DefaultDays) { $DefaultDays = $LastDays; - } + } my @Days = (1,2,3,5,7,10,14,20,30,45,60,90,120,180 ); print $query -> popup_menu (-name => 'days', -values => \@Days, -default => $DefaultDays, -onChange => "submit()"); @@ -39,7 +39,7 @@ sub DaysPulldown (;$) { sub DateTimePulldown (%) { # Note capitalization my (%Params) = @_; - + my $Name = $Params{-name} || "date"; my $Disabled = $Params{-disabled} || 0; my $DateOnly = $Params{-dateonly} || 0; @@ -47,7 +47,7 @@ sub DateTimePulldown (%) { # Note capitalization my $OneTime = $Params{-onetime} || 0; my $OneLine = $Params{-oneline} || 0; my $Granularity = $Params{-granularity} || 5; - + my $Default = $Params{-default}; my $HelpLink = $Params{-helplink} || ""; @@ -55,13 +55,13 @@ sub DateTimePulldown (%) { # Note capitalization my $Required = $Params{-required} || 0; my $NoBreak = $Params{-nobreak} ; my $ExtraText = $Params{-extratext}; - + my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } - + } + my ($Sec,$Min,$Hour,$Day,$Mon,$Year) = localtime(time); $Year += 1900; $Min = (int (($Min+($Granularity/2))/$Granularity))*$Granularity; # Nearest $Granularity minutes @@ -69,13 +69,13 @@ sub DateTimePulldown (%) { # Note capitalization my $DefaultHHMM; if ($Default) { my ($DefaultDate,$DefaultTime); - if ($DateOnly) { + if ($DateOnly) { $DefaultDate = $Default; } elsif ($TimeOnly) { $DefaultTime = $Default; } else { ($DefaultDate,$DefaultTime) = split /\s+/,$Default; - } + } ($Year,$Mon,$Day) = split /-/,$DefaultDate; $Day = int($Day); @@ -88,41 +88,41 @@ sub DateTimePulldown (%) { # Note capitalization $Sec = int($Sec); $DefaultHHMM = sprintf "%2.2d:%2.2d",$Hour,$Min; } - + my @Years = (); for (my $i = $FirstYear; $i<=$Year+1; ++$i) { # $FirstYear - current year + 1 push @Years,$i; - } + } my @Days = (); for (my $i = 1; $i<=31; ++$i) { # $FirstYear - current year push @Days,$i; - } + } my @Hours = (); for (my $i = 0; $i<24; ++$i) { push @Hours,$i; - } + } my @Minutes = (); for (my $i = 0; $i<=55; $i=$i+5) { push @Minutes,(sprintf "%2.2d",$i); - } - + } + my @Times = (); for (my $Hour = 0; $Hour<=23; ++$Hour) { for (my $Min = 0; $Min<=59; $Min=$Min+$Granularity) { push @Times,sprintf "%2.2d:%2.2d",$Hour,$Min; - } - } - - my $ElementTitle = &FormElementTitle(-helplink => $HelpLink , + } + } + + my $ElementTitle = &FormElementTitle(-helplink => $HelpLink , -helptext => $HelpText , -extratext => $ExtraText, -text => $Text , -nobreak => $NoBreak , -required => $Required ); - print $ElementTitle,"\n"; + print $ElementTitle,"\n"; unless ($DateOnly) { if ($OneTime) { @@ -135,10 +135,10 @@ sub DateTimePulldown (%) { # Note capitalization } unless ($OneLine || $DateOnly || $TimeOnly) { print "\n"; - } + } if ($OneLine) { print " \n"; - } + } unless ($TimeOnly) { print $query -> popup_menu (-name => $Name."day",-values => \@Days, -default => $Day, $Booleans); print $query -> popup_menu (-name => $Name."month",-values => \@AbrvMonths, -default => $AbrvMonths[$Mon], $Booleans); @@ -150,11 +150,11 @@ sub DateTimePullDown { #FIXME: Replace with DateTimePulldown my ($sec,$min,$hour,$day,$mon,$year) = localtime(time); $year += 1900; $min = (int (($min+3)/5))*5; # Nearest five minutes - + my @days = (); for ($i = 1; $i<=31; ++$i) { push @days,$i; - } + } my @months = ("Jan","Feb","Mar","Apr","May","Jun", "Jul","Aug","Sep","Oct","Nov","Dec"); @@ -162,18 +162,18 @@ sub DateTimePullDown { #FIXME: Replace with DateTimePulldown my @years = (); for ($i = $FirstYear; $i<=$year; ++$i) { # $FirstYear - current year push @years,$i; - } + } my @hours = (); for ($i = 0; $i<24; ++$i) { push @hours,$i; - } + } my @minutes = (); for ($i = 0; $i<=55; $i=$i+5) { push @minutes,(sprintf "%2.2d",$i); - } - + } + print FormElementTitle(-helplink => "overdate", -helptext => "Date & Time"); print $query -> popup_menu (-name => 'overday',-values => \@days, -default => $day); print $query -> popup_menu (-name => 'overmonth',-values => \@months, -default => $months[$mon]); @@ -185,11 +185,11 @@ sub DateTimePullDown { #FIXME: Replace with DateTimePulldown } sub PubInfoBox { - my $ElementTitle = &FormElementTitle(-helplink => "pubinfo", + my $ElementTitle = &FormElementTitle(-helplink => "pubinfo", -helptext => "Other publication information"); - print $ElementTitle,"\n"; - - print $query -> textarea (-name => 'pubinfo', -default => $PubInfoDefault, + print $ElementTitle,"\n"; + my $SafeDefault = SmartHTML({-text => $PubInfoDefault},); + print $query -> textarea (-name => 'pubinfo', -default => $SafeDefault, -columns => 60, -rows => 3); }; @@ -197,31 +197,33 @@ sub InstitutionSelect (;%) { # Scrolling selectable list for institutions require "Sorts.pm"; my (%Params) = @_; - + my $Mode = $Params{-format} || "short"; my $Disabled = $Params{-disabled} || "0"; my $Required = $Params{-required} || $FALSE; - + my $ExtraText; if ($Mode eq "full") {$ExtraText = "(Long descriptions in brackets)";} - - - my $ElementTitle = &FormElementTitle(-helplink => "institution", + + + my $ElementTitle = &FormElementTitle(-helplink => "institution", -helptext => "Institution", -extratext => $ExtraText, -required => $Required); - print $ElementTitle,"\n"; + print $ElementTitle,"\n"; my @InstIDs = sort byInstitution keys %Institutions; my %InstLabels = (); foreach my $ID (@InstIDs) { + my $LongName = SmartHTML({-text => $Institutions{$ID}{LONG}},); + my $ShortName = SmartHTML({-text => $Institutions{$ID}{SHORT}},); if ($Mode eq "full") { - $InstLabels{$ID} = $Institutions{$ID}{SHORT}." [".$Institutions{$ID}{LONG}."]"; + $InstLabels{$ID} = $ShortName." [".$LongName."]"; } else { - $InstLabels{$ID} = $Institutions{$ID}{SHORT}; + $InstLabels{$ID} = $ShortName; } - } - if ($Disabled) { + } + if ($Disabled) { print $query -> scrolling_list(-name => "inst", -values => \@InstIDs, -labels => \%InstLabels, -size => 10, -disabled); @@ -233,37 +235,37 @@ sub InstitutionSelect (;%) { # Scrolling selectable list for institutions sub NameEntryBox (;%) { my (%Params) = @_; - + my $Disabled = $Params{-disabled} || "0"; - + my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } - + } + print "
    \n"; print "\n"; print "\n"; print "\n"; print "
    \n"; - my $ElementTitle = FormElementTitle(-helplink => "authorentry", + my $ElementTitle = FormElementTitle(-helplink => "authorentry", -helptext => "First Name", -required => $TRUE); - print $ElementTitle,"\n"; - print $query -> textfield (-name => 'first', + print $ElementTitle,"\n"; + print $query -> textfield (-name => 'first', -size => 20, -maxlength => 32,$Booleans); print "
    \n"; - $ElementTitle = FormElementTitle(-helplink => "authorentry", + $ElementTitle = FormElementTitle(-helplink => "authorentry", -helptext => "Middle Initial(s)"); - print $ElementTitle,"\n"; - print $query -> textfield (-name => 'middle', + print $ElementTitle,"\n"; + print $query -> textfield (-name => 'middle', -size => 10, -maxlength => 16,$Booleans); print "
    \n"; - $ElementTitle = FormElementTitle(-helplink => "authorentry", + $ElementTitle = FormElementTitle(-helplink => "authorentry", -helptext => "Last Name", -required => $TRUE); - print $ElementTitle,"\n"; - print $query -> textfield (-name => 'lastname', + print $ElementTitle,"\n"; + print $query -> textfield (-name => 'lastname', -size => 20, -maxlength => 32,$Booleans); print "
    \n"; @@ -274,7 +276,7 @@ sub UpdateButton { # unless (&CanModify) {return;} - $query -> param('mode','update'); + $query -> param('mode','update'); $query -> param('docid',$DocumentID); print $query -> startform('POST',$DocumentAddForm); @@ -289,13 +291,13 @@ sub UpdateButton { sub UpdateDBButton { my ($DocumentID,$Version) = @_; - + # unless (&CanModify) {return;} $query -> param('mode', 'updatedb'); $query -> param('docid', $DocumentID); $query -> param('version',$Version); - + print $query -> startform('POST',$DocumentAddForm); print "

    \n"; print $query -> hidden(-name => 'mode', -default => 'updatedb'); @@ -314,7 +316,7 @@ sub AddFilesButton { $query -> param('docid',$DocumentID); $query -> param('version',$Version); - + print $query -> startform('POST',$AddFilesForm); print "
    \n"; print $query -> hidden(-name => 'docid', -default => $DocumentID); @@ -325,9 +327,9 @@ sub AddFilesButton { print "\n"; } -sub TextField (%) { +sub TextField (%) { my (%Params) = @_; - + my $HelpLink = $Params{-helplink} ; my $HelpText = $Params{-helptext} ; my $ExtraText = $Params{-extratext}; @@ -339,28 +341,28 @@ sub TextField (%) { my $Size = $Params{-size} || 40; my $MaxLength = $Params{-maxlength} || 240; my $Disabled = $Params{-disabled} || $FALSE; - - my %Options = (); + + my %Options = (); if ($Disabled) { $Options{-disabled} = "disabled"; - } + } - my $ElementTitle = &FormElementTitle(-helplink => $HelpLink , + my $ElementTitle = &FormElementTitle(-helplink => $HelpLink , -helptext => $HelpText , -extratext => $ExtraText, -text => $Text , -nobreak => $NoBreak , -required => $Required , ); - print $ElementTitle,"\n"; - print $query -> textfield (-name => $Name, -default => $Default, + print $ElementTitle,"\n"; + print $query -> textfield (-name => $Name, -default => $Default, -size => $Size, -maxlength => $MaxLength, %Options,); -} +} -sub TextArea (%) { +sub TextArea (%) { require "Utilities.pm"; my (%Params) = @_; - + my $HelpLink = $Params{-helplink} ; my $HelpText = $Params{-helptext} ; my $ExtraText = $Params{-extratext}; @@ -371,21 +373,21 @@ sub TextArea (%) { my $Default = $Params{-default} || ""; my $Columns = $Params{-columns} || 40; my $Rows = $Params{-rows} || 6; - - my $ElementTitle = &FormElementTitle(-helplink => $HelpLink , + + my $ElementTitle = &FormElementTitle(-helplink => $HelpLink , -helptext => $HelpText , -extratext => $ExtraText, -text => $Text , -nobreak => $NoBreak , -required => $Required ); - print $ElementTitle,"\n"; - print $query -> textarea (-name => $Name, -default => &SafeHTML($Default), + print $ElementTitle,"\n"; + print $query -> textarea (-name => $Name, -default => SmartHTML({-text=>$Default}), -columns => $Columns, -rows => $Rows); -} +} -sub FormElementTitle (%) { +sub FormElementTitle (%) { my (%Params) = @_; - + my $HelpLink = $Params{-helplink} || ""; my $HelpText = $Params{-helptext} || ""; my $ExtraText = $Params{-extratext} || ""; @@ -397,14 +399,14 @@ sub FormElementTitle (%) { my $TitleText = ""; my $Colon = ""; - + unless ($HelpLink || $Text) { return $TitleText; - } - + } + unless ($NoColon) { $Colon = ":"; - } + } unless ($NoBold) { $TitleText .= ""; } @@ -412,26 +414,26 @@ sub FormElementTitle (%) { $TitleText .= ""; $TitleText .= "$HelpText$Colon"; } elsif ($Text) { - $TitleText .= "$Text$Colon"; + $TitleText .= "$Text$Colon"; } unless ($NoBold) { $TitleText .= ""; } - + if ($Required) { $TitleText .= $RequiredMark; - } - + } + if ($ExtraText) { $TitleText .= " $ExtraText"; - } - - if ($NoBreak) { + } + + if ($NoBreak) { # $TitleText .= "\n"; } else { $TitleText .= "
    \n"; - } - + } + return $TitleText; } diff --git a/DocDB/cgi/GeneralInstructions.pm b/DocDB/cgi/GeneralInstructions.pm index 4514a69b..0bb7469d 100644 --- a/DocDB/cgi/GeneralInstructions.pm +++ b/DocDB/cgi/GeneralInstructions.pm @@ -6,7 +6,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # Additional Text: Marcia Teckenbrock # This file is part of DocDB. @@ -335,7 +335,7 @@ HTML When reserving a document, you must supply:

    • A title
    • -
    • A requester (who is requesting the document?)
    • +
    • A submitter (who is requesting or uoloading the document?)
    • A document type (talk, note, etc.)
    @@ -360,10 +360,14 @@ HTML

    When updating a document, you can change all the information above. - However, all the forms should be pre-filled for you with the information from - the previous version. You will either have to supply all the files you want to - be in the new version, or choose to have unchanged files copied to the next version.

    - + However, all the forms should be pre-filled for you with the information from the previous version. + For documents with multiple files, you may update just some of the files or all of them. In either case, + the version number will be incremented. DocDB assumes the new document revision will include the same set + (hence, the same number) of files. Therefore, for each file listed, you need to either provide an updated file + (using Browse), or explicitly copy the previous version of the file to the new version of the document. + To copy a file, click the box to the right of the line: Copy filename from previous version: + If you want to drop a file from the new version, leave its box unchecked, and at the end of the + list of files click the box in front of New version has fewer files.

    Finally, updating the database information about the document is similar to updating the document except for two things. First, you can't supply new @@ -471,7 +475,7 @@ HTML forms to your liking and to save some typing by telling the database who you are.

    -

    Once the database knows who you are, your name will be pre-selected as the requester and +

    Once the database knows who you are, your name will be pre-selected as the submitter and author of new documents. You can, of course, change this setting to enter documents by people other than (or in addition to) yourself.

    @@ -500,7 +504,7 @@ HTML if ($UseSignoffs) { print "

    Document Signoffs

    \n"; - print "

    An optional component of DocDB is to allow some documents to be signed + print "

    An optional component of DocDB is to allow some documents to be signed or approved by a group of people before becoming approved. People with Personal Accounts can sign documents. The list of people needing to approve a document is editable by the same groups that can edit the document itself.

    @@ -508,21 +512,13 @@ HTML To freeze a document and its meta-information such that only managers can modify it or unfreeze it, ask the
    DocDB - administrators for the procedure.

    \n"; + administrators for the procedure. The administrators can also add or subtract from the list of possible approvers.

    \n"; print "

    When displaying document version(s) in a list, there are obvious indications of which documents are approved, which are unapproved, and which are obsolete - (even if they were approved at some time). All information about who signed' + (even if they were approved at some time). All information about who signed each version of each document is kept.

    \n"; - print "

    DocDB contains the ability to allow any number of approval topologies. - For instance, person A or person B might be allowed to sign at the first step, - followed by person C at the second step. Or, person A and person B may both have to - sign (but in parallel) before person C can sign. However, the current DocDB code only - allows one topology (an ordered list). When a document under control is - updated, the signoff list structure is preserved, but the approvals themselves - are cleared.

    \n"; - print "

    The signoff system provides a number of additional convieniences:

    • Email notifications to signatories when a document is ready for their @@ -531,16 +527,61 @@ HTML
    • List of all documents a person is a signatory (actual or requested) on
    \n"; - print "

    A number of other features are planned and will be added as needed:

    -
      -
    • Email reports of outstanding signatures needed (to desired signatory and - other signatories of documents)
    • -
    • More complicated approval topolgies (OR's, parallel paths, etc.)
    • -
    • Reminders if a document goes unsigned for a while
    • -
    • Restricting the list of people who may sign documents to a sub-set of those with - personal accounts
    • -
    \n"; - } + print <How signature lists work varies a bit based on the action you are taking with a document.

    +

    New Documents

    + +

    On the new document page is a box labeled Signoffs. + There is also a link (Signoff Chooser) to the list of all people that have + been enabled to be approvers for DocDB.

    + +

    If the submitter chooses to enable signoffs for a document, click the + Signoff Chooser + link and pick one or more individuals to approve the document. You can + do this by selecting the names on the pop-up window in the order in which + the approvals should occur. Approvers will be sent e-mail in that order.

    + +

    The status of the document will be Unapproved until signoffs are + completed. The list of selected approvers is at the bottom of the DocDB + page for the document, and includes the status of the signoff process.

    + + +

    Updating Documents

    + +

    When updating a document, you are allowed to change the approvers required, + including + removing all approvers. Then update the document as needed and any signoffs + will be + handled as for new documents. All necessary approvals are set to unapproved + for the new version of the document.

    + + +

    Updating Metadata

    +

    When updating metadata, you are allowed to change the approvers required, + including + removing all approvers. Then update the metadata as needed. All necessary approvals are set to unapproved + for the document.

    + + + +

    Adding Files to a Document

    +

    Adding a file does not allow any changes to the list of approvers. + All necessary approvals are set to unapproved + for the document.

    + + +

    Approvers

    +

    Approvers will receive an e-mail requesting they sign the document. A URL + of the document page + is included in the e-mail. This document page contains a button to press + (and possibly a password to enter) next + to the name of the approver. Once all approvers have signed the document, the status + will change to Approved.

    + +HTML + +} print < Vars; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); @ErrorStack = (); @WarnStack = (); -# Parameters to script +# Parameters to script -my $Password = $CGIParams{password}; -my $Username = $CGIParams{admuser}; -my $Action = $CGIParams{admaction}; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; +my $Force = $Untaint -> extract(-as_printable => "admforce") || ""; -my $Description = $CGIParams{description}; -my $Name = $CGIParams{name}; -my $ParentID = $CGIParams{parent}; -my @ChildIDs = split /\0/,$CGIParams{child}; -my $View = $CGIParams{view}; -my $Create = $CGIParams{create}; -my $Admin = $CGIParams{admin}; -my $NoPerm = $CGIParams{remove}; -my $RemoveChildren = $CGIParams{removesubs}; -my $Force = $CGIParams{admforce}; +my $Description = $Untaint -> extract(-as_safehtml => "description") || ""; +my $Name = $Untaint -> extract(-as_safehtml => "name") || ""; +my $ParentID = $Untaint -> extract(-as_integer => "parent") || 0; +my @ChildIDs = @{ $Untaint -> extract(-as_listofint => "child") || undef }; +my $View = $Untaint -> extract(-as_printable => "view") || ""; +my $Create = $Untaint -> extract(-as_printable => "create") || ""; +my $Admin = $Untaint -> extract(-as_printable => "admin") || ""; +my $NoPerm = $Untaint -> extract(-as_printable => "remove") || ""; +my $RemoveChildren = $Untaint -> extract(-as_printable => "removesubs") || ""; if ($View) {$View = 1;} # Make sure they are in format MySQL is expecting if ($Create) {$Create = 1;} @@ -71,7 +73,7 @@ $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,$Msg_AdminNoConnect; -} +} print $query -> header( -charset => $HTTP_ENCODING ); DocDBHeader("Modified Groups"); @@ -80,7 +82,7 @@ EndPage(@ErrorStack); unless (CanAdminister()) { push @ErrorStack,$Msg_AdminNoLogin; -} +} EndPage(@ErrorStack); GetSecurityGroups(); @@ -109,29 +111,29 @@ if ($Action eq "Delete") { # Delete group ($Count) = $RSC -> fetchrow_array; if ($Count) { push @WarnStack,"Action would change view list on $Count document(s)."; - } + } $TotalCount += $Count; ($Count) = $RMC -> fetchrow_array; if ($Count) { push @WarnStack,"Action would change modify list on $Count document(s)."; - } + } $TotalCount += $Count; ($Count) = $MSC -> fetchrow_array; if ($Count) { push @WarnStack,"Action would change view list on $Count event(s)."; - } + } $TotalCount += $Count; ($Count) = $MMC -> fetchrow_array; if ($Count) { push @WarnStack,"Action would change modify list on $Count event(s)."; - } + } $TotalCount += $Count; ($Count) = $EUC -> fetchrow_array; if ($Count) { push @WarnStack,"Action would change groups for $Count user(s)."; - } + } $TotalCount += $Count; - } + } if ($Force || !$TotalCount) { my $RSD = $dbh -> prepare("delete from RevisionSecurity where GroupID=?"); @@ -144,7 +146,7 @@ if ($Action eq "Delete") { # Delete group $Count = $RSD -> execute($ParentID); if (int($Count)) { push @ActionStack,"Group removed from view list on $Count document(s)."; - } + } $Count = $RMD -> execute($ParentID); if (int($Count)) { push @ActionStack,"Group removed from modify list on $Count document(s)."; @@ -169,7 +171,7 @@ if ($Action eq "Delete") { # Delete group push @ActionStack,"$SecurityGroups{$ParentID}{NAME} has been deleted."; push @ActionStack,"Remove group from .htpasswd file and run scripts/Resecure if applicable."; } else { - push @ErrorStack,"Action could lead to unintended consequences. + push @ErrorStack,"Action could lead to unintended consequences. Use the force option if you want to proceed."; } } @@ -179,15 +181,15 @@ if ($Action eq "Delete") { # Delete group } EndPage(@ErrorStack); -# Deal with name changes +# Deal with name changes - if ($Name) { + if ($Name) { push @ActionStack,"Updating group name."; my $GroupUpdate = $dbh->prepare( "update SecurityGroup set Name=? where GroupID=?"); $GroupUpdate -> execute($Name,$ParentID); } - if ($Description) { + if ($Description) { push @ActionStack,"Updating group description."; my $GroupUpdate = $dbh->prepare( "update SecurityGroup set Description=? where GroupID=?"); @@ -210,32 +212,32 @@ if ($Action eq "Delete") { # Delete group push @ActionStack,"Adding subordinate."; $HierarchyInsert -> execute($ChildID,$ParentID); } - } + } } -# Update permissions - +# Update permissions + if ($NoPerm) { my $GroupUpdate = $dbh->prepare( "update SecurityGroup set CanCreate=0,CanAdminister=0,CanView=0,CanConfig=0 where GroupID=?"); $GroupUpdate -> execute($ParentID); - } + } if ($View) { my $GroupUpdate = $dbh->prepare( "update SecurityGroup set CanView=1 where GroupID=?"); $GroupUpdate -> execute($ParentID); - } + } if ($Create) { my $GroupUpdate = $dbh->prepare( "update SecurityGroup set CanCreate=1 where GroupID=?"); $GroupUpdate -> execute($ParentID); - } + } if ($Admin) { my $GroupUpdate = $dbh->prepare( "update SecurityGroup set CanAdminister=1 where GroupID=?"); $GroupUpdate -> execute($ParentID); - } - + } + } elsif ($Action eq "New") { # Create new groups push @ActionStack,"Adding a new group."; my $GroupInsert = $dbh->prepare( @@ -249,13 +251,13 @@ if ($Action eq "Delete") { # Delete group "insert into GroupHierarchy (HierarchyID,ChildID,ParentID) ". "values (0,?,?)"); foreach my $ChildID (@ChildIDs) { - if ($ChildID) { + if ($ChildID && $ChildID != $ParentID) { $HierarchyInsert -> execute($ChildID,$ParentID); } - } + } } else { push @ErrorStack,"No valid action was specified."; -} +} # For modify or new fetch institution information and display. @@ -285,9 +287,9 @@ if ($Action eq "Modify" || $Action eq "New") { print "\n"; print "\n"; print "\n"; -} +} DocDBNavBar(); DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/GroupAdministerForm b/DocDB/cgi/GroupAdministerForm index 0c932c72..07f45fbe 100755 --- a/DocDB/cgi/GroupAdministerForm +++ b/DocDB/cgi/GroupAdministerForm @@ -1,17 +1,17 @@ #! /usr/bin/env perl # -# Description: This script provides a form to administer groups in +# Description: This script provides a form to administer groups in # the DocDB and shows the relationships between groups. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -23,7 +23,7 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI qw(-nosticky); +use CGI qw(-nosticky); use DBI; require "DocDBGlobals.pm"; @@ -40,12 +40,13 @@ require "HTMLUtilities.pm"; require "Sorts.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI -> connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); GetSecurityGroups(); print $query -> header( -charset => $HTTP_ENCODING ); -DocDBHeader("Group Administration","",-scripts => ["PopUps","GroupAdminDisable"]); +DocDBHeader("Group Administration","",-scripts => ["PopUps","GroupAdminDisable"]); @ErrorStack = (); @WarnStack = (); @@ -91,14 +92,14 @@ print "\n"; print "\n"; print ''; -SecurityScroll(-name => 'parent', -disabled => $TRUE, +SecurityScroll(-name => 'parent', -disabled => $TRUE, -helplink => 'parent', -helptext => 'Group'); -print "\n"; +print "\n"; print ''; SecurityScroll(-name => 'child', -disabled => $TRUE, -multiple => $TRUE, -helplink => 'child', -helptext => 'Subordinates'); print "
    \n"; -print $query -> checkbox(-name => "removesubs", -value => 'removesubs', +print $query -> checkbox(-name => "removesubs", -value => 'removesubs', -label => '', -disabled => 'disabled'); print "Remove all"; print "\n"; @@ -131,7 +132,11 @@ my @GroupIDs = sort numerically keys %SecurityGroups; print ''; foreach my $GroupID (@GroupIDs) { print "\n"; - print "\n"; + print "\n"; print "\n"; print "\n"; -} +} print "
    $SecurityGroups{$GroupID}{NAME}
    ($SecurityGroups{$GroupID}{Description})
    "; + print SmartHTML({-text => $SecurityGroups{$GroupID}{NAME}},); + print "
    ("; + print SmartHTML({-text => $SecurityGroups{$GroupID}{Description}},); + print ")
    \n"; print "Dominant groups:\n"; PrintGroupParents($GroupID); @@ -145,7 +150,7 @@ foreach my $GroupID (@GroupIDs) { PrintGroupPermissions($GroupID); print "
    \n"; print "
    \n"; diff --git a/DocDB/cgi/GroupHTML.pm b/DocDB/cgi/GroupHTML.pm index ad6abb67..cf1bb378 100644 --- a/DocDB/cgi/GroupHTML.pm +++ b/DocDB/cgi/GroupHTML.pm @@ -1,5 +1,5 @@ -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/HTMLUtilities.pm b/DocDB/cgi/HTMLUtilities.pm index 9274504c..2929212c 100644 --- a/DocDB/cgi/HTMLUtilities.pm +++ b/DocDB/cgi/HTMLUtilities.pm @@ -1,16 +1,16 @@ # -# Description: Routines to output headers, footers, navigation bars, etc. +# Description: Routines to output headers, footers, navigation bars, etc. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -22,24 +22,67 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - require "ProjectRoutines.pm"; +sub SmartHTML ($) { + my ($ArgRef) = @_; + my $Text = exists $ArgRef->{-text} ? $ArgRef->{-text} : ""; + my $MakeURLs = exists $ArgRef->{-makeURLs} ? $ArgRef->{-makeURLs} : $FALSE; + my $AddLineBreaks = exists $ArgRef->{-addLineBreaks} ? $ArgRef->{-addLineBreaks} : $FALSE; + + # Escape text into &x1234; format ignoring a alphanumerics and a few special characters + $Text =~ s{([^\:\/\.\-\?\=\+\w\s&#%;]|&(?!#?\w+;))}{"&#x".sprintf("%x", unpack(U,$1)).";"}ge; + + # Turn found URLs into hyperlinks, adapted from Perl Cookbook, 6.21 + if ($MakeURLs) { + my $urls = '(http|telnet|gopher|file|wais|ftp|https)'; + my $ltrs = '\w'; + my $gunk = '/#~:.?+=&%@!{};\-'; + my $punc = '.:?\-'; + my $any = "${ltrs}${gunk}${punc}"; + $Text =~ s{ + \b # start at word boundary + ( # begin $1 { + $urls : # need resource and a colon + [$any] +? # followed by on or more + # of any valid character, but + # be conservative and take only + # what you need to.... + ) # end $1 } + (?= # look-ahead non-consumptive assertion + [$punc]* # either 0 or more punctuation + [^$any] # followed by a non-url char + | # or else + $ # then end of the string + ) + }{$1}igox; + } + + # Make two line-feeds into a paragraph break and one into a line break in HTML + if ($AddLineBreaks) { + $Text =~ s/\s*\n\s*\n\s*//g; # Replace two new lines and any space with

    + $Text =~ s/\s*\n\s*/\n/g; + $Text =~ s//\n/g; + } + + return $Text; +} + sub PrettyHTML ($) { my ($HTML) = @_; - + # This function is supposed to pretty-up any valid (X)HTML, but - # it doesn't work particularly well. As written, things like   are not + # it doesn't work particularly well. As written, things like   are not # valid XML. One possibility is to use HTML::Entities::encode_numeric in some way # which should produce safe entities or to use a subsitution map - + return $HTML; - + use HTML::Entities; use XML::Twig; - + my $OldHTML = $HTML; - + $HTML = HTML::Entities::decode($HTML); $HTML = HTML::Entities::encode($HTML,'&'); @@ -50,12 +93,12 @@ sub PrettyHTML ($) { } else { push @DebugStack,"HTML Parse failed with error: ".$@; return $OldHTML; - } + } } -sub DocDBHeader { +sub DocDBHeader { my ($Title,$PageTitle,%Params) = @_; - + my $Search = $Params{-search}; # Fix search page! my $NoBody = $Params{-nobody}; my $Refresh = $Params{-refresh} || ""; @@ -64,10 +107,10 @@ sub DocDBHeader { my @ScriptParts = split /\//,$ENV{SCRIPT_NAME}; my $ScriptName = pop @ScriptParts; - unless ($PageTitle) { + unless ($PageTitle) { $PageTitle = $Title; - } - + } + # FIXME: Do Hash lookup for scripts as they are certified XHTML? if ($DOCTYPE) { print $DOCTYPE; @@ -79,17 +122,17 @@ sub DocDBHeader { print "\n"; if ($Refresh) { print "\n"; - } + } print '',"\n"; print "$Title\n"; # Include DocDB style sheets - + my @PublicCSS = (""); if ($Public) { @PublicCSS = ("","Public"); } - + foreach my $ScriptCSS ("",$ScriptName) { foreach my $ProjectCSS ("",$ShortProject) { foreach my $PublicCSS (@PublicCSS) { @@ -100,7 +143,7 @@ sub DocDBHeader { if ($BrowserCSS eq "_IE") { # Use IE format for including. Hopefully we can not give these to IE7 print "\n"; + print "\n"; } else { print "\n"; } @@ -118,10 +161,10 @@ sub DocDBHeader { EventSearchScript(); } print "\n"; - } + } if (defined &ProjectHeader) { - &ProjectHeader($Title,$PageTitle); + &ProjectHeader($Title,$PageTitle); } print "\n"; @@ -131,30 +174,30 @@ sub DocDBHeader { } else { if ($NoBody) { print "\n"; - } else { + } else { print "\n"; - } - } - + } + } + if (defined &ProjectBodyStart && !$NoBody) { - &ProjectBodyStart($Title,$PageTitle); + &ProjectBodyStart($Title,$PageTitle); } } sub DocDBFooter ($$;%) { require "ResponseElements.pm"; - + my ($WebMasterEmail,$WebMasterName,%Params) = @_; - + my $NoBody = $Params{-nobody}; &DebugPage("At DocDBFooter"); - - unless ($NoBody) { + + unless ($NoBody) { if (defined &ProjectFooter) { - &ProjectFooter($WebMasterEmail,$WebMasterName); + &ProjectFooter($WebMasterEmail,$WebMasterName); } - } + } print "\n"; } diff --git a/DocDB/cgi/Images.pm b/DocDB/cgi/Images.pm index f59f8e5d..67b2f236 100644 --- a/DocDB/cgi/Images.pm +++ b/DocDB/cgi/Images.pm @@ -5,7 +5,7 @@ # Author: Eric Vaandering (ewv@fnal.gov) # Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/InstitutionAdminister b/DocDB/cgi/InstitutionAdminister index 51d62959..e450f719 100755 --- a/DocDB/cgi/InstitutionAdminister +++ b/DocDB/cgi/InstitutionAdminister @@ -3,17 +3,17 @@ # Description: This script is called by AdministerForm and does administration # on Institutions in the DB. This script adds, modifies and deletes # institutions. It will not delete institutions if there are authors -# associated with that institution. +# associated with that institution. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,38 +26,40 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "AuthorSQL.pm"; require "AuthorHTML.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines - -%params = $query -> Vars; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); @ErrorStack = (); @WarnStack = (); -# Parameters to script +# Parameters to script -$Password = $params{password}; -my $Username = $params{admuser}; -$Action = $params{admaction}; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; -$InstitutionID = $params{inst}; -$LongName = $params{longdesc}; -$ShortName = $params{shortdesc}; +my $InstitutionID = $Untaint -> extract(-as_integer => "inst") || 0; +my $LongName = $Untaint -> extract(-as_safehtml => "longdesc") || ""; +my $ShortName = $Untaint -> extract(-as_safehtml => "shortdesc") || ""; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,$Msg_AdminNoConnect; -} +} print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("Modified List of Institutions"); @@ -65,13 +67,13 @@ print $query -> header( -charset => $HTTP_ENCODING ); unless (&CanAdminister) { push @ErrorStack,$Msg_AdminNoLogin; -} +} &EndPage(@ErrorStack); &GetInstitutions; if ($Action eq "Delete") { # Delete institutions - @AuthorIDs = &GetInstitutionAuthors($InstitutionID); + @AuthorIDs = &GetInstitutionAuthors($InstitutionID); if (!$InstitutionID) { push @ErrorStack,$Msg_ModInstEmpty; } elsif (@AuthorIDs) { @@ -81,7 +83,7 @@ if ($Action eq "Delete") { # Delete institutions } else { my $InstitutionDelete = $dbh -> prepare("delete from Institution where InstitutionID=?"); $InstitutionDelete -> execute($InstitutionID); - print "$Institutions{$InstitutionID}{LONG} has been deleted.
    \n"; + print "The institution has been deleted.
    \n"; } } elsif ($Action eq "Modify") { # Modify institutions unless ($InstitutionID) { @@ -89,16 +91,16 @@ if ($Action eq "Delete") { # Delete institutions } &EndPage(@ErrorStack); -# Deal with name changes +# Deal with name changes - if ($ShortName) { - print "Updating short topic name.
    \n"; + if ($ShortName) { + print "Updating short institution name.
    \n"; my $InstitutionUpdate = $dbh->prepare( "update Institution set ShortName=? where InstitutionID=?"); $InstitutionUpdate -> execute($ShortName,$InstitutionID); } - if ($LongName) { - print "Updating long topic name.
    \n"; + if ($LongName) { + print "Updating long institution name.
    \n"; my $InstitutionUpdate = $dbh->prepare( "update Institution set LongName=? where InstitutionID=?"); $InstitutionUpdate -> execute($LongName,$InstitutionID); @@ -113,17 +115,18 @@ if ($Action eq "Delete") { # Delete institutions $InstitutionID = $InstitutionInsert -> {mysql_insertid}; # Works with MySQL only } else { push @ErrorStack,"No valid action was specified."; -} +} # For modify or new fetch institution information and display. +ClearInstitutions(); if ($Action eq "Modify" || $Action eq "New") { &FetchInstitution($InstitutionID); print "

    Here are the results of your modification:
    \n"; - print "Short name: $Institutions{$InstitutionID}{SHORT}
    \n"; - print "Long name: $Institutions{$InstitutionID}{LONG}
    \n"; + print "Short institution name: $Institutions{$InstitutionID}{SHORT}
    \n"; + print "Long institution name: $Institutions{$InstitutionID}{LONG}
    \n"; print "

    \n"; -} +} print "

    \n"; @@ -132,5 +135,5 @@ print "

    \n"; &DocDBNavBar; &DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/JournalAdminister b/DocDB/cgi/JournalAdminister index d96d68dd..937ff6b6 100755 --- a/DocDB/cgi/JournalAdminister +++ b/DocDB/cgi/JournalAdminister @@ -2,17 +2,17 @@ # # Description: This script is called by AdministerForm and does administration # on journals in the DB. This script adds, modifies and deletes -# journals. +# journals. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -25,41 +25,43 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "MiscSQL.pm"; require "JournalHTML.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines - -%params = $query -> Vars; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); @ErrorStack = (); @WarnStack = (); -# Parameters to script +# Parameters to script -$Password = $params{password}; -my $Username = $params{admuser}; -$Action = $params{admaction}; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; -$JournalID = $params{journal}; -$FullName = $params{name}; -$Abbreviation = $params{abbr}; -$Acronym = $params{acronym}; -$Publisher = $params{pub}; -$URL = $params{url}; +my $JournalID = $Untaint -> extract(-as_integer => "journal") || 0; +my $FullName = $Untaint -> extract(-as_safehtml => "name") || ""; +my $Abbreviation = $Untaint -> extract(-as_safehtml => "abbr") || ""; +my $Acronym = $Untaint -> extract(-as_safehtml => "acronym") || ""; +my $Publisher = $Untaint -> extract(-as_safehtml => "pub") || ""; +my $URL = $Untaint -> extract(-as_safehtml => "url") || ""; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,$Msg_AdminNoConnect; -} +} print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("Modified List of Institutions"); @@ -67,7 +69,7 @@ print $query -> header( -charset => $HTTP_ENCODING ); unless (&CanAdminister) { push @ErrorStack,$Msg_AdminNoLogin; -} +} &EndPage(@ErrorStack); &GetJournals; @@ -86,33 +88,33 @@ if ($Action eq "Delete") { # Delete institutions } &EndPage(@ErrorStack); -# Deal with name changes +# Deal with name changes - if ($FullName) { + if ($FullName) { print "Updating journal name.
    \n"; my $JournalUpdate = $dbh->prepare( "update Journal set Name=? where JournalID=?"); $JournalUpdate -> execute($FullName,$JournalID); } - if ($Abbreviation) { + if ($Abbreviation) { print "Updating journal abbreviation.
    \n"; my $JournalUpdate = $dbh->prepare( "update Journal set Abbreviation=? where JournalID=?"); $JournalUpdate -> execute($Abbreviation,$JournalID); } - if ($Acronym) { + if ($Acronym) { print "Updating journal acronym.
    \n"; my $JournalUpdate = $dbh->prepare( "update Journal set Acronym=? where JournalID=?"); $JournalUpdate -> execute($Acronym,$JournalID); } - if ($Publisher) { + if ($Publisher) { print "Updating journal publisher.
    \n"; my $JournalUpdate = $dbh->prepare( "update Journal set Publisher=? where JournalID=?"); $JournalUpdate -> execute($Publisher,$JournalID); } - if ($URL) { + if ($URL) { print "Updating journal URL.
    \n"; my $JournalUpdate = $dbh->prepare( "update Journal set URL=? where JournalID=?"); @@ -129,7 +131,7 @@ if ($Action eq "Delete") { # Delete institutions $JournalID = $JournalInsert -> {mysql_insertid}; # Works with MySQL only } else { push @ErrorStack,"No valid action was specified."; -} +} # For modify or new fetch institution information and display. @@ -142,7 +144,7 @@ if ($Action eq "Modify" || $Action eq "New") { print "Publisher: $Journals{$JournalID}{Publisher}
    \n"; print "URL: $Journals{$JournalID}{URL}
    \n"; print "

    \n"; -} +} print "

    \n"; @@ -151,5 +153,5 @@ print "

    \n"; &DocDBNavBar; &DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/JournalHTML.pm b/DocDB/cgi/JournalHTML.pm index b1da4841..673abf64 100644 --- a/DocDB/cgi/JournalHTML.pm +++ b/DocDB/cgi/JournalHTML.pm @@ -1,16 +1,16 @@ # -# Description: Routines with form elements and other HTML generating +# Description: Routines with form elements and other HTML generating # code pertaining to Journals and References. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -22,69 +22,71 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +require "HTMLUtilities.pm"; + sub JournalSelect (;%) { my (%Params) = @_; - + my $Disabled = $Params{-disabled} || "0"; my $Mode = $Params{-format} || "0"; - + my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } - + } + my @JournalIDs = keys %Journals; my %JournalLabels = (); foreach my $ID (@JournalIDs) { - $JournalLabels{$ID} = $Journals{$ID}{Abbreviation}; + $JournalLabels{$ID} = SmartHTML({-text => $Journals{$ID}{Abbreviation}},); } @JournalIDs = sort @JournalIDs; #FIXME Sort by abbreviation print FormElementTitle(-helplink => "journal", -helptext => "Journal"); - print $query -> scrolling_list(-name => "journal", -values => \@JournalIDs, - -labels => \%JournalLabels, -size => 10, + print $query -> scrolling_list(-name => "journal", -values => \@JournalIDs, + -labels => \%JournalLabels, -size => 10, -default => $JournalDefault, $Booleans); } sub JournalEntryBox (;%) { my (%Params) = @_; - + my $Disabled = $Params{-disabled} || "0"; my $Mode = $Params{-format} || "0"; - + my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } + } print "\n"; print "\n"; print "\n"; print "\n"; print "\n"; print "\n"; print "
    \n"; print FormElementTitle(-helplink => "journalentry", -helptext => "Full Name"); - print $query -> textfield (-name => 'name', + print $query -> textfield (-name => 'name', -size => 40, -maxlength => 128, $Booleans); print "\n"; print FormElementTitle(-helplink => "journalentry", -helptext => "Publisher"); - print $query -> textfield (-name => 'pub', + print $query -> textfield (-name => 'pub', -size => 40, -maxlength => 64, $Booleans); print "
    \n"; print FormElementTitle(-helplink => "journalentry", -helptext => "Abbreviation"); - print $query -> textfield (-name => 'abbr', + print $query -> textfield (-name => 'abbr', -size => 40, -maxlength => 64, $Booleans); print "\n"; print FormElementTitle(-helplink => "journalentry", -helptext => "URL"); - print $query -> textfield (-name => 'url', + print $query -> textfield (-name => 'url', -size => 40, -maxlength => 240, $Booleans); print "
    \n"; print FormElementTitle(-helplink => "journalentry", -helptext => "Acronym"); - print $query -> textfield (-name => 'acronym', + print $query -> textfield (-name => 'acronym', -size => 8, -maxlength => 8, $Booleans); print "
    \n"; @@ -107,11 +109,11 @@ sub JournalTable (;$) { my @JournalIDs = sort keys %Journals; #FIXME Sort by abbreviation foreach my $ID (@JournalIDs) { print "\n"; - print "$Journals{$ID}{Name}\n"; - print "$Journals{$ID}{Abbreviation}\n"; - print "$Journals{$ID}{Acronym}\n"; - print "$Journals{$ID}{Publisher}\n"; - print "$Journals{$ID}{URL}\n"; + print "".SmartHTML({-text => $Journals{$ID}{Name}},)."\n"; + print "".SmartHTML({-text => $Journals{$ID}{Abbreviation}},)."\n"; + print "".SmartHTML({-text => $Journals{$ID}{Acronym}},)."\n"; + print "".SmartHTML({-text => $Journals{$ID}{Publisher}},)."\n"; + print "".SmartHTML({-text => $Journals{$ID}{URL}, -makeURLs => $TRUE},)."\n"; print "\n"; } print "\n"; @@ -119,7 +121,7 @@ sub JournalTable (;$) { sub ReferenceForm { require "MiscSQL.pm"; - + GetJournals(); my @JournalIDs = keys %Journals; @@ -129,33 +131,33 @@ sub ReferenceForm { } @JournalIDs = sort @JournalIDs; #FIXME Sort by acronym unshift @JournalIDs,0; $JournalLabels{0} = "----"; # Null Journal - my $ElementTitle = FormElementTitle(-helplink => "reference", + my $ElementTitle = FormElementTitle(-helplink => "reference", -helptext => "Journal References"); - print $ElementTitle,"\n"; + print $ElementTitle,"\n"; my @ReferenceIDs = (@ReferenceDefaults,0); - + print "\n"; - foreach my $ReferenceID (@ReferenceIDs) { + foreach my $ReferenceID (@ReferenceIDs) { print "\n"; my $JournalDefault = $RevisionReferences{$ReferenceID}{JournalID}; my $VolumeDefault = $RevisionReferences{$ReferenceID}{Volume} ; my $PageDefault = $RevisionReferences{$ReferenceID}{Page} ; print ""; print ""; print "\n"; + print "\n"; } print "
    Journal: \n"; - print $query -> popup_menu(-name => "journal", -values => \@JournalIDs, + print $query -> popup_menu(-name => "journal", -values => \@JournalIDs, -labels => \%JournalLabels, -default => $JournalDefault); print "Volume: \n"; - print $query -> textfield (-name => 'volume', - -size => 8, -maxlength => 8, + print $query -> textfield (-name => 'volume', + -size => 8, -maxlength => 8, -default => $VolumeDefault); print "Page: \n"; - print $query -> textfield (-name => 'page', - -size => 8, -maxlength => 16, + print $query -> textfield (-name => 'page', + -size => 8, -maxlength => 16, -default => $PageDefault); - print "
    \n"; } diff --git a/DocDB/cgi/KeywordAdministerForm b/DocDB/cgi/KeywordAdministerForm index c8dd4820..89aeebfb 100755 --- a/DocDB/cgi/KeywordAdministerForm +++ b/DocDB/cgi/KeywordAdministerForm @@ -6,7 +6,7 @@ # Author: Lynn Garren (garren@fnal.gov) # Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -41,6 +41,7 @@ require "HTMLUtilities.pm"; require "Sorts.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI -> connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); &GetKeywords; diff --git a/DocDB/cgi/KeywordGroupAdminister b/DocDB/cgi/KeywordGroupAdminister index a495ef0b..bfb38b2c 100755 --- a/DocDB/cgi/KeywordGroupAdminister +++ b/DocDB/cgi/KeywordGroupAdminister @@ -3,17 +3,17 @@ # Description: This script is called by KeywordAdministerForm and does administration # on Keyword Groups in the DB. This script adds, modifies and deletes # these groups. It will not delete groups if there are associated -# keywords. +# keywords. # # Author: Lynn Garren (garren@fnal.gov) -# Modified: +# Modified: -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,38 +26,40 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "KeywordSQL.pm"; require "KeywordHTML.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines - -%params = $query -> Vars; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); @ErrorStack = (); @WarnStack = (); -# Parameters to script +# Parameters to script -$Password = $params{password}; -my $Username = $params{admuser}; -$Action = $params{admaction}; +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; -$KeywordGroupID = $params{keywordgroup}; -$LongName = $params{longdesc}; -$ShortName = $params{shortdesc}; +my $KeywordGroupID = $Untaint -> extract(-as_integer => "keywordgroup") || 0; +my $LongName = $Untaint -> extract(-as_safehtml => "longdesc") || ""; +my $ShortName = $Untaint -> extract(-as_safehtml => "shortdesc") || ""; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,$Msg_AdminNoConnect; -} +} print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("Modified List of Keyword Groups"); @@ -66,13 +68,13 @@ print $query -> header( -charset => $HTTP_ENCODING ); unless (&CanAdminister) { push @ErrorStack,$Msg_AdminNoLogin; -} +} &EndPage(@ErrorStack); &GetKeywords; if ($Action eq "Delete") { # Delete keyword groups - @KeywordListIDs = &GetKeywordsByKeywordGroupID($KeywordGroupID); + @KeywordListIDs = &GetKeywordsByKeywordGroupID($KeywordGroupID); if (!$KeywordGroupID) { push @ErrorStack,$Msg_ModKeyGrEmpty; } elsif (@KeywordListIDs) { # Not sure we want this anymore @@ -90,15 +92,15 @@ if ($Action eq "Delete") { # Delete keyword groups } &EndPage(@ErrorStack); -# Deal with name changes +# Deal with name changes - if ($ShortName) { + if ($ShortName) { print "Updating short description.
    \n"; my $KeywordGroupUpdate = $dbh->prepare( "update KeywordGroup set ShortDescription=? where KeywordGroupID=?"); $KeywordGroupUpdate -> execute($ShortName,$KeywordGroupID); } - if ($LongName) { + if ($LongName) { print "Updating long description.
    \n"; my $KeywordGroupUpdate = $dbh->prepare( "update KeywordGroup set LongDescription=? where KeywordGroupID=?"); @@ -114,7 +116,7 @@ if ($Action eq "Delete") { # Delete keyword groups $KeywordGroupID = $KeywordGroupInsert -> {mysql_insertid}; # Works with MySQL only } else { push @ErrorStack,"No valid action was specified."; -} +} # For modify or new fetch information and display. @@ -124,7 +126,7 @@ if ($Action eq "Modify" || $Action eq "New") { print "Short description: $KeywordGroups{$KeywordGroupID}{Short}
    \n"; print "Long description: $KeywordGroups{$KeywordGroupID}{Long}
    \n"; print "

    \n"; -} +} print "

    \n"; $keyadminform = "Administer Keywords"; @@ -139,5 +141,5 @@ print "

    \n"; &DocDBNavBar; &DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/KeywordHTML.pm b/DocDB/cgi/KeywordHTML.pm index 53df0eca..fa63711c 100644 --- a/DocDB/cgi/KeywordHTML.pm +++ b/DocDB/cgi/KeywordHTML.pm @@ -1,18 +1,18 @@ # # Name: KeywordHTML.pm -# Description: Routines to produce snippets of HTML and form elements -# dealing with keywords +# Description: Routines to produce snippets of HTML and form elements +# dealing with keywords # # Author: Lynn Garren (garren@fnal.gov) # Modified: Eric Vaandering (ewv@fnal.gov) # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -24,27 +24,35 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +use HTML::Entities; +use URI::Escape; + +require "HTMLUtilities.pm"; + sub KeywordGroupInfo ($;$) { my ($KeyID,$mode) = @_; - + require "KeywordSQL.pm"; - + &FetchKeywordGroup($KeyID); my $info; if ($mode eq "short") { - $info = $KeywordGroups{$KeyID}{Short}; + $info = SmartHTML({-text=>$KeywordGroups{$KeyID}{Short}}); } elsif ($mode eq "long") { - $info = $KeywordGroups{$KeyID}{Long}; + $info = SmartHTML({-text=>$KeywordGroups{$KeyID}{Long}}); } else { - $info = $KeywordGroups{$KeyID}{Short}; + $info = SmartHTML({-text=>$KeywordGroups{$KeyID}{Short}}); } - + return $info; } sub KeywordsbyKeywordGroup ($;$) { + + # FIXME_XSS: Check to make sure this kind of search still works. + # May need to remove special characters or adapt search atoms my ($KeywordGroupID,$Mode) = @_; - + require "Sorts.pm"; my @KeywordIDs = sort byKeyword &GetKeywordsByKeywordGroupID($KeywordGroupID); @@ -55,19 +63,20 @@ sub KeywordsbyKeywordGroup ($;$) { foreach my $KeywordID (@KeywordIDs) { my $KeyLink; if ($Mode eq "chooser") { + my $SafeKeyword = SmartHTML({-text=>$Keywords{$KeywordID}{Short}}); $KeyLink = "$Keywords{$KeywordID}{Short}"; + "onclick=\"InsertKeyword('$SafeKeyword');\">$SafeKeyword"; } else { $KeyLink = &KeywordLinkByID($KeywordID,-format => "short"); } print "

  • $KeyLink
  • \n"; - } + } print "\n"; } sub KeywordTable { my ($Mode) = @_; - + require "Sorts.pm"; my $NCols = 4; @@ -80,7 +89,7 @@ sub KeywordTable { unless ($Col % $NCols) { if ($Row) { print "\n"; - } + } print "\n"; ++$Row; } @@ -88,7 +97,7 @@ sub KeywordTable { &KeywordsbyKeywordGroup($KeywordGroupID,$Mode); print "\n"; ++$Col; - } + } print "\n"; print "\n"; } @@ -104,7 +113,7 @@ sub KeywordDetailedList { my $KeywordGroup = &KeywordGroupInfo($KeywordGroupID,"short"); my $Label = $KeywordGroup; $Label =~ s/\s+//; - + print " \n"; print " $KeywordGroup\n"; print " \n"; @@ -135,15 +144,15 @@ sub KeywordDetailedList { print " $Link\n"; print " $Text\n"; print "\n"; - } + } - } + } print "\n"; } sub KeywordSelect (%) { # Scrolling selectable list for keyword groups - my (%Params) = @_; - + my (%Params) = @_; + my $Format = $Params{-format} || "short"; # short, long, full my $Multiple = $Params{-multiple} || ""; # Any non-null text is "true" my $Name = $Params{-name} || "keywordlist"; @@ -151,99 +160,104 @@ sub KeywordSelect (%) { # Scrolling selectable list for keyword groups my $Disabled = $Params{-disabled} || "0"; my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } - + } + # Scrolling selectable list for keywords my @KeywordIDs = sort byKeyword keys %Keywords; my %KeywordLabels = (); foreach my $ID (@KeywordIDs) { if ($Format eq "short") { - $KeywordLabels{$ID} = $Keywords{$ID}{Short}; + $KeywordLabels{$ID} = SmartHTML({-text=>$Keywords{$ID}{Short}}); } elsif ($Format eq "long") { - $KeywordLabels{$ID} = $Keywords{$ID}{Long}; + $KeywordLabels{$ID} = SmartHTML({-text=>$Keywords{$ID}{Long}}); } elsif ($Format eq "full") { - $KeywordLabels{$ID} = $Keywords{$ID}{Short}." ["; + $KeywordLabels{$ID} = SmartHTML({-text=>$Keywords{$ID}{Short}})." ["; if ($MaxLabel) { if ( (length $Keywords{$ID}{Long}) > $MaxLabel) { - $KeywordLabels{$ID} .= substr($Keywords{$ID}{Long},0,$MaxLabel)." ..."; + $KeywordLabels{$ID} .= substr(SmartHTML({-text=>$Keywords{$ID}{Long}}),0,$MaxLabel)." ..."; } else { - $KeywordLabels{$ID} .= $Keywords{$ID}{Long}; + $KeywordLabels{$ID} .= SmartHTML({-text=>$Keywords{$ID}{Long}}); } - $KeywordLabels{$ID} .= "]"; - } + $KeywordLabels{$ID} .= "]"; + } } - } + } print FormElementTitle(-helplink => "keywords", -helptext => "Keywords"); - print $query -> scrolling_list(-name => "keywordlist", -values => \@KeywordIDs, + print $query -> scrolling_list(-name => "keywordlist", -values => \@KeywordIDs, -labels => \%KeywordLabels, -size => 10, -multiple => $Multiple, $Booleans ); }; sub KeywordGroupSelect (%) { # Scrolling selectable list for keyword groups - my (%Params) = @_; - + my (%Params) = @_; + my $Format = $Params{-format} || "short"; # short, full my $Multiple = $Params{-multiple} || ""; # Any non-null text is "true" my $Name = $Params{-name} || "keywordgroup"; my $Remove = $Params{-remove} || ""; my $Disabled = $Params{-disabled} || "0"; - + my $Booleans = ""; - + if ($Disabled) { $Booleans .= "-disabled"; - } - + } + print FormElementTitle(-helplink => "keywordgroups", -helptext => "Keyword Groups"); my @KeyGroupIDs = keys %KeywordGroups; my %GroupLabels = (); - + foreach my $ID (@KeyGroupIDs) { if ($Format eq "full") { - $GroupLabels{$ID} = "$KeywordGroups{$ID}{Short} [$KeywordGroups{$ID}{Long}]"; - } else { - $GroupLabels{$ID} = $KeywordGroups{$ID}{Short}; - } - } + $GroupLabels{$ID} = SmartHTML({-text=>$KeywordGroups{$ID}{Short}})." ".SmartHTML({-text=>$KeywordGroups{$ID}{Long}}); + } else { + $GroupLabels{$ID} = SmartHTML({-text=>$KeywordGroups{$ID}{Short}}); + } + } if ($Remove) { unshift @KeyGroupIDs,"-1"; $GroupLabels{"-1"} = "Remove existing groups"; } - - print $query -> scrolling_list(-name => $Name, - -values => \@KeyGroupIDs, - -labels => \%GroupLabels, -size => 10, + + print $query -> scrolling_list(-name => $Name, + -values => \@KeyGroupIDs, + -labels => \%GroupLabels, -size => 10, -multiple => $Multiple, $Booleans); }; sub KeywordLinkByID ($;%) { my ($KeywordID,%Params) = @_; - + my $Format = $Params{-format} || "short"; # short, long my $NoLink = $Params{-nolink} || ""; # will just return information &FetchKeyword($KeywordID); - my $Keyword = $Keywords{$KeywordID}{Short}; + my $SafeShortKeyword = SmartHTML( {-text => $Keywords{$KeywordID}{Short}} ); + my $SafeLongKeyword = SmartHTML( {-text => $Keywords{$KeywordID}{Long}} ); + my $UnsafeURI = decode_entities($Keywords{$KeywordID}{Short}); + my $SafeURI = uri_escape($UnsafeURI); my $Link; - - unless ($NoLink) { - $Link .= ""; + + # FIXME_XSS: Check to make sure this kind of search still works. + # May need to remove special characters or adapt search atoms + unless ($NoLink) { + $Link .= ""; } - - if ($Format eq "short") { - $Link .= $Keywords{$KeywordID}{Short}; + + if ($Format eq "short") { + $Link .= $SafeShortKeyword; } elsif ($Format eq "long") { - $Link .= $Keywords{$KeywordID}{Long}; - } + $Link .= $SafeLongKeyword; + } - unless ($NoLink) { + unless ($NoLink) { $Link .= ""; } - + return $Link; } @@ -251,26 +265,29 @@ sub KeywordLink ($;%) { # FIXME: Allow parameters of short, long, full a la Lynn my ($Keyword,%Params) = @_; my $Format = $Params{-format} || "short"; # short, full - - my $ret = ""; - $ret .= "$Keyword"; + my $SafeKeyword = SmartHTML( {-text => $Keyword} ); + my $UnsafeURI = decode_entities($Keyword); + my $SafeURI = uri_escape($UnsafeURI); + my $ret = ""; + $ret .= "$SafeKeyword"; $ret .= ""; return $ret; -} +} sub KeywordsBox (%) { - my (%Params) = @_; + my (%Params) = @_; #FIXME: Get rid of global default - + my $Required = $Params{-required} || 0; - my $ElementTitle = &FormElementTitle(-helplink => "keywords" , + my $ElementTitle = &FormElementTitle(-helplink => "keywords" , -helptext => "Keywords" , -extratext => "(space separated) - Keyword Chooser", -required => $Required ); - print $ElementTitle,"\n"; - print $query -> textfield (-name => 'keywords', -default => $KeywordsDefault, + print $ElementTitle,"\n"; + my $SafeDefault = SmartHTML({-text => $KeywordsDefault},); + print $query -> textfield (-name => 'keywords', -default => $KeywordsDefault, -size => 70, -maxlength => 240); }; diff --git a/DocDB/cgi/KeywordListAdminister b/DocDB/cgi/KeywordListAdminister index 6022b8a4..dae6381d 100755 --- a/DocDB/cgi/KeywordListAdminister +++ b/DocDB/cgi/KeywordListAdminister @@ -1,17 +1,17 @@ #! /usr/bin/env perl # # Description: This script is called by KeywordAdministerForm and does administration -# on the Keyword table in the DB. +# on the Keyword table in the DB. # # Author: Lynn Garren (garren@fnal.gov) # Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -27,6 +27,7 @@ # FIXME: Check for duplicate keyword, warn use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -34,33 +35,34 @@ require "Sorts.pm"; require "ResponseElements.pm"; require "Security.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "KeywordHTML.pm"; require "KeywordSQL.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines - -%params = $query -> Vars; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); @ErrorStack = (); @WarnStack = (); -# Parameters to script - -my $Password = $params{password}; -my $Username = $params{admuser}; -my $Action = $params{admaction}; +# Parameters to script + +my $Password = $Untaint -> extract(-as_printable => "password") || ""; +my $Username = $Untaint -> extract(-as_printable => "admuser") || ""; +my $Action = $Untaint -> extract(-as_printable => "admaction") || ""; -my $KeywordID = $params{keywordlist}; -my @KeywordGroupIDs = split /\0/,$params{keywordgroup}; -my $LongName = $params{longdesc}; -my $ShortName = $params{shortdesc}; +my $KeywordID = $Untaint -> extract(-as_integer => "keywordlist") || 0; +my @KeywordGroupIDs = @{ $Untaint -> extract(-as_listofint => "keywordgroup") || undef }; +my $LongName = $Untaint -> extract(-as_safehtml => "longdesc") || ""; +my $ShortName = $Untaint -> extract(-as_safehtml => "shortdesc") || ""; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$Username,$Password); unless ($dbh) { push @ErrorStack,$Msg_AdminNoConnect; -} +} print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("Modified List of Keywords"); @@ -68,10 +70,10 @@ print $query -> header( -charset => $HTTP_ENCODING ); unless (&CanAdminister) { push @ErrorStack,$Msg_AdminNoLogin; -} +} &EndPage(@ErrorStack); -if ($Action eq "Delete") { +if ($Action eq "Delete") { unless ($KeywordID) { push @ErrorStack,$Msg_ModKeywdEmpty; @@ -79,9 +81,9 @@ if ($Action eq "Delete") { &EndPage(@ErrorStack); &FetchKeyword($KeywordID); my $KeywordLink = &KeywordLinkByID($KeywordID); - + &DeleteKeyword($KeywordID); # Delete KeywordID from Keyword table - + print "$KeywordLink has been removed from the database.
    \n"; } elsif ($Action eq "Modify") { unless ($KeywordID) { @@ -89,29 +91,29 @@ if ($Action eq "Delete") { } &EndPage(@ErrorStack); -# Deal with name changes +# Deal with name changes - if ($ShortName) { + if ($ShortName) { print "Updating short keyword name.
    \n"; my $KeywordUpdate = $dbh->prepare( "update Keyword set ShortDescription=? where KeywordID=?"); $KeywordUpdate -> execute($ShortName,$KeywordID); } - if ($LongName) { + if ($LongName) { print "Updating long keyword name.
    \n"; my $KeywordUpdate = $dbh->prepare( "update Keyword set LongDescription=? where KeywordID=?"); $KeywordUpdate -> execute($LongName,$KeywordID); } -# Deal with KeywordGroup changes +# Deal with KeywordGroup changes @KeywordGroupIDs = sort numerically @KeywordGroupIDs; # Want to get -1: remove first foreach my $KeywordGroupID (@KeywordGroupIDs) { if ($KeywordGroupID == -1) { # Remove existing KeywordGrouping entries my $GroupingDelete = $dbh -> prepare("delete from KeywordGrouping where KeywordID=?"); $GroupingDelete -> execute($KeywordID); - } elsif ($KeywordGroupID) { + } elsif ($KeywordGroupID) { my $GroupingSelect = $dbh -> prepare( "select KeywordGroupingID from KeywordGrouping where KeywordID=? and KeywordGroupID=?"); $GroupingSelect -> execute($KeywordID,$KeywordGroupID); @@ -130,11 +132,11 @@ if ($Action eq "Delete") { print "Adding a new keyword.
    \n"; my $KeywordInsert = $dbh->prepare( - "insert into Keyword (KeywordID, ShortDescription, LongDescription) ". + "insert into Keyword (KeywordID, ShortDescription, LongDescription) ". "values (0,?,?)"); my $KeywordGroupingInsert = $dbh->prepare( - "insert into KeywordGrouping (KeywordGroupingID, KeywordGroupID, KeywordID) ". + "insert into KeywordGrouping (KeywordGroupingID, KeywordGroupID, KeywordID) ". "values (0,?,?)"); $KeywordInsert -> execute($ShortName,$LongName); @@ -142,10 +144,10 @@ if ($Action eq "Delete") { foreach my $KeywordGroupID (@KeywordGroupIDs) { $KeywordGroupingInsert -> execute($KeywordGroupID,$KeywordID); - } + } } else { push @ErrorStack,"No valid action was specified."; -} +} # For modify or new fetch information and display. @@ -158,7 +160,7 @@ if ($Action eq "Modify" || $Action eq "New") { print "Short description: $ShortLink
    \n"; print "Long description: $LongLink
    \n"; print "

    \n"; -} +} print "

    \n"; $keyadminform = "Administer Keywords"; @@ -173,5 +175,5 @@ print "

    \n"; &DocDBNavBar; &DocDBFooter($DBWebMasterEmail,$DBWebMasterName); - + exit; diff --git a/DocDB/cgi/KeywordSQL.pm b/DocDB/cgi/KeywordSQL.pm index 4d3507d8..9b7a05c2 100644 --- a/DocDB/cgi/KeywordSQL.pm +++ b/DocDB/cgi/KeywordSQL.pm @@ -5,7 +5,7 @@ # Author: Lynn Garren (garren@fnal.gov) # Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. diff --git a/DocDB/cgi/ListAllMeetings b/DocDB/cgi/ListAllMeetings index 2d48c63a..d2ecc19b 100755 --- a/DocDB/cgi/ListAllMeetings +++ b/DocDB/cgi/ListAllMeetings @@ -8,7 +8,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -26,22 +26,24 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; require "MeetingSQL.pm"; require "MeetingHTML.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "SecuritySQL.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); -%params = $query -> Vars; - -my $Mode = $params{mode} || "display"; -my $EventGroupID = $params{eventgroupid}; -my $EventGroup = $params{eventgroup}; +my $Mode = $Untaint -> extract(-as_printable => "mode") || "display"; +my $EventGroupID = $Untaint -> extract(-as_integer => "eventgroupid") || 0; +my $EventGroup = $Untaint -> extract(-as_integer => "eventgroup") || 0; GetSecurityGroups(); diff --git a/DocDB/cgi/ListAuthors b/DocDB/cgi/ListAuthors index 96e16878..99df7d66 100755 --- a/DocDB/cgi/ListAuthors +++ b/DocDB/cgi/ListAuthors @@ -2,12 +2,12 @@ # # Author Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -19,7 +19,7 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI; +use CGI; use DBI; require "DocDBGlobals.pm"; @@ -28,6 +28,7 @@ require "ResponseElements.pm"; require "HTMLUtilities.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); GetInstitutions(); diff --git a/DocDB/cgi/ListBy b/DocDB/cgi/ListBy index 61a5afda..4d022bda 100755 --- a/DocDB/cgi/ListBy +++ b/DocDB/cgi/ListBy @@ -8,7 +8,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -27,6 +27,7 @@ use Benchmark; use CGI; +use CGI::Untaint; use DBI; $StartTime = new Benchmark; @@ -35,30 +36,31 @@ require "DocDBGlobals.pm"; require "DocumentHTML.pm"; require "SecuritySQL.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "DocumentUtilities.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -%params = $query -> Vars; +my $Days = $Untaint -> extract(-as_integer => "days") || 0; +my $TypeID = $Untaint -> extract(-as_integer => "typeid") || 0; +my $AuthorID = $Untaint -> extract(-as_integer => "authorid") || 0; -my $Days = $params{days} || 0; -my $TypeID = $params{typeid} || 0; -my $AuthorID = $params{authorid} || 0; +my $TopicID = $Untaint -> extract(-as_integer => "topicid") || 0; +my $Topic = $Untaint -> extract(-as_safehtml => "topic") || ""; -my $TopicID = $params{topicid} || 0; -my $Topic = $params{topic} || 0; +my $EventID = $Untaint -> extract(-as_integer => "eventid") || 0; +my $EventGroupID = $Untaint -> extract(-as_integer => "eventgroupid") || 0; +my $EventGroup = $Untaint -> extract(-as_safehtml => "eventgroup") || ""; -my $EventID = $params{eventid} || 0; -my $EventGroupID = $params{eventgroupid} || 0; -my $EventGroup = $params{eventgroup} || ""; +my $GroupID = $Untaint -> extract(-as_integer => "groupid") || 0; +my $Group = $Untaint -> extract(-as_safehtml => "group") || ""; -my $GroupID = $params{groupid} || 0; -my $Group = $params{group} || ""; +my $AllPubs = $Untaint -> extract(-as_safehtml => "allpubs") || ""; +my $AllDocs = $Untaint -> extract(-as_safehtml => "alldocs") || ""; -my $AllPubs = $params{allpubs} || ""; -my $AllDocs = $params{alldocs} || ""; - -my $Mode = $params{mode} || ""; +my $Mode = $Untaint -> extract(-as_safehtml => "mode") || ""; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); @@ -116,15 +118,16 @@ if ($Days) { $SubTopicMessage = "(subtopic of ".TopicLink({-topicid => $ParentTopicID}).")"; } - $Message = "These documents on $Topics{$TopicID}{Long} - $SubTopicMessage "; + $Message = "These documents on ". + SmartHTML({-text=>$Topics{$TopicID}{Long}}). + " $SubTopicMessage "; if ($HasSubTopics) { $Message .= "and sub-topics "; } $Message .= "are available:"; my %Hash = GetEventHashByTopic($TopicID); if (%Hash) { - $Message .= '
    (List events on '.$Topics{$TopicID}{Long}.')'; + $Message .= '
    (List events on '.SmartHTML({-text=>$Topics{$TopicID}{Long}}).')'; } } elsif ($AuthorID) { @@ -144,11 +147,12 @@ if ($Days) { my $Link = AuthorLink($AuthorID); - $Message = "$Link of $Institutions{$Authors{$AuthorID}{InstitutionID}}{LONG} - is listed as an author on the following documents:"; + $Message = "$Link of "; + $Message .= SmartHTML( {-text => $Institutions{$Authors{$AuthorID}{InstitutionID}}{LONG}, } ); + $Message .= " is listed as an author on the following documents:"; my %Hash = GetEventHashByModerator($AuthorID); if (%Hash) { - $Message .= '
    (List events moderated by '.$Authors{$AuthorID}{FULLNAME}.')'; + $Message .= '
    (List events moderated by '.$Link.')'; } @DocumentIDs = GetAuthorDocuments($AuthorID); } elsif ($EventID) { @@ -161,9 +165,11 @@ if ($Days) { $FieldListOptions{-eventid} = $EventID; $FieldListOptions{-eventgroupid} = $Conferences{$EventID}{EventGroupID}; $Title = "Document List by Event"; - $Message = "These documents from $Conferences{$EventID}{LongDescription} "; + $Message = "These documents from "; + $Message .= SmartHTML({-text => $Conferences{$EventID}{LongDescription}}); + $Message .= " "; if ($Conferences{$EventID}{URL}) { - $Message .= "($Conferences{$EventID}{URL}) "; + $Message .= "(".SmartHTML({-text => $Conferences{$EventID}{URL}, -makeURLs=>$TRUE}).") "; } $Message .= "are available:"; $List = $dbh -> prepare("select DISTINCT(DocumentRevision.DocumentID) from ". @@ -185,7 +191,9 @@ if ($Days) { $FieldListOptions{-eventgroupid} = $EventGroupID; $FieldListOptions{-default} = "Event Group Default"; $Title = "Document List by Event Group"; - $Message = "These documents from $EventGroups{$EventGroupID}{LongDescription} are available:"; + $Message = "These documents from "; + $Message .= SmartHTML({-text => $EventGroups{$EventGroupID}{LongDescription},}); + $Message .=" are available:"; $List = $dbh -> prepare("select DISTINCT(DocumentRevision.DocumentID) from ". "DocumentRevision,RevisionEvent,Conference where DocumentRevision.DocRevID=RevisionEvent.DocRevID ". "and DocumentRevision.Obsolete=0 and RevisionEvent.ConferenceID=Conference.ConferenceID and Conference.EventGroupID=?"); @@ -195,8 +203,10 @@ if ($Days) { FetchDocType ($TypeID); $FieldListOptions{-doctypeid} = $TypeID; $Title = "Document List by Type"; - $Message = "These documents of type - $DocumentTypes{$TypeID}{SHORT} are available:"; + + $Message = "These documents of type "; + $Message .= SmartHTML({-text => $DocumentTypes{$TypeID}{SHORT},}); + $Message .= " are available:"; $List = $dbh -> prepare("select DISTINCT(DocumentRevision.DocumentID) from ". "DocumentRevision where DocumentRevision.DocTypeID=?"); @@ -206,11 +216,13 @@ if ($Days) { $GroupID = FetchSecurityGroupByName($Group); } $Title = "Document List by Group"; - $Message = "These documents for - $SecurityGroups{$GroupID}{NAME} are available:"; + $Message = "These documents for "; + $Message .= SmartHTML({-text => $SecurityGroups{$GroupID}{NAME},}); + $Message .= " are available:"; $List = $dbh -> prepare("select DISTINCT(DocumentRevision.DocumentID) from ". - "DocumentRevision,RevisionSecurity where DocumentRevision.DocRevID=RevisionSecurity.DocRevID and RevisionSecurity.GroupID=?"); + "DocumentRevision,RevisionSecurity where DocumentRevision.DocRevID=RevisionSecurity.DocRevID ". + "and DocumentRevision.Obsolete=0 and RevisionSecurity.GroupID=?"); $List -> execute($GroupID); } elsif ($AllPubs) { $Title = "$Project Publications"; diff --git a/DocDB/cgi/ListEventsBy b/DocDB/cgi/ListEventsBy index b7e0ce06..b3f3219c 100755 --- a/DocDB/cgi/ListEventsBy +++ b/DocDB/cgi/ListEventsBy @@ -9,7 +9,7 @@ # # Author: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. @@ -44,6 +44,7 @@ require "TopicHTML.pm"; require "CalendarHTML.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); # Parameters to script @@ -91,7 +92,9 @@ if ($TopicID) { $EventHash{$ID} = $Hash{$ID}; } } - $HTML .= "

    Events for $Topics{$TopicID}{Long} "; + $HTML .= "

    Events for "; + $HTML .= SmartHTML({-text=>$Topics{$TopicID}{Long}}); + $HTML .= " "; if (scalar(@ChildTopicIDs) > 1) { $HTML .= " and its sub-topics"; } @@ -105,8 +108,9 @@ if ($TopicID) { my $Link = AuthorLink($AuthorID); - $HTML .= "

    Events moderated by $Link of - $Institutions{$Authors{$AuthorID}{InstitutionID}}{LONG}"; + $HTML .= "

    Events moderated by $Link of "; + $HTML .= SmartHTML({-text=>$Institutions{$Authors{$AuthorID}{InstitutionID}}{LONG}}); + $HTML .= ""; if ($Preferences{Components}{iCal}) { $HTML .= ' '.ICalLink({ -authorid => $AuthorID }); } @@ -170,8 +174,8 @@ if (@HashIDs) { } $Title = SessionLink(-sessionid => $SessionID, -format => "full"); - $Location = join '
    ',$Sessions{$SessionID}{Location}, - $Sessions{$SessionID}{AltLocation}; + $Location = join '
    ',SmartHTML({-text=>$Sessions{$SessionID}{Location}}), + SmartHTML({-text=>$Sessions{$SessionID}{AltLocation}}); $Topics = TopicListByID({ -linktype => "event", -listformat => "br", -sortby => "name", -topicids => $Sessions{$SessionID}{Topics}, }); @@ -192,8 +196,8 @@ if (@HashIDs) { } $Title = EventLink(-eventid => $EventID,); - $Location = join '
    ',$Conferences{$EventID}{Location}, - $Conferences{$EventID}{AltLocation}; + $Location = join '
    ',SmartHTML({-text=>$Conferences{$EventID}{Location}}), + SmartHTML({-text=>$Conferences{$EventID}{AltLocation}}); $Topics = TopicListByID({ -linktype => "event", -listformat => "br", -sortby => "name", -topicids => $Conferences{$EventID}{Topics}, }); $Time = 'All day/no time'; diff --git a/DocDB/cgi/ListGroupUsers b/DocDB/cgi/ListGroupUsers index 1d12505c..27bf7ee2 100755 --- a/DocDB/cgi/ListGroupUsers +++ b/DocDB/cgi/ListGroupUsers @@ -6,15 +6,15 @@ # receiving what. # # Author: Eric Vaandering (ewv@fnal.gov) -# Modified: +# Modified: # -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,7 +26,7 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI qw(-nosticky); +use CGI qw(-nosticky); use DBI; require "DocDBGlobals.pm"; @@ -39,12 +39,13 @@ require "SecuritySQL.pm"; require "NotificationSQL.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI -> connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); GetSecurityGroups(); print $query -> header( -charset => $HTTP_ENCODING ); -DocDBHeader("List of Groups and Users",""); +DocDBHeader("List of Groups and Users",""); @ErrorStack = (); @WarnStack = (); @@ -62,18 +63,19 @@ EndPage(); print "

    DocDB Security Groups

    \n"; -print "

    These are the security groups withing DocDB and a summary of their +print "

    These are the security groups withing DocDB and a summary of their permissions. To see the individual members of these groups, see the lists below or click on the group name which will take you to the list.

    \n"; -print ''."\n"; +print '
    '."\n"; print ''."\n"; foreach my $SecurityGroupID (@SecurityGroupIDs) { + my $Name = SmartHTML({-text => $SecurityGroups{$SecurityGroupID}{NAME}}); + my $Description = SmartHTML({-text => $SecurityGroups{$SecurityGroupID}{Description}}); print ''; - print ''; - print ''; + print ''; + print ''; print ''; print ''; print ''; @@ -87,19 +89,23 @@ my @EmailUserIDs = sort EmailUserIDsByName GetEmailUserIDs(); print "

    DocDB Users By Group

    \n"; foreach my $SecurityGroupID (@SecurityGroupIDs) { - my $GroupName = $SecurityGroups{$SecurityGroupID}{NAME}; + my $GroupName = SmartHTML({-text => $SecurityGroups{$SecurityGroupID}{NAME}}); + my @EmailUserIDs = sort EmailUserIDsByName FetchEmailUserIDsBySecurityGroup($SecurityGroupID); if (@EmailUserIDs) { print "

    $GroupName has these members:

    \n
      \n"; foreach my $EmailUserID (@EmailUserIDs) { - if ($EmailUser{$EmailUserID}{Name}) { - print "
    • $EmailUser{$EmailUserID}{Name} ($EmailUser{$EmailUserID}{Username}, $EmailUser{$EmailUserID}{EmailAddress})
    • \n"; - } + if ($EmailUser{$EmailUserID}{Name}) { + my $Name = SmartHTML({-text => $EmailUser{$EmailUserID}{Name}}); + my $Username = SmartHTML({-text => $EmailUser{$EmailUserID}{Username}}); + my $Email = SmartHTML({-text => $EmailUser{$EmailUserID}{EmailAddress}}); + print "
    • $Name ($Username, $Email)
    • \n"; + } } print "
    \n"; } else { print "

    $GroupName has no members.

    \n"; - } + } } DocDBNavBar(); diff --git a/DocDB/cgi/ListGroups b/DocDB/cgi/ListGroups index 50afb95e..98237d4b 100755 --- a/DocDB/cgi/ListGroups +++ b/DocDB/cgi/ListGroups @@ -2,12 +2,12 @@ # # Author Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -19,7 +19,7 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI; +use CGI; use DBI; require "DocDBGlobals.pm"; @@ -29,6 +29,7 @@ require "HTMLUtilities.pm"; require "DBUtilities.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); CreateConnection(-type => "ro"); GetSecurityGroups(); @@ -42,10 +43,10 @@ print "\n"; foreach my $GroupID (keys %SecurityGroups) { print "\n"; print "\n"; - print "\n"; + print "\n"; print "\n"; -} - +} + print "
    GroupDescriptionAdmin?Create?View?
    '. - $SecurityGroups{$SecurityGroupID}{NAME}.''.$SecurityGroups{$SecurityGroupID}{Description}.''.$Name.''.$Description.''.('No','Yes')[$SecurityGroups{$SecurityGroupID}{CanAdminister}].''.('No','Yes')[$SecurityGroups{$SecurityGroupID}{CanCreate}]. ''.('No','Yes')[$SecurityGroups{$SecurityGroupID}{CanView}]. '
    GroupDescription
    ",SecurityLink( {-groupid => $GroupID} ),"",$SecurityGroups{$GroupID}{Description},"",SmartHTML({-text=>$SecurityGroups{$GroupID}{Description}}),"
    \n"; diff --git a/DocDB/cgi/ListKeywords b/DocDB/cgi/ListKeywords index 9aaf669c..a0a8f8de 100755 --- a/DocDB/cgi/ListKeywords +++ b/DocDB/cgi/ListKeywords @@ -1,20 +1,20 @@ #! /usr/bin/env perl # # Name: ListKeywords -# Description: Lists the managed keywords. +# Description: Lists the managed keywords. # In the first mode, links perform a search -# In chooser mode, links insert the keyword into the +# In chooser mode, links insert the keyword into the # form on the calling page # # Author: Lynn Garren (garren@fnal.gov) # Modified: Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,7 +26,8 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI; +use CGI; +use CGI::Untaint; use DBI; require "DocDBGlobals.pm"; @@ -34,18 +35,19 @@ require "KeywordSQL.pm"; require "ResponseElements.pm"; require "KeywordHTML.pm"; require "HTMLUtilities.pm"; +require "UntaintInput.pm"; require "Messages.pm"; $query = new CGI; # Global for subroutines -%params = $query -> Vars; +$query -> autoEscape(0); +my $Untaint = CGI::Untaint -> new($query -> Vars); -my $Mode = $params{mode} || "display"; -my $Format = $params{format} || "short" ; +my $Mode = $Untaint -> extract(-as_printable => "mode") || "display"; +my $Format = $Untaint -> extract(-as_printable => "format") || "short"; $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); - print $query -> header( -charset => $HTTP_ENCODING ); &DocDBHeader("List of Keywords","", -scripts => ["PopUps","InsertKeyword"]); @@ -57,7 +59,7 @@ if ($Mode eq "chooser") { print "

    \n"; print "Please use the following keywords to facilitate searches. Note that spaces are NOT allowed in keywords. To suggest additional keywords, send mail - to an adminstrator. The links below + to an administrator. The links below will search the database for all instances of a single keyword. Use the search form to do a more complicated search.

    \n"; @@ -67,7 +69,7 @@ if ($Mode eq "chooser") { } elsif ($Format eq "long") { print "

    The abbreviated listing lists all the keywords compactly.\n

    "; - } + } if ($KeywordAddendumText) { print "

    $KeywordAddendumText

    \n"; } diff --git a/DocDB/cgi/ListManagedDocuments b/DocDB/cgi/ListManagedDocuments index afe7aaa9..ca8c3b87 100755 --- a/DocDB/cgi/ListManagedDocuments +++ b/DocDB/cgi/ListManagedDocuments @@ -2,12 +2,12 @@ # # Author Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -36,8 +36,7 @@ require "HTMLUtilities.pm"; require "DocumentUtilities.pm"; $query = new CGI; # Global for subroutines - -%params = $query -> Vars; +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); diff --git a/DocDB/cgi/ListTopics b/DocDB/cgi/ListTopics index 352333e1..7b2a9705 100755 --- a/DocDB/cgi/ListTopics +++ b/DocDB/cgi/ListTopics @@ -2,12 +2,12 @@ # # Author Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -26,14 +26,17 @@ require "DocDBGlobals.pm"; require "TopicSQL.pm"; require "TopicHTML.pm"; require "HTMLUtilities.pm"; +require "ResponseElements.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); GetTopics(); print $query -> header( -charset => $HTTP_ENCODING ); DocDBHeader("List of Topics"); +EndPage(); TopicsTable(); diff --git a/DocDB/cgi/ListTypes b/DocDB/cgi/ListTypes index 6d7fc85d..293aea4f 100755 --- a/DocDB/cgi/ListTypes +++ b/DocDB/cgi/ListTypes @@ -2,12 +2,12 @@ # # Author Eric Vaandering (ewv@fnal.gov) -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -19,7 +19,7 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -use CGI; +use CGI; use DBI; require "DocDBGlobals.pm"; @@ -28,6 +28,7 @@ require "ResponseElements.pm"; require "HTMLUtilities.pm"; $query = new CGI; # Global for subroutines +$query -> autoEscape(0); $dbh = DBI->connect('DBI:mysql:'.$db_name.':'.$db_host,$db_rouser,$db_ropass); &GetDocTypes; diff --git a/DocDB/cgi/MailNotification.pm b/DocDB/cgi/MailNotification.pm index d9984bdc..1979a6a8 100644 --- a/DocDB/cgi/MailNotification.pm +++ b/DocDB/cgi/MailNotification.pm @@ -1,9 +1,19 @@ -# Copyright 2001-2009 Eric Vaandering, Lynn Garren, Adam Bryant +# Name: $RCSfile$ +# Description: This script provides a form to administer users receiving +# e-mail notifications and shows the complete list of who is +# receiving what. +# +# Revision: $Revision$ +# Modified: $Author$ on $Date$ +# +# Author: Eric Vaandering (ewv@fnal.gov) + +# Copyright 2001-2013 Eric Vaandering, Lynn Garren, Adam Bryant # This file is part of DocDB. # DocDB is free software; you can redistribute it and/or modify -# it under the terms of version 2 of the GNU General Public License +# it under the terms of version 2 of the GNU General Public License # as published by the Free Software Foundation. # DocDB is distributed in the hope that it will be useful, @@ -15,11 +25,15 @@ # along with DocDB; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +use HTML::Entities; + +require "HTMLUtilities.pm"; + sub MailNotices (%) { unless ($MailInstalled) { return; - } + } require Mail::Send; require Mail::Mailer; @@ -29,21 +43,21 @@ sub MailNotices (%) { require "ResponseElements.pm"; require "Utilities.pm"; require "Security.pm"; - + my (%Params) = @_; my $DocRevID = $Params{-docrevid}; my $Type = $Params{-type} || "updateunknown"; my @EmailUserIDs = @{$Params{-emailids}}; - + FetchDocRevisionByID($DocRevID); my $DocumentID = $DocRevisions{$DocRevID}{DOCID}; my $Version = $DocRevisions{$DocRevID}{Version}; - -# Figure out who cares + +# Figure out who cares my @Addressees = (); - if ($Type eq "update" || $Type eq "updatedb" || $Type eq "add" || + if ($Type eq "update" || $Type eq "updatedb" || $Type eq "add" || $Type eq "reserve" || $Type eq "addfiles" || $Type eq "updateunknown") { @Addressees = UsersToNotify($DocRevID,{-period => "Immediate"} ); } elsif ($Type eq "signature") { @@ -51,7 +65,7 @@ sub MailNotices (%) { FetchEmailUser($EmailUserID); push @Addressees,$EmailUser{$EmailUserID}{EmailAddress}; } - } elsif ($Type eq "approved") { + } elsif ($Type eq "approved") { @Addressees = UsersToNotify($DocRevID,{-period => "Immediate"} ); my %EmailUsers = (); my @SignoffIDs = GetAllSignoffsByDocRevID($DocRevID); @@ -61,12 +75,12 @@ sub MailNotices (%) { my $EmailUserID = $Signatures{$SignatureID}{EmailUserID}; FetchEmailUser($EmailUserID); push @Addressees,$EmailUser{$EmailUserID}{EmailAddress}; - } - } - } - + } + } + } + @Addressees = Unique(@Addressees); - + # If anyone, open the mailer if (@Addressees) { @@ -78,13 +92,13 @@ sub MailNotices (%) { my $Title = $DocRevisions{$DocRevID}{Title}; my ($Subject,$Message,$Feedback); - - if ($Type eq "update" || $Type eq "updatedb" || $Type eq "add" || + + if ($Type eq "update" || $Type eq "updatedb" || $Type eq "add" || $Type eq "reserve" || $Type eq "addfiles" || $Type eq "updateunknown") { $Subject = "$FullID: $Title"; $Message = "The following document was added or updated ". "in the $Project Document Database:\n\n"; - $Feedback = "E-mail sent to: "; + $Feedback = "E-mail sent to: "; if ($Type eq "update") { $Message = "The following document was updated ". "in the $Project Document Database:\n\n"; @@ -100,7 +114,7 @@ sub MailNotices (%) { } elsif ($Type eq "addfiles") { $Message = "Files were added to the following document ". "in the $Project Document Database:\n\n"; - } + } } elsif ($Type eq "signature") { $Subject = "Ready for signature: $FullID: $Title"; $Message = "The following document ". @@ -108,30 +122,28 @@ sub MailNotices (%) { "is ready for your signature:\n". "(Note that you may not be able to sign if you share ". "signature authority with someone who has already signed.)\n\n"; - $Feedback = "Signature(s) requested from: "; + $Feedback = "Signature(s) requested from: "; } elsif ($Type eq "approved") { $Subject = "Approved: $FullID: $Title"; $Message = "The following document ". "in the $Project Document Database ". "has been approved (received all necessary signatures).\n\n"; - $Feedback = "Approval notification sent to: "; - } + $Feedback = "Approval notification sent to: "; + } $Headers{To} = \@Addressees; $Headers{From} = "$Project Document Database <$DBWebMasterEmail>"; - $Headers{Subject} = $Subject; + $Headers{Subject} = HTML::Entities::decode_entities($Subject); $Mailer -> open(\%Headers); # Start mail with headers - print $Mailer $Message; + print $Mailer HTML::Entities::decode_entities($Message); RevisionMailBody($DocRevID); # Write the body $Mailer -> close; # Complete the message and send it my $Addressees = join ', ',@Addressees; - $Addressees =~ s/\&/\&\;/g; - $Addressees =~ s//\>\;/g; - + $Addressees = SmartHTML({-text => $Addressees}); + print $Feedback,$Addressees,"

    "; - } + } } sub RevisionMailBody ($) { @@ -144,11 +156,11 @@ sub RevisionMailBody ($) { require "Sorts.pm"; FetchDocRevisionByID($DocRevID); - + my $Title = $DocRevisions{$DocRevID}{Title}; my $FullID = FullDocumentID($DocRevisions{$DocRevID}{DOCID},$DocRevisions{$DocRevID}{VERSION}); my $URL = DocumentURL($DocRevisions{$DocRevID}{DOCID}); - + FetchAuthor($DocRevisions{$DocRevID}{Submitter}); my $Submitter = $Authors{$DocRevisions{$DocRevID}{Submitter}}{FULLNAME}; @@ -157,9 +169,9 @@ sub RevisionMailBody ($) { my @AuthorIDs = AuthorRevIDsToAuthorIDs({ -authorrevids => \@AuthorRevIDs, }); my @TopicIDs = GetRevisionTopics({-docrevid => $DocRevID}); my @EventIDs = GetRevisionEvents($DocRevID); - -# Build list of authors - + +# Build list of authors + my @Authors = (); foreach $AuthorID (@AuthorIDs) { FetchAuthor($AuthorID); @@ -169,9 +181,9 @@ sub RevisionMailBody ($) { push @Authors,$Authors{$AuthorID}{FULLNAME}; } my $Authors = join ', ',@Authors; - + # Build list of topics - + my @Topics = (); foreach $TopicID (@TopicIDs) { FetchTopic({-topicid => $TopicID}); @@ -181,9 +193,9 @@ sub RevisionMailBody ($) { push @Topics,$Topics{$TopicID}{Long}; } my $Topics = join ', ',@Topics; - -# Build list of events - + +# Build list of events + my @Events = (); foreach $EventID (@EventIDs) { FetchConferenceByConferenceID($EventID); @@ -194,25 +206,25 @@ sub RevisionMailBody ($) { " (".EuroDate($Conferences{$EventID}{StartDate}).")"; } my $Events = join ', ',@Events; - - + + # Construct the mail body - - print $Mailer " Title: ",$DocRevisions{$DocRevID}{Title},"\n"; - print $Mailer " Document ID: ",$FullID,"\n"; - print $Mailer " URL: ",$URL,"\n"; - print $Mailer " Date: ",$DocRevisions{$DocRevID}{DATE},"\n"; - print $Mailer "Submitted by: ",$Submitter,"\n"; - print $Mailer " Authors: ",$Authors,"\n"; - print $Mailer " Topics: ",$Topics,"\n"; + + print $Mailer " Title: ",HTML::Entities::decode_entities($DocRevisions{$DocRevID}{Title}),"\n"; + print $Mailer " Document ID: ",HTML::Entities::decode_entities($FullID),"\n"; + print $Mailer " URL: ",HTML::Entities::decode_entities($URL),"\n"; + print $Mailer " Date: ",HTML::Entities::decode_entities($DocRevisions{$DocRevID}{DATE}),"\n"; + print $Mailer "Submitted by: ",HTML::Entities::decode_entities($Submitter),"\n"; + print $Mailer " Authors: ",HTML::Entities::decode_entities($Authors),"\n"; + print $Mailer " Topics: ",HTML::Entities::decode_entities($Topics),"\n"; if ($Events) { - print $Mailer " Events: ",$Events,"\n"; - } - print $Mailer " Keywords: ",$DocRevisions{$DocRevID}{Keywords},"\n"; - print $Mailer " Abstract: ",$DocRevisions{$DocRevID}{Abstract},"\n"; + print $Mailer " Events: ",HTML::Entities::decode_entities($Events),"\n"; + } + print $Mailer " Keywords: ",HTML::Entities::decode_entities($DocRevisions{$DocRevID}{Keywords}),"\n"; + print $Mailer " Abstract: ",HTML::Entities::decode_entities($DocRevisions{$DocRevID}{Abstract}),"\n"; if ($DocRevisions{$DocRevID}{Note}) { - print $Mailer " Notes: ",$DocRevisions{$DocRevID}{Note},"\n"; - } + print $Mailer " Notes: ",HTML::Entities::decode_entities($DocRevisions{$DocRevID}{Note}),"\n"; + } } sub UsersToNotify ($$) { @@ -223,14 +235,14 @@ sub UsersToNotify ($$) { require "MeetingSQL.pm"; require "NotificationSQL.pm"; require "TopicSQL.pm"; - + require "Security.pm"; require "Utilities.pm"; require "AuthorUtilities.pm"; unless ($Period eq "Immediate" || $Period eq "Daily" || $Period eq "Weekly") { return undef; - } + } GetTopics(); @@ -248,12 +260,12 @@ sub UsersToNotify ($$) { "select EmailUserID from Notification where Period=? and Type=? and TextKey=?"); # Get users interested in this particular document (only immediate) - + if ($Period eq "Immediate") { $Fetch -> execute("Immediate","Document",$DocumentID); $Fetch -> bind_columns(undef,\($UserID)); while ($Fetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } } @@ -263,12 +275,12 @@ sub UsersToNotify ($$) { $Fetch -> execute($Period,"AllDocuments",1); $Fetch -> bind_columns(undef,\($UserID)); while ($Fetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } $Fetch -> execute($Period,"AllDocuments",0); $Fetch -> bind_columns(undef,\($UserID)); while ($Fetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } # Get users interested in topics for this reporting period @@ -276,7 +288,7 @@ sub UsersToNotify ($$) { GetTopics(); my @TopicIDs = (); my @InitialTopicIDs = GetRevisionTopics( {-docrevid => $DocRevID} ); - + foreach my $TopicID (@InitialTopicIDs) { push @TopicIDs,@{$TopicProvenance{$TopicID}}; # Add ancestors to list } @@ -285,10 +297,10 @@ sub UsersToNotify ($$) { $Fetch -> execute($Period,"Topic",$TopicID); $Fetch -> bind_columns(undef,\($UserID)); while ($Fetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } - } - + } + # Get users interested in events for this reporting period my @EventIDs = GetRevisionEvents($DocRevID); @@ -297,17 +309,17 @@ sub UsersToNotify ($$) { $Fetch -> execute($Period,"Event",$EventID); $Fetch -> bind_columns(undef,\($UserID)); while ($Fetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } my $EventGroupID = $Conferences{$EventID}{EventGroupID}; - + $Fetch -> execute($Period,"EventGroup",$EventGroupID); $Fetch -> bind_columns(undef,\($UserID)); while ($Fetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } - } + } # Get users interested in authors for this reporting period @@ -317,12 +329,12 @@ sub UsersToNotify ($$) { $Fetch -> execute($Period,"Author",$AuthorID); $Fetch -> bind_columns(undef,\($UserID)); while ($Fetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } - } + } # Get users interested in keywords for this reporting period - + FetchDocRevisionByID($DocRevID); my @Keywords = split /,*\s+/,$DocRevisions{$DocRevID}{Keywords}; # Comma and/or space separated @@ -331,13 +343,13 @@ sub UsersToNotify ($$) { $TextFetch -> execute($Period,"Keyword",$Keyword); $TextFetch -> bind_columns(undef,\($UserID)); while ($TextFetch -> fetch) { - $UserIDs{$UserID} = 1; + $UserIDs{$UserID} = 1; } - } + } -# Translate UserIDs into E-mail addresses, +# Translate UserIDs into E-mail addresses, # verify user is allowed to receive notification - + foreach $UserID (keys %UserIDs) { my $EmailUserID = FetchEmailUser($UserID); if ($EmailUserID && CanAccess($DocumentID,$Version,$EmailUserID)) { @@ -347,8 +359,8 @@ sub UsersToNotify ($$) { push @Addressees,$EmailAddress; } } - } - + } + return @Addressees; } @@ -360,12 +372,12 @@ sub EmailKeywordForm ($) { require "FormElements.pm"; - print FormElementTitle(-helplink => "notifykeyword", -helptext => $Period, + print FormElementTitle(-helplink => "notifykeyword", -helptext => $Period, -extratext => "(separate with spaces)"); my $Keywords = join ' ',sort @Defaults; - print $query -> textfield (-name => $Name , -default => $Keywords, + print $query -> textfield (-name => $Name , -default => $Keywords, -size => 80, -maxlength => 400); } @@ -378,7 +390,7 @@ sub EmailAllForm ($) { print $query -> checkbox(-name => $Name, -checked => 'checked', -value => 1, -label => 'All Documents'); } else { print $query -> checkbox(-name => $Name, -value => 1, -label => 'All Documents'); - } + } } sub DisplayNotification ($$;$) { @@ -398,38 +410,38 @@ sub DisplayNotification ($$;$) { my @EventGroupIDs = @{$Notifications{$EmailUserID}{"EventGroup_".$Set}}; my @Keywords = @{$Notifications{$EmailUserID}{"Keyword_".$Set}}; my @AllDocuments = @{$Notifications{$EmailUserID}{"AllDocuments_".$Set}}; - + my $NewNotify = (@AllDocuments || @AuthorIDs || @TopicIDs || @EventIDs || @EventGroupIDs || @Keywords); - + if ($NotifyAllTopics || $NewNotify) { - print "$Set notifications:\n"; - print "