#!/usr/bin/perl # # Copyright 1997,1998 GIZMOsoft Software -- all rights reserved. # local (@Orders,$OrderCount); local ($LocationRedirectionSupport,$SubdirectorySupport,$OrderDirectoryPath); local ($ParsedHeaderSupport,$PostCallToCCProc); $LocationRedirectionSupport = 1; # $SubdirectorySupport = 1; $ParsedHeaderSupport = 1; $OrderDirectoryPath = 'orderdir/'; $NotificationEmail = ''; $ReturnAddr = 'robot@unknown.com'; $MailHost = '$$MailHost$$'; $OrgName = 'Horizon Herbs, LLC'; $CurrencySymbol = '$'; $BaseCatalogURL = ''; $PostCallToCCProc = 0; $ProcessorURL = ''; $Extension = '.ord'; $ParmMap=""; $ParmTypeMap=""; $ParmSourceMap=""; $NotificationMessage = 'You can view the new order at http://www.chatlink.com/~herbseed/orders.html'; $FileName = "gizorder.ord"; $Error = 0; $TempDataDir = $OrderDirectoryPath; $TempDataDir =~ s/\\/\//g; $TempDataDir =~ s/\/\//\//g; $TempDataDir = substr($TempDataDir,0,length($TempDataDir)-1) if (substr($TempDataDir,length($TempDataDir)-1) eq "/"); $ThisDir = ""; $DirLastSlash = rindex($TempDataDir,"/"); if ($DirLastSlash > -1) { $ThisDir = substr($OrderDirectoryPath,0,$DirLastSlash+1); }; %data_received = &User_Data; &No_SSI(*data_received); &GetCookieArray(); sub SendEmailUnix { local ($EmailAddr,$OrderNumber,$Message) = @_; open(MAIL,"|/usr/lib/sendmail -t") || print &GetTextHeader(1,"Cannot find email program /usr/lib/sendmail"); print MAIL "To: $EmailAddr\n"; print MAIL "From: $ReturnAddr\n"; print MAIL "Subject: New order $OrderNumber\n"; print MAIL "$Message\n\n"; return close(MAIL); }; sub SendEmailWin { local ($EmailAddr,$OrderNumber,$Message) = @_; $Settings = "$MailHost\n$ReturnAddr\n$OranizationName\n\n\n\n"; open (MAIL, "|gizmail $NotificationEmail -M$MailHost -f$ReturnAddr -o$OrgName \"-sOrder $OrderNumber\"") || die "Cannot mail via -M$MailHost, check your settings"; print MAIL $Message; close (MAIL); }; sub SendEmail { local ($EmailAddr,$OrderNumber,$Message) = @_; if ( (1 || length($MailHost)) && length($EmailAddr) > 0) { &SendEmailUnix($EmailAddr,$OrderNumber,$Message); } else { &SendEmailWin($EmailAddr,$OrderNumber,$Message); }; }; sub GetTextHeader { local ($NowError,$Instr) = @_; local ($Outstr); $Error = 1 if ($NowError); $Outstr = ""; $Outstr .= "HTTP/1.0 200 OK\n" if (!$ParsedHeaderSupport); $Outstr .= "Content-type: text/html\n\n"; $Outstr .= $Instr; return $Outstr; } sub DeleteCookieText { local ($CookieName) = @_; local ($OutTxt); if ($LocationRedirectionSupport) { $OutTxt = "Set-Cookie: $CookieName=NULL; path=/; expires=Monday, 01-Jan-95 00:00:01\n"; } else { $OutTxt = "\n\n"; }; return $OutTxt; }; sub SetCookieText { local ($CookieName,$CookieValue) = @_; local ($OutTxt); $OutTxt = "\n\n"; return $OutTxt; }; sub GetCookieArray { local ($Total,$SubTotal); local($ThisFile); if (!defined($data_received{'OrderNumber'})) { opendir(ORDERS,$OrderDirectoryPath) || print &GetTextHeader(1,"Cannot open directory $OrderDirectoryPath for reading."); @RawOrders = readdir(ORDERS); close (ORDERS); foreach $RawOrder (@RawOrders) { $StartIndex = index($RawOrder,'.ord'); if ($StartIndex > 0 && $StartIndex == (length($RawOrder) - 4) ) { push (@Orders,$RawOrder); }; }; $OrderCount = @Orders; @Orders = reverse(sort(@Orders)); }; if ($data_received{'TrxType'} eq 'A') { &ListAllOrders(); }; if ($data_received{'TrxType'} eq 'F') { if ($OrderCount == 0) { print &GetTextHeader(0,''); print ''; print ""; print "

