Skip to content

Commit

Permalink
Middleware to pass user token to API server
Browse files Browse the repository at this point in the history
Change-Id: Icb81bc1e9ebe57ff07fa2d3c427061b2eef4ed61
  • Loading branch information
Deepinder Setia committed Apr 17, 2015
1 parent 983d9a2 commit 1b1b33d
Show file tree
Hide file tree
Showing 3 changed files with 51 additions and 2 deletions.
1 change: 1 addition & 0 deletions SConscript
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ sources = [
'neutron_plugin_contrail/plugins/opencontrail/contrail_plugin_ipam.py',
'neutron_plugin_contrail/plugins/opencontrail/contrail_plugin_policy.py',
'neutron_plugin_contrail/plugins/opencontrail/contrail_plugin_vpc.py',
'neutron_plugin_contrail/plugins/opencontrail/neutron_middleware.py',
'neutron_plugin_contrail/plugins/opencontrail/loadbalancer/__init__.py',
'neutron_plugin_contrail/plugins/opencontrail/loadbalancer/loadbalancer_db.py',
'neutron_plugin_contrail/plugins/opencontrail/loadbalancer/loadbalancer_healthmonitor.py',
Expand Down
14 changes: 12 additions & 2 deletions neutron_plugin_contrail/plugins/opencontrail/contrail_plugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@
from oslo_log import log as logging

from simplejson import JSONDecodeError
from eventlet.greenthread import getcurrent

LOG = logging.getLogger(__name__)

Expand All @@ -55,9 +56,11 @@
help='Enable Contrail extensions(policy, ipam)'),
]


class InvalidContrailExtensionError(exc.ServiceUnavailable):
message = _("Invalid Contrail Extension: %(ext_name) %(ext_class)")


class NeutronPluginContrailCoreV2(neutron_plugin_base_v2.NeutronPluginBaseV2,
securitygroup.SecurityGroupPluginBase,
portbindings_base.PortBindingBaseMixin,
Expand Down Expand Up @@ -171,9 +174,16 @@ def _request_api_server(self, url, data=None, headers=None):
return response

def _request_api_server_authn(self, url, data=None, headers=None):
# forward user token to API server for RBAC
# token saved earlier in the pipeline
try:
auth_token = getcurrent().contrail_vars.token
except AttributeError:
auth_token = None

authn_headers = headers or {}
if self._authn_token is not None:
authn_headers['X-AUTH-TOKEN'] = self._authn_token
if auth_token or self._authn_token:
authn_headers['X-AUTH-TOKEN'] = auth_token or self._authn_token
response = self._request_api_server(url, data, headers=authn_headers)
return response

Expand Down
38 changes: 38 additions & 0 deletions neutron_plugin_contrail/plugins/opencontrail/neutron_middleware.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import logging

from eventlet import corolocal
from eventlet.greenthread import getcurrent

"""
This middleware is used to forward user token to Contrail API server.
Middleware is inserted at head of Neutron pipeline via api-paste.ini file
so that user token can be preserved in local storage of Neutron thread.
This is needed because neutron will later remove the user token before control
finally reaches Contrail plugin. Contrail plugin will retreive the user token
from thread's local storage and pass it to API server via X-AUTH-TOKEN header.
"""


class UserToken(object):
def __init__(self, app, conf):
self._logger = logging.getLogger(__name__)
self._app = app
self._conf = conf

def __call__(self, env, start_response):
# preserve user token for later forwarding to contrail API server
cur_greenlet = getcurrent()
cur_greenlet.contrail_vars = corolocal.local()
cur_greenlet.contrail_vars.token = env.get('HTTP_X_AUTH_TOKEN')
return self._app(env, start_response)


def token_factory(global_conf, **local_conf):
"""Paste factory."""

conf = global_conf.copy()
conf.update(local_conf)

def _factory(app):
return UserToken(app, conf)
return _factory

0 comments on commit 1b1b33d

Please sign in to comment.