| page.title=Network Security Configuration | |
| page.keywords=security,network,config | |
| page.metaDescription=Feature that allows app developers to customize network security settings in a safe configuration file. | |
| page.image=images/cards/card-nyc_2x.jpg | |
| @jd:body | |
| <div id="tb-wrapper"> | |
| <div id="tb"> | |
| <h2>In this document</h2> | |
| <ol> | |
| <li><a href="#manifest">Adding a Security Configuration File</a></li> | |
| <li><a href="#CustomTrust">Customizing Trusted CAs</a> | |
| <ol> | |
| <li><a href="#ConfigCustom">Configuring a Trusted Custom CA</a></li> | |
| <li><a href="#LimitingCas">Limiting the Set of Trusted CAs</a></li> | |
| <li><a href="#TrustingAdditionalCas">Trusting Additional CAs</a></li> | |
| </ol> | |
| </li> | |
| <li><a href="#TrustingDebugCa">Debugging-only CAs</a></li> | |
| <li><a href="#CleartextTrafficPermitted">Opting Out of Cleartext Traffic</a></li> | |
| <li><a href="#CertificatePinning">Pinning Certificates</a></li> | |
| <li><a href="#ConfigInheritance">Configuration Inheritance Behavior</a></li> | |
| <li><a href="#FileFormat">Configuration File Format</a></li> | |
| </ol> | |
| </div> | |
| </div> | |
| <p> | |
| The Network Security Configuration feature lets apps customize their network | |
| security settings in a safe, declarative configuration file without modifying | |
| app code. These settings can be configured for specific domains and for a | |
| specific app. The key capabilities of this feature are as follows: | |
| </p> | |
| <ul> | |
| <li> | |
| <b>Custom trust anchors:</b> Customize which Certificate Authorities (CA) | |
| are trusted for an app's secure connections. For | |
| example, trusting particular self-signed certificates or restricting the | |
| set of public CAs that the app trusts. | |
| </li> | |
| <li> | |
| <b>Debug-only overrides:</b> Safely debug secure connections in an app | |
| without added risk to the installed base. | |
| </li> | |
| <li> | |
| <b>Cleartext traffic opt-out:</b> Protect apps from | |
| accidental usage of cleartext traffic. | |
| </li> | |
| <li> | |
| <b>Certificate pinning:</b> Restrict an app's secure connection to | |
| particular certificates. | |
| </li> | |
| </ul> | |
| <h2 id="manifest">Adding a Security Configuration File</h2> | |
| <p> | |
| The Network Security Configuration feature uses an XML file where you specify | |
| the settings for your app. You must include an entry in the manifest of your | |
| app to point to this file. The following code excerpt from a manifest | |
| demonstrates how to create this entry: | |
| </p> | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <manifest ... > | |
| <application android:networkSecurityConfig="@xml/network_security_config" | |
| ... > | |
| ... | |
| </application> | |
| </manifest> | |
| </pre> | |
| <h2 id="CustomTrust">Customizing Trusted CAs</h2> | |
| <p> | |
| An app may want to trust a custom set of CAs instead of the platform | |
| default. The most common reasons of this are: | |
| </p> | |
| <ul> | |
| <li>Connecting to a host with a custom certificate authority, such as a | |
| CA that is self-signed or is issued internally within a company. | |
| </li> | |
| <li>Limiting the set of CAs to only the CAs you trust instead of every | |
| pre-installed CA. | |
| </li> | |
| <li>Trusting additional CAs not included in the system. | |
| </li> | |
| </ul> | |
| <p> | |
| By default, secure connections (using protocols like TLS and HTTPS) from all | |
| apps trust the pre-installed system CAs, and apps targeting Android 6.0 (API | |
| level 23) and lower also trust the user-added CA store by default. An app can | |
| customize its own connections using {@code base-config} (for app-wide | |
| customization) or {@code domain-config} (for per-domain customization). | |
| </p> | |
| <h3 id="ConfigCustom">Configuring a Custom CA</h3> | |
| <p> | |
| Assume you want to connect to your host which uses a self-signed SSL | |
| certificate or to a host whose SSL certificate is issued by a non-public CA | |
| which you trust, such as your company's internal CA. | |
| </p> | |
| <p> | |
| <code>res/xml/network_security_config.xml</code>: | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <domain-config> | |
| <domain includeSubdomains="true">example.com</domain> | |
| <trust-anchors> | |
| <certificates src="@raw/my_ca"/> | |
| </trust-anchors> | |
| </domain-config> | |
| </network-security-config> | |
| </pre> | |
| </p> | |
| <p> | |
| Add the self-signed or non-public CA certificate, in PEM or DER format, to | |
| {@code res/raw/my_ca}. | |
| </p> | |
| <h3 id="LimitingCas">Limiting the Set of Trusted CAs</h3> | |
| <p> | |
| An app that does not want to trust all CAs trusted by system can | |
| instead specify its own reduced set of CAs to trust. This protects the | |
| app from fradulent certificates issued by any of the other CAs. | |
| </p> | |
| <p> | |
| The configuration to limit the set of trusted CAs is similar to <a href= | |
| "#ConfigCustom">trusting a custom CA</a> for a specific domain except | |
| that multiple CAs are provided in the resource. | |
| </p> | |
| <p> | |
| <code>res/xml/network_security_config.xml</code>: | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <domain-config> | |
| <domain includeSubdomains="true">secure.example.com</domain> | |
| <domain includeSubdomains="true">cdn.example.com</domain> | |
| <trust-anchors> | |
| <certificates src="@raw/trusted_roots"/> | |
| </trust-anchors> | |
| </domain-config> | |
| </network-security-config> | |
| </pre> | |
| </p> | |
| <p> | |
| Add the trusted CAs, in PEM or DER format, to {@code res/raw/trusted_roots}. | |
| Note that if using PEM format the file must contain <em>only</em> PEM data | |
| and no extra text. You can also provide multiple | |
| <a href="#certificates"><code><certificates></code></a> | |
| elements instead of one. | |
| </p> | |
| <h3 id="TrustingAdditionalCas"> | |
| Trusting Additional CAs | |
| </h3> | |
| <p> | |
| An app may want to trust additional CAs not trusted by the system, | |
| this could be due to the system not yet including the CA or a CA that does | |
| not meet the requirements for inclusion into the Android system. An | |
| app can do this by specifying multiple certificate sources for a | |
| configuration. | |
| </p> | |
| <p> | |
| <code>res/xml/network_security_config.xml</code>: | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <base-config> | |
| <trust-anchors> | |
| <certificates src="@raw/extracas"/> | |
| <certificates src="system"/> | |
| </trust-anchors> | |
| </base-config> | |
| </network-security-config> | |
| </pre> | |
| </p> | |
| <h2 id="TrustingDebugCa">Configuring CAs for Debugging</h2> | |
| <p> | |
| When debugging an app that connects over HTTPS, you may want to | |
| connect to a local development server, which does not have the SSL | |
| certificate for your production server. In order to support this without any | |
| modification to your app's code, you can specify debug-only CAs, which | |
| are trusted <i>only</i> when <a href= | |
| "{@docRoot}guide/topics/manifest/application-element.html#debug"> | |
| android:debuggable</a> | |
| is {@code true}, by using {@code debug-overrides}. Normally, IDEs and build | |
| tools set this flag automatically for non-release builds. | |
| </p> | |
| <p> | |
| This is safer than the usual conditional code because, as a security | |
| precaution, app stores do not accept apps which are marked | |
| debuggable. | |
| </p> | |
| <p> | |
| <code>res/xml/network_security_config.xml</code>: | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <debug-overrides> | |
| <trust-anchors> | |
| <certificates src="@raw/debug_cas"/> | |
| </trust-anchors> | |
| </debug-overrides> | |
| </network-security-config> | |
| </pre> | |
| </p> | |
| <h2 id="CleartextTrafficPermitted">Opting Out of Cleartext Traffic</h2> | |
| <p> | |
| Applications intending to connect to destinations using only secure | |
| connections can opt-out of supporting cleartext (using the unencrypted HTTP | |
| protocol instead of HTTPS) to those destinations. This option helps prevent | |
| accidental regressions in apps due to changes in URLs provided by external | |
| sources such as backend servers. | |
| See {@link android.security.NetworkSecurityPolicy#isCleartextTrafficPermitted | |
| NetworkSecurityPolicy.isCleartextTrafficPermitted()} for more details. | |
| </p> | |
| <p> | |
| For example, an app may want to ensure that all connections to {@code | |
| secure.example.com} are always done over HTTPS to protect sensitive traffic | |
| from hostile networks. | |
| </p> | |
| <p> | |
| <code>res/xml/network_security_config.xml</code>: | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <domain-config cleartextTrafficPermitted="false"> | |
| <domain includeSubdomains="true">secure.example.com</domain> | |
| </domain-config> | |
| </network-security-config> | |
| </pre> | |
| </p> | |
| <h2 id="CertificatePinning">Pinning Certificates</h2> | |
| <p> | |
| Normally, an app trusts all pre-installed CAs. If any of these CAs were to | |
| issue a fradulent certificate, the app would be at risk from a | |
| man-in-the-middle attack. Some apps choose to limit the set of certificates | |
| they accept by either limiting the set of CAs they trust or by certificate | |
| pinning. | |
| </p> | |
| <p> | |
| Certificate pinning is done by providing a set of certificates by hash of the | |
| public key (<code>SubjectPublicKeyInfo</code> of the X.509 certificate). A | |
| certificate chain is then valid only if the certificate chain contains at | |
| least one of the pinned public keys. | |
| </p> | |
| <p> | |
| Note that, when using certificate pinning, you should always include a backup | |
| key so that if you are forced to switch to new keys or change CAs (when | |
| pinning to a CA certificate or an intermediate of that CA), your | |
| app's connectivity is unaffected. Otherwise, you must push out | |
| an update to the app to restore connectivity. | |
| </p> | |
| <p> | |
| Additionally, it is possible to set an expiration time for pins after which | |
| pinning is not performed. This helps prevent connectivity issues in | |
| apps which have not been updated. However, setting an expiration time | |
| on pins may enable pinning bypass. | |
| </p> | |
| <p> | |
| <code>res/xml/network_security_config.xml</code>: | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <domain-config> | |
| <domain includeSubdomains="true">example.com</domain> | |
| <pin-set expiration="2018-01-01"> | |
| <pin digest="SHA-256">7HIpactkIAq2Y49orFOOQKurWxmmSFZhBCoQYcRhJ3Y=</pin> | |
| <!-- backup pin --> | |
| <pin digest="SHA-256">fwza0LRMXouZHRC8Ei+4PyuldPDcf3UKgO/04cDM1oE=</pin> | |
| </pin-set> | |
| </domain-config> | |
| </network-security-config> | |
| </pre> | |
| </p> | |
| <h2 id="ConfigInheritance">Configuration Inheritance Behavior</h2> | |
| <p> | |
| Values not set in a specific configuration are inherited. This behavior allows | |
| more complex configurations while keeping the configuration file readable. | |
| </p> | |
| <p> | |
| If a value is not set in a specific entry, then the value from the more | |
| general entry is used. For example, values not set in a {@code domain-config} | |
| are taken from the parent {@code domain-config}, if nested, or from the {@code | |
| base-config} if not. Values not set in the {@code base-config} use the | |
| platform default values. | |
| </p> | |
| <p> | |
| For example, consider where all connections to subdomains of {@code | |
| example.com} must use a custom set of CAs. Additonally, cleartext traffic to | |
| these domains is permitted <em>except</em> when connecting to {@code | |
| secure.example.com}. By nesting the configuration for {@code | |
| secure.example.com} inside the configuration for {@code example.com}, the | |
| {@code trust-anchors} does not need to be duplicated. | |
| </p> | |
| <p> | |
| <code>res/xml/network_security_config.xml</code>: | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <domain-config> | |
| <domain includeSubdomains="true">example.com</domain> | |
| <trust-anchors> | |
| <certificates src="@raw/my_ca"/> | |
| </trust-anchors> | |
| <domain-config cleartextTrafficPermitted="false"> | |
| <domain includeSubdomains="true">secure.example.com</domain> | |
| </domain-config> | |
| </domain-config> | |
| </network-security-config> | |
| </pre> | |
| </p> | |
| <h2 id="FileFormat">Configuration File Format</h2> | |
| <p> | |
| The Network Security Configuration feature uses an XML file format. | |
| The overall structure of the file is shown in the following code sample: | |
| </p> | |
| <pre> | |
| <?xml version="1.0" encoding="utf-8"?> | |
| <network-security-config> | |
| <base-config> | |
| <trust-anchors> | |
| <certificates src="..."/> | |
| ... | |
| </trust-anchors> | |
| </base-config> | |
| <domain-config> | |
| <domain>android.com</domain> | |
| ... | |
| <trust-anchors> | |
| <certificates src="..."/> | |
| ... | |
| </trust-anchors> | |
| <pin-set> | |
| <pin digest="...">...</pin> | |
| ... | |
| </pin-set> | |
| </domain-config> | |
| ... | |
| <debug-overrides> | |
| <trust-anchors> | |
| <certificates src="..."/> | |
| ... | |
| </trust-anchors> | |
| </debug-overrides> | |
| </network-security-config> | |
| </pre> | |
| <p> | |
| The following sections describe the syntax and other details of the file | |
| format. | |
| </p> | |
| <h3 id="network-security-config"> | |
| <network-security-config> | |
| </h3> | |
| <dl class="xml"> | |
| <dt> | |
| can contain: | |
| </dt> | |
| <dd> | |
| 0 or 1 of <code><a href="#base-config"><base-config></a></code><br> | |
| Any number of <code><a href= | |
| "#domain-config"><domain-config></a></code><br> | |
| 0 or 1 of <code><a href="#debug-overrides"><debug-overrides></a></code> | |
| </dd> | |
| </dl> | |
| <h3 id="base-config"> | |
| <base-config> | |
| </h3> | |
| <dl class="xml"> | |
| <dt> | |
| syntax: | |
| </dt> | |
| </dl> | |
| <pre class="stx"> | |
| <base-config <a href= | |
| "#CleartextTrafficPermitted">cleartextTrafficPermitted</a>=["true" | "false"]> | |
| ... | |
| </base-config> | |
| </pre> | |
| <dl class="xml"> | |
| <dt> | |
| can contain: | |
| </dt> | |
| <dd> | |
| <code><a href="#trust-anchors"><trust-anchors></a></code> | |
| </dd> | |
| <dt> | |
| description: | |
| </dt> | |
| <dd> | |
| The default configuration used by all connections whose destination is not | |
| covered by a <a href="#domain-config"><code>domain-config</code></a>. | |
| <p> | |
| Any values that are not set use the platform default values. The default | |
| configuration for apps targeting Android 7.0 (API level 24) and higher is as | |
| follows: | |
| </p> | |
| <pre> | |
| <base-config cleartextTrafficPermitted="true"> | |
| <trust-anchors> | |
| <certificates src="system" /> | |
| </trust-anchors> | |
| </base-config> | |
| </pre> | |
| The default configuration for apps targeting Android 6.0 (API level 23) and | |
| lower is as follows: | |
| <pre> | |
| <base-config cleartextTrafficPermitted="true"> | |
| <trust-anchors> | |
| <certificates src="system" /> | |
| <certificates src="user" /> | |
| </trust-anchors> | |
| </base-config> | |
| </pre> | |
| </dd> | |
| </dl> | |
| <h3 id="domain-config"><domain-config></h3> | |
| <dl class="xml"> | |
| <dt>syntax:</dt> | |
| <dd> | |
| <pre class="stx"><domain-config <a href="#CleartextTrafficPermitted">cleartextTrafficPermitted</a>=["true" | "false"]> | |
| ... | |
| </domain-config></pre> | |
| </dd> | |
| <dt>Can Contain:</dt> | |
| <dd> | |
| 1 or more <code><a href="#domain"><domain></a></code> | |
| <br/>0 or 1 <code><a href="#trust-anchors"><trust-anchors></a></code> | |
| <br/>0 or 1 <code><a href="#pin-set"><pin-set></code></a> | |
| <br/>Any number of nested <code><domain-config></code></dd> | |
| <dt>Description</dt> | |
| <dd>Configuration used for connections to specific destinations, as defined by | |
| the {@code domain} elements. | |
| <p>Note that if multiple {@code domain-config} elements cover a destination, the | |
| configuration with the most specific (longest) matching domain rule is | |
| used.</p></dd> | |
| </dl> | |
| <h3 id="domain"><domain></h3> | |
| <dl class="xml"> | |
| <dt> | |
| syntax: | |
| </dt> | |
| <dd> | |
| <pre class="stx"> | |
| <domain includeSubdomains=["true" | "false"]>example.com</domain> | |
| </pre> | |
| </dd> | |
| <dt> | |
| Attributes: | |
| </dt> | |
| <dd> | |
| <dl class="attr"> | |
| <dt> | |
| {@code includeSubdomains} | |
| </dt> | |
| <dd> | |
| If {@code "true"}, then this domain rule matches the domain and all | |
| subdomains, including subdomains of subdomains. Otherwise, the rule only | |
| applies to exact matches. | |
| </dd> | |
| </dl> | |
| </dd> | |
| <dt> | |
| Description: | |
| </dt> | |
| </dl> | |
| <h3 id="debug-overrides"><debug-overrides></h3> | |
| <dl class="xml"> | |
| <dt> | |
| syntax: | |
| </dt> | |
| <dd> | |
| <pre class="stx"> | |
| <debug-overrides> | |
| ... | |
| </debug-overrides> | |
| </pre> | |
| </dd> | |
| <dt> | |
| Can Contain: | |
| </dt> | |
| <dd> | |
| 0 or 1 <code><a href="#trust-anchors"><trust-anchors></a></code> | |
| </dd> | |
| <dt> | |
| Description: | |
| </dt> | |
| <dd> | |
| Overrides to be applied when <a href= | |
| "{@docRoot}guide/topics/manifest/application-element.html#debug">android:debuggable</a> | |
| is {@code "true"}, which is normally the case for non-release builds | |
| generated by IDEs and build tools. Trust anchors specified in {@code | |
| debug-overrides} are added to all other configurations, and certificate | |
| pinning is not performed when the server's certificate chain uses one of | |
| these debug-only trust anchors. If <a href= | |
| "{@docRoot}guide/topics/manifest/application-element.html#debug">android:debuggable</a> | |
| is {@code "false"}, then this section is completely ignored. | |
| </dd> | |
| </dl> | |
| <h3 id="trust-anchors"><trust-anchors></h3> | |
| <dl class="xml"> | |
| <dt> | |
| syntax: | |
| </dt> | |
| <dd> | |
| <pre class="stx"> | |
| <trust-anchors> | |
| ... | |
| </trust-anchors> | |
| </pre> | |
| </dd> | |
| <dt> | |
| Can Contain: | |
| </dt> | |
| <dd> | |
| Any number of <code><a href="#certificates"><certificates></a></code> | |
| </dd> | |
| <dt> | |
| Description: | |
| </dt> | |
| <dd> | |
| Set of trust anchors for secure connections. | |
| </dd> | |
| </dl> | |
| <h3 id="certificates"><certificates></h3> | |
| <dl class="xml"> | |
| <dt>syntax:</dt> | |
| <dd><pre class="stx"><certificates src=["system" | "user" | "<i>raw resource</i>"] | |
| overridePins=["true" | "false"] /> | |
| </pre></dd> | |
| <dt>description:</dt> | |
| <dd>Set of X.509 certificates for {@code trust-anchors} elements.</dd> | |
| <dt>attributes:</dt> | |
| <dd><dl class="attr"> | |
| <dt>{@code src}</dt> | |
| <dd> | |
| The source of CA certificates. Each certificate can be one of the following: | |
| <ul> | |
| <li>a raw resource ID pointing to a file containing X.509 certificates. | |
| Certificates must be encoded in DER or PEM format. In the case of PEM | |
| certificates, the file <em>must not</em> contain extra non-PEM data such as | |
| comments. | |
| </li> | |
| <li>{@code "system"} for the pre-installed system CA certificates | |
| </li> | |
| <li>{@code "user"} for user-added CA certificates | |
| </li> | |
| </ul> | |
| </dd> | |
| <dt>{@code overridePins}</dt> | |
| <dd> | |
| <p> | |
| Specifies if the CAs from this source bypass certificate pinning. If {@code | |
| "true"}, then pinning is not performed on certificate chains which are | |
| signed by one of the CAs from this source. This can be useful for debugging | |
| CAs or for testing man-in-the-middle attacks on your app's secure traffic. | |
| </p> | |
| <p> | |
| Default is {@code "false"} unless specified in a {@code debug-overrides} | |
| element, in which case the default is {@code "true"}. | |
| </p> | |
| </dd> | |
| </dl> | |
| </dd> | |
| <h3 id="pin-set"><pin-set></h3> | |
| <dl class="xml"> | |
| <dt> | |
| syntax: | |
| </dt> | |
| <dd> | |
| <pre class="stx"> | |
| <pin-set expiration="date"> | |
| ... | |
| </pin-set> | |
| </pre> | |
| </dd> | |
| <dt> | |
| Can Contain: | |
| </dt> | |
| <dd> | |
| Any number of <code><a href="#pin"><pin></a></code> | |
| </dd> | |
| <dt> | |
| Description: | |
| </dt> | |
| <dd> | |
| A set of public key pins. For a secure connection to be trusted, one of the | |
| public keys in the chain of trust must be in the set of pins. See | |
| <code><a href="#pin"><pin></a></code> for the format of pins. | |
| </dd> | |
| <dt> | |
| Attributes: | |
| </dt> | |
| <dd> | |
| <dl class="attr"> | |
| <dt> | |
| {@code expiration} | |
| </dt> | |
| <dd> | |
| The date, in {@code yyyy-MM-dd} format, on which the pins expire, thus | |
| disabling pinning. If the attribute is not set, then the pins do not | |
| expire. | |
| <p> | |
| Expiration helps prevent connectivity issues in apps which do not get | |
| updates to their pin set, such as when the user disables app updates. | |
| </p> | |
| </dd> | |
| </dl> | |
| </dd> | |
| </dl> | |
| <h3 id="pin"><pin></h3> | |
| <dl class="xml"> | |
| <dt> | |
| syntax: | |
| </dt> | |
| <dd> | |
| <pre class="stx"> | |
| <pin digest=["SHA-256"]>base64 encoded digest of X.509 | |
| SubjectPublicKeyInfo (SPKI)</pin> | |
| </pre> | |
| </dd> | |
| <dt> | |
| Attributes: | |
| </dt> | |
| <dd> | |
| <dl class="attr"> | |
| <dt> | |
| {@code digest} | |
| </dt> | |
| <dd> | |
| The digest algorithm used to generate the pin. Currently, only | |
| {@code "SHA-256"} is supported. | |
| </dd> | |
| </dl> | |
| </dd> | |
| </dl> |