Can't purge Cloudflare Workers cache using API

api

#1

I am using Cloudflare Workers to be the CDN for my DigitalOcean Spaces. I prefix all of my files with a lowercase x and use the route https://x6f.cc/x* for scripts enabled. The script below is fairly simple and works really well.

I only use one version of my site and that’s https://DOMAIN.com, I don’t use www or http.

In the Cache API Example it uses the entire request as the key for the cache. I believe that makes it impossible to use the main Cloudflare API to purge a single file. I modified mine to use the URL of the request. However, I am still having issues purging the cache of an individual file. I am using the Cloudflare SDK to call the cachePurge method on a Zones object.

If I purge everything from the web interface, the cached file goes away. I’ve disabled all page rules. My caching level is set to standard. The browser expiration is at 4 hours. I’m using curl to get the headers of the response to help me determine if the file was deleted.

It seems like the only way to purge files created by the Workers Cache API is to purge everything in your zone.

addEventListener('fetch', event => {
  event.respondWith(handleRequest(event, event.request))
})

/**
 * Fetch and log a request
 * @param {Request} request
 */
async function handleRequest(event, request) {

  let response;
  let cache = caches.default;

  const parts = request.url.split("/")
  const file = parts.pop();

  // Don't use CDN. When we delete a file from Spaces, we don't want
  // it cached on two CDNs. Then we'd have to clear the cache for 
  // DO and CF.
  const requestUrl = 'https://SPACES_NAME.nyc3.digitaloceanspaces.com/' + file;

  response = await cache.match(event.request.url);
  
  if(response) {
    response = new Response(response.body, response);
    response.headers.set('x6-cache', 'hit');
  }

  if(!response) {
    response = await fetch(requestUrl);
    response = new Response(response.body, response);
    response.headers.set('x6-cache', 'miss');
    event.waitUntil(cache.put(event.request.url, response.clone()));
  }

  return response;
}

#2

Cache API is per datacenter. Enterprise customer can purge per tag.
Have you tried KV to do this?

I use ?sync on the url to sync from server to kv.


#3

I think I read somewhere that with Argo the Cache API isn’t per data-center. I’ll see if I can find where I saw that.

Unfortunately, KV only offers values up to 64 kB and that isn’t enough for me. I really like your idea of ?sync. Maybe I could use a query like that to purge the file from the cache that way with a Worker.


#4

Here is where I read about Argo’s cache with Workers: Cloudflare Workers Beta Feedback


#5

Support just informed me this is a known issue and they’re working with DigitalOcean to resolve it.


#6

When calling the ?sync my worker does a fetch to Cloudflare API, purging the cache for URL but without the “?sync”

https://api.cloudflare.com/#zone-purge-files-by-url

The worker fetches DigitalOcean like this:

let response    
const cache_time = 900
    response = await fetch("https://SPACE.nyc3.digitaloceanspaces.com/static/" + path, {
        cf: {
          cacheTtlByStatus: {
            "200-299": cache_time,
            404: 1,
            "500-599": -1
          },
          apps: false,
          minify: {
            javascript: true,
            css: true,
            html: true
          }
        }
      })

#7

I’m using the Workers Cache API, so I think it works differently.