home *** CD-ROM | disk | FTP | other *** search
Text File | 1996-02-09 | 31.9 KB | 1,192 lines |
- #DEFINE CRLF CHR(13)+CHR(10)
-
- LOCAL lcProgram,lcFullPath,lnAtPos,lcFoxTools,lcError,lcFileName
- LOCAL lcScreenIcon,lcScreenCaption,lcSetPath,lnSelect
- PRIVATE gcINIFile,gcHTTPRoot,gcScriptRoot,gcSemaphoreRoot,gcPath
-
-
- SET TALK OFF
- SET ESCAPE OFF
- SET COLLATE TO 'MACHINE'
- SET COMPATIBLE OFF
- SET CONFIRM ON
- SET DECIMALS TO 9
- SET EXACT OFF
- SET EXCLUSIVE OFF
- SET MEMOWIDTH TO 1024
- SET MULTILOCKS ON
- SET POINT TO '.'
- SET SAFETY OFF
- SET UDFPARMS TO VALUE
- SET MESSAGE TO ' '
- lcProgram=SYS(16)
- lnAtPos=RAT('\',lcProgram)
- lcFullPath=LEFT(lcProgram,lnAtPos)
- CD (lcFullPath)
- lcFoxTools='foxtools.fll'
- IF NOT FILE(lcFoxTools)
- lcFoxTools=HOME()+lcFoxTools
- ENDIF
- IF NOT FILE(lcFoxTools)
- =MESSAGEBOX('Missing FOXTOOLS.FLL',16,_screen.Caption)
- RETURN .F.
- ENDIF
- ON ERROR
- ERASE ERROR.txt
- SET LIBRARY TO (lcFoxTools) ADDITIVE
-
- lnSelect=SELECT()
- lcSetPath=SET('PATH')
- lcOnError=ON('ERROR')
- lcScreenIcon=_screen.Icon
- _screen.Icon='net13.ico'
- lcScreenCaption=_screen.Caption
- _screen.Caption='WWW Data Server'
-
- gcINIFile="vfpis.ini"
- gcHTTPRoot=""
- gcScriptRoot=""
- gcSemaphoreRoot=FULLPATH('\temp\')
- ON ERROR =.F.
- MD (gcSemaphoreRoot)
- ON ERROR
- gcPath=""
-
- ON ERROR DO ErrorHandler WITH ERROR(),MESSAGE(),PROGRAM(),LINENO(),MESSAGE(1)
-
- *Read the initialization file and set up root paths. If the
- *INI file doesn't exist or is empty, ask the user to set one up.
-
- IF FILE(gcINIFile)
- =readini(gcINIFile)
- ENDIF
- IF EMPTY(gcHTTPRoot)
- DO FORM SpecRoot
- ENDIF
- IF EMPTY(gcScriptRoot)
- gcScriptRoot=gcHTTPRoot
- ENDIF
- SET PATH TO (gcPath)
- CLOSE ALL DATABASES
- CLOSE ALL
- lcFileName=LOWER(FULLPATH('querylog.dbf',lcProgram))
- IF NOT FILE(lcFileName)
- CREATE TABLE (lcFileName) (TimeStamp T, IDCFile C(32), Parameters M)
- USE
- ENDIF
- USE (lcFileName) ALIAS QueryLog EXCLUSIVE
-
- DO FORM server
- CLOSE ALL DATABASES
- CLOSE ALL
- SELECT (lnSelect)
- IF NOT EMPTY(lcScreenCaption)
- _screen.Caption=lcScreenCaption
- ENDIF
- IF NOT EMPTY(lcScreenIcon)
- _screen.Icon=lcScreenIcon
- ENDIF
- SET MESSAGE TO
- SET PATH TO (lcSetPath)
- IF EMPTY(lcError)
- ON ERROR
- ELSE
- ON ERROR &lcError
- ENDIF
-
- RETURN
-
-
-
- FUNCTION executeprocess(tcFileName)
- LOCAL lcDataFile,lcAckFile,lnDFH,lnAFH,lcParameter
-
- lcDataFile=gcSemaphoreRoot+JustStem(ALLTRIM(tcFileName))+".dat"
- lcAckFile=gcSemaphoreRoot+JustStem(ALLTRIM(tcFileName))+".ack"
- lnDFH=FOPEN(lcDataFile)
- lcParameter=""
- IF lnDFH > 0
- DO WHILE NOT FEOF(lnDFH)
- lcParameter=lcParameter+FREAD(lnDFH,1000)
- ENDDO
- =FCLOSE(lnDFH)
- ERASE (lcDataFile)
- lcResultPage=GenPage(lcParameter)
- lnDFH=FCREATE(lcDataFile)
- =FWRITE(lnDFH,lcResultPage)
- =FCLOSE(lnDFH)
- lnAFH=FCREATE(lcAckFile)
- * Create Acknowledgement file
- =FCLOSE(lnAFH)
- ELSE
- * Error opening data file
- ENDIF
- ENDFUNC
-
-
- * HTML Page Generation Program
- * This program takes a SQL Query, and several other parameters and
- * generates an output document in HTML which can be used by a WWW
- * Browser.
- * This function goes for bulletproof simple error handling when it is interpreting
- * an .HTX file. If it runs into a logical error, it will simply attempt to continue.
- ****************
- FUNCTION genpage(cParameters)
-
- LOCAL lnAtPos,lcFileName,lcAlias
- LOCAL lFailure, cResultPage, lcError, lnSelect
- LOCAL cSQLStatement, cKeyColumn, cDescriptColumn, ;
- cBackgroundImg, iCount, cTmpString, cPrevNext, ;
- IDCFile, lcTemplate, lcLine, lcTmpLine, ;
- lcLineCopy, lFailure, cExecSQLString, lhTemplate, llDone, ;
- llGetNewLine, lcTmpExp, lcExp1, lcExp2, lcOperator, lcIfStatement, ;
- lcTrueStatement, lcFalseStatement, lcHTMLPath, lcIDCFile, ;
- lcDefErr, llDefaultError, lcReturnData, llReturnData
-
- *These symbols, we want available in the sub programs. They will all be available,
- *along with all of the parsed in environment variables, to the functions that execute
- *conditionals and detail lines. This allows those functions to simply utilize their
- *environment.
-
- PRIVATE laEnvVariables, lnEnvVariables, IDC_DataSource, IDC_Template, ;
- IDC_SQLStatement, IDC_DefaultParameters, IDC_Expires, IDC_MaxFieldSize, ;
- IDC_Password, IDC_RequiredParameters, IDC_Username, laDefaultParameters, ;
- laRequiredParameters, CurrentRecord, laTables, CommandSuccess, ;
- lnRecordsReturned, IDC_MaxRecords
-
- CommandSuccess="FALSE"
- lcAlias=''
-
- *Parse out all of the environment variables and HTML variables that are
- *sent to us via the CGI script (contained in cParameters) and place them
- *in an array for ease of reference. The variables are placed in an array
- *as VARIABLE_NAME, VALUE pairs.
- lnEnvVariables=0
- DIMENSION laEnvVariables[1,2]
-
- IF LEFT(cParameters,1)=='&'
- cParameters=ALLTRIM(SUBSTR(cParameters,2))
- ENDIF
-
- lnEnvVariables=ParseVars(cParameters,@laEnvVariables,.T.)
-
- *Parse out the contents of QUERY_STRING if it is not empty.
- IF NOT EMPTY(getparam("QUERY_STRING"))
- lnEnvVariables=ParseVars(getparam("QUERY_STRING"),@laEnvVariables)
- ENDIF
-
- *Find out if the user has turned off default error processing for the
- *executable command.
- lcDefErr=getparam("DefError")
- IF UPPER(ALLT(lcDefErr))=="OFF"
- llDefaultError=.F.
- ELSE
- llDefaultError=.T.
- ENDIF
-
- *Find out if the user would like the data back as a block of data.
- lcReturnData=getparam("ReturnAsFile")
- IF UPPER(ALLT(lcReturnData))=="ON"
- llReturnData=.T.
- ELSE
- llReturnData=.F.
- ENDIF
-
- *Build an absolute path representing where the calling HTML page was located.
- lcHTMLPath=BldPath()
-
- *Get pointer to .IDC file via passed in HTML parameter
- IDCFile=getparam("IDCFile")
-
- lcIDCFile=getparam("IDCFile")
- IF NOT EMPTY(IDCFile)
- IDCFile=LOWER(FULLPATH(lcIDCFile))
- IF NOT FILE(IDCFile)
- IDCFile=LOWER(FULLPATH(gcScriptRoot+lcIDCFile))
- IF NOT FILE(IDCFile)
- IDCFile=LOWER(FULLPATH(lcHTMLPath+lcIDCFile))
- IF NOT FILE(IDCFile)
- IDCFile=LOWER(FULLPATH(gcHTTPRoot+lcIDCFile))
- ENDIF
- ENDIF
- ENDIF
- IDCFile=LOWER(FULLPATH(IDCFile))
- ENDIF
-
- *Append query log
- lnSelect=SELECT()
- SELECT QueryLog
- IF RECCOUNT()>=1000
- ZAP
- ENDIF
- INSERT INTO QueryLog (TimeStamp, IDCFile, Parameters) ;
- VALUES (DATETIME(), lcIDCFile, cParameters)
- SELECT 0
-
- IF EMPTY(IDCFile)
- =Cleanup()
- RETURN errorpage("No .IDC file was specified. The server cannot continue.")
- ENDIF
- IF NOT FILE(IDCFile)
- =Cleanup()
- RETURN errorpage("Specified .IDC file ("+lcIDCFile+") not found. The server cannot continue.")
- ENDIF
-
- *Verify required IDC information
- IDC_DataSource=parmsub(getidcp(IDCFile,"DataSource"))
- IDC_Template=parmsub(getidcp(IDCFile,"Template"))
- IF EMPTY(IDC_Template)
- =Cleanup()
- RETURN errorpage("Specified .IDC file ("+IDCFile+ ;
- ") does not contain correct data or cannot be accessed."+ ;
- " The template entry could not be located. The server cannot continue.")
- ENDIF
- IDC_SQLStatement=parmsub(getidcp(IDCFile,"SQLStatement"))
- IF EMPTY(IDC_SQLStatement)
- =Cleanup()
- RETURN errorpage("Specified .IDC file ("+IDCFile+ ;
- ") does not contain correct data or cannot be accessed."+ ;
- " The SQL statement entry could not be located. The server cannot continue.")
- ENDIF
- DIMENSION laDefaultParameters(1,2)
- IDC_DefaultParameters=getidcp(IDCFile,"DefaultParameters",@laDefaultParameters)
- IDC_MaxRecords=VAL(parmsub(getidcp(IDCFile,"MaxRecords")))
- IDC_UserName=parmsub(getidcp(IDCFile,"UserName"))
- IDC_Password=parmsub(getidcp(IDCFile,"Password"))
- IDC_Expires=parmsub(getidcp(IDCFile,"Expires"))
- IDC_MaxFieldSize=parmsub(getidcp(IDCFile,"MaxFieldSize"))
- DIMENSION laRequiredParameters(1,2)
- IDC_RequiredParameters=getidcp(IDCFile,"RequiredParameters",@laRequiredParameters)
- lcSQLStatement=IDC_SQLStatement
- lcTemplate=IDC_Template
-
- *Save server settings
- lcError = ON('ERROR')
-
- *Initialize result page
- cResultPage = 'Content-Type: text/html'+CRLF+CRLF
-
- lFailure = .F.
-
- *Check to see whether we will be accessing an ODBC datasource or native data
- IF EMPTY(IDC_DataSource)
- *NATIVE DATA
- cExecSQLString=lcSQLStatement
- IF EMPTY(cExecSQLString)
- =Cleanup()
- RETURN errorpage("The SQL statement supplied by the IDC file could not be understood. The server cannot continue.")
- ENDIF
-
- *Execute SQL String and trap for a failure
- _TALLY=0
- lFailure = .F.
- cSQLStatement=cExecSQLString
- *Convert string to UPPERCASE, TRIM, and remove TABs for easy
- *syntax checking.
- cExecSQLString=UPPER(ALLTRIM(STRTRAN(cExecSQLString,CHR(9),' ')))
- *Special case the general SELECT statement without an INTO (the default
- *for Wizard generated stuff.)
- IF cExecSQLString="SELECT " AND ATC(" INTO ",cExecSQLString)=0
- * cExecSQLString needs to carry through the case sensitivity of the
- * original SQL SELECT
- cExecSQLString = cSQLStatement + " INTO CURSOR TempResult"
- ELSE
- IF cExecSQLString="SELECT " OR;
- cExecSQLString="DELETE " OR;
- cExecSQLString="INSERT " OR;
- cExecSQLString="UPDATE " OR;
- cExecSQLString="ALTER TABLE " OR;
- cExecSQLString="CREATE CURSOR " OR;
- cExecSQLString="CREATE TABLE "
- * cExecSQLString needs to carry through the case sensitivity of the
- * original SQL SELECT
- cExecSQLString = cSQLStatement
- ELSE
- lFailure = .T.
- ENDIF
- ENDIF
- * At this point, if there has been some error evaluating the SQL statement,
- * or if the SQL statement is not one of the above valid types, the lFailure
- * flag is set, and the SQL statement will not be executed.
- IF NOT lFailure
- lnAtPos=ATC(' FROM ',cExecSQLString)
- IF lnAtPos>0
- lcAlias=ALLTRIM(SUBSTR(cExecSQLString,lnAtPos+6))
- lnAtPos=AT(' ',lcAlias)
- IF lnAtPos>0
- lcAlias=ALLTRIM(LEFT(lcAlias,lnAtPos-1))
- ENDIF
- IF LEFT(lcAlias,1)=="'" OR LEFT(lcAlias,1)=='"' OR ;
- LEFT(lcAlias,1)=='['
- lcAlias=EVALUATE(lcAlias)
- ENDIF
- lcAlias=UPPER(lcAlias)
- lcFileName=LOWER(lcAlias)
- lnAtPos=AT('.',lcAlias)
- IF lnAtPos>0
- lcAlias=ALLTRIM(LEFT(lcAlias,lnAtPos-1))
- ENDIF
- IF NOT '.'$lcFileName
- lcFileName=lcFileName+'.dbf'
- ENDIF
- lcFileName=LOWER(lcFileName)
- IF NOT FILE(lcFileName)
- =Cleanup()
- RETURN errorpage('The SQL statement FROM table ['+lcFileName+'] not found.<BR>'+ ;
- 'Table specified must be in PATH of data server specified in VFPIS.INI.<BR>'+CRLF+ ;
- 'SQL String: <HR>'+cSQLStatement)
- ENDIF
- ENDIF
- ON ERROR lFailure = .T.
- &cExecSQLString
- ON ERROR &lcError
- IF USED(lcAlias)
- USE IN (lcAlias)
- ENDIF
- ENDIF
-
-
- IF lFailure = .T.
- IF llDefaultError
- =Cleanup()
- RETURN errorpage('The command generated an error.<BR>'+ ;
- 'Please Contact the system administrator.<BR>'+CRLF+ ;
- 'SQL String: <HR>'+cSQLStatement)
- ELSE
- CommandSuccess="FALSE"
- ENDIF
- ELSE
- CommandSuccess="TRUE"
- ENDIF
-
- lnRecordsReturned=_TALLY
- IF lnRecordsReturned = 0
- CurrentRecord=0
- ELSE
- CurrentRecord=1
- IF llReturnData
- RETURN makedata()
- ENDIF
- ENDIF
-
- ELSE
- cExecSQLString=lcSQLStatement
- IF EMPTY(cExecSQLString)
- =Cleanup()
- RETURN errorpage("The SQL statement supplied by the IDC file could not be understood. The server cannot continue.")
- ENDIF
-
- lnConn=SQLCONNECT(IDC_DataSource,IDC_Username,IDC_Password)
- IF lnConn <= 0
- =Cleanup()
- RETURN errorpage("The connection to "+IDC_DataSource+" as "+IDC_Username+" could not be made. The server cannot continue.")
- ENDIF
-
- *Execute SQL String and trap for a failure
- cSQLStatement=cExecSQLString
-
- lnExecRet=0
- DO WHILE lnExecRet=0
- lnExecRet = SQLEXEC(lnConn,cSQLStatement,'TempResult')
- ENDDO
-
- IF lnExecRet < 0
- lFailure = .T.
- ENDIF
-
- =SQLDISCONNECT(lnConn)
-
- IF lFailure = .T.
- IF llDefaultError
- =Cleanup()
- RETURN errorpage('The command generated an error.<BR>'+ ;
- 'Please Contact the system administrator.<BR>'+CRLF+ ;
- 'SQL String: <HR>'+cSQLStatement)
- ELSE
- CommandSuccess="FALSE"
- ENDIF
- ELSE
- CommandSuccess="TRUE"
- ENDIF
-
- lnRecordsReturned=RECCOUNT('TempResult')
- IF lnRecordsReturned = 0
- CurrentRecord=0
- ELSE
- CurrentRecord=1
- IF llReturnData
- =Cleanup()
- RETURN makedata()
- ENDIF
- ENDIF
-
- ENDIF
-
- *Create HTML return page from .HTX and data
-
- *Verify the existence of the Template (.HTX) file. It must be next to the .IDC file,
- *pathed relative to the .IDC file, or in the Script root.
- lcTmpFile=lcTemplate
- lcTemplate=addbs(justpath(IDCFile))+lcTemplate
- IF NOT FILE(lcTemplate)
- lcTemplate=gcScriptRoot+lcTmpFile
- IF NOT FILE(lcTemplate)
- =Cleanup()
- RETURN errorpage('The template file could not be located. The server cannot continue.')
- ENDIF
- ENDIF
-
- lhTemplate=FOPEN(lcTemplate)
- IF lhTemplate < 0
- =Cleanup()
- RETURN errorpage('The template file ('+lcTemplate+') could not be opened successfully. The server cannot continue.')
- ENDIF
-
- llGetNewLine=.T.
-
- DO WHILE NOT FEOF(lhTemplate)
- IF llGetNewLine
- lcLine=FGETS(lhTemplate)
- ELSE
- *Toggle GetNewLine back to True
- llGetNewLine=.T.
- ENDIF
- lcLineCopy=UPPER(lcLine)
- DO CASE
- *The BeginDetail structure is linear, but must be repeated for
- *each record in the return set. IFs can be nested within a Detail
- *section, so, once the detail section is loaded, it must be parsed
- *for IFs. However
- CASE "<%BEGINDETAIL%>" $ lcLineCopy
- *If the BEGINDETAIL is not at the beginning of the line, put the
- *prefix into the Result page. Then work on the detail chunk.
- IF lcLineCopy != "<%BEGINDETAIL%>"
- cResultPage=cResultPage+SUBSTR(lcLine,1,AT("<%BEGINDETAIL%>",lcLineCopy)-1)
- lcLine=SUBSTR(lcLine,AT("<%BEGINDETAIL%>",lcLineCopy)+15)+CRLF
- ELSE
- *If there's stuff after the BEGINDETAIL symbol, stuff it into the lcLine
- IF LEN(lcLine)>LEN("<%BEGINDETAIL%>")
- lcLine=SUBSTR(lcLine,16)
- ELSE
- lcLine=""
- ENDIF
- ENDIF
- llDone=.F.
- IF NOT EMPTY(lcLine)
- IF "<%ENDDETAIL%>" $ UPPER(lcLine)
- lcTmpLine=lcLine
- IF UPPER(lcTmpLine)!="<%ENDDETAIL%>"
- lcLine=SUBSTR(lcTmpLine,1,AT("<%ENDDETAIL%>",UPPER(lcTmpLine))-1)
- ENDIF
- IF LEN(lcTmpLine)>LEN("<%ENDDETAIL%>")
- lcSuffix=SUBSTR(lcTmpLine,AT("<%ENDDETAIL%>",UPPER(lcTmpLine))+13)
- ELSE
- lcSuffix=""
- ENDIF
- llDone=.T.
- ENDIF
- ENDIF
- DO WHILE NOT llDone AND NOT FEOF(lhTemplate)
- lcTmpLine=FGETS(lhTemplate)
- IF NOT("<%ENDDETAIL%>" $ UPPER(lcTmpLine))
- *Add to the block until you hit an ENDDETAIL
- lcLine=lcLine+lcTmpLine+CRLF
- ELSE
- *Add everything up to the beginning of the ENDDETAIL and store everything
- *afterward in lcSuffix for processing later.
- IF UPPER(lcTmpLine)!="<%ENDDETAIL%>"
- lcLine=lcLine+SUBSTR(lcTmpLine,1,AT("<%ENDDETAIL%>",UPPER(lcTmpLine))-1)
- ENDIF
- IF LEN(lcTmpLine)>LEN("<%ENDDETAIL%>")
- lcSuffix=SUBSTR(lcTmpLine,AT("<%ENDDETAIL%>",UPPER(lcTmpLine))+13)
- ELSE
- lcSuffix=""
- ENDIF
- llDone=.T.
- ENDIF
- ENDDO
- IF NOT llDone
- *Error: Mismatched Begin/EndDetail, close template file and exit
- =FCLOSE(lhTemplate)
- =Cleanup()
- RETURN errorpage("The template file ("+lcTemplate+") contained a mismatched BeginDetail/EndDetail structure. The server cannot continue.")
- ENDIF
- IF lnRecordsReturned > 0
- lcDetailExec=''
- DO WHILE AT("<%",lcLine) > 0
- lcDetailExec=lcDetailExec+'"'+STRTRAN(SUBSTR(lcLine,1,AT("<%",lcLine)-1),'"','"+["]+"')+'"+'
- lcLine=SUBSTR(lcLine,AT("<%",lcLine))
- IF UPPER(lcLine)="<%IF "
- *Process the IF structure into an IIF
- *Trim the IF and ENDIF symbols.
- lcIfStatement=SUBSTR(lcLine,6,AT("<%ENDIF%>",UPPER(lcLine))-6)
- *Strip out Expression 1, Expression 2, and the Operator
- lcExp1=ALLT(SUBSTR(lcIfStatement,1,AT(" ",lcIfStatement)-1))
- lcIfStatement=ALLT(SUBSTR(lcIfStatement,AT(" ",lcIfStatement)))
- lcOperator=ALLT(SUBSTR(lcIfStatement,1,AT(" ",lcIfStatement)-1))
- lcIfStatement=ALLT(SUBSTR(lcIfStatement,AT(" ",lcIfStatement)))
- lcExp2=ALLT(SUBSTR(lcIfStatement,1,AT("%>",lcIfStatement)-1))
- lcIfStatement=SUBSTR(lcIfStatement,AT("%>",lcIfStatement)+2)
- IF NOT('"'$lcExp1 OR "'"$lcExp1 OR '['$lcExp1)
- lcExp1=UPPER(lcExp1)
- lcExp1=STRTRAN(lcExp1,"IDC.","IDC_")
- ENDIF
- IF NOT('"'$lcExp2 OR "'"$lcExp2 OR '['$lcExp2)
- lcExp2=UPPER(lcExp2)
- lcExp2=STRTRAN(lcExp2,"IDC.","IDC_")
- ENDIF
- lcOperator=UPPER(lcOperator)
- DO CASE
- CASE lcOperator="CONTAINS"
- lcTmpExp=lcExp2
- lcExp2=lcExp1
- lcExp1=lcTmpExp
- lcOperator="$"
- CASE lcOperator="EQ"
- lcOperator="="
- CASE lcOperator="GT"
- lcOperator=">"
- CASE lcOperator="LT"
- lcOperator="<"
- ENDCASE
- IF "<%ELSE%>"$UPPER(lcIfStatement)
- lcTrueStatement=SUBSTR(lcIfStatement,1,AT("<%ELSE%>",UPPER(lcIfStatement))-1)
- lcIfStatement=SUBSTR(lcIfStatement,AT("<%ELSE%>",UPPER(lcIfStatement))+8)
- lcFalseStatement=lcIfStatement
- lcFalseStatement=STRTRAN(lcFalseStatement,'"','"+["]+"')
- ELSE
- lcTrueStatement=lcIfStatement
- lcFalseStatement=""
- ENDIF
- lcTrueStatement=STRTRAN(lcTrueStatement,'"','"+["]+"')
- lcIIF='IIF('+lcExp1+lcOperator+lcExp2+',"'+lcTrueStatement+'","'+lcFalseStatement+'")+'
- lcDetailExec=lcDetailExec+lcIIF
- IF LEN(lcLine)>AT("<%ENDIF%>",UPPER(lcLine))+9
- lcLine=SUBSTR(lcLine,AT("<%ENDIF%>",UPPER(lcLine))+9)
- ELSE
- lcLine=""
- ENDIF
- ELSE
- *This is a symbol structure. If it is valid, extract the symbol and place it into
- *the executable line.
- IF AT("%>",lcLine)=0
- =FCLOSE(lhTemplate)
- =Cleanup()
- RETURN errorpage("The detail line in "+lcTemplate+" contains a mismatched symbol structure. The server cannot continue.")
- ENDIF
- lcSymbol=SUBSTR(lcLine,3,AT("%>",lcLine)-3)
- lcDetailExec=lcDetailExec+'EXPTOC('+ALLT(lcSymbol)+')+'
- IF LEN(lcLine)>LEN(lcSymbol)+4
- lcLine=SUBSTR(lcLine,AT("%>",lcLine)+2)
- ELSE
- lcLine=""
- ENDIF
- ENDIF
- ENDDO
- lcDetailExec=lcDetailExec+'"'+STRTRAN(lcLine,'"','"+["]+"')+'"'
- =DetailEx(lcDetailExec,@laEnvVariables,@cResultPage)
- ENDIF
- *If the suffix has stuff to process, then don't get a new file line, start with the suffix.
- IF NOT EMPTY(lcSuffix)
- llGetNewLine=.F.
- lcLine=lcSuffix
- ENDIF
- CASE "<%IF" $ lcLineCopy
- IF lcLineCopy != "<%IF "
- cResultPage=cResultPage+SUBSTR(lcLine,1,AT("<%IF ",lcLineCopy)-1)
- lcLine=SUBSTR(lcLine,AT("<%IF ",lcLineCopy)+5)+CRLF
- ELSE
- IF LEN(lcLine)>LEN("<%IF ")
- lcLine=SUBSTR(lcLine,5)
- ELSE
- =FCLOSE(lhTemplate)
- =Cleanup()
- RETURN errorpage("The template file contained an improperly formed IF construct. The server cannot continue.")
- ENDIF
- ENDIF
- llDone=.F.
- DO WHILE NOT llDone AND NOT FEOF(lhTemplate)
- lcTmpLine=FGETS(lhTemplate)
- IF NOT("<%ENDIF%>" $ UPPER(lcTmpLine))
- lcLine=lcLine+lcTmpLine+CRLF
- ELSE
- *Add everything up to the beginning of the ENDIF and store everything
- *afterward in lcSuffix for processing later.
- IF UPPER(lcTmpLine)!="<%ENDIF%>"
- lcLine=lcLine+SUBSTR(lcTmpLine,1,AT("<%ENDIF%>",UPPER(lcTmpLine))-1)
- ENDIF
- IF LEN(lcTmpLine)>LEN("<%ENDIF%>")
- lcSuffix=SUBSTR(lcTmpLine,AT("<%ENDIF%>",UPPER(lcTmpLine))+9)
- ELSE
- lcSuffix=""
- ENDIF
- llDone=.T.
- ENDIF
- ENDDO
- IF NOT llDone
- *Error: Mismatched If/Endif, close template file and exit
- =FCLOSE(lhTemplate)
- =Cleanup()
- RETURN errorpage("The template file ("+lcTemplate+") contained a mismatched If/EndIf structure. The server cannot continue.")
- ENDIF
- *At this point, the entire structure between the <%IF and the <%ENDIF%> non inclusive is
- *in lcLine. This will include the conditional parameters and an <%ELSE%> if such a thing exists.
- *In addition, everything after the structure will be contained in lcSuffix.
- lcIfStatement=LTRIM(lcLine)
- *Strip out Expression 1, Expression 2, and the Operator
- lcExp1=ALLT(SUBSTR(lcIfStatement,1,AT(" ",lcIfStatement)-1))
- lcIfStatement=ALLT(SUBSTR(lcIfStatement,AT(" ",lcIfStatement)))
- lcOperator=ALLT(SUBSTR(lcIfStatement,1,AT(" ",lcIfStatement)-1))
- lcIfStatement=ALLT(SUBSTR(lcIfStatement,AT(" ",lcIfStatement)))
- lcExp2=ALLT(SUBSTR(lcIfStatement,1,AT("%>",lcIfStatement)-1))
- lcIfStatement=SUBSTR(lcIfStatement,AT("%>",lcIfStatement)+2)
- *If the expressions aren't character literals, make them uppercase
- *for case insensitivity. Also check to see if they reference IDC.
- *variables at this point.
- IF NOT('"'$lcExp1 OR "'"$lcExp1 OR '['$lcExp1)
- lcExp1=UPPER(lcExp1)
- lcExp1=STRTRAN(lcExp1,"IDC.","IDC_")
- ENDIF
- IF NOT('"'$lcExp2 OR "'"$lcExp2 OR '['$lcExp2)
- lcExp2=UPPER(lcExp2)
- lcExp2=STRTRAN(lcExp2,"IDC.","IDC_")
- ENDIF
- lcOperator=UPPER(lcOperator)
- DO CASE
- CASE lcOperator="CONTAINS"
- lcTmpExp=lcExp2
- lcExp2=lcExp1
- lcExp1=lcTmpExp
- lcOperator="$"
- CASE lcOperator="EQ"
- lcOperator="="
- CASE lcOperator="GT"
- lcOperator=">"
- CASE lcOperator="LT"
- lcOperator="<"
- ENDCASE
- IF "<%ELSE%>"$UPPER(lcIfStatement)
- lcTrueStatement=SUBSTR(lcIfStatement,1,AT("<%ELSE%>",UPPER(lcIfStatement))-1)
- lcIfStatement=SUBSTR(lcIfStatement,AT("<%ELSE%>",UPPER(lcIfStatement))+8)
- lcFalseStatement=lcIfStatement
- ELSE
- lcTrueStatement=lcIfStatement
- lcFalseStatement=""
- ENDIF
- IF EvalCond(lcExp1+lcOperator+lcExp2,@laEnvVariables)
- lcLine=lcTrueStatement+lcSuffix
- ELSE
- lcLine=lcFalseStatement+lcSuffix
- ENDIF
- IF NOT EMPTY(lcLine)
- llGetNewLine=.F.
- ENDIF
- OTHERWISE
- cResultPage=cResultPage+lcLine+CRLF
- ENDCASE
- ENDDO
- IF lnRecordsReturned=0
- cResultPage=cResultPage+'No matches found.'+CRLF
- ENDIF
-
- *Append query log
- lnSelect=SELECT()
- SELECT QueryLog
- INSERT INTO QueryLog (TimeStamp, IDCFile, Parameters) ;
- VALUES (DATETIME(), lcIDCFile, 'Returned')
- SELECT 0
-
- =FCLOSE(lhTemplate)
-
- =Cleanup()
- RETURN cResultPage
-
- PROCEDURE Cleanup()
- LOCAL lnCount
-
- IF USED('TempResult')
- USE IN TempResult
- ENDIF
-
- PROCEDURE errorpage (lcErrorMessage)
- LOCAL cResultPage
- cResultPage = 'Content-Type: text/html'+CRLF+CRLF
-
- cResultPage = cResultPage + ;
- '<html><head><title>FoxPro Search Failed</title></head>'+ ;
- CRLF
- cResultPage = cResultPage + ;
- '<body>'+CRLF
- cResultPage = cResultPage + ;
- '<h1>FoxPro Search Failed</h1>'+CRLF
-
- cResultPage = cResultPage + ;
- ' '+ALLT(lcErrorMessage)+'<hr></body></html>'+CRLF
-
- RETURN cResultPage
-
- FUNCTION FormFld(FldValue)
- FldValue=STRTRAN(FldValue,CRLF,"<BR>")
- IF RIGHT(FldValue,4)="<BR>"
- FldValue=SUBSTR(FldValue,1,LEN(FldValue)-4)
- ENDIF
- RETURN FldValue
-
- FUNCTION Findmkl(cKeyColumn)
- PRIVATE Curlen, MAXLEN
- Curlen=0
- MAXLENGTH=0
-
- SCAN
- Curlen=LEN(ALLT(EVAL(cKeyColumn)))
- IF Curlen > MAXLEN
- MAXLENGTH=Curlen
- ENDIF
- ENDSCAN
- GO TOP
-
- RETURN MAXLEN
-
- FUNCTION MakeData
- LOCAL cResultPage,cFileName,nFH,nFSize
- cResultPage="<Content-type:text/plain>"+CRLF
- cFileName=SYS(3)+'.TXT'
- SELECT TempResult
- IF IDC_MaxRecords > 0
- LIST NEXT IDC_MaxRecords TO FILE (cFileName) NOCONSOLE
- ELSE
- LIST TO FILE (cFileName) NOCONSOLE
- ENDIF
- nFH=FOPEN(cFileName)
-
- IF nFH > 0
- nFSize=FSEEK(nFH,0,2)
- =FSEEK(nFH,0,0)
- cResultPage=cResultPage+FREAD(nFH,nFSize)
- ELSE
- RETURN ErrorPage("An error occurred trying to create your data stream. The server cannot continue.")
- ENDIF
- =FCLOSE(nFH)
- ERASE (cFileName)
- RETURN cResultPage
-
-
-
- FUNCTION bldpath
- LOCAL lcPath, lcRefer, lcSubPath
-
- lcPath=gcHTTPRoot
-
- lcRefer=getparam("HTTP_REFERER")
- IF NOT EMPTY(lcRefer)
- lcRefer=STRTRAN(lcRefer,"//","")
- lcRefer=STRTRAN(lcRefer,"/","\")
- lcRefer=SUBSTR(lcRefer,AT("\",lcRefer)+1)
- lcRefer=LEFT(lcRefer,RAT("\",lcRefer))
- ENDIF
-
- lcPath=lcPath+lcRefer
-
- RETURN lcPath
-
-
-
- FUNCTION DetailEx(lcDetailLine,laSymbolTable,cResultPage)
- EXTERNAL ARRAY laSymbolTable
- LOCAL lnMaxRecords,lnCount
-
- IF IDC_MaxRecords > 0
- lnMaxRecords=MIN(IDC_MaxRecords,lnRecordsReturned)
- ELSE
- lnMaxRecords=lnRecordsReturned
- ENDIF
-
- *Execute IIF with local environment
- lcDetailLine=STRTRAN(lcDetailLine,CRLF,"")
-
- SELECT TempResult
-
- lnCount=0
- SCAN REST
- IF lnCount>=lnMaxRecords
- EXIT
- ENDIF
- lnCount=lnCount+1
- cResultPage=cResultPage+EVALUATE(lcDetailLine)
- cResultPage=cResultPage+CRLF
- CurrentRecord=CurrentRecord+1
- ENDSCAN
-
- IF CurrentRecord > 0
- CurrentRecord=1
- ENDIF
-
- RETURN
-
-
-
- *This function takes a conditional statement and evaluates it based on the
- *entire environment state at this time.
-
- FUNCTION EvalCond(lcConditional,laSymbolTable)
- EXTERNAL ARRAY laSymbolTable
-
- RETURN EVALUATE(lcConditional)
-
-
-
- FUNCTION exptoc(eExprVal)
-
- DO CASE
- CASE ISNULL(eExprVal)
- RETURN 'NULL'
- CASE TYPE('eExprVal') $ 'CM'
- RETURN ALLTRIM(eExprVal)
- CASE TYPE('eExprVal') $ 'NFYB'
- RETURN ALLTRIM(STR(eExprVal))
- CASE TYPE('eExprVal') $ 'L'
- RETURN ALLTRIM(IIF(eExprVal,'TRUE','FALSE'))
- CASE TYPE('eExprVal') $ 'D'
- RETURN ALLTRIM(DTOC(eExprVal))
- CASE TYPE('eExprVal') $ 'T'
- RETURN ALLTRIM(TTOC(eExprVal))
- OTHERWISE
- RETURN '*****'
- ENDCASE
-
-
-
- * Function GETIDCP (Get IDC Parameters)
- * Fetches requested parameter from the IDC file and returns the
- * value as a character string. This function has a polymorphic
- * return type: in the case where the DefaultParameters parameter is
- * fetched, the function returns a numeric value indicating how many
- * default parameters were fetched. The parameters and values are stored
- * in the passed-by-reference array as a parameter,value pair.
- * Errors result in the null string being returned.
-
- FUNCTION getidcp(cIDCFile,cParameter,aDefArray)
-
- IF PARAMETERS()<2
- RETURN ""
- ENDIF
-
- llFound=.F.
-
- cParameter=ALLT(cParameter)
- cIDCFile=ALLT(cIDCFile)
-
- lhIDC=FOPEN(cIDCFile)
-
- IF lhIDC < 0
- RETURN ""
- ENDIF
-
- DO WHILE NOT llFound AND NOT FEOF(lhIDC)
- lcLine=FGETS(lhIDC)
- IF NOT EMPTY(lcLine)
- lcLineTok=UPPER(STRTRAN(lcLine," ",""))
- IF (UPPER(cParameter)+":")$lcLineTok
- llFound=.T.
- ENDIF
- ENDIF
- ENDDO
-
- IF NOT llFound
- =FCLOSE(lhIDC)
- RETURN ""
- ENDIF
-
- llDone=.F.
- DO WHILE NOT llDone AND NOT FEOF(lhIDC)
- lcAddLine=ALLT(FGETS(lhIDC))
- IF LEFT(lcAddLine,1) = "+"
- lcLine=lcLine+" "+ALLT(SUBSTR(lcAddLine,2))
- ELSE
- llDone=.T.
- ENDIF
- ENDDO
-
- =FCLOSE(lhIDC)
-
- *Add filler so AT will never fail.
- lcLine=lcLine+" "
-
- lcValue=LTRIM(SUBSTR(lcLine,AT(":",lcLine)+1))
-
- IF UPPER(cParameter)="DEFAULTPARAMETERS" OR UPPER(cParameter)="REQUIREDPARAMETERS"
- lnParameters=0
- DO WHILE AT("=",lcValue)>0
- * Add filler so loop works in 0 case
- lcValue=lcValue+", "
- lnParameters=lnParameters+1
- DIMENSION aDefArray(lnParameters,2)
- aDefArray(lnParameters,1)=ALLT(SUBSTR(lcValue,1,AT("=",lcValue)-1))
- aDefArray(lnParameters,2)=ALLT(SUBSTR(lcValue,AT("=",lcValue)+1,AT(",",lcValue)-(AT("=",lcValue)+1)))
- lcValue=SUBSTR(lcValue,AT(",",lcValue)+1)
- ENDDO
- RETURN lnParameters
- ENDIF
-
- RETURN lcValue
-
-
-
- FUNCTION getparam
- LPARAMETER cVar
- EXTERNAL ARRAY laEnvVariables
-
- LOCAL nLocation, llDone, nFrom
-
- llDone=.F.
- nFrom=1
-
- *Find the given variable in the first column of the environment variables array if
- *it's there at all.
- DO WHILE llDone=.F.
- nLocation=ASCAN(laEnvVariables,cVar,nFrom)
- IF nLocation=0
- llDone=.T.
- ELSE
- IF ASUBSCRIPT(laEnvVariables,nLocation,2) = 1
- llDone=.T.
- ELSE
- nFrom=nLocation+1
- ENDIF
- ENDIF
- ENDDO
-
- IF nLocation > 0
- RETURN laEnvVariables[ASUBSCRIPT(laEnvVariables,nLocation+1,1),ASUBSCRIPT(laEnvVariables,nLocation+1,2)]
- ELSE
- RETURN ""
- ENDIF
-
-
-
- FUNCTION GetToken(INSTR,innum,insep)
- ** GetToken.
- ** Parameters:
- ** 1) Input string to be parsed.
- ** 2) Number of token to return.
- ** 3) The delimiter that seperates tokens. (Default ",")
- PRIVATE ALL
-
- IF PARAM() < 2
- RETURN ""
- ENDIF
-
- IF PARAM() < 3
- insep = ","
- ENDIF
-
- maxnum = OCCURS(insep,INSTR)
-
- DO CASE
- CASE innum <= 0
- rval = ""
- CASE maxnum = 0 AND innum = 1
- rval = INSTR
- CASE maxnum = 0 AND innum > 1
- rval = ""
- CASE maxnum > 0 AND innum = 1
- rval = SUBSTR(INSTR,1,ATC(insep,INSTR)-1)
- CASE innum = maxnum + 1 AND LEN(INSTR) < ATC(insep,INSTR,maxnum)+1
- rval = ""
- CASE innum = maxnum + 1
- start = ATC(insep,INSTR,maxnum)+1
- stop = LEN(INSTR)
- rval = SUBSTR(INSTR,start,stop-start+1)
- CASE innum < maxnum + 1
- start = ATC(insep,INSTR,innum-1)+1
- stop = ATC(insep,INSTR,innum)-1
- rval = SUBSTR(INSTR,start,stop-start+1)
- CASE innum > maxnum + 1
- rval = ""
-
- ENDCASE
- RETURN rval
-
-
-
- FUNCTION isnum(lcNumber)
-
- IF EMPTY(lcNumber)
- RETURN .F.
- ENDIF
-
- lcNumber=UPPER(lcNumber)
-
- *Make sure there's not more than one of each E,-, and .
-
- IF STRTRAN(lcNumber,".","",1,1)!=STRTRAN(lcNumber,".","")
- RETURN .F.
- ENDIF
- IF STRTRAN(lcNumber,"E","",1,1)!=STRTRAN(lcNumber,"E","")
- RETURN .F.
- ENDIF
- IF STRTRAN(lcNumber,"-","",1,1)!=STRTRAN(lcNumber,"-","")
- RETURN .F.
- ENDIF
-
- IF CHRTRAN(lcNumber,"0123456789.E-",REPL(CHR(0),13))==REPL(CHR(0),LEN(lcNumber))
- RETURN .T.
- ELSE
- RETURN .F.
- ENDIF
-
-
-
- FUNCTION parmsub(lcRootString)
- EXTERNAL ARRAY laEnvVariables
-
- lcFilledString=lcRootString
-
- *Iterate through for each possible environment variable. Faster than parsing everything out.
-
- FOR nCnt=1 TO lnEnvVariables
- lcFilledString=STRTRAN(lcFilledString,"%"+ALLT(laEnvVariables[nCnt,1])+"%",laEnvVariables[nCnt,2])
- ENDFOR
-
- RETURN lcFilledString
-
-
-
- FUNCTION ParseVars(cParameters,laEnvVariables,llCreate)
-
- LOCAL nVCount, cToken
-
- IF EMPTY(cParameters)
- RETURN 0
- ENDIF
-
- IF llCreate
- nVCount=1
- ELSE
- nVCount=ALEN(laEnvVariables,1)+1
- ENDIF
- cToken=GETTOKEN(cParameters,1,"&")
- DO WHILE NOT EMPTY(cToken)
- DIMENSION laEnvVariables[nVCount,2]
- laEnvVariables[nVCount,1]=ALLT(SUBSTR(cToken,1,ATC("=",cToken)-1))
- IF ATC("=",cToken)=LEN(cToken)
- laEnvVariables[nVCount,2]=""
- ELSE
- cToken = SUBSTR(cToken,ATC("=",cToken)+1)
- cToken = StripASCII(cToken)
- laEnvVariables[nVCount,2] = STRTRAN(cToken,"+"," ")
- ENDIF
- nVCount=nVCount+1
- cToken=GETTOKEN(cParameters,nVCount,"&")
- ENDDO
-
- nVCount=nVCount-1
-
- RETURN nVCount
-
- FUNCTION StripASCII
- LPARAMETER clString
-
- LOCAL cReplace
-
- DO WHILE ATC("%",clString) > 0
- cReplace = SUBSTR(clString,ATC("%",clString),3)
- clString = STRTRAN(clString,cReplace,gethex(cReplace))
- ENDDO
-
- RETURN clString
-
-
-
- FUNCTION gethex(cHex)
-
- nRval = getval(SUBSTR(cHex,2,1))*16+getval(SUBSTR(cHex,3,1))
-
- RETURN CHR(nRval)
-
-
-
- FUNCTION getval(cVal)
-
- DO CASE
- CASE ASC(cVal) >= 65
- nRval = ASC(cVal)-55
- CASE ASC(cVal) >= 48
- nRval = ASC(cVal)-48
- ENDCASE
-
- RETURN nRval
-
-
-
- FUNCTION readini(filename)
-
- PRIVATE pcfg,prdline,ptoken,pvalue
-
- pcfg = FOPEN(filename)
-
- IF pcfg < 0
- RETURN .F.
- ENDIF
-
- DO WHILE NOT(FEOF(pcfg))
- prdline = FGETS(pcfg)
- IF NOT EMPTY(prdline)
- ptoken = UPPER(ALLTRIM(SUBSTR(prdline,1,AT("=",prdline)-1)))
- pvalue = UPPER(ALLTRIM(SUBSTR(prdline,AT("=",prdline)+1)))
- DO CASE
- CASE ptoken == "HTTPROOT"
- gcHTTPRoot = pvalue
- CASE ptoken == "SCRIPTROOT"
- gcScriptRoot = pvalue
- CASE ptoken == "SEMAPHORE"
- gcSemaphoreRoot = pvalue
- CASE ptoken == "PATH"
- gcPath = pvalue
- ENDCASE
- ENDIF
- ENDDO
-
- =FCLOSE(pcfg)
-
- RETURN .T.
-
-
-
- FUNCTION runspec
- gcINIFile='is.ini'
- gcHTTPRoot=""
- gcScriptRoot=""
-
- DO FORM specroot
- RETURN
-
-
-
- FUNCTION ErrorHandler(tnErrorNo,tcMsg,tcProgramName,tnLineNo,tcCodeLine)
- LOCAL laDir[1]
-
- IF ADIR(laDir,'error.txt')>0
- IF laDir[2]>65535 OR (DATE()-laDir[3])>14
- ERASE error.txt
- ENDIF
- ENDIF
- SET TEXTMERGE OFF
- SET TEXTMERGE TO ERROR ADDITIVE
- SET TEXTMERGE ON NOSHOW
- \Error occured : <<DATE()>> at <<TIME()>>
- \Error message : <<tcMsg>>
- \Error number : <<tnErrorNo>>
- \Procedure name: <<PROPER(tcProgramName)>>
- \Line number : <<tnLineNo>>
- IF NOT EMPTY(ALIAS())
- \Alias : [<<ALIAS()>>]
- \Record number : <<RECNO()>>
- ENDIF
- \<<tcCodeLine>>
- \
- \
- SET TEXTMERGE OFF
- SET TEXTMERGE TO
- ENDFUNC
-