Skip to content

Commit

Permalink
Add sig_v5 support to duo_client_python calls and v2 integrations han…
Browse files Browse the repository at this point in the history
…dler (#188)

* Add sig_v5 support to duo_client_python calls and update integrations to v2 handler

* Fix billing tests

* Update docstring for integrations to
call out that sso feature is not released

---------

Co-authored-by: Jamie Pringle <[email protected]>
  • Loading branch information
jpringle03 and jpringle03 authored Feb 10, 2023
1 parent f6c9cd6 commit 42a5a1d
Show file tree
Hide file tree
Showing 12 changed files with 425 additions and 125 deletions.
85 changes: 69 additions & 16 deletions duo_client/admin.py
Original file line number Diff line number Diff line change
Expand Up @@ -216,11 +216,43 @@

class Admin(client.Client):
account_id = None
admin_sig_version = 5

def api_call(self, method, path, params):
def api_call(self, method, path, params, sig_version=admin_sig_version):
if self.account_id is not None:
params['account_id'] = self.account_id
return super(Admin, self).api_call(method, path, params)
return super(Admin, self).api_call(
method,
path,
params,
sig_version=sig_version
)

def json_api_call(self, method, path, params, sig_version=admin_sig_version):
return super(Admin, self).json_api_call(
method,
path,
params,
sig_version=sig_version
)

def json_paging_api_call(self, method, path, params, sig_version=admin_sig_version):
return super(Admin, self).json_paging_api_call(
method,
path,
params,
sig_version=sig_version
)

def json_cursor_api_call(self, method, path, params, get_records_func, sig_version=admin_sig_version):
return super(Admin, self).json_cursor_api_call(
method,
path,
params,
get_records_func,
sig_version=sig_version
)


@classmethod
def _canonicalize_ip_whitelist(klass, ip_whitelist):
Expand Down Expand Up @@ -2378,8 +2410,8 @@ def get_integrations_generator(self):
"""
return self.json_paging_api_call(
'GET',
'/admin/v1/integrations',
{}
'/admin/v2/integrations',
{},
)

def get_integrations(self, limit=None, offset=0):
Expand All @@ -2398,8 +2430,8 @@ def get_integrations(self, limit=None, offset=0):
if limit:
return self.json_api_call(
'GET',
'/admin/v1/integrations',
{'limit': limit, 'offset': offset}
'/admin/v2/integrations',
{'limit': limit, 'offset': offset},
)

return list(self.get_integrations_generator())
Expand All @@ -2417,8 +2449,8 @@ def get_integration(self, integration_key):
params = {}
response = self.json_api_call(
'GET',
'/admin/v1/integrations/' + integration_key,
params
'/admin/v2/integrations/' + integration_key,
params,
)
return response

Expand All @@ -2441,7 +2473,8 @@ def create_integration(self,
ip_whitelist=None,
ip_whitelist_enroll_policy=None,
groups_allowed=None,
self_service_allowed=None):
self_service_allowed=None,
sso=None):
"""Creates a new integration.
name - The name of the integration (required)
Expand All @@ -2467,6 +2500,9 @@ def create_integration(self,
adminapi_write_resource - <bool:write resource permission>|None
groups_allowed - <str: CSV list of gkeys of groups allowed to auth>
self_service_allowed - <bool: self service permission>|None
sso - <dict: parameters for generic single sign-on> (optional)
New argument for unreleased feature. Will return an error if used.
Client will be updated again in the future when feature is released.
Returns the created integration.
Expand Down Expand Up @@ -2514,9 +2550,12 @@ def create_integration(self,
params['groups_allowed'] = groups_allowed
if self_service_allowed is not None:
params['self_service_allowed'] = '1' if self_service_allowed else '0'
if sso is not None:
params['sso'] = sso
response = self.json_api_call('POST',
'/admin/v1/integrations',
params)
'/admin/v2/integrations',
params,
)
return response

def delete_integration(self, integration_key):
Expand All @@ -2528,8 +2567,12 @@ def delete_integration(self, integration_key):
"""
integration_key = six.moves.urllib.parse.quote_plus(str(integration_key))
path = '/admin/v1/integrations/%s' % integration_key
return self.json_api_call('DELETE', path, {})
path = '/admin/v2/integrations/%s' % integration_key
return self.json_api_call(
'DELETE',
path,
{},
)

def update_integration(self,
integration_key,
Expand All @@ -2551,7 +2594,8 @@ def update_integration(self,
ip_whitelist=None,
ip_whitelist_enroll_policy=None,
groups_allowed=None,
self_service_allowed=None):
self_service_allowed=None,
sso=None):
"""Updates an integration.
integration_key - The key of the integration to update. (required)
Expand All @@ -2576,6 +2620,9 @@ def update_integration(self,
reset_secret_key - <any value>|None
groups_allowed - <str: CSV list of gkeys of groups allowed to auth>
self_service_allowed - True|False|None
sso - <dict: parameters for generic single sign-on> (optional)
New argument for unreleased feature. Will return an error if used.
Client will be updated again in the future when feature is released.
If any value other than None is provided for 'reset_secret_key'
(for example, 1), then a new secret key will be generated for the
Expand All @@ -2587,7 +2634,7 @@ def update_integration(self,
"""
integration_key = six.moves.urllib.parse.quote_plus(str(integration_key))
path = '/admin/v1/integrations/%s' % integration_key
path = '/admin/v2/integrations/%s' % integration_key
params = {}
if name is not None:
params['name'] = name
Expand Down Expand Up @@ -2629,11 +2676,17 @@ def update_integration(self,
params['groups_allowed'] = groups_allowed
if self_service_allowed is not None:
params['self_service_allowed'] = '1' if self_service_allowed else '0'
if sso is not None:
params['sso'] = sso

if not params:
raise TypeError("No new values were provided")

response = self.json_api_call('POST', path, params)
response = self.json_api_call(
'POST',
path,
params,
)
return response

def get_admins(self, limit=None, offset=0):
Expand Down
Loading

0 comments on commit 42a5a1d

Please sign in to comment.