thetaphi                Thu Jul 24 13:40:40 2003 EDT

  Modified files:              
    /php-src/sapi/nsapi nsapi-readme.txt nsapi.c 
  Log:
  Possibility to use php5_execute to display server error pages or directory listing 
pages
  
Index: php-src/sapi/nsapi/nsapi-readme.txt
diff -u php-src/sapi/nsapi/nsapi-readme.txt:1.7 php-src/sapi/nsapi/nsapi-readme.txt:1.8
--- php-src/sapi/nsapi/nsapi-readme.txt:1.7     Wed Jul  2 18:39:37 2003
+++ php-src/sapi/nsapi/nsapi-readme.txt Thu Jul 24 13:40:40 2003
@@ -72,7 +72,7 @@
 Authentication configuration
 ----------------------------
 
-PHP authentication cannot be used with any other authentication.  ALL
+PHP authentication cannot be used with any other authentication. ALL
 AUTHENTICATION IS PASSED TO YOUR PHP SCRIPT.  To configure PHP
 Authentication for the entire server, add the following line:
 
@@ -91,3 +91,31 @@
     AuthTrans fn=php5_auth_trans
     </Object>
 
+
+Special use for error pages or self-made directory listings
+-----------------------------------------------------------
+
+You can use PHP to generate the error pages for "404 Not Found"
+or similar. Add the following line to the object in obj.conf for
+every error page you want to overwrite:
+
+    Error fn="php5_execute" code=XXX script="/path/to/script.php" [inikey=value 
inikey=value...]
+
+where XXX ist the HTTP error code. Please delete any other Error
+directives which could interfere with yours.
+If you want to place a page for all errors that could exist, leave
+the "code" parameter out. Your script can get the HTTP status code
+with $_SERVER['ERROR_TYPE'].
+
+Another posibility is to generate self-made directory listings.
+Just generate a PHP script which displays a directory listing and
+replace the corresponding default Service line for
+type="magnus-internal/directory" in obj.conf with the following:
+
+    Service fn="php5_execute" type="magnus-internal/directory" 
script="/path/to/script.php" [inikey=value inikey=value...]
+
+For both error and directory listing pages the original URI and
+translated URI are in the variables $_SERVER['PATH_INFO'] and
+$_SERVER['PATH_TRANSLATED'].
+
+$ Id: $
Index: php-src/sapi/nsapi/nsapi.c
diff -u php-src/sapi/nsapi/nsapi.c:1.52 php-src/sapi/nsapi/nsapi.c:1.53
--- php-src/sapi/nsapi/nsapi.c:1.52     Mon Jul 21 10:20:47 2003
+++ php-src/sapi/nsapi/nsapi.c  Thu Jul 24 13:40:40 2003
@@ -17,7 +17,7 @@
    +----------------------------------------------------------------------+
 */
 
-/* $Id: nsapi.c,v 1.52 2003/07/21 14:20:47 thetaphi Exp $ */
+/* $Id: nsapi.c,v 1.53 2003/07/24 17:40:40 thetaphi Exp $ */
 
 /*
  * PHP includes
@@ -90,6 +90,9 @@
        Session *sn;
        Request *rq;
        int     read_post_bytes;
+       char *path_info;
+       int fixed_script; /* 0 if script is from URI, 1 if script is from "script" 
parameter */
+       short http_error; /* 0 in normal mode; for errors the HTTP error code */
 } nsapi_request_context;
 
 /*
@@ -118,8 +121,6 @@
 static size_t nsapi_reqpb_size = sizeof(nsapi_reqpb)/sizeof(nsapi_reqpb[0]);
 
 static nsapi_equiv nsapi_vars[] = {
-       { "PATH_INFO",                  "path-info" },
-       { "SCRIPT_FILENAME",    "path" },
        { "AUTH_TYPE",                  "auth-type" },
        { "CLIENT_CERT",                "auth-cert" },
        { "REMOTE_USER",                "auth-user" }
@@ -134,7 +135,8 @@
 };
 static size_t nsapi_client_size = sizeof(nsapi_client)/sizeof(nsapi_client[0]);
 
-static char *nsapi_exclude_from_ini_entries[] = { "fn", "type", "method", 
"directive", NULL };
+/* this parameters to "Service"/"Error" are NSAPI ones which should not be php.ini 
keys and are excluded */
+static char *nsapi_exclude_from_ini_entries[] = { "fn", "type", "method", 
"directive", "code", "reason", "script", NULL };
 
 static char *nsapi_strdup(char *str)
 {
@@ -201,7 +203,7 @@
        NULL,
        NULL,
        PHP_MINFO(nsapi),
-       "$Revision: 1.52 $",
+       "$Revision: 1.53 $",
        STANDARD_MODULE_PROPERTIES
 };
 /* }}} */