Sorry, no new orders

"; print ""; } else { &DisplayOrder($Orders[0]); }; }; if ($data_received{'TrxType'} eq 'D') { &DeleteOrder(); }; if (!defined($data_received{'TrxType'}) && defined($data_received{'TrxOrderData'})) { &AddOrder(); }; if ($data_received{'TrxType'} eq 'S') { $ThisFile = $data_received{'OrderNumber'} . '.ord'; &DisplayOrder($ThisFile); }; } sub AddOrder { local(%Temp,$OutStr); $GizFieldData = $data_received{'OrderData0'};; $GizFieldData .= $data_received{'OrderData1'};; $GizFieldData .= $data_received{'OrderData2'};; $GizFieldData .= $data_received{'OrderData3'};; $GizFieldData .= $data_received{'OrderData4'};; $GizFieldData .= $data_received{'OrderData5'};; $GizFieldData .= $data_received{'OrderData6'};; $GizFieldData .= $data_received{'OrderData7'};; $GizFieldData .= $data_received{'OrderData8'};; $GizFieldData .= $data_received{'OrderData9'};; $GizFieldData .= $data_received{'OrderData10'};; $GizFieldData .= $data_received{'OrderData11'};; $GizFieldData .= $data_received{'OrderData12'};; $GizFieldData .= $data_received{'OrderData13'};; $GizFieldData .= $data_received{'OrderData14'};; $GizFieldData .= $data_received{'OrderData15'};; $GizFieldData .= $data_received{'OrderData16'};; $GizFieldData .= $data_received{'OrderData17'};; $GizFieldData .= $data_received{'OrderData18'};; $GizFieldData .= $data_received{'OrderData19'};; $data_received{'TrxOrderData'} .= $GizFieldData; $data_received{'TrxOrderNumber'} = &LaunderValue($data_received{'TrxOrderNumber'}); $ThisFile = $data_received{'TrxOrderNumber'} . $Extension; ++$data_received{'TrxOrderNumber'} if (-e(ThisFile)); $ThisFile = $data_received{'TrxOrderNumber'} . $Extension; $ThisFile = $OrderDirectoryPath . $ThisFile; open(ORDER,"+>$ThisFile") || print &GetTextHeader(1,"Cannot open $ThisFile for writing."); print ORDER $GizFieldData; close (ORDER); $OutStr = ""; if (0) { if ($PostCallToCCProc) { # Calls to Processor requiring METHOD=POST &GetNextURL(); $OutStr .= $Ack; } else { # Faster call to processor with METHOD=GET $OutStr .= &GetNextURL(); }; } else { # No call to online processor $LocationRedirectionSupport = 0; $OutStr = &GetTextHeader(0,''); $OutStr .= 'Horizon Herbs, LLC - Thank you'."\n"; $OutStr .= "\n"; $OutStr .= &DeleteCookieText('GizField'); $OutStr .= &DeleteCookieText('GizItemOrders'); $OutStr .= '

Horizon Herbs, LLC

'."\n"; $OutStr .= "

Thank you!

\n"; $OutStr .= "

Your order has been processed
\n"; $OutStr .= "Order Number $data_received{'TrxOrderNumber'}\n"; $OutStr .= "

\n"; $OutStr .= 'Your order will be confirmed via e-mail. '."\n"; $OutStr .= "

