Skip to content

feat(IamAssumeAuthenticator): introduce a new authenticator #211

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 12 commits into from
Oct 15, 2024
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
88 changes: 83 additions & 5 deletions .secrets.baseline
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"files": "package-lock.json|^.secrets.baseline$",
"lines": null
},
"generated_at": "2024-09-16T18:49:02Z",
"generated_at": "2024-10-08T13:48:47Z",
"plugins_used": [
{
"name": "AWSKeyDetector"
Expand Down Expand Up @@ -70,23 +70,55 @@
"hashed_secret": "91dfd9ddb4198affc5c194cd8ce6d338fde470e2",
"is_secret": false,
"is_verified": false,
"line_number": 65,
"line_number": 66,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "4f51cde3ac0a5504afa4bc06859b098366592c19",
"is_secret": false,
"is_verified": false,
"line_number": 207,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "e87559ed7decb62d0733ae251ae58d42a55291d8",
"is_secret": false,
"is_verified": false,
"line_number": 209,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "12f4a68ed3d0863e56497c9cdb1e2e4e91d5cb68",
"is_secret": false,
"is_verified": false,
"line_number": 273,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "c837b75d7cd93ef9c2243ca28d6e5156259fd253",
"is_secret": false,
"is_verified": false,
"line_number": 277,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "98635b2eaa2379f28cd6d72a38299f286b81b459",
"is_secret": false,
"is_verified": false,
"line_number": 387,
"line_number": 502,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "47fcf185ee7e15fe05cae31fbe9e4ebe4a06a40d",
"is_secret": false,
"is_verified": false,
"line_number": 482,
"line_number": 597,
"type": "Secret Keyword",
"verified_result": null
}
Expand All @@ -96,7 +128,7 @@
"hashed_secret": "fdee05598fdd57ff8e9ae29e92c25a04f2c52fa6",
"is_secret": false,
"is_verified": false,
"line_number": 30,
"line_number": 31,
"type": "Secret Keyword",
"verified_result": null
}
Expand Down Expand Up @@ -151,6 +183,16 @@
"verified_result": null
}
],
"resources/ibm-credentials-iam-assume.env": [
{
"hashed_secret": "f2e7745f43b0ef0e2c2faf61d6c6a28be2965750",
"is_secret": false,
"is_verified": false,
"line_number": 2,
"type": "Secret Keyword",
"verified_result": null
}
],
"resources/ibm-credentials-iam.env": [
{
"hashed_secret": "b9cad336062c0dc3bb30145b1a6697fccfe755a6",
Expand Down Expand Up @@ -299,6 +341,42 @@
"verified_result": null
}
],
"test/test_iam_assume_authenticator.py": [
{
"hashed_secret": "4080eeeaf54faf879b9e8d99c49a8503f7e855bb",
"is_secret": false,
"is_verified": false,
"line_number": 97,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "37e94c31b6a756ba2afd2fe9a9765172cd79ac47",
"is_secret": false,
"is_verified": false,
"line_number": 170,
"type": "Secret Keyword",
"verified_result": null
},
{
"hashed_secret": "da2f27d2c57a0e1ed2dc3a34b4ef02faf2f7a4c2",
"is_secret": false,
"is_verified": false,
"line_number": 191,
"type": "Hex High Entropy String",
"verified_result": null
}
],
"test/test_iam_assume_token_manager.py": [
{
"hashed_secret": "da2f27d2c57a0e1ed2dc3a34b4ef02faf2f7a4c2",
"is_secret": false,
"is_verified": false,
"line_number": 55,
"type": "Hex High Entropy String",
"verified_result": null
}
],
"test/test_iam_authenticator.py": [
{
"hashed_secret": "4080eeeaf54faf879b9e8d99c49a8503f7e855bb",
Expand Down
155 changes: 135 additions & 20 deletions Authentication.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@
The python-sdk-core project supports the following types of authentication:
- Basic Authentication
- Bearer Token Authentication
- Identity and Access Management (IAM) Authentication
- Identity and Access Management (IAM) Authentication (grant type: apikey)
- Identity and Access Management (IAM) Authentication (grant type: assume)
- Container Authentication
- VPC Instance Authentication
- Cloud Pak for Data Authentication
Expand All @@ -16,7 +17,7 @@ to understand which authenticators are supported for that service.

The python-sdk-core allows an authenticator to be specified in one of two ways:
1. programmatically - the SDK user invokes the appropriate function(s) to create an instance of the
desired authenticator and then passes the authenticator instance when constructing an instance of the service.
desired authenticator and then passes the authenticator instance when constructing an instance of the service client.
2. configuration - the SDK user provides external configuration information (in the form of environment variables
or a credentials file) to indicate the type of authenticator, along with the configuration of the necessary properties for that authenticator. The SDK user then invokes the configuration-based service client constructor method to construct an instance of the authenticator and service client that reflect the external configuration information.

Expand All @@ -26,7 +27,7 @@ which will include the following:
- The properties associated with the authenticator
- An example of how to construct the authenticator programmatically
- An example of how to configure the authenticator through the use of external
configuration information. The configuration examples below will use
configuration information. The configuration examples below will use
environment variables, although the same properties could be specified in a
credentials file instead.

Expand Down Expand Up @@ -122,16 +123,16 @@ service = ExampleServiceV1.new_instance(service_name='example_service')

Note that the use of external configuration is not as useful with the `BearerTokenAuthenticator` as it
is for other authenticator types because bearer tokens typically need to be obtained and refreshed
programmatically since they normally have a relatively short lifespan before they expire. This
programmatically since they normally have a relatively short lifespan before they expire. This
authenticator type is intended for situations in which the application will be managing the bearer
token itself in terms of initial acquisition and refreshing as needed.


## Identity and Access Management (IAM) Authentication
The `IamAuthenticator` will accept a user-supplied api key and will perform
## Identity and Access Management (IAM) Authentication (grant type: apikey)
The `IamAuthenticator` will accept a user-supplied apikey and will perform
the necessary interactions with the IAM token service to obtain a suitable
bearer token for the specified api key. The authenticator will also obtain
a new bearer token when the current token expires. The bearer token is
bearer token for the specified apikey. The authenticator will also obtain
a new bearer token when the current token expires. The bearer token is
then added to each outbound request in the `Authorization` header in the
form:
```
Expand All @@ -140,7 +141,7 @@ form:

### Properties

- apikey: (required) the IAM api key
- apikey: (required) the IAM api key to be used to obtain an IAM access token.

- url: (optional) The base endpoint URL of the IAM token service.
The default value of this property is the "prod" IAM token service endpoint
Expand All @@ -157,7 +158,7 @@ endpoint as well (`https://iam.test.cloud.ibm.com`).

- client_id/client_secret: (optional) The `client_id` and `client_secret` fields are used to form a
"basic auth" Authorization header for interactions with the IAM token server. If neither field
is specified, then no Authorization header will be sent with token server requests. These fields
is specified, then no Authorization header will be sent with token server requests. These fields
are optional, but must be specified together.

- scope: (optional) the scope to be associated with the IAM access token.
Expand Down Expand Up @@ -199,6 +200,120 @@ service = ExampleServiceV1.new_instance(service_name='example_service')
```


## Identity and Access Management (IAM) Authentication (grant type: assume)
The `IAMAssumeAuthenticator` performs a two-step token fetch sequence to obtain
a bearer token that allows the application to assume the identity of a trusted profile:
1. First, the authenticator obtains an initial bearer token using grant type
`urn:ibm:params:oauth:grant-type:apikey`.
This initial token will reflect the identity associated with the input apikey.
2. Second, the authenticator uses the grant type `urn:ibm:params:oauth:grant-type:assume` to obtain a bearer token
that reflects the identity of the trusted profile, passing in the initial bearer token
from the first step, along with the trusted profile-related inputs.

The authenticator will also obtain a new bearer token when the current token expires.
The bearer token is then added to each outbound request in the `Authorization` header in the
form:
```
Authorization: Bearer <bearer-token>
```

### Properties

- apikey: (required) the IAM apikey to be used to obtain the initial IAM access token.

- iam_profile_crn: (optional) the Cloud Resource Name (CRN) associated with the trusted profile
for which an access token should be fetched.
Exactly one of iam_profile_crn, iam_profile_id or iam_profile_name must be specified.

- iam_profile_id: (optional) the ID associated with the trusted profile
for which an access token should be fetched.
Exactly one of iam_profile_crn, iam_profile_id or iam_profile_name must be specified.

- iam_profile_name: (optional) the name associated with the trusted profile
for which an access token should be fetched. When specifying this property, you must also
specify the iam_account_id property as well.
Exactly one of iam_profile_crn, iam_profile_id or iam_profile_name must be specified.

- iam_account_id: (optional) the ID associated with the IAM account that contains the trusted profile
referenced by the iam_profile_name property. The imaAccountId property must be specified if and only if
the iam_profile_name property is specified.

- url: (optional) The base endpoint URL of the IAM token service.
The default value of this property is the "prod" IAM token service endpoint
(`https://iam.cloud.ibm.com`).
Make sure that you use an IAM token service endpoint that is appropriate for the
location of the service being used by your application.
For example, if you are using an instance of a service in the "production" environment
(e.g. `https://resource-controller.cloud.ibm.com`),
then the default "prod" IAM token service endpoint should suffice.
However, if your application is using an instance of a service in the "staging" environment
(e.g. `https://resource-controller.test.cloud.ibm.com`),
then you would also need to configure the authenticator to use the IAM token service "staging"
endpoint as well (`https://iam.test.cloud.ibm.com`).

- client_id/client_secret: (optional) The `client_id` and `client_secret` fields are used to form a
"basic auth" Authorization header for interactions with the IAM token server when fetching the
initial IAM access token. These fields are optional, but must be specified together.

- scope: (optional) the scope to be used when obtaining the initial IAM access token.
If not specified, then no scope will be associated with the access token.

- disable_ssl_verification: (optional) A flag that indicates whether verification of the server's SSL
certificate should be disabled or not. The default value is `false`.

- headers: (optional) A set of key/value pairs that will be sent as HTTP headers in requests
made to the IAM token service.

### Usage Notes
- The IAMAssumeAuthenticator is used to obtain an access token (a bearer token) from the IAM token service
that allows an application to "assume" the identity of a trusted profile.

- The authenticator first uses the apikey, url, client_id/client_secret, scope, disable_ssl_verification, and headers
properties to obtain an initial access token by invoking the IAM `get_token`
(grant_type=`urn:ibm:params:oauth:grant-type:apikey`) operation.

- The authenticator then uses the initial access token along with the url, iam_profile_crn, iam_profile_id,
iam_profile_name, iam_account_id, disable_ssl_verification, and headers properties to obtain an access token by invoking
the IAM `get_token` (grant_type=`urn:ibm:params:oauth:grant-type:assume`) operation.
The access token resulting from this second step will reflect the identity of the specified trusted profile.

- When providing the trusted profile information, you must specify exactly one of: iam_profile_crn, iam_profile_id
or iam_profile_name. If you specify iam_profile_crn or iam_profile_id, then the trusted profile must exist in the same account that is
associated with the input apikey. If you specify iam_profile_name, then you must also specify the iam_account_id property
to indicate the IAM account in which the named trusted profile can be found.

### Programming example
```python
from ibm_cloud_sdk_core.authenticators import IAMAssumeAuthenticator
from <sdk-package-name>.example_service_v1 import *

# Create the authenticator.
authenticator = IAMAssumeAuthenticator('myapikey')

# Construct the service instance.
service = ExampleServiceV1(authenticator=authenticator)

# 'service' can now be used to invoke operations.
```

### Configuration example
External configuration:
```
export EXAMPLE_SERVICE_AUTH_TYPE=iamAssume
export EXAMPLE_SERVICE_APIKEY=myapikey
export EXAMPLE_SERVICE_IAM_PROFILE_ID=myprofile-1
```
Application code:
```python
from <sdk-package-name>.example_service_v1 import *

# Construct the service instance.
service = ExampleServiceV1.new_instance(service_name='example_service')

# 'service' can now be used to invoke operations.
```


## Container Authentication
The `ContainerAuthenticator` is intended to be used by application code
running inside a compute resource managed by the IBM Kubernetes Service (IKS)
Expand All @@ -207,7 +322,7 @@ within the compute resource's local file system.
The CR token is similar to an IAM apikey except that it is managed automatically by
the compute resource provider (IKS).
This allows the application developer to:
- avoid storing credentials in application code, configuraton files or a password vault
- avoid storing credentials in application code, configuration files or a password vault
- avoid managing or rotating credentials

The `ContainerAuthenticator` will retrieve the CR token from
Expand Down Expand Up @@ -251,7 +366,7 @@ endpoint as well (`https://iam.test.cloud.ibm.com`).

- client_id/client_secret: (optional) The `client_id` and `client_secret` fields are used to form a
"basic auth" Authorization header for interactions with the IAM token server. If neither field
is specified, then no Authorization header will be sent with token server requests. These fields
is specified, then no Authorization header will be sent with token server requests. These fields
are optional, but must be specified together.

- scope (optional): the scope to be associated with the IAM access token.
Expand Down Expand Up @@ -304,7 +419,7 @@ The compute resource identity feature allows you to assign a trusted IAM profile
This, in turn, allows applications running within the compute resource to take on this identity when interacting with
IAM-secured IBM Cloud services.
This results in a simplified security model that allows the application developer to:
- avoid storing credentials in application code, configuraton files or a password vault
- avoid storing credentials in application code, configuration files or a password vault
- avoid managing or rotating credentials

The `VPCInstanceAuthenticator` will invoke the appropriate operations on the compute resource's locally-available
Expand All @@ -323,11 +438,11 @@ The IAM access token is added to each outbound request in the `Authorization` he
- iam_profile_id: (optional) the id of the linked trusted IAM profile to be used when obtaining the IAM access token.

- url: (optional) The VPC Instance Metadata Service's base URL.
The default value of this property is `http://169.254.169.254`. However, if the VPC Instance Metadata Service is configured
The default value of this property is `http://169.254.169.254`. However, if the VPC Instance Metadata Service is configured
with the HTTP Secure Protocol setting (`https`), then you should configure this property to be `https://api.metadata.cloud.ibm.com`.

Usage Notes:
1. At most one of `iam_profile_crn` or `iam_profile_id` may be specified. The specified value must map
1. At most one of `iam_profile_crn` or `iam_profile_id` may be specified. The specified value must map
to a trusted IAM profile that has been linked to the compute resource (virtual server instance).

2. If both `iam_profile_crn` and `iam_profile_id` are specified, then an error occurs.
Expand Down Expand Up @@ -367,11 +482,11 @@ service = ExampleServiceV1.new_instance(service_name='example_service')
```


## Cloud Pak for Data
## Cloud Pak for Data
The `CloudPakForDataAuthenticator` will accept a user-supplied username value, along with either a
password or apikey, and will
perform the necessary interactions with the Cloud Pak for Data token service to obtain a suitable
bearer token. The authenticator will also obtain a new bearer token when the current token expires.
password or apikey, and will perform the necessary interactions with the Cloud Pak for Data token
service to obtain a suitable bearer token. The authenticator will also obtain a new bearer token
when the current token expires.
The bearer token is then added to each outbound request in the `Authorization` header in the
form:
```
Expand Down Expand Up @@ -449,7 +564,7 @@ form:
- url: (required) The URL representing the MCSP token service endpoint's base URL string. Do not include the
operation path (e.g. `/siusermgr/api/1.0/apikeys/token`) as part of this property's value.

- disable_ssl_verification: (optional) A flag that indicates whether verificaton of the server's SSL
- disable_ssl_verification: (optional) A flag that indicates whether verification of the server's SSL
certificate should be disabled or not. The default value is `false`.

- headers: (optional) A set of key/value pairs that will be sent as HTTP headers in requests
Expand Down
Loading