[Osaas-commits] r43 - in trunk: . server/osaas server/test

scm-commit@wald.intevation.org scm-commit at wald.intevation.org
Thu Nov 20 20:01:56 CET 2008


Author: bh
Date: 2008-11-20 20:01:55 +0100 (Thu, 20 Nov 2008)
New Revision: 43

Modified:
   trunk/ChangeLog
   trunk/server/osaas/formparser.py
   trunk/server/osaas/server.py
   trunk/server/test/test_formparser.py
   trunk/server/test/test_osasserver.py
Log:
Implement filtering of requests correctly.  In particular, do not
check whether all required fields are present before filtering the
requests.  For instance, in the old implementation GetCapabilities
requests were rejected with a 400 HTTP response because of missing
WIDTH fields instead of being accepted and then discarded.

* server/osaas/formparser.py (Record.set_fields)
(Record.validate_fields): Move the check for required fields into
the new method validate_fields.  Now the validation requires an
extra method call and is not implicitly done by parse_formdata
anymore.

* server/osaas/server.py
(OSAASRequestHandler.handle_owsaccounting_formdata): Call
default_filter before validating the parsed record.

* server/test/test_osasserver.py: Use a real GetCapabilities
request so that this test really tests whether those are ignored.
Before, the GetCapabilities request had all of the required fields
of a GetMap request too, to make sure it actually got through to
the default_filter instead of being rejected because of missing
required fields.

* server/test/test_formparser.py
(FormParsingTests.test_missing_required_parameters_in_formdata)
(FormParsingTests.test_missing_required_parameters_in_requeststring):
Adapt to formparser changes.  These tests now require an explicit
validate_fields call.


Modified: trunk/ChangeLog
===================================================================
--- trunk/ChangeLog	2008-11-20 16:28:42 UTC (rev 42)
+++ trunk/ChangeLog	2008-11-20 19:01:55 UTC (rev 43)
@@ -1,5 +1,36 @@
 2008-11-20  Bernhard Herzog  <bh at intevation.de>
 
+	Implement filtering of requests correctly.  In particular, do not
+	check whether all required fields are present before filtering the
+	requests.  For instance, in the old implementation GetCapabilities
+	requests were rejected with a 400 HTTP response because of missing
+	WIDTH fields instead of being accepted and then discarded.
+
+	* server/osaas/formparser.py (Record.set_fields)
+	(Record.validate_fields): Move the check for required fields into
+	the new method validate_fields.  Now the validation requires an
+	extra method call and is not implicitly done by parse_formdata
+	anymore.
+
+	* server/osaas/server.py
+	(OSAASRequestHandler.handle_owsaccounting_formdata): Call
+	default_filter before validating the parsed record.
+
+	* server/test/test_osasserver.py: Use a real GetCapabilities
+	request so that this test really tests whether those are ignored.
+	Before, the GetCapabilities request had all of the required fields
+	of a GetMap request too, to make sure it actually got through to
+	the default_filter instead of being rejected because of missing
+	required fields.
+
+	* server/test/test_formparser.py
+	(FormParsingTests.test_missing_required_parameters_in_formdata)
+	(FormParsingTests.test_missing_required_parameters_in_requeststring):
+	Adapt to formparser changes.  These tests now require an explicit
+	validate_fields call.
+
+2008-11-20  Bernhard Herzog  <bh at intevation.de>
+
 	* server/test/test_formparser.py (FormParsingTests.check_exception):
 	Check whether an exception was raised at all.  Without this,
 	function calls which did not raise exceptions were considered as a

Modified: trunk/server/osaas/formparser.py
===================================================================
--- trunk/server/osaas/formparser.py	2008-11-20 16:28:42 UTC (rev 42)
+++ trunk/server/osaas/formparser.py	2008-11-20 19:01:55 UTC (rev 43)
@@ -1,4 +1,4 @@
-# Copyright (C) 2007 by Intevation GmbH
+# Copyright (C) 2007, 2008 by Intevation GmbH
 # Authors:
 # Bernhard Herzog <bh at intevation.de>
 #
@@ -36,6 +36,9 @@
 
 class Record:
 