\n"; $OutStr .= "\n"; $OutStr .= "
\n"; }; if (!$Error) { print $OutStr; } else { print "There is a problem writing the order! Inform the "; print "webmaster that the order directory does not exist, "; print "has the wrong permissions, or the Order Data Directory "; print "is not correctly set in WebGIZMO."; print "\n"; }; }; sub DisplayOrder { local($ThisFile) = @_; local($ThisCVal,$Counter,$CrumbSize,$Start); $ThisFile = $OrderDirectoryPath . $ThisFile; open(ORDER,"<$ThisFile") || print &GetTextHeader(1,"Cannot open $ThisFile for reading"); @Orders = ; $CVal = $Orders[0]; print &GetTextHeader(0,''); &ParseOrderData($CVal); print ''; print ''; print "$OrgName - Received Order"; print ''."\n"; $TemplFile = $ThisDir.'order.jst'; open (TEMPL, "<$TemplFile") || print "Could not open file $TemplFile
"; @Scripts = ; close(TEMPL); foreach $ScriptLine (@Scripts) { print $ScriptLine; }; print ''."\n"; print ''."\n"; print '

'.$OrgName.'

'."\n"; print '
'; print '
'; print ''; print ''; print 'Order '.$OrderField{'TrxOrderNumber'}.''; print '
Sent '.$OrderField{'TrxOrderDate'}; print '     Authorization: '.$CookieData{'GizAuth'} if (defined($CookieData{'GizAuth'})); print '
'; print ''; print '
'; print ""; print &GenerateShipTo(); if ($OrderField{'TrxControlData'} ne '' && $CookieData{'GizAuth'} eq '') { print "\n'."\n"; }; print &GenerateCartItems(); print "Ordered Using $OrderField{'BrowserIDField'}"; print ''; }; sub DeleteOrder { $data_received{'OrderNumber'} = &LaunderValue($data_received{'OrderNumber'}); $ThisFile = $data_received{'OrderNumber'} . '.ord'; $ThisFile = $OrderDirectoryPath . $ThisFile; $HeaderLines = &GetTextHeader(0,''); $HeaderLines .= ''; $HeaderLines .= "Order Log"; unlink($ThisFile) || print &GetTextHeader(1,"Cannot erase $ThisFile"); if (!$LocationRedirectionSupport) { print $HeaderLines; }; print &DeleteCookieText('OrderGizField'); print &DeleteCookieText('OrderGizItemOrders'); print &DeleteCookieText('OrderGizAuth'); print &DeleteCookieText('GizItemJar_0'); print &DeleteCookieText('GizItemJar_1'); print &DeleteCookieText('GizItemJar_2'); print &DeleteCookieText('GizItemJar_3'); print &DeleteCookieText('GizItemJar_4'); print &DeleteCookieText('GizFieldsJar_0'); print &DeleteCookieText('GizFieldsJar_1'); print &DeleteCookieText('GizFieldsJar_2'); print &DeleteCookieText('GizFieldsJar_3'); print &DeleteCookieText('GizFieldsJar_4'); if ($LocationRedirectionSupport) { print $HeaderLines; }; print ""; if (!$Error) { print "

Order $data_received{'OrderNumber'} deleted

\n"; print "\n"; } else { print "

"; print "There is a problem deleting the order! "; print "Either the file is already deleted, "; print "the order directory does not exist, "; print "has the wrong permissions, or the Order Data "; print "Directory is not correctly set in WebGIZMO."; print "

"; }; print ""; }; sub ListAllOrders { print &GetTextHeader(0,''); print ''; print ""; print "

Orders

"; foreach $Order (@Orders) { $StrEnd = index($Order,'.ord'); $ThisOrd = substr($Order,0,$StrEnd); if ($StrEnd != -1) { print "$ThisOrd
\n"; }; }; print ""; }; ################################################################################### # No_SSI # # This function scans user input for Server Side Includes commands, which a hacker to use to gain un- # authorized access to data. # ################################################################################## sub No_SSI { local (*data) = @_; foreach $key (sort keys(%data)) { $data{$key} =~ s///g; } } #################################################################################### # User_Data # # This fuction gets the input string from the browser, and decodes it into an associative array of fields (keys) # and values. Multiple values for a field are concatenated with a ':' # ##################################################################################### sub User_Data { local(%user_data, $user_string, $name_value_pair); local(@name_value_pairs, $name, $value); # If the data was sent via POST, then it is available # from standard input. Otherwise, the data is in the # QUERY_STRING environment variable. if ($ENV{"REQUEST_METHOD"} eq "POST") { read(STDIN,$user_string,$ENV{"CONTENT_LENGTH"}) } else { $user_string = $ENV{"QUERY_STRING"}; } # This line changes the + signs to spaces. $user_string =~ s/\+/ /g; # This line places each name/value pair as a separate # element in the name_value_pairs array. @name_value_pairs = split(/&/, $user_string); # This code loops over each element in the name_value_parirs # array, splits it on the = sign, and palces the value # into the user_data associative array with the name as the # key. foreach $name_value_pair (@name_value_pairs) { ($name, $value) = split(/=/, $name_value_pair); # These two lines decode the values from any URL # hexadecimal encoding. The first section searches for a # hexadecimal number and the second part converts the # hex number to decimal and returns the character # equivalent. $name =~ s/%([a-fA-F0-9][a-fA-F0-9])/pack("C",hex($1))/ge; $value =~ s/%([a-fA-F0-9][a-fA-F0-9])/pack("C",hex($1))/ge; # If the name/value pair has already been given a value, # as in the case of multiple items being selected, then # separate the items with a " : ". if (defined($user_data{$name})) { $user_data{$name} .= " : " . $value; } else { $user_data{$name} = $value; } } return %user_data; } sub EncodeChar { local ($InChar) = @_; local($RetChar); return $InChar if ($InChar ge 'a' && $InChar le 'z'); return $InChar if ($InChar ge 'A' && $InChar le 'Z'); return $InChar if ($InChar ge '0' && $InChar le '9'); return $InChar if ($InChar eq '.' || $InChar eq '_'); return $InChar if ($InChar eq '-' || $InChar eq ' '); ## return '+' if ($InChar eq ' '); removed only for writing cookies $Hex = sprintf("%lX", ord($InChar)); $RetChar = '%'; $RetChar .= '0' if (length($Hex) <2); $RetChar .= $Hex; return $RetChar; }; sub Encode { local($InStr) = @_; local($Ret,$j); $Ret = ""; for ($j=0;$j'."\n"; $URL .= &Encode(&DeQuote($ParmNames[$i]))."=".&Encode(&DeQuote($ParmValues[$i])); $URL .= "\&" if (($i+1) < @ParmNames); }; $URL =~ s/ /\+/g; # Change spaces to plus signs if ($LocationRedirectionSupport) { $Ret = "Location: $URL\n\n"; } else { $Ret = &GetTextHeader(0,''); $Ret.= "Processing Payment\n"; $Ret.= "\n"; $Ret.= ''."\n"; $Ret.= "

Processing Your Order

\n"; $Ret.= "If you're stuck, click here to continue.\n"; $Ret.= "

\n"; }; # # Create acknowlegement screeen $Ack = &GetTextHeader(0,''); $Ack .= "\n"; $Ack .= "\n\n"; $Ack .= ''; $Ack .= "

$OrgName

\n"; $Ack .= '

About to process your order of '.$DispTotal.'

'."\n"; $Ack .= "
\n"; $Ack .= $Form; $Ack .= ''."\n"; $Ack .= ''."\n"; return $Ret; }; sub LaunderValue { local($InVal) = @_; return "" if (!defined($InVal)); return "" if ($InVal eq ""); if ($InVal =~ /^([-\@\w.]+)$/) { $InVal = $1; return $InVal; } else { &GetTextHeader(1,"Value $InVal is tainted and suspect!"); die ("Tainted value $Inval is suspect!"); }; }; sub DeQuote { local($InStr) = @_; local($OutStr); $Char=0; $OutStr = ""; for ($Char=0;$Char"; $OutStr .= "

"; $OutStr .= "" if ($i == ($FieldCount-1) && ($i+1)%2); $OutStr .= "" if ($i%2 || $i == ($FieldCount-1)); }; if ($OrderField{'DeliveryNotes'} ne '') { $OutStr .= ""; $OutStr .= ""; }; $OutStr .= '
"; $IsEmail = $IsURL = 0; $IsEmail = ($DisplayFieldValue[$i] =~ m/@/g); $IsURL = (substr($DisplayFieldValue[$i],0,7) eq "http://"); $IsEmail=$IsURL=0 if ($DisplayFieldValue[$i] =~ m/\s/g); $OutStr .= "" if ($IsURL); $OutStr .= "" if ($IsEmail); $OutStr .= $DisplayFieldValue[$i]; $OutStr .= "" if ($IsEmail || $IsURL); $OutStr .= "
Notes:$OrderField{'DeliveryNotes'}

'; return $OutStr; }; sub ExtractLastNumber { local($TextInput) = @_; $CharIndex = length($TextInput); $ThisChar; $NumFound = 0; $Numeric; $OutStr = ''; while ($CharIndex > 0) { $ThisChar = substr($TextInput,--$CharIndex,1); $Numeric = 0; if ($ThisChar =~ m/\d/) { $NumFound = 1; $Numeric = 1; }; if ($Numeric || ($NumFound && $ThisChar eq '.')) { $OutStr = $ThisChar . $OutStr; } else { $CharIndex=-1 if ($NumFound && $ThisChar ne ','); }; }; return $OutStr; }; sub GenerateCartItems { $SubTotal = 0; $OrderText = ''; $TotalShipping = 0; $ShippingApplies = 0; $OutStr = ''; $OutStr .= ''; $OutStr .= ''; $OutStr .= ''; $OutStr .= '
TaxShippingTotal
'; $OutStr .= "($OrderField{'TaxDetailField'}) " if ($OrderField{'TaxDetailField'}ne''); $OutStr .= $OrderField{'TrxTaxAmount'}; $OutStr .= ''; $OutStr .= "($OrderField{'ShipField'}) " if ($OrderField{'ShipField'}ne''); $OutStr .= $OrderField{'TrxShipAmount'}; $OutStr .= "$OrderField{'TrxTotalAmount'}
"; $NumItems = @OrderItem; $OutStr .= '
'; $OutStr .= ''; $OutStr .= ''; $OutStr .= ''."\n"; for ($Count=0;$Count<$NumItems;$Count++) { $PreAndNameString = ''; $PostNameString = ''; if ($OrderItem[$Count]{'Quantity'} != 0) { $PreAndNameString = '\n"; }; }; $OutStr .= '
ItemPriceQtyAmount
'; $PreAndNameString .= ''; if ($OrderItem[$Count]{'ItemID'} ne '') { $PreAndNameString .= '['.$OrderItem[$Count]{'ItemID'}.'] '; }; $PreAndNameString .= $OrderItem[$Count]{'Name'}; $PreAndNameString .= ''; $PostNameString = ""; if ($OrderItem[$Count]{'Options'} > 0) { $PostNameString = '
    '; for ($OptionCount=0; $OptionCount<$OrderItem[$Count]{'Options'};$OptionCount++) { $PostNameString .= '
  • '; $PostNameString .= $OrderItem[$Count]{'Option'}[$OptionCount]; $PostNameString .= '
  • '; }; $PostNameString .= '
'; }; $OutStr .= $PreAndNameString; $OutStr .= $PostNameString; $OutStr .= '
'; $OutStr .= $CurrencySymbol . sprintf ("%1.2f",$OrderItem[$Count]{'Price'}); $OutStr .= ''; $OutStr .= $OrderItem[$Count]{'Quantity'}; $OutStr .= ''; $Extended= $OrderItem[$Count]{'Quantity'} * $OrderItem[$Count]{'Price'}; $OutStr .= $CurrencySymbol . sprintf ("%1.2f",$Extended); $OutStr .= ''; if (($OrderItem[$Count]{'TaxCode'} < 1) || ($OrderField{'TaxDetailField'} eq '')) { $OutStr .= " " ; } else { $OutStr .= "(Tx)" if ($OrderItem[$Count]{'TaxCode'} == 1); $OutStr .= "(Use Tax)" if ($OrderItem[$Count]{'TaxCode'} == 2); }; $OutStr .= "
'; return $OutStr; };