npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2025 – Pkg Stats / Ryan Hefner

@pkerschbaum/garden-snail

v1.3.0-pkerschbaum.1

Published

Turborepo remote cache server

Downloads

11

Readme

Garden Snail

Compatible with turborepo 1.10, 1.11, 1.12, 1.13 Compatible with turborepo 2.0, 2.1

Garden Snail is a self-hosted Remote Cache server for Turborepo written in NestJS. It serves as a drop-in replacement for Vercel's remote cache and supports storing the artifacts locally or in a s3 compatible storage.

Getting started

The easiest way to get started is to use the published Docker image. It runs the remote cache server listening on port 3000.

docker run \
-e AUTH_TOKENS=change_this \
-e STORAGE_PROVIDER=local \
-e LOCAL_STORAGE_PATH=blobs \
-v "$(pwd)"/blobs:/garden-snail/blobs \
-p 3000:3000 \
pkarolyi/garden-snail

You can also build and run the application yourself, you will need NodeJS 20.15.1 and pnpm 9.5.0:

pnpm install
pnpm build
node dist/main

Environment variables

# required: comma separated list of valid tokens (do not include spaces), eg. "token1,token2,token3"
AUTH_TOKENS=

# required: "s3" or "local"
STORAGE_PROVIDER=

# required if provider is local, eg. "blobs" will point to /garden-snail/blobs in the container
LOCAL_STORAGE_PATH=

# required if provider is s3
S3_BUCKET=

# optional if provider is s3
S3_ACCESS_KEY_ID=
S3_SECRET_ACCESS_KEY=
S3_REGION=
S3_SESSION_TOKEN=
S3_FORCE_PATH_STYLE=
S3_ENDPOINT=

Configuring Turborepo to use your cache server

Quick start

You will need to configure Turborepo to use your self-hosted remote cache server. The fastest option for checking that the server worked is by running the following command, note that the team option must start with team_:

turbo run build --api="https://my-server.example.com" --team "team_xxxx" --token="a_valid_auth_token"

If you see "remote caching enabled" printed that means that it is using the cache. Also you should see some logs from the remote cache server.

After running the build once, delete the local cache files (node_modules/.cache for turbo@1 and .turbo/cache for turbo@2 and if you are using NextJs then also .next) and running the build again without any changes. You should see "FULL TURBO" printed as Turborepo uses your remote cache to download the artifacts instead of building them again.

Long-term setup

This cli flag version however is not the best as it exposes your token in your shell's history. You should preferably use environment variables to configure Turborepo:

# Set the base URL for Remote Cache.
TURBO_API=

# Your team id (must start with "team_")
TURBO_TEAMID=

# One of the tokens from the server's "AUTH_TOKENS"
TURBO_TOKEN=

# If you are on a slow connection you may need to set this (timeout is in seconds, defaults to 60)
TURBO_REMOTE_CACHE_TIMEOUT=

If you used Vercel's remote cache before, remove .turbo/config.json to make sure those settings won't interfere with the custom remote cache.

In the current version any valid AUTH_TOKEN has acess to any team, so don't use teams for access control.

Storage Options

You can choose between local and s3 storage for storing the cached artifacts. The artifacts will be stored as team/hash in both cases.

Local

When using the local storage options the artifacts will be saved in the location specified with the LOCAL_STORAGE_PATH environment variable. Note that the node user that is used by default only has access to the /garden-snail directory. Storage paths by default are relative to this directory.

You can then mount the specified storage path as a Docker volume to provide persistent storage for your deployment.

Example

docker run \
-e AUTH_TOKENS=change_this \
-e STORAGE_PROVIDER=local \
-e LOCAL_STORAGE_PATH=blobs \
-v "$(pwd)"/blobs:/garden-snail/blobs \
-p 3000:3000 \
pkarolyi/garden-snail

S3

The s3 storage driver supports AWS S3 and any S3 compatible storage that works with the @aws-sdk/client-s3 client from the JavaScript v3 AWS SDK. This includes for example DigitalOcean Spaces or MinIO.

You will need to create the storage bucket and set up a user with the correct permissions. Garden Snail needs to be able to put and get objects and to use multipart uploads for storing large artifacts. The following is an example AWS Policy if using the bucket garden-snail-test:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "AccessBucketGardenSnailTest",
      "Effect": "Allow",
      "Action": [
        "s3:PutObject",
        "s3:GetObject",
        "s3:DeleteObject",
        "s3:AbortMultipartUpload",
        "s3:ListMultipartUploadParts",
        "s3:ListBucketMultipartUploads"
      ],
      "Resource": "arn:aws:s3:::garden-snail-test/*"
    }
  ]
}

Then you will need to specify the connection parameters for the S3 client. The storage bucket (S3_BUCKET) is required. The credentials of the user (S3_ACCESS_KEY_ID and S3_SECRET_ACCESS_KEY) are optional, but you will need to set them if you are not using an other method of providing access to the bucket.

If using a more advanced or custom setup you may need to set the following environment variables too:

  • S3_REGION - This defaults to us-east-1 if not set
  • S3_ENDPOINT - If using a custom s3 provider you will need to set this
  • S3_FORCE_PATH_STYLE - Some custom providers need this to be set to "true"
  • S3_SESSION_TOKEN - If using a more advanced credentials setup you may need this
  • If you need any other option feel free to open a PR or an issue!

The remote cache server does not remove old artifacts. If you need to limit the space used consider setting up Object Expiration.

Example

docker run \
-e AUTH_TOKENS=change_this \
-e STORAGE_PROVIDER=s3 \
-e S3_BUCKET=your_bucket \
-e S3_ACCESS_KEY_ID=your_access_key_id \
-e S3_SECRET_ACCESS_KEY=your_secret_access_key \
-p 3000:3000 \
pkarolyi/garden-snail

Notes

  • Check the integration tests on the workflow runs for a given tag to check for compatibility.
  • The 1.1.0 release and releases prior to that do not include any authorization or rate limiting functionality.
  • 1.2.0 is the first release with authentication. Rate limiting is not yet implemented.