| < draft-ietf-oauth-native-apps-09.txt | draft-ietf-oauth-native-apps-10.txt > | |||
|---|---|---|---|---|
| OAuth Working Group W. Denniss | OAuth Working Group W. Denniss | |||
| Internet-Draft Google | Internet-Draft Google | |||
| Intended status: Best Current Practice J. Bradley | Intended status: Best Current Practice J. Bradley | |||
| Expires: September 7, 2017 Ping Identity | Expires: October 28, 2017 Ping Identity | |||
| March 6, 2017 | April 26, 2017 | |||
| OAuth 2.0 for Native Apps | OAuth 2.0 for Native Apps | |||
| draft-ietf-oauth-native-apps-09 | draft-ietf-oauth-native-apps-10 | |||
| Abstract | Abstract | |||
| OAuth 2.0 authorization requests from native apps should only be made | OAuth 2.0 authorization requests from native apps should only be made | |||
| through external user-agents, primarily the user's browser. This | through external user-agents, primarily the user's browser. This | |||
| specification details the security and usability reasons why this is | specification details the security and usability reasons why this is | |||
| the case, and how native apps and authorization servers can implement | the case, and how native apps and authorization servers can implement | |||
| this best practice. | this best practice. | |||
| Status of This Memo | Status of This Memo | |||
| skipping to change at page 1, line 35 ¶ | skipping to change at page 1, line 35 ¶ | |||
| Internet-Drafts are working documents of the Internet Engineering | Internet-Drafts are working documents of the Internet Engineering | |||
| Task Force (IETF). Note that other groups may also distribute | Task Force (IETF). Note that other groups may also distribute | |||
| working documents as Internet-Drafts. The list of current Internet- | working documents as Internet-Drafts. The list of current Internet- | |||
| Drafts is at http://datatracker.ietf.org/drafts/current/. | Drafts is at http://datatracker.ietf.org/drafts/current/. | |||
| Internet-Drafts are draft documents valid for a maximum of six months | Internet-Drafts are draft documents valid for a maximum of six months | |||
| and may be updated, replaced, or obsoleted by other documents at any | and may be updated, replaced, or obsoleted by other documents at any | |||
| time. It is inappropriate to use Internet-Drafts as reference | time. It is inappropriate to use Internet-Drafts as reference | |||
| material or to cite them other than as "work in progress." | material or to cite them other than as "work in progress." | |||
| This Internet-Draft will expire on September 7, 2017. | This Internet-Draft will expire on October 28, 2017. | |||
| Copyright Notice | Copyright Notice | |||
| Copyright (c) 2017 IETF Trust and the persons identified as the | Copyright (c) 2017 IETF Trust and the persons identified as the | |||
| document authors. All rights reserved. | document authors. All rights reserved. | |||
| This document is subject to BCP 78 and the IETF Trust's Legal | This document is subject to BCP 78 and the IETF Trust's Legal | |||
| Provisions Relating to IETF Documents | Provisions Relating to IETF Documents | |||
| (http://trustee.ietf.org/license-info) in effect on the date of | (http://trustee.ietf.org/license-info) in effect on the date of | |||
| publication of this document. Please review these documents | publication of this document. Please review these documents | |||
| skipping to change at page 2, line 15 ¶ | skipping to change at page 2, line 15 ¶ | |||
| described in the Simplified BSD License. | described in the Simplified BSD License. | |||
| Table of Contents | Table of Contents | |||
| 1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 2 | 1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 2 | |||
| 2. Notational Conventions . . . . . . . . . . . . . . . . . . . 3 | 2. Notational Conventions . . . . . . . . . . . . . . . . . . . 3 | |||
| 3. Terminology . . . . . . . . . . . . . . . . . . . . . . . . . 3 | 3. Terminology . . . . . . . . . . . . . . . . . . . . . . . . . 3 | |||
| 4. Overview . . . . . . . . . . . . . . . . . . . . . . . . . . 4 | 4. Overview . . . . . . . . . . . . . . . . . . . . . . . . . . 4 | |||
| 4.1. Authorization Flow for Native Apps Using the Browser . . 5 | 4.1. Authorization Flow for Native Apps Using the Browser . . 5 | |||
| 5. Using Inter-app URI Communication for OAuth . . . . . . . . . 6 | 5. Using Inter-app URI Communication for OAuth . . . . . . . . . 6 | |||
| 6. Initiating the Authorization Request from a Native App . . . 6 | 6. Initiating the Authorization Request from a Native App . . . 7 | |||
| 7. Receiving the Authorization Response in a Native App . . . . 7 | 7. Receiving the Authorization Response in a Native App . . . . 7 | |||
| 7.1. App-declared Custom URI Scheme Redirection . . . . . . . 7 | 7.1. Private-use URI Scheme Redirection . . . . . . . . . . . 7 | |||
| 7.2. App-claimed HTTPS URI Redirection . . . . . . . . . . . . 8 | 7.2. Claimed HTTPS URI Redirection . . . . . . . . . . . . . . 8 | |||
| 7.3. Loopback URI Redirection . . . . . . . . . . . . . . . . 9 | 7.3. Loopback Interface Redirection . . . . . . . . . . . . . 9 | |||
| 8. Security Considerations . . . . . . . . . . . . . . . . . . . 9 | 8. Security Considerations . . . . . . . . . . . . . . . . . . . 9 | |||
| 8.1. Embedded User-Agents . . . . . . . . . . . . . . . . . . 9 | 8.1. Protecting the Authorization Code . . . . . . . . . . . . 9 | |||
| 8.2. Non-Browser External User-Agents . . . . . . . . . . . . 10 | 8.2. OAuth Implicit Flow . . . . . . . . . . . . . . . . . . . 10 | |||
| 8.3. Phishability of In-App Browser Tabs . . . . . . . . . . . 10 | 8.3. Loopback Redirect Considerations . . . . . . . . . . . . 10 | |||
| 8.4. Protecting the Authorization Code . . . . . . . . . . . . 11 | 8.4. Registration of Native App Clients . . . . . . . . . . . 11 | |||
| 8.5. OAuth Implicit Flow . . . . . . . . . . . . . . . . . . . 12 | 8.5. Client Authentication . . . . . . . . . . . . . . . . . . 12 | |||
| 8.6. Loopback Redirect Considerations . . . . . . . . . . . . 12 | 8.6. Client Impersonation . . . . . . . . . . . . . . . . . . 12 | |||
| 8.7. Registration of Native App Clients . . . . . . . . . . . 12 | 8.7. Phishability of In-App Browser Tabs . . . . . . . . . . . 12 | |||
| 8.8. Client Authentication . . . . . . . . . . . . . . . . . . 13 | 8.8. Cross-App Request Forgery Protections . . . . . . . . . . 13 | |||
| 8.9. Client Impersonation . . . . . . . . . . . . . . . . . . 13 | 8.9. Authorization Server Mix-Up Mitigation . . . . . . . . . 13 | |||
| 8.10. Cross-App Request Forgery Protections . . . . . . . . . . 14 | 8.10. Non-Browser External User-Agents . . . . . . . . . . . . 13 | |||
| 8.11. Authorization Server Mix-Up Mitigation . . . . . . . . . 14 | 8.11. Embedded User-Agents . . . . . . . . . . . . . . . . . . 14 | |||
| 9. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 14 | 9. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 14 | |||
| 10. References . . . . . . . . . . . . . . . . . . . . . . . . . 15 | 10. References . . . . . . . . . . . . . . . . . . . . . . . . . 15 | |||
| 10.1. Normative References . . . . . . . . . . . . . . . . . . 15 | 10.1. Normative References . . . . . . . . . . . . . . . . . . 15 | |||
| 10.2. Informative References . . . . . . . . . . . . . . . . . 15 | 10.2. Informative References . . . . . . . . . . . . . . . . . 15 | |||
| Appendix A. Server Support Checklist . . . . . . . . . . . . . . 16 | Appendix A. Server Support Checklist . . . . . . . . . . . . . . 16 | |||
| Appendix B. Operating System Specific Implementation Details . . 16 | Appendix B. Operating System Specific Implementation Details . . 16 | |||
| B.1. iOS Implementation Details . . . . . . . . . . . . . . . 17 | B.1. iOS Implementation Details . . . . . . . . . . . . . . . 17 | |||
| B.2. Android Implementation Details . . . . . . . . . . . . . 17 | B.2. Android Implementation Details . . . . . . . . . . . . . 17 | |||
| B.3. Windows Implementation Details . . . . . . . . . . . . . 18 | B.3. Windows Implementation Details . . . . . . . . . . . . . 18 | |||
| B.4. macOS Implementation Details . . . . . . . . . . . . . . 18 | B.4. macOS Implementation Details . . . . . . . . . . . . . . 18 | |||
| skipping to change at page 3, line 37 ¶ | skipping to change at page 3, line 37 ¶ | |||
| "native app" An application that is installed by the user to their | "native app" An application that is installed by the user to their | |||
| device, as distinct from a web app that runs in the browser | device, as distinct from a web app that runs in the browser | |||
| context only. Apps implemented using web-based technology but | context only. Apps implemented using web-based technology but | |||
| distributed as a native app, so-called hybrid apps, are considered | distributed as a native app, so-called hybrid apps, are considered | |||
| equivalent to native apps for the purpose of this specification. | equivalent to native apps for the purpose of this specification. | |||
| "OAuth" In this document, OAuth refers to OAuth 2.0 [RFC6749]. | "OAuth" In this document, OAuth refers to OAuth 2.0 [RFC6749]. | |||
| "external user-agent" A user-agent capable of handling the | "external user-agent" A user-agent capable of handling the | |||
| authorization request that is a separate entity to the native app | authorization request that is a separate entity or security domain | |||
| making the request (such as a browser), such that the app cannot | to the native app making the request (such as a browser), such | |||
| access the cookie storage or modify the page content. | that the app cannot access the cookie storage, nor inspect or | |||
| modify page content. | ||||
| "embedded user-agent" A user-agent hosted inside the native app | "embedded user-agent" A user-agent hosted inside the native app | |||
| itself (such as via a web-view), with which the app has control | itself (such as via a web-view), with which the app has control | |||
| over to the extent it is capable of accessing the cookie storage | over to the extent it is capable of accessing the cookie storage | |||
| and/or modify the page content. | and/or modify the page content. | |||
| "app" Shorthand for "native app". | "app" Shorthand for "native app". | |||
| "app store" An ecommerce store where users can download and purchase | "app store" An ecommerce store where users can download and purchase | |||
| apps. | apps. | |||
| skipping to change at page 4, line 21 ¶ | skipping to change at page 4, line 21 ¶ | |||
| "in-app browser tab" A full page browser with limited navigation | "in-app browser tab" A full page browser with limited navigation | |||
| capabilities that is displayed inside a host app, but retains the | capabilities that is displayed inside a host app, but retains the | |||
| full security properties and authentication state of the browser. | full security properties and authentication state of the browser. | |||
| Has different platform-specific product names, such as | Has different platform-specific product names, such as | |||
| SFSafariViewController on iOS, and Custom Tabs on Android. | SFSafariViewController on iOS, and Custom Tabs on Android. | |||
| "inter-app communication" Communication between two apps on a | "inter-app communication" Communication between two apps on a | |||
| device. | device. | |||
| "claimed HTTPS URL" Some platforms allow apps to claim a HTTPS URL | "claimed HTTPS URI" Some platforms allow apps to claim a HTTPS | |||
| after proving ownership of the domain name. URLs claimed in such | scheme URI after proving ownership of the domain name. URIs | |||
| a way are then opened in the app instead of the browser. | claimed in such a way are then opened in the app instead of the | |||
| browser. | ||||
| "custom URI scheme" A private-use URI scheme defined by the app and | "private-use URI scheme" A private-use URI scheme defined by the app | |||
| registered with the operating system. URI requests to such | and registered with the operating system. URI requests to such | |||
| schemes trigger the app which registered it to be launched to | schemes trigger the app which registered it to be launched to | |||
| handle the request. | handle the request. | |||
| "web-view" A web browser UI component that can be embedded in apps | "web-view" A web browser UI component that can be embedded in apps | |||
| to render web pages, used to create embedded user-agents. | to render web pages, used to create embedded user-agents. | |||
| "reverse domain name notation" A naming convention based on the | "reverse domain name notation" A naming convention based on the | |||
| domain name system, but where where the domain components are | domain name system, but where the domain components are reversed, | |||
| reversed, for example "app.example.com" becomes "com.example.app". | for example "app.example.com" becomes "com.example.app". | |||
| 4. Overview | 4. Overview | |||
| The best current practice for authorizing users in native apps is to | The best current practice for authorizing users in native apps is to | |||
| perform the OAuth authorization request in an external user-agent | perform the OAuth authorization request in an external user-agent | |||
| (typically the browser), rather than an embedded user-agent (such as | (typically the browser), rather than an embedded user-agent (such as | |||
| one implemented with web-views). | one implemented with web-views). | |||
| Previously it was common for native apps to use embedded user-agents | Previously it was common for native apps to use embedded user-agents | |||
| (commonly implemented with web-views) for OAuth authorization | (commonly implemented with web-views) for OAuth authorization | |||
| requests. That approach has many drawbacks, including the host app | requests. That approach has many drawbacks, including the host app | |||
| being able to copy user credentials and cookies, and the user needing | being able to copy user credentials and cookies, and the user needing | |||
| to authenticate from scratch in each app. See Section 8.1 for a | to authenticate from scratch in each app. See Section 8.11 for a | |||
| deeper analysis of using embedded user-agents for OAuth. | deeper analysis of using embedded user-agents for OAuth. | |||
| Native app authorization requests that use the browser are more | Native app authorization requests that use the browser are more | |||
| secure and can take advantage of the user's authentication state. | secure and can take advantage of the user's authentication state. | |||
| Being able to use the existing authentication session in the browser | Being able to use the existing authentication session in the browser | |||
| enables single sign-on, as users don't need to authenticate to the | enables single sign-on, as users don't need to authenticate to the | |||
| authorization server each time they use a new app (unless required by | authorization server each time they use a new app (unless required by | |||
| authorization server policy). | authorization server policy). | |||
| Supporting authorization flows between a native app and the browser | Supporting authorization flows between a native app and the browser | |||
| is possible without changing the OAuth protocol itself, as the | is possible without changing the OAuth protocol itself, as the | |||
| authorization request and response are already defined in terms of | authorization request and response are already defined in terms of | |||
| URIs, which emcompasses URIs that can be used for inter-process | URIs, which emcompasses URIs that can be used for inter-process | |||
| communication. Some OAuth server implementations that assume all | communication. Some OAuth server implementations that assume all | |||
| skipping to change at page 6, line 30 ¶ | skipping to change at page 6, line 33 ¶ | |||
| 5. Using Inter-app URI Communication for OAuth | 5. Using Inter-app URI Communication for OAuth | |||
| Just as URIs are used for OAuth 2.0 [RFC6749] on the web to initiate | Just as URIs are used for OAuth 2.0 [RFC6749] on the web to initiate | |||
| the authorization request and return the authorization response to | the authorization request and return the authorization response to | |||
| the requesting website, URIs can be used by native apps to initiate | the requesting website, URIs can be used by native apps to initiate | |||
| the authorization request in the device's browser and return the | the authorization request in the device's browser and return the | |||
| response to the requesting native app. | response to the requesting native app. | |||
| By applying the same principles from the web to native apps, we gain | By applying the same principles from the web to native apps, we gain | |||
| benefits seen on the web like the usability of a single sign-on | benefits seen on the web, like the usability of a single sign-on | |||
| session, and the security of a separate authentication context. It | session and the security of a separate authentication context. It | |||
| also reduces the implementation complexity by reusing similar flows | also reduces the implementation complexity by reusing similar flows | |||
| as the web, and increases interoperability by relying on standards- | as the web, and increases interoperability by relying on standards- | |||
| based web flows that are not specific to a particular platform. | based web flows that are not specific to a particular platform. | |||
| Native apps MUST use an external user-agent to perform OAuth | Native apps MUST use an external user-agent to perform OAuth | |||
| authentication requests. This is achieved by opening the | authentication requests. This is achieved by opening the | |||
| authorization request in the browser (detailed in Section 6), and | authorization request in the browser (detailed in Section 6), and | |||
| using a redirect URI that will return the authorization response back | using a redirect URI that will return the authorization response back | |||
| to the native app, as defined in Section 7. | to the native app, as defined in Section 7. | |||
| skipping to change at page 7, line 33 ¶ | skipping to change at page 7, line 39 ¶ | |||
| There are several redirect URI options available to native apps for | There are several redirect URI options available to native apps for | |||
| receiving the authorization response from the browser, the | receiving the authorization response from the browser, the | |||
| availability and user experience of which varies by platform. | availability and user experience of which varies by platform. | |||
| To fully support this best practice, authorization servers MUST | To fully support this best practice, authorization servers MUST | |||
| support the following three redirect URI options. Native apps MAY | support the following three redirect URI options. Native apps MAY | |||
| use whichever redirect option suits their needs best, taking into | use whichever redirect option suits their needs best, taking into | |||
| account platform specific implementation details. | account platform specific implementation details. | |||
| 7.1. App-declared Custom URI Scheme Redirection | 7.1. Private-use URI Scheme Redirection | |||
| Many mobile and desktop computing platforms support inter-app | Many mobile and desktop computing platforms support inter-app | |||
| communication via URIs by allowing apps to register private-use | communication via URIs by allowing apps to register private-use URI | |||
| custom URI schemes like "com.example.app". When the browser or | schemes (sometimes colloquially referred to as custom URL schemes) | |||
| another app attempts to load a URI with a custom scheme, the app that | like "com.example.app". When the browser or another app attempts to | |||
| registered it is launched to handle the request. | load a URI with a custom scheme, the app that registered it is | |||
| launched to handle the request. | ||||
| To perform an OAuth 2.0 authorization request with a custom URI | To perform an OAuth 2.0 authorization request with a private-use URI | |||
| scheme redirect, the native app launches the browser with a standard | scheme redirect, the native app launches the browser with a standard | |||
| authorization request, but one where the redirection URI utilizes a | authorization request, but one where the redirection URI utilizes a | |||
| custom URI scheme it registered with the operating system. | custom URI scheme it registered with the operating system. | |||
| When choosing a URI scheme to associate with the app, apps MUST use a | When choosing a URI scheme to associate with the app, apps MUST use a | |||
| URI scheme based on a domain name under their control, expressed in | URI scheme based on a domain name under their control, expressed in | |||
| reverse order, as recommended by Section 3.8 of [RFC7595] for | reverse order, as recommended by Section 3.8 of [RFC7595] for | |||
| private-use URI schemes. | private-use URI schemes. | |||
| For example, an app that controls the domain name "app.example.com" | For example, an app that controls the domain name "app.example.com" | |||
| can use "com.example.app" as their scheme. Some authorization | can use "com.example.app" as their scheme. Some authorization | |||
| servers assign client identifiers based on domain names, for example | servers assign client identifiers based on domain names, for example | |||
| "client1234.usercontent.example.net", which can also be used as the | "client1234.usercontent.example.net", which can also be used as the | |||
| domain name for the scheme when reversed in the same manner. A | domain name for the scheme when reversed in the same manner. A | |||
| scheme such as "myapp" however would not meet this requirement, as it | scheme such as "myapp" however would not meet this requirement, as it | |||
| is not based on a domain name. | is not based on a domain name. | |||
| Care must be taken when there are multiple apps by the same publisher | Care must be taken when there are multiple apps by the same publisher | |||
| that each scheme is unique within that group. On platforms that use | that each scheme is unique within that group. On platforms that use | |||
| app identifiers that are also based on reverse order domain names, | app identifiers that are also based on reverse order domain names, | |||
| those can be reused as the custom URI scheme for the OAuth redirect | those can be reused as the private-use URI scheme for the OAuth | |||
| to help avoid this problem. | redirect to help avoid this problem. | |||
| Following the requirements of [RFC3986] Section 3.2, as there is no | Following the requirements of [RFC3986] Section 3.2, as there is no | |||
| naming authority for custom URI scheme redirects, only a single slash | naming authority for private-use URI scheme redirects, only a single | |||
| ("/") appears after the scheme component. A complete example of a | slash ("/") appears after the scheme component. A complete example | |||
| redirect URI utilizing a custom URI scheme: | of a redirect URI utilizing a private-use URI scheme: | |||
| com.example.app:/oauth2redirect/example-provider | com.example.app:/oauth2redirect/example-provider | |||
| When the authentication server completes the request, it redirects to | When the authentication server completes the request, it redirects to | |||
| the client's redirection URI like it would any redirect URI. As the | the client's redirection URI like it would any redirect URI. As the | |||
| redirection URI uses a custom scheme it results in the operating | redirection URI uses a custom scheme it results in the operating | |||
| system launching the native app, passing in the URI as a launch | system launching the native app, passing in the URI as a launch | |||
| parameter. The native app then processes the authorization response | parameter. The native app then processes the authorization response | |||
| like normal. | like normal. | |||
| 7.2. App-claimed HTTPS URI Redirection | 7.2. Claimed HTTPS URI Redirection | |||
| Some operating systems allow apps to claim HTTPS URL paths in domains | Some operating systems allow apps to claim HTTPS scheme URIs in | |||
| they control. When the browser encounters a claimed URL, instead of | domains they control. When the browser encounters a claimed URI, | |||
| the page being loaded in the browser, the native app is launched with | instead of the page being loaded in the browser, the native app is | |||
| the URL supplied as a launch parameter. | launched with the URI supplied as a launch parameter. | |||
| Such claimed HTTPS URIs can be used as OAuth redirect URIs. They are | Such URIs can be used as OAuth redirect URIs. They are | |||
| indistinguishable from OAuth redirects of web-based clients. An | indistinguishable from OAuth redirects of web-based clients. An | |||
| example is: | example is: | |||
| https://app.example.com/oauth2redirect/example-provider | https://app.example.com/oauth2redirect/example-provider | |||
| App-claimed HTTPS redirect URIs have some advantages in that the | App-claimed HTTPS redirect URIs have some advantages in that the | |||
| identity of the destination app is guaranteed by the operating | identity of the destination app is guaranteed by the operating | |||
| system. Due to this reason, they SHOULD be used over the other | system. Due to this reason, they SHOULD be used over the other | |||
| redirect choices for native apps where possible. | redirect choices for native apps where possible. | |||
| App-claimed HTTPS redirect URIs function as normal HTTPS redirects | Claimed HTTPS redirect URIs function as normal HTTPS redirects from | |||
| from the perspective of the authorization server, though as stated in | the perspective of the authorization server, though as stated in | |||
| Section 8.7, it REQUIRED that the authorization server is able to | Section 8.4, it REQUIRED that the authorization server is able to | |||
| distinguish between public native app clients that use app-claimed | distinguish between public native app clients that use app-claimed | |||
| HTTPS redirect URIs and confidential web clients. | HTTPS redirect URIs and confidential web clients. | |||
| 7.3. Loopback URI Redirection | 7.3. Loopback Interface Redirection | |||
| Native apps that are able to open a port on the loopback network | Native apps that are able to open a port on the loopback network | |||
| interface without needing special permissions (typically, those on | interface without needing special permissions (typically, those on | |||
| desktop operating systems) can use the loopback network interface to | desktop operating systems) can use the loopback network interface to | |||
| receive the OAuth redirect. | receive the OAuth redirect. | |||
| Loopback redirect URIs use the HTTP scheme and are constructed with | Loopback redirect URIs use the HTTP scheme and are constructed with | |||
| the loopback IP literal and whatever port the client is listening on. | the loopback IP literal and whatever port the client is listening on. | |||
| That is, "http://127.0.0.1:{port}/{path}" for IPv4, and | That is, "http://127.0.0.1:{port}/{path}" for IPv4, and | |||
| "http://[::1]:{port}/{path}" for IPv6. A complete example of such a | "http://[::1]:{port}/{path}" for IPv6. A complete example of such a | |||
| skipping to change at page 9, line 29 ¶ | skipping to change at page 9, line 35 ¶ | |||
| http://127.0.0.1:61023/oauth2redirect/example-provider | http://127.0.0.1:61023/oauth2redirect/example-provider | |||
| The authorization server MUST allow any port to be specified at the | The authorization server MUST allow any port to be specified at the | |||
| time of the request for loopback IP redirect URIs, to accommodate | time of the request for loopback IP redirect URIs, to accommodate | |||
| clients that obtain an available ephemeral port from the operating | clients that obtain an available ephemeral port from the operating | |||
| system at the time of the request. | system at the time of the request. | |||
| 8. Security Considerations | 8. Security Considerations | |||
| 8.1. Embedded User-Agents | 8.1. Protecting the Authorization Code | |||
| Embedded user-agents are an alternative method for authorizing native | ||||
| apps. They are however unsafe for use by third-parties to the | ||||
| authorization server by definition, as the app that hosts the | ||||
| embedded user-agent can access the user's full authentication | ||||
| credential, not just the OAuth authorization grant that was intended | ||||
| for the app. | ||||
| In typical web-view based implementations of embedded user-agents, | ||||
| the host application can: log every keystroke entered in the form to | ||||
| capture usernames and passwords; automatically submit forms and | ||||
| bypass user-consent; copy session cookies and use them to perform | ||||
| authenticated actions as the user. | ||||
| Even when used by trusted apps belonging to the same party as the | ||||
| authorization server, embedded user-agents violate the principle of | ||||
| least privilege by having access to more powerful credentials than | ||||
| they need, potentially increasing the attack surface. | ||||
| Encouraging users to enter credentials in an embedded user-agent | ||||
| without the usual address bar and visible certificate validation | ||||
| features that browsers have makes it impossible for the user to know | ||||
| if they are signing in to the legitimate site, and even when they | ||||
| are, it trains them that it's OK to enter credentials without | ||||
| validating the site first. | ||||
| Aside from the security concerns, embedded user-agents do not share | ||||
| the authentication state with other apps or the browser, requiring | ||||
| the user to login for every authorization request and leading to a | ||||
| poor user experience. | ||||
| Native apps MUST NOT use embedded user-agents to perform | ||||
| authorization requests. | ||||
| Authorization endpoints MAY take steps to detect and block | ||||
| authorization requests in embedded user-agents. | ||||
| 8.2. Non-Browser External User-Agents | ||||
| This best practice recommends a particular type of external user- | ||||
| agent, the user's browser. Other external user-agent patterns may | ||||
| also be viable for secure and usable OAuth. This document makes no | ||||
| comment on those patterns. | ||||
| 8.3. Phishability of In-App Browser Tabs | ||||
| While in-app browser tabs provide a secure authentication context, as | ||||
| the user initiates the flow from a native app, it is possible for | ||||
| that native app to completely fake an in-app browser tab. | ||||
| This can't be prevented directly - once the user is in the native | ||||
| app, that app is fully in control of what it can render - however | ||||
| there are several mitigating factors. | ||||
| Importantly, such an attack that uses a web-view to fake an in-app | ||||
| browser tab will always start with no authentication state. If all | ||||
| native apps use the techniques described in this best practice, users | ||||
| will not need to sign-in frequently and thus should be suspicious of | ||||
| any sign-in request when they should have already been signed-in. | ||||
| This is the case even for authorization servers that require | ||||
| occasional or frequent re-authentication, as such servers can | ||||
| preserve some user identifiable information from the old session, | ||||
| like the email address or profile picture and display that | ||||
| information during re-authentication. | ||||
| Users who are particularly concerned about their security may also | ||||
| take the additional step of opening the request in the browser from | ||||
| the in-app browser tab, and completing the authorization there, as | ||||
| most implementations of the in-app browser tab pattern offer such | ||||
| functionality. | ||||
| 8.4. Protecting the Authorization Code | ||||
| The redirect URI options documented in Section 7 share the benefit | The redirect URI options documented in Section 7 share the benefit | |||
| that only a native app on the same device can receive the | that only a native app on the same device can receive the | |||
| authorization code which limits the attack surface, however code | authorization code which limits the attack surface, however code | |||
| interception by a native app other than the intended app may still be | interception by a native app other than the intended app may still be | |||
| possible. | possible. | |||
| A limitation of using custom URI schemes for redirect URIs is that | A limitation of using private-use URI schemes for redirect URIs is | |||
| multiple apps can typically register the same scheme, which makes it | that multiple apps can typically register the same scheme, which | |||
| indeterminate as to which app will receive the Authorization Code. | makes it indeterminate as to which app will receive the Authorization | |||
| PKCE [RFC7636] details how this limitation can be used to execute a | Code. PKCE [RFC7636] details how this limitation can be used to | |||
| code interception attack (see Figure 1). | execute a code interception attack (see Figure 1). | |||
| Loopback IP based redirect URIs may be susceptible to interception by | Loopback IP based redirect URIs may be susceptible to interception by | |||
| other apps listening on the same loopback interface. | other apps listening on the same loopback interface. | |||
| As most forms of inter-app URI-based communication sends data over | As most forms of inter-app URI-based communication sends data over | |||
| insecure local channels, eavesdropping and interception of the | insecure local channels, eavesdropping and interception of the | |||
| authorization response is a risk for native apps. App-claimed HTTPS | authorization response is a risk for native apps. App-claimed HTTPS | |||
| redirects are hardened against this type of attack due to the | redirects are hardened against this type of attack due to the | |||
| presence of the URI authority, but they are still public clients and | presence of the URI authority, but they are still public clients and | |||
| the URI is still transmitted over local channels with unknown | the URI is still transmitted over local channels with unknown | |||
| skipping to change at page 12, line 5 ¶ | skipping to change at page 10, line 30 ¶ | |||
| app that intercepted the authorization code would not be in | app that intercepted the authorization code would not be in | |||
| possession of this secret, rendering the code useless. | possession of this secret, rendering the code useless. | |||
| Public native app clients MUST protect the authorization request with | Public native app clients MUST protect the authorization request with | |||
| PKCE [RFC7636]. Authorization servers MUST support PKCE [RFC7636] | PKCE [RFC7636]. Authorization servers MUST support PKCE [RFC7636] | |||
| for public native app clients. Authorization servers SHOULD reject | for public native app clients. Authorization servers SHOULD reject | |||
| authorization requests from native apps that don't use PKCE by | authorization requests from native apps that don't use PKCE by | |||
| returning an error message as defined in Section 4.4.1 of PKCE | returning an error message as defined in Section 4.4.1 of PKCE | |||
| [RFC7636]. | [RFC7636]. | |||
| 8.5. OAuth Implicit Flow | 8.2. OAuth Implicit Flow | |||
| The OAuth 2.0 Implicit Flow as defined in Section 4.2 of OAuth 2.0 | The OAuth 2.0 Implicit Flow as defined in Section 4.2 of OAuth 2.0 | |||
| [RFC6749] generally works with the practice of performing the | [RFC6749] generally works with the practice of performing the | |||
| authorization request in the browser, and receiving the authorization | authorization request in the browser, and receiving the authorization | |||
| response via URI-based inter-app communication. However, as the | response via URI-based inter-app communication. However, as the | |||
| Implicit Flow cannot be protected by PKCE (which is a required in | Implicit Flow cannot be protected by PKCE (which is a required in | |||
| Section 8.4), the use of the Implicit Flow with native apps is NOT | Section 8.1), the use of the Implicit Flow with native apps is NOT | |||
| RECOMMENDED. | RECOMMENDED. | |||
| Tokens granted via the implicit flow also cannot be refreshed without | Tokens granted via the implicit flow also cannot be refreshed without | |||
| user interaction, making the code flow - which can issue refresh | user interaction, making the code flow - which can issue refresh | |||
| tokens - the more practical option for native app authorizations that | tokens - the more practical option for native app authorizations that | |||
| require refreshing. | require refreshing. | |||
| 8.6. Loopback Redirect Considerations | 8.3. Loopback Redirect Considerations | |||
| Loopback interface redirect URIs use the "http" scheme (i.e. without | Loopback interface redirect URIs use the "http" scheme (i.e. without | |||
| TLS). This is acceptable for loopback interface redirect URIs as the | TLS). This is acceptable for loopback interface redirect URIs as the | |||
| HTTP request never leaves the device. | HTTP request never leaves the device. | |||
| Clients should open the network port only when starting the | Clients should open the network port only when starting the | |||
| authorization request, and close it once the response is returned. | authorization request, and close it once the response is returned. | |||
| Clients should listen on the loopback network interface only, to | Clients should listen on the loopback network interface only, to | |||
| avoid interference by other network actors. | avoid interference by other network actors. | |||
| While redirect URIs using localhost (i.e. | While redirect URIs using localhost (i.e. | |||
| "http://localhost:{port}/") function similarly to loopback IP | "http://localhost:{port}/") function similarly to loopback IP | |||
| redirects described in Section 7.3, the use of "localhost" is NOT | redirects described in Section 7.3, the use of "localhost" is NOT | |||
| RECOMMENDED. Specifying a redirect URI with the loopback IP literal | RECOMMENDED. Specifying a redirect URI with the loopback IP literal | |||
| rather than localhost avoids inadvertently listening on network | rather than localhost avoids inadvertently listening on network | |||
| interfaces other than the loopback interface. It is also less | interfaces other than the loopback interface. It is also less | |||
| susceptible to client side firewalls, and misconfigured host name | susceptible to client side firewalls, and misconfigured host name | |||
| resolution on the user's device. | resolution on the user's device. | |||
| 8.7. Registration of Native App Clients | 8.4. Registration of Native App Clients | |||
| Native apps, except when using a mechanism like Dynamic Client | Native apps, except when using a mechanism like Dynamic Client | |||
| Registration [RFC7591] to provision per-instance secrets, are | Registration [RFC7591] to provision per-instance secrets, are | |||
| classified as public clients, as defined by Section 2.1 of OAuth 2.0 | classified as public clients, as defined by Section 2.1 of OAuth 2.0 | |||
| [RFC6749] and MUST be registered with the authorization server as | [RFC6749] and MUST be registered with the authorization server as | |||
| such. Authorization servers MUST record the client type in the | such. Authorization servers MUST record the client type in the | |||
| client registration details in order to identify and process requests | client registration details in order to identify and process requests | |||
| accordingly. | accordingly. | |||
| Authorization servers MUST require clients to register their complete | Authorization servers MUST require clients to register their complete | |||
| redirect URI (including the path component), and reject authorization | redirect URI (including the path component), and reject authorization | |||
| requests that specify a redirect URI that doesn't exactly match the | requests that specify a redirect URI that doesn't exactly match the | |||
| one that was registered, with the exception of loopback redirects, | one that was registered, with the exception of loopback redirects, | |||
| where an exact match is required except for the port URI component. | where an exact match is required except for the port URI component. | |||
| For Custom URI scheme based redirects, authorization servers SHOULD | For private-use URI scheme based redirects, authorization servers | |||
| enforce the requirement in Section 7.1 that clients use reverse | SHOULD enforce the requirement in Section 7.1 that clients use | |||
| domain name based schemes. At a minimum, any scheme that doesn't | reverse domain name based schemes. At a minimum, any scheme that | |||
| contain a period character ("."), SHOULD be rejected. | doesn't contain a period character ("."), SHOULD be rejected. | |||
| In addition to the collision resistant properties, requiring a URI | In addition to the collision resistant properties, requiring a URI | |||
| scheme based on a domain name that is under the control of the app | scheme based on a domain name that is under the control of the app | |||
| can help to prove ownership in the event of a dispute where two apps | can help to prove ownership in the event of a dispute where two apps | |||
| claim the same custom URI scheme (where one app is acting | claim the same private-use URI scheme (where one app is acting | |||
| maliciously). For example, if two apps claimed "com.example.app", | maliciously). For example, if two apps claimed "com.example.app", | |||
| the owner of "example.com" could petition the app store operator to | the owner of "example.com" could petition the app store operator to | |||
| remove the counterfeit app. Such a petition is harder to prove if a | remove the counterfeit app. Such a petition is harder to prove if a | |||
| generic URI scheme was used. | generic URI scheme was used. | |||
| Authorization servers MAY request the inclusion of other platform- | Authorization servers MAY request the inclusion of other platform- | |||
| specific information, such as the app package or bundle name, or | specific information, such as the app package or bundle name, or | |||
| other information used to associate the app that may be useful for | other information used to associate the app that may be useful for | |||
| verifying the calling app's identity, on operating systems that | verifying the calling app's identity, on operating systems that | |||
| support such functions. | support such functions. | |||
| 8.8. Client Authentication | 8.5. Client Authentication | |||
| Secrets that are statically included as part of an app distributed to | Secrets that are statically included as part of an app distributed to | |||
| multiple users should not be treated as confidential secrets, as one | multiple users should not be treated as confidential secrets, as one | |||
| user may inspect their copy and learn the shared secret. For this | user may inspect their copy and learn the shared secret. For this | |||
| reason, and those stated in Section 5.3.1 of [RFC6819], it is NOT | reason, and those stated in Section 5.3.1 of [RFC6819], it is NOT | |||
| RECOMMENDED for authorization servers to require client | RECOMMENDED for authorization servers to require client | |||
| authentication of public native apps clients using a shared secret, | authentication of public native apps clients using a shared secret, | |||
| as this serves little value beyond client identification which is | as this serves little value beyond client identification which is | |||
| already provided by the "client_id" request parameter. | already provided by the "client_id" request parameter. | |||
| Authorization servers that still require a statically included shared | Authorization servers that still require a statically included shared | |||
| secret for native app clients MUST treat the client as a public | secret for native app clients MUST treat the client as a public | |||
| client (as defined by Section 2.1 of OAuth 2.0 [RFC6749]), and not | client (as defined by Section 2.1 of OAuth 2.0 [RFC6749]), and not | |||
| accept the secret as proof of the client's identity. Without | accept the secret as proof of the client's identity. Without | |||
| additional measures, such clients are subject to client impersonation | additional measures, such clients are subject to client impersonation | |||
| (see Section 8.9). | (see Section 8.6). | |||
| 8.9. Client Impersonation | 8.6. Client Impersonation | |||
| As stated in Section 10.2 of OAuth 2.0 [RFC6749], the authorization | As stated in Section 10.2 of OAuth 2.0 [RFC6749], the authorization | |||
| server SHOULD NOT process authorization requests automatically | server SHOULD NOT process authorization requests automatically | |||
| without user consent or interaction, except when the identity of the | without user consent or interaction, except when the identity of the | |||
| client can be assured. This includes the case where the user has | client can be assured. This includes the case where the user has | |||
| previously approved an authorization request for a given client id - | previously approved an authorization request for a given client id - | |||
| unless the identity of the client can be proven, the request SHOULD | unless the identity of the client can be proven, the request SHOULD | |||
| be processed as if no previous request had been approved. | be processed as if no previous request had been approved. | |||
| Measures such as claimed HTTPS redirects MAY be accepted by | Measures such as claimed HTTPS redirects MAY be accepted by | |||
| authorization servers as identity proof. Some operating systems may | authorization servers as identity proof. Some operating systems may | |||
| offer alternative platform-specific identity features which MAY be | offer alternative platform-specific identity features which MAY be | |||
| accepted, as appropriate. | accepted, as appropriate. | |||
| 8.10. Cross-App Request Forgery Protections | 8.7. Phishability of In-App Browser Tabs | |||
| While in-app browser tabs provide a secure authentication context, as | ||||
| the user initiates the flow from a native app, it is possible for | ||||
| that native app to completely fake an in-app browser tab. | ||||
| This can't be prevented directly - once the user is in the native | ||||
| app, that app is fully in control of what it can render - however | ||||
| there are several mitigating factors. | ||||
| Importantly, such an attack that uses a web-view to fake an in-app | ||||
| browser tab will always start with no authentication state. If all | ||||
| native apps use the techniques described in this best practice, users | ||||
| will not need to sign-in frequently and thus should be suspicious of | ||||
| any sign-in request when they should have already been signed-in. | ||||
| This is the case even for authorization servers that require | ||||
| occasional or frequent re-authentication, as such servers can | ||||
| preserve some user identifiable information from the old session, | ||||
| like the email address or profile picture and display that | ||||
| information during re-authentication. | ||||
| Users who are particularly concerned about their security may also | ||||
| take the additional step of opening the request in the browser from | ||||
| the in-app browser tab, and completing the authorization there, as | ||||
| most implementations of the in-app browser tab pattern offer such | ||||
| functionality. | ||||
| 8.8. Cross-App Request Forgery Protections | ||||
| Section 5.3.5 of [RFC6819] recommends using the "state" parameter to | Section 5.3.5 of [RFC6819] recommends using the "state" parameter to | |||
| link client requests and responses to prevent CSRF attacks. | link client requests and responses to prevent CSRF attacks. | |||
| It is similarly RECOMMENDED for native apps to include a high entropy | It is similarly RECOMMENDED for native apps to include a high entropy | |||
| secure random number in the "state" parameter of the authorization | secure random number in the "state" parameter of the authorization | |||
| request, and reject any incoming authorization responses without a | request, and reject any incoming authorization responses without a | |||
| state value that matches a pending outgoing authorization request. | state value that matches a pending outgoing authorization request. | |||
| 8.11. Authorization Server Mix-Up Mitigation | 8.9. Authorization Server Mix-Up Mitigation | |||
| To protect against a compromised or malicious authorization server | To protect against a compromised or malicious authorization server | |||
| attacking another authorization server used by the same app, it is | attacking another authorization server used by the same app, it is | |||
| REQUIRED that a unique redirect URI is used for each authorization | REQUIRED that a unique redirect URI is used for each authorization | |||
| server used by the app (for example, by varying the path component), | server used by the app (for example, by varying the path component), | |||
| and that authorization responses are rejected if the redirect URI | and that authorization responses are rejected if the redirect URI | |||
| they were received on doesn't match the redirect URI in a outgoing | they were received on doesn't match the redirect URI in a outgoing | |||
| authorization request. | authorization request. | |||
| The native app MUST store the redirect uri used in the authorization | The native app MUST store the redirect URI used in the authorization | |||
| request with the authorization session data (i.e. along with "state" | request with the authorization session data (i.e. along with "state" | |||
| and other related data), and MUST verify that the URI on which the | and other related data), and MUST verify that the URI on which the | |||
| authorization response was received exactly matches it. | authorization response was received exactly matches it. | |||
| The requirements of Section 8.7 that authorization servers reject | The requirements of Section 8.4 that authorization servers reject | |||
| requests with URIs that don't match what was registered are also | requests with URIs that don't match what was registered are also | |||
| required to prevent such attacks. | required to prevent such attacks. | |||
| 8.10. Non-Browser External User-Agents | ||||
| This best practice recommends a particular type of external user- | ||||
| agent, the user's browser. Other external user-agent patterns may | ||||
| also be viable for secure and usable OAuth. This document makes no | ||||
| comment on those patterns. | ||||
| 8.11. Embedded User-Agents | ||||
| OAuth 2.0 [RFC6749] Section 9 documents two approaches for native | ||||
| apps to interact with the authorization endpoint. This best current | ||||
| practice requires that native apps MUST NOT use embedded user-agents | ||||
| to perform authorization requests, and allows that authorization | ||||
| endpoints MAY take steps to detect and block authorization requests | ||||
| in embedded user-agents. The security considerations for these | ||||
| requirements are detailed herein. | ||||
| Embedded user-agents are an alternative method for authorizing native | ||||
| apps. These embedded user agents are unsafe for use by third-parties | ||||
| to the authorization server by definition, as the app that hosts the | ||||
| embedded user-agent can access the user's full authentication | ||||
| credential, not just the OAuth authorization grant that was intended | ||||
| for the app. | ||||
| In typical web-view based implementations of embedded user-agents, | ||||
| the host application can: log every keystroke entered in the form to | ||||
| capture usernames and passwords; automatically submit forms and | ||||
| bypass user-consent; copy session cookies and use them to perform | ||||
| authenticated actions as the user. | ||||
| Even when used by trusted apps belonging to the same party as the | ||||
| authorization server, embedded user-agents violate the principle of | ||||
| least privilege by having access to more powerful credentials than | ||||
| they need, potentially increasing the attack surface. | ||||
| Encouraging users to enter credentials in an embedded user-agent | ||||
| without the usual address bar and visible certificate validation | ||||
| features that browsers have makes it impossible for the user to know | ||||
| if they are signing in to the legitimate site, and even when they | ||||
| are, it trains them that it's OK to enter credentials without | ||||
| validating the site first. | ||||
| Aside from the security concerns, embedded user-agents do not share | ||||
| the authentication state with other apps or the browser, requiring | ||||
| the user to login for every authorization request which is often | ||||
| considered an inferior user experience. | ||||
| 9. IANA Considerations | 9. IANA Considerations | |||
| [RFC Editor: please do NOT remove this section.] | [RFC Editor: please do NOT remove this section.] | |||
| This document has no IANA actions. | ||||
| Section 7.1 specifies how private-use URI schemes are used for inter- | Section 7.1 specifies how private-use URI schemes are used for inter- | |||
| app communication in OAuth protocol flows. This document requires in | app communication in OAuth protocol flows. This document requires in | |||
| Section 7.1 that such schemes are based on domain names owned or | Section 7.1 that such schemes are based on domain names owned or | |||
| assigned to the app, as recommended in Section 3.8 of [RFC7595]. Per | assigned to the app, as recommended in Section 3.8 of [RFC7595]. Per | |||
| section 6 of [RFC7595], registration of domain based URI schemes with | Section 6 of [RFC7595], registration of domain based URI schemes with | |||
| IANA is not required. Therefore, this document has no IANA actions. | IANA is not required. | |||
| 10. References | 10. References | |||
| 10.1. Normative References | 10.1. Normative References | |||
| [RFC2119] Bradner, S., "Key words for use in RFCs to Indicate | [RFC2119] Bradner, S., "Key words for use in RFCs to Indicate | |||
| Requirement Levels", BCP 14, RFC 2119, | Requirement Levels", BCP 14, RFC 2119, | |||
| DOI 10.17487/RFC2119, March 1997, | DOI 10.17487/RFC2119, March 1997, | |||
| <http://www.rfc-editor.org/info/rfc2119>. | <http://www.rfc-editor.org/info/rfc2119>. | |||
| skipping to change at page 16, line 19 ¶ | skipping to change at page 16, line 24 ¶ | |||
| [SamplesForWindows] | [SamplesForWindows] | |||
| Denniss, W., "OAuth for Apps: Samples for Windows", July | Denniss, W., "OAuth for Apps: Samples for Windows", July | |||
| 2016, <https://github.com/googlesamples/oauth-apps-for- | 2016, <https://github.com/googlesamples/oauth-apps-for- | |||
| windows>. | windows>. | |||
| Appendix A. Server Support Checklist | Appendix A. Server Support Checklist | |||
| OAuth servers that support native apps must: | OAuth servers that support native apps must: | |||
| 1. Support custom URI-scheme redirect URIs. This is required to | 1. Support private-use URI scheme redirect URIs. This is required | |||
| support mobile operating systems. See Section 7.1. | to support mobile operating systems. See Section 7.1. | |||
| 2. Support HTTPS redirect URIs for use with public native app | 2. Support HTTPS scheme redirect URIs for use with public native app | |||
| clients. This is used by apps on advanced mobile operating | clients. This is used by apps on advanced mobile operating | |||
| systems that allow app-claimed HTTPS URIs. See Section 7.2. | systems that allow app-claimed URIs. See Section 7.2. | |||
| 3. Support loopback IP redirect URIs. This is required to support | 3. Support loopback IP redirect URIs. This is required to support | |||
| desktop operating systems. See Section 7.3. | desktop operating systems. See Section 7.3. | |||
| 4. Not assume native app clients can keep a secret. If secrets are | 4. Not assume native app clients can keep a secret. If secrets are | |||
| distributed to multiple installs of the same native app, they | distributed to multiple installs of the same native app, they | |||
| should not be treated as confidential. See Section 8.8. | should not be treated as confidential. See Section 8.5. | |||
| 5. Support PKCE [RFC7636]. Required to protect authorization code | 5. Support PKCE [RFC7636]. Required to protect authorization code | |||
| grants sent to public clients over inter-app communication | grants sent to public clients over inter-app communication | |||
| channels. See Section 8.4 | channels. See Section 8.1 | |||
| Appendix B. Operating System Specific Implementation Details | Appendix B. Operating System Specific Implementation Details | |||
| This document primarily defines best practices in an generic manner, | This document primarily defines best practices in an generic manner, | |||
| referencing techniques commonly available in a variety of | referencing techniques commonly available in a variety of | |||
| environments. This non-normative section documents operating system | environments. This non-normative section documents operating system | |||
| specific implementation details of the best practice. | specific implementation details of the best practice. | |||
| The implementation details herein are considered accurate at the time | The implementation details herein are considered accurate at the time | |||
| of publishing but will likely change over time. It is hoped that | of publishing but will likely change over time. It is hoped that | |||
| skipping to change at page 17, line 13 ¶ | skipping to change at page 17, line 15 ¶ | |||
| event of a conflict. | event of a conflict. | |||
| B.1. iOS Implementation Details | B.1. iOS Implementation Details | |||
| Apps can initiate an authorization request in the browser without the | Apps can initiate an authorization request in the browser without the | |||
| user leaving the app, through the SFSafariViewController class which | user leaving the app, through the SFSafariViewController class which | |||
| implements the in-app browser tab pattern. Safari can be used to | implements the in-app browser tab pattern. Safari can be used to | |||
| handle requests on old versions of iOS without | handle requests on old versions of iOS without | |||
| SFSafariViewController. | SFSafariViewController. | |||
| To receive the authorization response, both custom URI scheme | To receive the authorization response, both private-use URI scheme | |||
| redirects and claimed HTTPS links (known as Universal Links) are | redirects (referred to as Custom URL Schemes) and claimed HTTPS links | |||
| viable choices, and function the same whether the request is loaded | (known as Universal Links) are viable choices, and function the same | |||
| in SFSafariViewController or the Safari app. Apps can claim Custom | whether the request is loaded in SFSafariViewController or the Safari | |||
| URI schemes with the "CFBundleURLTypes" key in the application's | app. Apps can claim Custom URI schemes with the "CFBundleURLTypes" | |||
| property list file "Info.plist", and HTTPS links using the Universal | key in the application's property list file "Info.plist", and HTTPS | |||
| Links feature with an entitlement file and an association file on the | links using the Universal Links feature with an entitlement file and | |||
| domain. | an association file on the domain. | |||
| Universal Links are the preferred choice on iOS 9 and above due to | Universal Links are the preferred choice on iOS 9 and above due to | |||
| the ownership proof that is provided by the operating system. | the ownership proof that is provided by the operating system. | |||
| A complete open source sample is included in the AppAuth for iOS and | A complete open source sample is included in the AppAuth for iOS and | |||
| macOS [AppAuth.iOSmacOS] library. | macOS [AppAuth.iOSmacOS] library. | |||
| B.2. Android Implementation Details | B.2. Android Implementation Details | |||
| Apps can initiate an authorization request in the browser without the | Apps can initiate an authorization request in the browser without the | |||
| user leaving the app, through the Android Custom Tab feature which | user leaving the app, through the Android Custom Tab feature which | |||
| implements the in-app browser tab pattern. The user's default | implements the in-app browser tab pattern. The user's default | |||
| browser can be used to handle requests when no browser supports | browser can be used to handle requests when no browser supports | |||
| Custom Tabs. | Custom Tabs. | |||
| Android browser vendors should support the Custom Tabs protocol (by | Android browser vendors should support the Custom Tabs protocol (by | |||
| providing an implementation of the "CustomTabsService" class), to | providing an implementation of the "CustomTabsService" class), to | |||
| provide the in-app browser tab user experience optimization to their | provide the in-app browser tab user experience optimization to their | |||
| users. Chrome is one such browser that implements Custom Tabs. | users. Chrome is one such browser that implements Custom Tabs. | |||
| To receive the authorization response, custom URI schemes are broadly | To receive the authorization response, private-use URI schemes are | |||
| supported through Android Implicit Intends. Claimed HTTPS redirect | broadly supported through Android Implicit Intends. Claimed HTTPS | |||
| URIs through Android App Links are available on Android 6.0 and | redirect URIs through Android App Links are available on Android 6.0 | |||
| above. Both types of redirect URIs are registered in the | and above. Both types of redirect URIs are registered in the | |||
| application's manifest. | application's manifest. | |||
| A complete open source sample is included in the AppAuth for Android | A complete open source sample is included in the AppAuth for Android | |||
| [AppAuth.Android] library. | [AppAuth.Android] library. | |||
| B.3. Windows Implementation Details | B.3. Windows Implementation Details | |||
| Universal Windows Platform (UWP) apps can use the Web Authentication | Universal Windows Platform (UWP) apps can use the Web Authentication | |||
| Broker API in SSO mode as an external user-agent for authorization | Broker API in SSO mode as an external user-agent for authorization | |||
| flows, and all app types can open an authorization request in the | flows, and all app types can open an authorization request in the | |||
| skipping to change at page 18, line 26 ¶ | skipping to change at page 18, line 26 ¶ | |||
| not used in SSO mode, the broker is an embedded user-agent, hence | not used in SSO mode, the broker is an embedded user-agent, hence | |||
| only operation in SSO mode is RECOMMENDED. | only operation in SSO mode is RECOMMENDED. | |||
| To use the Web Authentication Broker in SSO mode, the redirect URI | To use the Web Authentication Broker in SSO mode, the redirect URI | |||
| must be of the form "msapp://{appSID}" where "appSID" is the app's | must be of the form "msapp://{appSID}" where "appSID" is the app's | |||
| SID, which can be found in the app's registration information. While | SID, which can be found in the app's registration information. While | |||
| Windows enforces the URI authority on such redirects, ensuring only | Windows enforces the URI authority on such redirects, ensuring only | |||
| the app with the matching SID can receive the response on Windows, | the app with the matching SID can receive the response on Windows, | |||
| the URI scheme could be claimed by apps on other platforms without | the URI scheme could be claimed by apps on other platforms without | |||
| the same authority present, thus this redirect type should be treated | the same authority present, thus this redirect type should be treated | |||
| similar to custom URI scheme redirects for security purposes. | similar to private-use URI scheme redirects for security purposes. | |||
| Both traditional and Universal Windows Platform (UWP) apps can | Both traditional and Universal Windows Platform (UWP) apps can | |||
| perform authorization requests in the user's browser. Traditional | perform authorization requests in the user's browser. Traditional | |||
| apps typically use a loopback redirect to receive the authorization | apps typically use a loopback redirect to receive the authorization | |||
| response, and listening on the loopback interface is allowed by | response, and listening on the loopback interface is allowed by | |||
| default firewall rules. Universal Windows Platform (UWP) apps can | default firewall rules. Universal Windows Platform (UWP) apps can | |||
| use custom URI scheme redirects to receive the authorization | use private-use URI scheme redirects to receive the authorization | |||
| response, which will bring the app to the foreground. Known on the | response, which will bring the app to the foreground. Known on the | |||
| platform as "URI Activation", the URI scheme is limited to 39 | platform as "URI Activation", the URI scheme is limited to 39 | |||
| characters in length, and may include the "." character, making short | characters in length, and may include the "." character, making short | |||
| reverse domain name based schemes (as recommended in Section 7.1) | reverse domain name based schemes (as recommended in Section 7.1) | |||
| possible. | possible. | |||
| An open source sample demonstrating these patterns is available | An open source sample demonstrating these patterns is available | |||
| [SamplesForWindows]. | [SamplesForWindows]. | |||
| B.4. macOS Implementation Details | B.4. macOS Implementation Details | |||
| Apps can initiate an authorization request in the user's default | Apps can initiate an authorization request in the user's default | |||
| browser using platform APIs for opening URIs in the browser. | browser using platform APIs for opening URIs in the browser. | |||
| To receive the authorization response, custom URI schemes are are a | To receive the authorization response, private-use URI schemes are | |||
| good redirect URI choice on macOS, as the user is returned right back | are a good redirect URI choice on macOS, as the user is returned | |||
| to the app they launched the request from. These are registered in | right back to the app they launched the request from. These are | |||
| the application's bundle information property list using the | registered in the application's bundle information property list | |||
| "CFBundleURLSchemes" key. Loopback IP redirects are another viable | using the "CFBundleURLSchemes" key. Loopback IP redirects are | |||
| option, and listening on the loopback interface is allowed by default | another viable option, and listening on the loopback interface is | |||
| firewall rules. | allowed by default firewall rules. | |||
| A complete open source sample is included in the AppAuth for iOS and | A complete open source sample is included in the AppAuth for iOS and | |||
| macOS [AppAuth.iOSmacOS] library. | macOS [AppAuth.iOSmacOS] library. | |||
| B.5. Linux Implementation Details | B.5. Linux Implementation Details | |||
| Opening the Authorization Request in the user's default browser | Opening the Authorization Request in the user's default browser | |||
| requires a distro-specific command, "xdg-open" is one such tool. | requires a distro-specific command, "xdg-open" is one such tool. | |||
| The loopback redirect is the recommended redirect choice for desktop | The loopback redirect is the recommended redirect choice for desktop | |||
| apps on Linux to receive the authorization response. | apps on Linux to receive the authorization response. | |||
| Appendix C. Acknowledgements | Appendix C. Acknowledgements | |||
| The author would like to acknowledge the work of Marius Scurtescu, | The author would like to acknowledge the work of Marius Scurtescu, | |||
| and Ben Wiley Sittler whose design for using custom URI schemes in | and Ben Wiley Sittler whose design for using private-use URI schemes | |||
| native OAuth 2.0 clients formed the basis of Section 7.1. | in native OAuth 2.0 clients formed the basis of Section 7.1. | |||
| The following individuals contributed ideas, feedback, and wording | The following individuals contributed ideas, feedback, and wording | |||
| that shaped and formed the final specification: | that shaped and formed the final specification: | |||
| Andy Zmolek, Steven E Wright, Brian Campbell, Paul Madsen, Nat | Andy Zmolek, Steven E Wright, Brian Campbell, Paul Madsen, Nat | |||
| Sakimura, Iain McGinniss, Rahul Ravikumar, Eric Sachs, Breno de | Sakimura, Iain McGinniss, Rahul Ravikumar, Eric Sachs, Breno de | |||
| Medeiros, Adam Dawes, Naveen Agarwal, Hannes Tschofenig, Ashish Jain, | Medeiros, Adam Dawes, Naveen Agarwal, Hannes Tschofenig, Ashish Jain, | |||
| Erik Wahlstrom, Bill Fisher, Sudhi Umarji, Michael B. Jones, Vittorio | Erik Wahlstrom, Bill Fisher, Sudhi Umarji, Michael B. Jones, Vittorio | |||
| Bertocci, Dick Hardt, David Waite, and Ignacio Fiorentino. | Bertocci, Dick Hardt, David Waite, and Ignacio Fiorentino. | |||
| End of changes. 52 change blocks. | ||||
| 180 lines changed or deleted | 186 lines changed or added | |||
This html diff was produced by rfcdiff 1.48. The latest version is available from http://tools.ietf.org/tools/rfcdiff/ | ||||