Describe the bug
Currently when creating the transport, the transport is initialized by doing a ping request to /v2, which may return a bearer challenge with no scopes. When making further requests, if the client gets a 401 for insufficient scope, the new scopes returned by the new bearer challenge are added to the list of scopes seen so far and the token is refreshed.
This is bad for two reasons:
To Reproduce
Initialize a transport with no initial scopes and attempt to pull a container from a harbor registry. We get a 401 regardless of having the correct auth material to exchange for tokens.
Expected behavior
We should be able to pull containers from harbor registries that use bearer tokens.
Additional context
- Version of the module: main branch as of June 23, 2023
- Registry used: harbor
Proposal
I believe the correct approach would be to implement a cache of tokens that is a map of set<scope> to token. Whenever a new request is attempted, do a request with no auth material to retrieve the bearer challenge with the required scopes. Check if we already have a token for that specific set of scopes and, if not, run the refresh workflow.
This can be done without breaking the existing API by conditioning the feature on a WithScopedTokens option in the transport constructor.
Describe the bug
Currently when creating the transport, the transport is initialized by doing a ping request to
/v2, which may return a bearer challenge with no scopes. When making further requests, if the client gets a 401 for insufficient scope, the new scopes returned by the new bearer challenge are added to the list of scopes seen so far and the token is refreshed.This is bad for two reasons:
To Reproduce
Initialize a transport with no initial scopes and attempt to pull a container from a harbor registry. We get a 401 regardless of having the correct auth material to exchange for tokens.
Expected behavior
We should be able to pull containers from harbor registries that use bearer tokens.
Additional context
Proposal
I believe the correct approach would be to implement a cache of tokens that is a map of
set<scope>totoken. Whenever a new request is attempted, do a request with no auth material to retrieve the bearer challenge with the required scopes. Check if we already have a token for that specific set of scopes and, if not, run the refresh workflow.This can be done without breaking the existing API by conditioning the feature on a
WithScopedTokensoption in the transport constructor.