diff --git a/nova/api/openstack/placement/handler.py b/nova/api/openstack/placement/handler.py index e0070769ebc4..8a6d8ad5f9bd 100644 --- a/nova/api/openstack/placement/handler.py +++ b/nova/api/openstack/placement/handler.py @@ -35,7 +35,7 @@ from nova.api.openstack.placement.handlers import root from nova.api.openstack.placement.handlers import usage from nova.api.openstack.placement import util from nova import exception -from nova.i18n import _LE +from nova.i18n import _, _LE LOG = logging.getLogger(__name__) @@ -154,6 +154,21 @@ class PlacementHandler(object): raise webob.exc.HTTPForbidden( 'admin required', json_formatter=util.json_error_formatter) + # Check that an incoming write-oriented request method has + # the required content-type header. If not raise a 400. If + # this doesn't happen here then webob.dec.wsgify (elsewhere + # in the stack) will raise an uncaught KeyError. Since that + # is such a generic exception we cannot merely catch it + # here, we need to avoid it ever happening. + # TODO(cdent): Move this and the auth checking above into + # middleware. It shouldn't be here. This is for dispatch not + # validation or authorization. + request_method = environ['REQUEST_METHOD'].upper() + if request_method in ('POST', 'PUT', 'PATCH'): + if 'CONTENT_TYPE' not in environ: + raise webob.exc.HTTPBadRequest( + _('content-type header required'), + json_formatter=util.json_error_formatter) try: return dispatch(environ, start_response, self._map) # Trap the small number of nova exceptions that aren't diff --git a/nova/tests/functional/api/openstack/placement/gabbits/basic-http.yaml b/nova/tests/functional/api/openstack/placement/gabbits/basic-http.yaml index 91efd558551d..00757ebba5c5 100644 --- a/nova/tests/functional/api/openstack/placement/gabbits/basic-http.yaml +++ b/nova/tests/functional/api/openstack/placement/gabbits/basic-http.yaml @@ -73,6 +73,11 @@ tests: data: I want a resource provider please status: 415 +- name: post resource provider missing content-type + POST: /resource_providers + data: I want a resource provider please + status: 400 + - name: post resource provider schema mismatch POST: /resource_providers request_headers: diff --git a/nova/tests/functional/api/openstack/placement/gabbits/microversion.yaml b/nova/tests/functional/api/openstack/placement/gabbits/microversion.yaml index 4fe986ea5529..a23effcabfcf 100644 --- a/nova/tests/functional/api/openstack/placement/gabbits/microversion.yaml +++ b/nova/tests/functional/api/openstack/placement/gabbits/microversion.yaml @@ -73,7 +73,10 @@ tests: - "invalid version string: 1.2.3" - name: error in application produces microversion headers + desc: we do not want xml POST: / + request_headers: + content-type: application/xml status: 405 response_headers: openstack-api-version: placement 1.0