Worker to change cacheKey based on user


We are using CloudFlare in front of an API whose origin server is behind auth. Users login, and most receive the same data. In a few cases, some users receive different data based on their username and access level.

E.g. users Rahul accesses the endpoint /fruit. Rahul receives Apples, Bananas. All other users receive Apples, Bananas and Pears.

So we need to change the cacheKey when Rahul (and a few others) make a request, appending their username or auth string, and this is where I’m stuck. I hacked up a basic example, but I’m struggling with the concept of what the worker should actually do. Is it:

  1. Have we got auth in the response? If so, Base64 decode the Authorization header to get the username
  2. Is username in the list of restricted usernames?
  3. If so, append cachekey.

Should the worker then check the cache for this cachekey and apply some logic (if not there, insert), or can I just return the altered cacheKey as this guide suggests?

I’ve tried various methods, and an additional problem was the worker seemed to interfere with the authentication (on the origin server), so I’m not sure if my understanding of what a worker can/should do is right.

Really appreciate if someone can advise


Made a bit of progress, but changing the cacheKey to append the user has no impact. If john accesses /fruit followed by amy, the headers should return a MISS for Amy but it’s always a HIT. Am I storing the new cacheKey correctly? event.waitUntil(cache.put(cacheKey, response.clone()))

  const request = event.request
  const cacheUrl = new URL(request.url)
  const users = ['john', 'amy', 'ed']

  let ds = request.headers.get("Authorization")
  if(ds && ds != null) {
    let ds_e = ds.split('Basic ')[1]
    // Decode Base64
    let ds_ue = atob(ds_e);
    let username = ds_ue.split(':')[0];
    let n = users.includes(username);
       if(n) {
        // Add username to cacheUrl to make it unique
        var cacheKey = new Request((cacheUrl + ds_e).toString(), request);
        var cacheType = 'username'

             else {
                 var cacheKey = new Request(cacheUrl.toString(), request);


  // Construct the cache key from the cache URL
  const cache = caches.default

  // Check whether the value is already available in the cache
  // if not, you will need to fetch it from origin, and store it in the cache
  // for future access
  let response = await cache.match(cacheKey)

  if (!response) {
    // If not in cache, get it from origin
    response = await fetch(request)

    // Must use Response constructor to inherit all of response's fields
    response = new Response(response.body, response)

    response.headers.set("X-BESPOKE-CACHEKEY", cacheUrl)
    if (cacheType) {
      response.headers.set("X-BESPOKE-CACHEKEYTYPE", 'username');
    {response.headers.set("X-BESPOKE-CACHEKEYTYPE", 'url');}

    // Store the fetched response as cacheKey
    // Use waitUntil so you can return the response without blocking on
    // writing to cache
    event.waitUntil(cache.put(cacheKey, response.clone()))
  return response

addEventListener("fetch", event => {
  try {
    const request = event.request
    return event.respondWith(handleRequest(event))
  } catch (e) {
    return event.respondWith(new Response("Error thrown " + e.message))