The OAuthRestTemplate uses authentication information (the OAuth token) when it performs requests to authenticate the client against a server. It retrieves the token from the OAuthSecurityContext by accessing the singleton OAuthSecurityContextHolder which is tied to the current thread. This conforms to other similar patterns where information is associate with threads (especially in web apps).
The following use-case however is rather not so nicely supported:
Using OAuthRestTemplates for backend components which are not directly user-related and therefore do not have a thread per user. For example I implemented a service which needs to access the same resource under two different users to propagate in one logical operation. The second access is writing a piece of information to the service on behalf of the second user - the information itself was retrieved on behalf of the first user - all in the same thread. The procedure is as follows:
1) Replace the original OAuthSecurityContext O1 via OAuthSecurityContextHolder with the OAuthSecurityContext O2 for the first user & backup the original OAuthSecurityContext O1.
2) Perform the first request
3) Replace the 1st OAuthSecurityContext O2 with the OAuthSecurityContext O3 of the second user via OAuthSecurityContextHolder
4) Perform the second request
5) Restore the originally found OAuthSecurityContext O1 via OAuthSecurityContextHolder
Because of the fact that the OAuthRestTemplate implementation exclusively considers the "current" OAuthSecurityContext stored in OAuthSecurityContextHolder as the security context it's not possible to pass in an OAuthSecurityContext per request. Therefore the client code needs to hot-replace the OAuthSecurityContext and afterwards revert OAuthSecurityContext as required by the application process.
That's definitely a source of error especially in terms of security flaws and long running threads if the client code "makes mistakes" when switching security contexts (e.g. forgets to restore the original context after a few requests).
I'd propose that the OAuthSecurityContext could be pass as method argument for a single request which would clearly define and limit the scope of a specific OAuthSecurityContext to the lifetime of a single request. That would provide the following benefits:
- It would be impossible to "forget" by accident a OAuthSecurityContext in the OAuthSecurityContextHolder and perform requests afterwards with "foreign" OAuthSecurityContexts
- issuing multiple requests using multiple OAuthSecurityContexts would be easier and cleaner in terms of code