+    def __init__(self):
+        self._fields = []
+
     def set_fields(self, fields, formdata, fieldname_normalizer=None):
         try:
             parsed_form = cgi.parse_qs(formdata, keep_blank_values=True,
@@ -50,17 +53,25 @@
                 parsed_form[normalized] = value
 
         for field in fields:
-            value = parsed_form.get(field.name)
+            value = parsed_form.pop(field.name, None)
             if value:
                 if len(value) == 1:
                     setattr(self, field.name, field.deserialize(value[0]))
                 else:
                     raise FormParserException("only one value allowed"
                                               " for field %r" % field.name)
-            elif field.required:
+        if parsed_form:
+            print "Record.set_fields: ignored fields", parsed_form
+
+        self._fields.extend(fields)
+
+    def validate_fields(self):
+        for field in self._fields:
+            if field.required and not hasattr(self, field.name):
                 raise FormParserException("formdata is missing required"
                                           " field %r" % field.name)
 
+
 form_fields = [Field(name, required=True)
                for name in ["user", "wmsidextern", "wmsidintern",
                             "requeststring"]]

Modified: trunk/server/osaas/server.py
===================================================================
--- trunk/server/osaas/server.py	2008-11-20 16:28:42 UTC (rev 42)
+++ trunk/server/osaas/server.py	2008-11-20 19:01:55 UTC (rev 43)
@@ -1,4 +1,4 @@
-# Copyright (C) 2007 by Intevation GmbH
+# Copyright (C) 2007, 2008 by Intevation GmbH
 # Authors:
 # Bernhard Herzog <bh at intevation.de>
 #
@@ -78,13 +78,20 @@
             self.send_error(400, "Bad request: %s" % err)
             return
 
-        if default_filter(record):
-            self.log_debug("passing record to db thread")
-            self.server.dbthreadpool.put(record)
-        else:
-            self.log_debug("record (SERVICE=%r, REQUEST=%r) was filtered out",
-                           record.SERVICE, record.REQUEST)
+        if not default_filter(record):
+            self.log_debug("record was filtered out: %s", record.raw_record)
+            self.send_response(200)
+            return
 
+        try:
+            record.validate_fields()
+        except FormParserException, err:
+            self.send_error(400, "Bad request: %s" % err)
+            return
+
+        self.log_debug("passing record to db thread")
+        self.server.dbthreadpool.put(record)
+
         self.send_response(200)
 
     def check_user(self):

Modified: trunk/server/test/test_formparser.py
===================================================================
--- trunk/server/test/test_formparser.py	2008-11-20 16:28:42 UTC (rev 42)
+++ trunk/server/test/test_formparser.py	2008-11-20 19:01:55 UTC (rev 43)
@@ -89,9 +89,10 @@
                              "%26BGCOLOR=0xffffff%26BBOX=0.0,0.0,460.0,348.0"
                              "%26LAYERS=gewaesser%26STYLES=%26SRS=EPSG:4326"
                              "%26SERVICE=WMS"])
+        record = parse_formdata(formdata)
         self.check_exception(FormParserException,
                              "formdata is missing required field 'user'",
-                             parse_formdata, formdata)
+                             record.validate_fields)
 
     def test_missing_required_parameters_in_requeststring(self):
         # requeststring is missing the required field "REQUEST"
@@ -105,9 +106,10 @@
                              "%26BGCOLOR=0xffffff%26BBOX=0.0,0.0,460.0,348.0"
                              "%26LAYERS=gewaesser%26STYLES=%26SRS=EPSG:4326"
                              "%26SERVICE=WMS"])
+        record = parse_formdata(formdata)
         self.check_exception(FormParserException,
                              "formdata is missing required field 'REQUEST'",
-                             parse_formdata, formdata)
+                             record.validate_fields)
 
     def test_duplicate_parameters(self):
         # The responsetime occurs twice

Modified: trunk/server/test/test_osasserver.py
===================================================================
--- trunk/server/test/test_osasserver.py	2008-11-20 16:28:42 UTC (rev 42)
+++ trunk/server/test/test_osasserver.py	2008-11-20 19:01:55 UTC (rev 43)
@@ -1,4 +1,4 @@
-# Copyright (C) 2007 by Intevation GmbH
+# Copyright (C) 2007, 2008 by Intevation GmbH
 # Authors:
 # Bernhard Herzog <bh at intevation.de>
 #
@@ -175,25 +175,19 @@
             "user=karl", "responsetime=2007-06-01T12:14:16Z",
             "wmsidextern=example.com%2Fcgi-bin%2Ffridawms",
             "wmsidintern=localhost%2Fcgi-bin%2Fmyfrida",
-            "requeststring=VERSION=1.1.1%26REQUEST=GetMap"
-            "%26FORMAT=image%2Fpng%26TRANSPARENT=TRUE"
-            "%26WIDTH=460%26HEIGHT=348"
-            "%26EXCEPTIONS=application%2Fvnd.ogc.se_xml"
-            "%26BGCOLOR=0xffffff%26BBOX=0.0,0.0,460.0,348.0"
-            "%26LAYERS=gewaesser%26STYLES=%26SRS=EPSG:4326"
-            "%26SERVICE=WMS"]))
+            "requeststring=VERSION=1.1.1%26REQUEST=GetCapabilities"
+                           "%26SERVICE=WMS"]))
         self.send_formdata_request("&".join([
             "user=karl", "responsetime=2007-06-01T12:14:17Z",
             "wmsidextern=example.com%2Fcgi-bin%2Ffridawms",
             "wmsidintern=localhost%2Fcgi-bin%2Fmyfrida",
-            "requeststring=VERSION=1.1.1%26REQUEST=GetCapabilities"
+            "requeststring=VERSION=1.1.1%26REQUEST=GetMap"
             "%26FORMAT=image%2Fpng%26TRANSPARENT=TRUE"
             "%26WIDTH=460%26HEIGHT=348"
             "%26EXCEPTIONS=application%2Fvnd.ogc.se_xml"
             "%26BGCOLOR=0xffffff%26BBOX=0.0,0.0,460.0,348.0"
             "%26LAYERS=gewaesser%26STYLES=%26SRS=EPSG:4326"
             "%26SERVICE=WMS"]))
-
         self.dbrequest_event.wait(1)
         self.assertEquals(len(self.dbrequests), 1)
         self.check_attributes(self.dbrequests[0],



More information about the Osaas-commits mailing list