@@ -475,8 +477,6 @@
        if (!strcasecmp(header_name, "Content-Type")) {
                param_free(pblock_remove("content-type", rc->rq->srvhdrs));
                pblock_nvinsert("content-type", header_content, rc->rq->srvhdrs);
-       } else if (!strcasecmp(header_name, "Set-Cookie")) {
-               pblock_nvinsert("set-cookie", header_content, rc->rq->srvhdrs);
        } else {
                pblock_nvinsert(header_name, header_content, rc->rq->srvhdrs);
        }
@@ -583,6 +583,7 @@
 {
        nsapi_request_context *rc = (nsapi_request_context *)SG(server_context);
        register size_t i;
+       int pos;
        char *value,*p;
        char buf[NS_BUF_SIZE + 1];
        struct pb_entry *entry;
@@ -652,40 +653,50 @@
 
        /* DOCUMENT_ROOT */
        if (value = request_translate_uri("/", rc->sn)) {
-               value[strlen(value) - 1] = 0;
+               value[strlen(value) - 1] = '\0';
                php_register_variable("DOCUMENT_ROOT", value, track_vars_array 
TSRMLS_CC);
                nsapi_free(value);
        }
 
-       /* PATH_TRANSLATED */
-       if (value = pblock_findval("path-info", rc->rq->vars)) {
-               if (value = request_translate_uri(value, rc->sn)) {
+       /* PATH_INFO / PATH_TRANSLATED */
+       if (rc->path_info) {
+               if (value = request_translate_uri(rc->path_info, rc->sn)) {
                        php_register_variable("PATH_TRANSLATED", value, 
track_vars_array TSRMLS_CC);
                        nsapi_free(value);
                }
+               php_register_variable("PATH_INFO", rc->path_info, track_vars_array 
TSRMLS_CC);
        }
 
-       /* Create full Request-URI */
-       if (value = pblock_findval("uri", rc->rq->reqpb)) {
-               strncpy(buf, value, NS_BUF_SIZE);
+       /* Create full Request-URI & Script-Name */
+       if (SG(request_info).request_uri) {
+               strncpy(buf, SG(request_info).request_uri, NS_BUF_SIZE);
                buf[NS_BUF_SIZE]='\0';
-               if (value = pblock_findval("query", rc->rq->reqpb)) {
+               if (SG(request_info).query_string) {
                        p = strchr(buf, 0);
-                       snprintf(p, NS_BUF_SIZE-(p-buf), "?%s", value);
+                       snprintf(p, NS_BUF_SIZE-(p-buf), "?%s", 
SG(request_info).query_string);
                        buf[NS_BUF_SIZE]='\0';
                }
                php_register_variable("REQUEST_URI", buf, track_vars_array TSRMLS_CC);
-       }
 
-       /* Create Script-Name */
-       if (value = pblock_findval("uri", rc->rq->reqpb)) {
-               strncpy(buf, value, NS_BUF_SIZE);
+               strncpy(buf, SG(request_info).request_uri, NS_BUF_SIZE);
                buf[NS_BUF_SIZE]='\0';
-               if (value = pblock_findval("path-info", rc->rq->vars)) {
-                       buf[strlen(buf) - strlen(value)] = '\0';
+               if (rc->path_info) {
+                       pos = strlen(SG(request_info).request_uri) - 
strlen(rc->path_info);
+                       if (pos>=0 && pos<=NS_BUF_SIZE && rc->path_info) {
+                               buf[pos] = '\0';
+                       } else {
+                               buf[0]='\0';
+                       }
                }
                php_register_variable("SCRIPT_NAME", buf, track_vars_array TSRMLS_CC);
        }
+       php_register_variable("SCRIPT_FILENAME", SG(request_info).path_translated, 
track_vars_array TSRMLS_CC);
+
+       /* special variables in error mode */
+       if (rc->http_error) {
+               sprintf(buf, "%d", rc->http_error);
+               php_register_variable("ERROR_TYPE", buf, track_vars_array TSRMLS_CC);
+       }
 }
 
 static void nsapi_log_message(char *message)
@@ -780,6 +791,13 @@
        log_error(LOG_INFORM, "php5_close", NULL, NULL, "Shutdown PHP Module");
 }
 
+/*********************************************************
+/ init SAF
+/
+/ Init fn="php5_init" [php_ini="/path/to/php.ini"]
+/   Initialize the NSAPI module in magnus.conf
+/
+/*********************************************************/
 int NSAPI_PUBLIC php5_init(pblock *pb, Session *sn, Request *rq)
 {
        php_core_globals *core_globals;
@@ -812,6 +830,21 @@
        return REQ_PROCEED;
 }
 
+/*********************************************************
+/ normal use in Service directive:
+/
+/ Service fn="php5_execute" type=... method=... [inikey=inivalue inikey=inivalue...]
+/
+/ use in Service for a directory to supply a php-made directory listing instead of 
server default:
+/
+/ Service fn="php5_execute" type="magnus-internal/directory" 
script="/path/to/script.php" [inikey=inivalue inikey=inivalue...]
+/
+/ use in Error SAF to display php script as error page:
+/
+/ Error fn="php5_execute" code=XXX script="/path/to/script.php" [inikey=inivalue 
inikey=inivalue...]
+/ Error fn="php5_execute" reason="Reason" script="/path/to/script.php" 
[inikey=inivalue inikey=inivalue...]
+/
+/*********************************************************/
 int NSAPI_PUBLIC php5_execute(pblock *pb, Session *sn, Request *rq)
 {
        int retval;
@@ -819,23 +852,47 @@
        zend_file_handle file_handle = {0};
        struct stat fst;
 
+       char *path_info;
        char *query_string    = pblock_findval("query", rq->reqpb);
        char *uri             = pblock_findval("uri", rq->reqpb);
-       char *path_info       = pblock_findval("path-info", rq->vars);
        char *request_method  = pblock_findval("method", rq->reqpb);
        char *content_type    = pblock_findval("content-type", rq->headers);
        char *content_length  = pblock_findval("content-length", rq->headers);
-       char *path_translated = pblock_findval("path", rq->vars);
+       char *directive       = pblock_findval("Directive", pb);
+       int error_directive   = (directive && !strcasecmp(directive, "error"));
+       int fixed_script      = 1;
+
+       /* try to use script parameter -> Error or Service for directory listing */
+       char *path_translated = pblock_findval("script", pb);
 
        TSRMLS_FETCH();
 
+       /* if script parameter is missing: normal use as Service SAF  */
+       if (!path_translated) {
+               path_translated = pblock_findval("path", rq->vars);
+               path_info       = pblock_findval("path-info", rq->vars);
+               fixed_script = 0;
+               if (error_directive) {
+                       /* go to next error directive if script parameter is missing */
+                       log_error(LOG_WARN, pblock_findval("fn", pb), sn, rq, "Missing 
'script' parameter");
+                       return REQ_NOACTION;
+               }
+       } else {
+               /* in error the path_info is the uri to the requested page */
+               path_info = pblock_findval("uri", rq->reqpb);
+       }
+
        /* check if this uri was included in an other PHP script with nsapi_virtual()
           by looking for a request context in the current thread */
        if (SG(server_context)) {
                /* send 500 internal server error */
                log_error(LOG_WARN, pblock_findval("fn", pb), sn, rq, "Cannot make 
nesting PHP requests with nsapi_virtual()");
-               protocol_status(sn, rq, 500, NULL);
-               return REQ_ABORTED;
+               if (error_directive) {
+                       return REQ_NOACTION;
+               } else {
+                       protocol_status(sn, rq, 500, NULL);
+                       return REQ_ABORTED;
+               }
        }
 
        request_context = (nsapi_request_context 
*)MALLOC(sizeof(nsapi_request_context));
@@ -843,6 +900,9 @@
        request_context->sn = sn;
        request_context->rq = rq;
        request_context->read_post_bytes = 0;
+       request_context->fixed_script = fixed_script;
+       request_context->http_error = (error_directive) ? rq->status_num : 0;
+       request_context->path_info = nsapi_strdup(path_info);
 
        SG(server_context) = request_context;
        SG(request_info).query_string = nsapi_strdup(query_string);
@@ -851,7 +911,7 @@
        SG(request_info).path_translated = nsapi_strdup(path_translated);
        SG(request_info).content_type = nsapi_strdup(content_type);
        SG(request_info).content_length = (content_length == NULL) ? 0 : 
strtoul(content_length, 0, 0);
-       SG(sapi_headers).http_response_code = 200;
+       SG(sapi_headers).http_response_code = (error_directive) ? rq->status_num : 200;
 
        nsapi_php_ini_entries(NSLS_C TSRMLS_CC);
 
@@ -868,16 +928,25 @@
                } else {
                        /* send 500 internal server error */
                        log_error(LOG_WARN, pblock_findval("fn", pb), sn, rq, "Cannot 
prepare PHP engine!");
-                       protocol_status(sn, rq, 500, NULL);
-                       retval=REQ_ABORTED;
+                       if (error_directive) {
+                               retval=REQ_NOACTION;
+                       } else {
+                               protocol_status(sn, rq, 500, NULL);
+                               retval=REQ_ABORTED;
+                       }
                }
        } else {
                /* send 404 because file not found */
-               log_error(LOG_WARN, pblock_findval("fn", pb), sn, rq, "Cannot execute 
PHP script: %s", SG(request_info).path_translated);
-               protocol_status(sn, rq, 404, NULL);
-               retval=REQ_ABORTED;
+               log_error(LOG_WARN, pblock_findval("fn", pb), sn, rq, "Cannot execute 
PHP script: %s (File not found)", SG(request_info).path_translated);
+               if (error_directive) {
+                       retval=REQ_NOACTION;
+               } else {
+                       protocol_status(sn, rq, 404, NULL);
+                       retval=REQ_ABORTED;
+               }
        }
 
+       nsapi_free(request_context->path_info);
        nsapi_free(SG(request_info).query_string);
        nsapi_free(SG(request_info).request_uri);
        nsapi_free((void*)(SG(request_info).request_method));

-- 
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to