Repository: Kinto/kinto

Issue:
500 error when json validation fails with additional properties
`<ValidationError: "Additional properties are not allowed ('blockID', 'id' were unexpected)">`

```
  File "/home/mathieu/Code/Mozilla/cliquet/cliquet/resource/__init__.py", line 395, in put
    new_record = self.process_record(post_record, old=existing)
  File "/home/mathieu/Code/Mozilla/kinto/kinto/views/records.py", line 71, in process_record
    field = e.path.pop() if e.path else e.validator_value.pop()
AttributeError: 'bool' object has no attribute 'pop' lang=None uid=67f1f8fc8d3dd228096950c20d6515c4786a675264741bec2995a560519aad87

```

Possible fix:

``` diff
         except jsonschema_exceptions.ValidationError as e:
-            field = e.path.pop() if e.path else e.validator_value.pop()
+            try:
+                field = e.path.pop() if e.path else e.validator_value.pop()
+            except AttributeError:
+                field = None
```

500 error when json validation fails with additional properties
`<ValidationError: "Additional properties are not allowed ('blockID', 'id' were unexpected)">`

```
  File "/home/mathieu/Code/Mozilla/cliquet/cliquet/resource/__init__.py", line 395, in put
    new_record = self.process_record(post_record, old=existing)
  File "/home/mathieu/Code/Mozilla/kinto/kinto/views/records.py", line 71, in process_record
    field = e.path.pop() if e.path else e.validator_value.pop()
AttributeError: 'bool' object has no attribute 'pop' lang=None uid=67f1f8fc8d3dd228096950c20d6515c4786a675264741bec2995a560519aad87

```

Possible fix:

``` diff
         except jsonschema_exceptions.ValidationError as e:
-            field = e.path.pop() if e.path else e.validator_value.pop()
+            try:
+                field = e.path.pop() if e.path else e.validator_value.pop()
+            except AttributeError:
+                field = None
```



Discussion:

Resolving patch:
diff --git a/kinto/views/records.py b/kinto/views/records.py
--- a/kinto/views/records.py
+++ b/kinto/views/records.py
@@ -73,7 +73,10 @@ def process_record(self, new, old=None):
             stripped.pop(self.schema_field, None)
             jsonschema.validate(stripped, schema)
         except jsonschema_exceptions.ValidationError as e:
-            field = e.path.pop() if e.path else e.validator_value.pop()
+            try:
+                field = e.path.pop() if e.path else e.validator_value.pop()
+            except AttributeError:
+                field = None
             raise_invalid(self.request, name=field, description=e.message)
 
         new[self.schema_field] = collection_timestamp


Test patch:
diff --git a/kinto/tests/test_views_collections_schema.py b/kinto/tests/test_views_collections_schema.py
--- a/kinto/tests/test_views_collections_schema.py
+++ b/kinto/tests/test_views_collections_schema.py
@@ -212,3 +212,13 @@ def test_records_are_validated_on_patch(self):
         self.app.patch_json(record_url,
                             {'data': record},
                             headers=self.headers)
+
+    def test_additional_properties_are_rejected(self):
+        record_id = '5443d83f-852a-481a-8e9d-5aa804b05b08'
+        record = VALID_RECORD.copy()
+        record['extra'] = 'blah!'
+        resp = self.app.put_json('%s/%s' % (RECORDS_URL, record_id),
+                                 {'data': record},
+                                 headers=self.headers,
+                                 status=400)
+        assert "'extra' was unexpected)" in resp.json['message']