Skip to content

Commit

Permalink
Optionally use "name" for auth body attributes intead of "id"
Browse files Browse the repository at this point in the history
This seems to be more compatible with providers, and is in the example provided on the openstack website: https://docs.openstack.org/api-ref/identity/v3/?expanded=password-authentication-with-unscoped-authorization-detail#password-authentication-with-unscoped-authorization

Co-authored-by: Daniel Jagszent <[email protected]>
Co-authored-by: Les Green <[email protected]>
  • Loading branch information
3 people authored Oct 23, 2020
1 parent f9b6e39 commit b53a77d
Show file tree
Hide file tree
Showing 5 changed files with 38 additions and 6 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -18,3 +18,4 @@ __pycache__/
/tests/.pytest_cache/
/tests/test.log
/tests/test_crit.log
/.history
2 changes: 2 additions & 0 deletions Changes.txt
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
UNRELEASED CHANGES
* Added ability to specify domain-name, project-domain-name and tenant-name as options
for the OpenStack Swift (Keystone v3) backend for providers that prefer name to id.

* The open() syscall supports the O_TRUNC flag now.

Expand Down
20 changes: 20 additions & 0 deletions rst/backends.rst
Original file line number Diff line number Diff line change
Expand Up @@ -269,6 +269,12 @@ The OpenStack backend accepts the following backend options:
If your provider did not give you a domain ID, then it is most likely
:var:`default`.

.. option:: domain-is-name

If your provider only supplies you with the name of your domain and not the uuid,
you need to set this :var:`domain-is-name` option, whereby the :var:`domain` is used as the domain name,
not the domain id.

.. option:: project-domain

In simple cases, the project domain will be the same as the auth
Expand All @@ -278,6 +284,20 @@ The OpenStack backend accepts the following backend options:
If your provider did not give you a domain ID, then it is most likely
:var:`default`.

.. option:: project-domain-is-name

If your provider only supplies you with the name of your project domain and not the uuid,
you need to set this :var:`project-domain-name` option, whereby the :var:`project-domain` is used
as the name of the project domain, not the id of the project domain.
If project-domain-is-name is not set, it is assumed the same as domain-is-name.

.. option:: tenant-is-name

Some providers use the tenant name to specify the storage location, and others use the tenant id.
If your provider uses the tenant name and not the id, you need to set this :var:`tenant-is-name` option.
If :var:`tenant-is-name` is provided, the :var:`<tenant>` component of the login is used as the tenant
name, not the tenant id.

.. __: http://tools.ietf.org/html/rfc2616#section-8.2.3
.. _OpenStack: http://www.openstack.org/
.. _Swift: http://openstack.org/projects/storage/
Expand Down
3 changes: 1 addition & 2 deletions src/s3ql/backends/swift.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,8 +39,7 @@ class Backend(AbstractBackend, metaclass=ABCDocstMeta):

hdr_prefix = 'X-Object-'
known_options = {'no-ssl', 'ssl-ca-path', 'tcp-timeout',
'disable-expect100', 'no-feature-detection',
'domain', 'project_domain'}
'disable-expect100', 'no-feature-detection'}

_add_meta_headers = s3c.Backend._add_meta_headers
_extractmeta = s3c.Backend._extractmeta
Expand Down
18 changes: 14 additions & 4 deletions src/s3ql/backends/swiftks.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@

class Backend(swift.Backend):

# Add the options for the v3 keystore swift.
known_options = swift.Backend.known_options | {'domain', 'project-domain', 'project-domain-is-name', 'domain-is-name', 'tenant-is-name'}

def __init__(self, options):
self.region = None
super().__init__(options)
Expand Down Expand Up @@ -76,15 +79,22 @@ def _get_conn(self):
tenant = None
user = self.login

# We can optionally configure with tenant name instead of id.
tenant_is_name = 'tenant-is-name' in self.options

# We can configure with domain as id or name.
domain = self.options.get('domain', None)
domain_is_name = 'domain-is-name' in self.options
if domain:
if not tenant:
raise ValueError("Tenant is required when Keystone v3 is used")

# In simple cases where there's only one domain, the project domain
# will be the same as the authentication domain, but this option
# allows for them to be different
# We can configure with project-domain as id or name
project_domain = self.options.get('project-domain', domain)
project_domain_is_name = ('project-domain-is-name' in self.options) or domain_is_name

auth_body = {
'auth': {
Expand All @@ -94,17 +104,17 @@ def _get_conn(self):
'user': {
'name': user,
'domain': {
'id': domain
('name' if domain_is_name else 'id'): domain
},
'password': self.password
}
}
},
'scope': {
'project': {
'id': tenant,
('name' if tenant_is_name else 'id'): tenant,
'domain': {
'id': project_domain
('name' if project_domain_is_name else 'id'): project_domain
}
}
}
Expand Down Expand Up @@ -141,7 +151,7 @@ def _get_conn(self):

cat = json.loads(conn.read().decode('utf-8'))

if self.options.get('domain', None):
if self.options.get('domain', None) or self.options.get('domain-name', None):
self.auth_token = resp.headers['X-Subject-Token']
service_catalog = cat['token']['catalog']
else:
Expand Down

0 comments on commit b53a77d

Please sign in to comment.