Cloudflare Edge-side personalization

You can use Cloudflare to classify visitors and execute personalization instructions on the edge. This approach gives you the user experience benefits of server-side rendering with the performance and scalability benefits of a CDN.

tip

For more information about the benefits of executing personalization using Cloudflare, see the overview of edge-side personalization.

Before you start

You must have the following available to complete the instructions in this section:

  1. Administrator access to Cloudflare Dashboard. You can use their free tier if you don't have an account.
  2. Ability to clone a GitHub repository.
  3. Node.js v16+ installed locally.
  4. An application with edge-side personalization activated.
  5. Npm access token from Uniform. Edge-side personalization requires private packages. If you don't have an access token, contact us.

Cloudflare Wrangler is a CLI enables you to send commands to Cloudflare without having to log into the Cloudflare dashboard. Entering commands on the CLI is faster than having to navigate through a lot of different screens in the dashboard.

  1. Install Wrangler.
  2. Authenticate to Cloudflare.

Next steps

Now you are ready to create the Cloudflare Worker, which is the component that executes the personalization instructions exposed by your front-end application.

You have two options for writing the Cloudflare Worker. You can build it from scratch or use a functional example provided by Uniform.

tip

This section guides you through the process of building a Cloudflare Worker that can execute Uniform personalization instructions by explaining each step. It takes longer to go through, but it will help you understand why each line of code is needed.

  1. Clone the following repository:

    https://github.com/cloudflare/worker-typescript-template
  2. Add the following environment variable to your workstation:

    NameValue
    NPM_TOKENThe npm access token from Uniform.

    About this step

    You can't set this value in the .env file. That file defines environment variables available within your app, while this environment is needed by another app (such as npm).

    You can set the environment variable to be system wide or just active in your current terminal.

  3. Add the following file to the root of the repository:

    //registry.npmjs.org/:_authToken=${NPM_TOKEN} engine-strict = true

    About this step

    This file ensures you can access the private packages required for edge-side personalization.

  4. Add the following packages:

    @uniformdev/context-edge @uniformdev/context-edge-cloudflare
  5. Add the following package as dev dependencies:

    @uniformdev/cli

    About this step

    The Uniform CLI is used to download the Uniform manifest during the build process.

  6. Add the following to the file tsconfig.json:

    "sourceMap": true, "esModuleInterop": true, "resolveJsonModule": true, "types": [

    About this step

    To keep this example simple and self-contained, the Uniform manifest is included with the Cloudflare Worker. This means that any time the manifest changes, the Cloudflare Worker must be re-deployed. Uniform webhooks can be used to automate this process.

  7. Add the following to the file package.json:

    ... "scripts": { "download:manifest": "uniform context manifest download --output ./src/context-manifest.json", "build": "webpack", "format": "prettier --write '*.{json,js}' 'src/**/*.{js,ts}' 'test/**/*.{js,ts}'", "lint": "eslint --max-warnings=0 src && prettier --check '*.{json,js}' 'src/**/*.{js,ts}' 'test/**/*.{js,ts}'", "test": "jest --config jestconfig.json --verbose" }, ...

    About this step

    This script uses the Uniform CLI to download the Uniform manifest to a local file.

  8. Replace the code in the file src/handler.ts with the following:

    import { createEdgeContext } from '@uniformdev/context-edge' import { createCloudflareProxyEdgeHandler } from '@uniformdev/context-edge-cloudflare' import { ManifestV2 } from '@uniformdev/context'
  9. Add the following code:

    import manifest from "./context-manifest.json";
  10. Add the following code:

    export async function handleRequest(request: Request): Promise<Response> { }

    About this step

    This is the function that runs when the Cloudflare Worker is invoked.

  11. Add the following code:

    export async function handleRequest(request: Request): Promise<Response> { //@ts-ignore if (!ORIGIN_URL) { console.error('ORIGIN_URL environment is not defined') return new Response('Configuration Error', { status: 500, }) } }

    About this step

    This adds validation logic to ensure the origin has been identified. The Cloudflare Worker makes a request to the origin to retrieve the markup with the personalization instructions.

  12. Add the following code:

    export async function handleRequest(request: Request): Promise<Response> { //@ts-ignore if (!ORIGIN_URL) { console.error('ORIGIN_URL environment is not defined') return new Response('Configuration Error', { status: 500, }) } const handler = createCloudflareProxyEdgeHandler() }

    About this step

    This code creates the component that makes a request to the origin and executes any personalization instructions in the response.

  13. Add the following code:

    export async function handleRequest(request: Request): Promise<Response> { //@ts-ignore if (!ORIGIN_URL) { console.error('ORIGIN_URL environment is not defined') return new Response('Configuration Error', { status: 500, }) } const handler = createCloudflareProxyEdgeHandler() const context = createEdgeContext({ request, manifest: manifest as ManifestV2, }) }

    About this step

    This creates the context object that has controls how the personalization process works.

  14. Add the following code:

    export async function handleRequest(request: Request): Promise<Response> { //@ts-ignore if (!ORIGIN_URL) { console.error('ORIGIN_URL environment is not defined') return new Response('Configuration Error', { status: 500, }) } const handler = createCloudflareProxyEdgeHandler() const context = createEdgeContext({ request, manifest: manifest as ManifestV2, }) const { response } = await handler({ context, request, //@ts-ignore originUrl: new URL(`https://${ORIGIN_URL}`).origin, }) return response }

    About this step

    This code uses the proxy edge handler to make a request to the origin, execute the personalization instructions in the response, and return a response using the personalized results.

  1. Create a file .env with the following environment variables:

    Variable nameValue
    UNIFORM_PROJECT_IDThe Uniform project whose manifest is retrieved.
    UNIFORM_API_KEYThe Uniform API key used to retrieve the manifest.
  2. In the file wrangler.toml, you must set the value for account_id. This must match your Cloudflare account ID You can retrieve this value by entering the following command on the CLI:

    wrangler whoami
  3. In the file wrangler.toml, you must set an environment variable to identify the origin (such as the web server that's hosting your front-end application). You must add a new section to the file:

    [vars] ORIGIN_URL = "!!! YOUR ORIGIN URL !!!"

    About this step

    While the variable name suggests this value should be a URL, it really must be the host name for the origin. For example, if the origin is located at https://some-origin.com, the value should be some-origin.com.

You can use Wrangler to run the Cloudflare Worker locally. This enables you to test and debug without having to deploy to Cloudflare.

  1. Enter the following command on the CLI:

    wrangler dev

    About this step

    This starts a local web server that hosts the Cloudflare Worker.

  2. Open your browser to the endpoint shown in the console.

  1. Enter the following commands on the CLI:

    wrangler build wrangler publish

    About this step

    These commands build and publish your Cloudflare Worker to Cloudflare.

Next steps

Now that you have Cloudflare delivering edge-side personalization, you might want to take advantage of another feature available when you run personalization on Cloudflare: location-based personalization.