Platforms

For both web and mobile platforms, we have established a security baseline to which our projects should adhere. This baseline should be present on all environments that are publicly available, which often are the test, acceptance and production environments. It is wise to make sure these settings are already present in early development in case they impact functionality.

Web

Web Server

These settings apply to all kinds of webservers, like Apache, Nginx or IIS.

Redirect to HTTPS

All HTTP traffic should be redirected to HTTPS to make sure traffic is encrypted.

More information can be found at: https://support.google.com/webmasters/answer/6073543?hl=en

All modern browsers will automatically try to use HTTPS, even when the user types http://. To make sure that your redirect is working, you can try to use CURL to make sure your redirect is actually working.

curl -I http://<domain>

If you get a 301 response to the HTTPS equivalent, then you've correctly set a redirect.

TLS 1.2 or higher

This guideline is explained in detail in chapter SSL.

Strong ciphers

This guideline is explained in detail in chapter SSL

No version information in HTTP response

By revealing version information in HTTP responses, attackers can use this information for targeted attacks. In all HTTP responses there should be no information about which software, frameworks or systems being used.

More information can be found at: https://www.troyhunt.com/shhh-dont-let-your-response-headers/

Debug information in acceptance and production

No debug information should be shown to the end-user in case of a critical error.

Headers

Referrer policy

We set the referrer policy by using the following header and value:

Referrer-Policy: same-origin

More information about this header can be found here: https://scotthelme.co.uk/a-new-security-header-referrer-policy/

Cache-Control

Browsers will store pages locally within their own cache, even when a HTTPS connection is being used. Attackers who gain access to a machine can use this to retrieve sensitive data from the cache of a browser. To prevent this, we set the following headers:

Cache-Control: no-store

Pragma: no-cache

More information about this header can be found at the site of OWASP: https://www.owasp.org/index.php/Testing_for_Browser_cache_weakness_(OTG-AUTHN-006)

X-Frame-Options

By using the X-Frame-Options header, a web application can tell the browser how it should act when the application is loaded within a frame. The web application can be vulnerable for clickjacking when this header is not used. The value should contain a curated list of origins that are allowed to load the application within a frame, or it should be disallowed at all.

To only allow the application to be loaded within a frame on the same origin, the following header should be used:

X-Frame-Options: SAMEORIGIN

The website may not be embedded:

X-Frame-Options: DENY

More information about this header can be found at the site of OWASP:

https://www.owasp.org/index.php/Clickjacking_Defense_Cheat_Sheet

Strict-Transport-Security

We use the Strict-Transport-Security header (HSTS) to inform the end-user that all (future) connections should use SSL/TLS. The following value is advised:

Strict-Transport-Security: max-age=31536000; includeSubdomains; preload;

By using this value, we also ensure that this domain (and all subdomains) are added to the Google Chrome global HSTS list which make sure that all connections use SSL/TLS or otherwise the browser will stop the user from connecting.

More information about this header can be found at Mozilla:

https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Strict-Transport-Security

X-Content-Type-Options

To make sure that MIME-types can't be changed during transport, we user the x-content-type-options header. We use the following value:

X-Content-Type-Options: nosniff

More information about this header can be found at Mozilla:

https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/X-Content-Type-Options

X-XSS-Protection

If the X-XSS-Protection header is used, a browser will ensure that the XSS filter will be enabled. This way, XSS-type attacks will be mitigated. All modern browsers support this header. We use the following value:

X-XSS-Protection: 1; mode=block

More information about this header can be found at Veracode:

https://www.veracode.com/blog/2014/03/guidelines-for-setting-security-headers

Permissions-Policy

This header ensures that the browser does not grant access to certain modern features and hardware like the microphone, geolocation etc. that the website does not need. Use the following value:

Permissions-Policy: geolocation=(), microphone=(), camera=(), magnetometer=(), gyroscope=(), payment=(), usb=()

Content-Security-Policy Header

The Content-Security-Policy header (also known as CSP header) dictates which content-types are allowed and from which origin. This is a useful tool againt client-side code-injection vulnerabilities. By default, we don't use the "unsafe-inline" and "unsafe-eval" values. Unfortunately, this does break functionality sometimes (e.g. when using a Google Maps map in your application) in which case it is allowed to deviate from this policy. Try to keep this value as strict as possible.

More information about this header can be found at OWASP:

https://www.owasp.org/index.php/Content_Security_Policy

Domains

DNSSEC

By default, the DNS-protocol does not use any encryption, causing all DNS lookups to be visible in a network. By enabling DNSSEC, lookups are encrypted and can not be intercepted by an attacker. For all public domains that are used within the application it holds that DNSSEC should be enabled, when supported by the registrar. It is not required for internal DNS-resolving (like for to example pods and services within a Kubernetes cluster).

API

CORS

Your API must use a CORS policy and it must be as strict as possible. Only allow hosts that need access to the resource within the policy (null is not a safe origin!).

Access-Control-Allow-Origin: <https://example.com>

If a mobile application needs to access this API then it is important to know what the origin of the application is. For Ionic applications this can be found at: https://ionicframework.com/docs/troubleshooting/cors

More information about this header can be found at Mozilla: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Access-Control-Allow-Origin

Web Application

CSRF Tokens

If an application uses cookies for authentication, then anti-csrf-tokens must be implemented on pages where users authenticate. Also, the web application must validate the HTTP-referrer of every request.

By implementing above, we ensure that end-users are protected against cross-site-request-forgery. More information can be found at: https://www.owasp.org/index.php/Cross-Site_Request_Forgery

If your application does not use cookies for authentication, then this does not apply.

Secure cookies

By enabling secure cookies we prevent that the content is sent through an unencrypted (HTTP) connection. If the content of a cookie is intercepted then an attacker can for example take over an user session.

CORS

Your application must use a CORS policy and it must be as strict as possible. Only allow hosts that need access to the resource within the policy (null is not a safe origin!).

Access-Control-Allow-Origin: <https://example.com>

More information about this header can be found at Mozilla: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Access-Control-Allow-Origin

Remove user specific data after logging out

When a user opts to log out of the application, any user info and/or access tokens should be cleared from the device.

Mobile

These settings apply to mobile apps, specifically for the iOS and Android platforms.

iOS

Storage

User info and credentials should be stored in a secure storage container. Containers that are considered secure, are:

  • Local & Session storage (in the browser)
  • Keychain

Remove user specific data after logging out

When a user opts to log out of the application, any user info and/or access tokens should be cleared from the device.

Strict permissions

An application should only request permissions that are strictly required for the app to function correctly.

Android

Storage

User info and credentials should be stored in a secure storage container. Containers that are considered secure, are:

  • Local & Session storage (in the browser)
  • Keystore

Back-up flag

Android offers the option to disable the backing-up of data of your app. If this flag is set to true (which it is by default), data of your application is available from a back-up. If the app stores sensitive data, the option to set this flag to false should be considered.

Autoverify

This requirement is only applicable to applications that are opened from external URLs, e.g., for password forget functionality. To ensure only allowed domains can open the app, applications should specify the autoVerify flag on the intents that are opened.

Remove user specific data after logging out

When a user opts to log out of the application, any user info and/or access tokens should be cleared from the device.

Strict permissions

An application should only request permissions that are strictly required for the app to function correctly.

Applications are signed with a v2 or newer signature

All Android applications that are signed (both app bundles as well as APK's) should be signed with a v2 or newer signature to prevent attackers from modifying the signature of an application due to a weakness in v1 signatures.