Problem 1: avoid using a browser.
The first important thing to understand is that originally, OAuth2 was designed for access to third-party APIs, so security flows and models are designed to be used by a third party.
However, if applicable, it seems that OAuth2 tokens will only be used by your application.
The authorization code flow is, in fact, the recommended flow for native mobile applications by RFCs. The main security mechanisms established are:
- Use of a redirect URI, to ensure that only the intended application receives the tokens
- Use of an authorization token, to mitigate the risks of token interception between the browser and the native application (as opposed to the implicit flow, in which it is sent directly in the URI fragment)
- Use of PKCE, for the same reasons.
However, with respect to the first point:
– Custom URL scheme: you cannot guarantee that another application on the device claims the custom URI scheme
– Universal URI: it implies a bad user interface and additional complexity
Using the authorization code flow has 3 benefits:
– Single Sign-On (SSO) with other native or web applications that use the same authentication service
– Allow third-party applications to use your authentication service (the OAuth2 form) without filtering user credentials (such as password) to the third-party application
– Some authentication schemes are only available in the browser, such as WebAuthn
However, if it is an application of the tour, and does not need SSO, and believes that the native UI is better, then my opinion is that it is acceptable from a security perspective. You can use the OAuth2 resource owner's Password credentials if you only need login / password authentication, otherwise you will need to extend this OAuth2 flow or implement it yourself.
Note that since you do not use redirect URIs at all and a mobile application is not able to keep a secret, well, secret (called
public client in the terminology of OAuth2), you basically cannot guarantee that it is really your native application that calls your authentication endpoint.
Therefore, it has 2 solutions:
– Enter your request with a secret. For example, it could be a secret embedded in a QR code that is sent by letter to your customer
– Protect your authentication API against brute force attacks and apply strict acceleration limits. Also, do not allow weak passwords and / or request a second factor for more confidential data
But since it is your application, and you are unlikely to install a keylogger in your own application (!), I don't see any point to crack the PIN (by the way, weak password with low entropy). If your mobile operating system is hacked and the "virus" has access to the memory and code of your application, there is nothing you can do anyway.
Problem 2: keep the access token safe.
The best practice is to keep the update token in KeyChain and the access token In Memory. When the access token is lost or expires, just request a new one using the access token.
To mitigate the risks of stolen tokens for confidential data, you can:
* limit the lifespan of such tokens
* request a second factor for such tokens
* Cryptographically link them to the calling application. This mechanism is called Possession Test (PoP) and is surprisingly still experimental. You can find more information at: enter the link description here and enter the link description here