Configuring Site Authentication

AEM Live supports token-based authentication. Site authentication is usually applied to both the preview and publish sites, but can also be configured to only protect either site individually.

Warning

Enabling Site Authentication for the publish sites (*.aem.live) will enforce authentication for all your site visitors (intranet). It will also prevent automatic PSI (Page Speed Insights) checks from running on your pull requests in GitHub. For use cases where your BYO CDN should use no (or different) authentication from your .live origin, you will need to configure preview only authentication or bypass authentication with an API_KEY.

If you use authentication, your BYO (production) CDN must not use (disable) caching, otherwise authentication is gradually circumvented.

Limitations

Enable Authentication for the Preview and Publish Sites

1. Enable the Configuration Service

All of the following instructions use the Configuration Service for your site, so follow the linked instructions to enable and authenticate, then perform the following API requests.

2. Create a token to access your protected site

POST an empty body to http://admin.hlx.page/config/{org}/sites/{site}/tokens.json the response will be a JSON object containing an id and value field. Remember both, you'll need them for the next steps:

curl -X POST https://admin.hlx.page/config/acme/sites/website/tokens.json \
  -H 'x-auth-token: <your-auth-token>'
{
  "id": "SGFsbG8gVG9iaWFz",
  "value": "hlx_ZGFzIGlzdCBkZWluIHRva2Vu",
  "created": "2024-08-21T18:28:54.075Z"
}

Note that you now have two tokens:

  1. The auth token for the admin API. This one is highly sensitive
  2. The site token, which can be shared with users and systems than need to access your site

3. Enable the token to access your site

POST to http://admin.hlx.page/config/{org}/sites/{site}/access/site.json so that accessing your site on aem.page and aem.live requires the token value you've retrieved in the previous step.

curl -X POST https://admin.hlx.page/config/acme/sites/website/access/site.json \
  -H 'content-type: application/json' \
  -H 'x-auth-token: <your-auth-token>' \
  --data '{
  "apiKeyId": ["SGFsbG8gVG9iaWFz"]
  }'
{
  "apiKeyId": ["SGFsbG8gVG9iaWFz"]
}

The response contains all token IDs that are currently valid. Each POST request resets the list of tokens, so if you want old tokens to remain valid, make sure to perform a GET request to the same URL before, so your list of tokens remains complete.

The example above sets the site property which controls access to both aem.page and aem.live. This is the most restrictive approach. If you want to limit access to both aem.page and aem.live, POST to site.json. If you want to limit access to aem.page only, post to preview.json. In the unlikely case that you want to limit access to aem.live only, and keep aem.page open, post to live.json.

If you have set tokens for live and either preview or live, then preview and live will override the site-wide settings.

4. Verify that access has been limited

When you open your site in your browser, you will see an HTTP 401 status code, indicating that no access is possible without authentication. Next, try to access the site and provide the token value:

curl https://main--website--acme.aem.live \
  -H 'authorization: token hlx_ZGFzIGlzdCBkZWluIHRva2Vu'

In this request we use the site token value in the Authorization header.

5. Make your CDN pass the right Authorization header

With this change, nobody can access your site without the correct authorization header. This includes your CDN, and therefore every visitor to your site. To enable access again, you need to add the Authorization header to each origin request your CDN makes.

The CDN setup instructions explain how to enable the authorization header for each supported Content Delivery Network.

Browser Access to the Protected Sites

Accessing protected sites directly from a browser requires users to have an appropriate role defined in the project configuration and to sign in using the AEM Sidekick Extension.