123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275 |
- program testcgiapp;
- {$mode objfpc}{$H+}
- uses
- Classes, SysUtils, CustApp, inifiles, process, httpdefs,custcgi
- { you can add units after this };
- type
- { TTestCGIApplication }
- TTestCGIApplication = class(TCustomApplication)
- private
- FCGB: String;
- FCGIE: TStrings;
- FCGV: TStrings;
- FMethod: String;
- Foutput: String;
- FPostData: String;
- FPathInfo : String;
- FScriptName: String;
- FURL: String;
- procedure CheckEnvironment;
- procedure CheckMethod;
- procedure ProcessConfig;
- procedure RunCGI;
- protected
- Property CGIEnvironment : TStrings Read FCGIE Write FCGIE;
- Property URL : String Read FURL Write FURL;
- Property PostData : String Read FPostData Write FPostData;
- Property Method : String Read FMethod Write FMethod;
- Property CGIOutput : String Read Foutput Write FOutput;
- Property CGIBinary : String Read FCGB Write FCGB;
- Property CGIVariables : TStrings Read FCGV Write FCGV;
- Property PathInfo : String Read FPathInfo Write FPathInfo;
- Property ScriptName : String Read FScriptName Write FScriptName;
- procedure DoRun; override;
- public
- constructor Create(TheOwner: TComponent); override;
- Destructor Destroy; override;
- procedure WriteHelp; virtual;
- end;
- { TTestCGIApplication }
- Resourcestring
- SErrUnsupportedMethod = 'Unsupported method: "%s"';
- SErrNoCGIBinary = 'No CGI binary specified';
- Const
- SConfig = 'Config';
- KeyURL = 'URL';
- KeyEnvironment = 'Environment';
- KeyMethod = 'Method';
- KeyPost = 'PostData';
- SEnvironment = KeyEnvironment;
- SVariables = 'Variables';
- procedure TTestCGIApplication.ProcessConfig;
- Var
- Ini : TInifile;
- S : String;
- begin
- Ini:=TIniFile.Create(GetOptionValue('c','config'));
- try
- With Ini do
- begin
- URL:=ReadString(SConfig,KeyURL,'');
- S:=ReadString(SConfig,KeyEnvironment,'');
- If (S<>'') and FileExists(S) then
- CGIEnvironment.LoadFromFile(S);
- If SectionExists(SEnvironment) then
- ReadSectionValues(SEnvironment,CGIEnvironment);
- If SectionExists(SVariables) then
- ReadSectionValues(SVariables,CGIVariables);
- If (Method='') then
- Method:=ReadString(SConfig,KeyMethod,'GET');
- PostData:=ReadString(SConfig,KeyPost,'');
- end;
- finally
- Ini.Free;
- end;
- end;
- procedure TTestCGIApplication.RunCGI;
- Var
- Proc : TProcess;
- begin
- If (CGIBinary='') then
- Raise Exception.Create(SerrNoCGIBinary);
- Proc:=TProcess.Create(Self);
- try
- Proc.CommandLine:=CGIBinary;
- Proc.Environment:=CGIEnvironment;
- Proc.Execute;
- finally
- Proc.Free;
- end;
- end;
- procedure TTestCGIApplication.CheckMethod;
- begin
- If (Method='') then
- Method:='GET'
- else
- begin
- Method:=Uppercase(Method);
- end;
- end;
- (*
- ({ 1: 'AUTH_TYPE' } fieldWWWAuthenticate, // ?
- { 2: 'CONTENT_LENGTH' } FieldContentLength,
- { 3: 'CONTENT_TYPE' } FieldContentType,
- { 4: 'GATEWAY_INTERFACE' } '',
- { 5: 'PATH_INFO' } '',
- { 6: 'PATH_TRANSLATED' } '',
- { 7: 'QUERY_STRING' } '',
- { 8: 'REMOTE_ADDR' } '',
- { 9: 'REMOTE_HOST' } '',
- { 10: 'REMOTE_IDENT' } '',
- { 11: 'REMOTE_USER' } '',
- { 12: 'REQUEST_METHOD' } '',
- { 13: 'SCRIPT_NAME' } '',
- { 14: 'SERVER_NAME' } '',
- { 15: 'SERVER_PORT' } '',
- { 16: 'SERVER_PROTOCOL' } '',
- { 17: 'SERVER_SOFTWARE' } '',
- { 18: 'HTTP_ACCEPT' } FieldAccept,
- { 19: 'HTTP_ACCEPT_CHARSET' } FieldAcceptCharset,
- { 20: 'HTTP_ACCEPT_ENCODING' } FieldAcceptEncoding,
- { 21: 'HTTP_IF_MODIFIED_SINCE' } FieldIfModifiedSince,
- { 22: 'HTTP_REFERER' } FieldReferer,
- { 23: 'HTTP_USER_AGENT' } FieldUserAgent,
- { 24: 'HTTP_COOKIE' } FieldCookie,
- // Additional Apache vars
- { 25: 'HTTP_CONNECTION' } FieldConnection,
- { 26: 'HTTP_ACCEPT_LANGUAGE' } FieldAcceptLanguage,
- { 27: 'HTTP_HOST' } '',
- { 28: 'SERVER_SIGNATURE' } '',
- { 29: 'SERVER_ADDR' } '',
- { 30: 'DOCUMENT_ROOT' } '',
- { 31: 'SERVER_ADMIN' } '',
- { 32: 'SCRIPT_FILENAME' } '',
- { 33: 'REMOTE_PORT' } '',
- { 34: 'REQUEST_URI' } '',
- { 35: 'CONTENT' } '',
- { 36: 'XHTTPREQUESTEDWITH' } ''
- *)
- procedure TTestCGIApplication.CheckEnvironment;
- Var
- L : TStrings;
- S,N,V : String;
- I : Integer;
- begin
- L:=CGIEnvironment;
- If L.IndexOfName('REQUEST_METHOD')=-1 then
- L.Values['REQUEST_METHOD']:=Method;
- S:=ScriptName;
- If (S='') then
- S:=CGIBinary;
- If L.IndexOfName('SCRIPT_NAME')=-1 then
- L.Values['SCRIPT_NAME']:=S;
- If L.IndexOfName('SCRIPT_FILENAME')=-1 then
- L.Values['SCRIPT_FILENAME']:=S;
- If (PathInfo<>'') then
- L.Values['PATH_INFO']:=PathInfo;
- If (Method='GET') then
- begin
- If L.IndexOfName('QUERY_STRING')=-1 then
- begin
- S:='';
- If (CGIVariables.Count>0) then
- For I:=0 to CGIVariables.Count-1 do
- begin
- CGIVariables.GetNameValue(I,N,V);
- If (S<>'') then
- S:=S+'&';
- S:=S+N+'='+HTTPEncode(V);
- end;
- L.Add('QUERY_STRING='+S)
- end;
- end
- end;
- procedure TTestCGIApplication.DoRun;
- var
- ErrorMsg: String;
- begin
- // parse parameters
- if HasOption('h','help') then begin
- WriteHelp;
- Terminate;
- Exit;
- end;
- if HasOption('c','config') then
- ProcessConfig;
- If HasOption('u','url') then
- URL:=GetOptionValue('u','url');
- If HasOption('e','environment') then
- CGIEnvironment.LoadFromFile(GetOptionValue('e','environment'));
- If HasOption('o','output') then
- CGIOutput:=GetOptionValue('o','output');
- If HasOption('m','method') then
- Method:=GetOptionValue('m','method');
- If HasOption('p','pathinfo') then
- PathInfo:=GetOptionValue('p','pathinfo');
- If HasOption('s','scriptname') then
- ScriptName:=GetOptionValue('s','scriptname');
- If HasOption('r','variables') then
- CGIOutput:=GetOptionValue('v','variables');
- If HasOption('i','input') then
- CGIBinary:=GetOptionValue('i','input');
- CheckMethod;
- CheckEnvironment;
- RunCGI;
- { add your program here }
- // stop program loop
- Terminate;
- end;
- constructor TTestCGIApplication.Create(TheOwner: TComponent);
- begin
- inherited Create(TheOwner);
- StopOnException:=True;
- FCGIE:=TStringList.Create;
- FCGV:=TStringList.Create;
- end;
- destructor TTestCGIApplication.Destroy;
- begin
- FreeAndNil(FCGIE);
- FreeAndNil(FCGV);
- inherited Destroy;
- end;
- procedure TTestCGIApplication.WriteHelp;
- begin
- Writeln('Usage: ',ExeName,' [options]');
- Writeln('Where options is one of : ');
- Writeln(' -h this help');
- Writeln(' -c|--config=file use file for configuration');
- Writeln(' -e|--environment=file use file for CGI environment (overrides config).');
- Writeln(' -i|--input=file use file as CGI binary.');
- Writeln(' -m|--method=method use method to invoke CGI (overrides config, default is GET).');
- Writeln(' -o|--output=file use file for CGI output (overrides config).');
- Writeln(' -p|--pathinfo=path use path for PATH_INFO environment variable (overrides config).');
- Writeln(' -r|--variables=file read query variables from file (overrides config).');
- Writeln(' -u|--url=URL use URL as the URL (overrides config).');
- end;
- var
- Application: TTestCGIApplication;
- begin
- Application:=TTestCGIApplication.Create(nil);
- Application.Title:='Test CGI application';
- Application.Run;
- Application.Free;
- end.
|