Tutorials

How to Share an Env File With Your Team (Without Leaking It)

Never commit it, never paste it into chat. Use a one-time link to bootstrap a new laptop and a secrets manager for everything after that.

To share an env file with your team, never commit it to Git or paste it into chat. For a one-off laptop setup, send the contents as a one-time link that self-destructs after one view, with a passcode sent separately. For ongoing access, keep the variables in a secrets manager your team pulls from.

Key takeaways

  • Keep .env out of Git with .gitignore and commit a .env.example with placeholder values instead.
  • Use a one-time link for bootstrapping: one view, short expiry, passcode sent over a different channel.
  • Use a secrets manager when many people or machines need the same values over time.
  • Send development credentials to laptops, not production ones.
  • If a .env file ever landed in chat history or a repo, rotate every secret in it.

What's the safest way to share an env file with your team?

It depends on whether you are solving a one-time problem or an ongoing one. Most teams have both.

The one-time problem: a new developer joins on Monday, clones the repo, runs the app and gets a wall of errors because DATABASE_URL and STRIPE_TEST_KEY are missing. Someone needs to get them a working .env today.

The ongoing problem: ten people and three CI pipelines need the same values, those values change, and you need to know who has access. That calls for a secrets manager, not a better way of passing files around.

If you only remember one rule, make it this: the file should never sit anywhere permanent that wasn't designed to hold secrets. That rules out Git, chat history, wikis, tickets and shared drives.

Why you should never commit .env to Git

A committed .env is copied to every clone, every fork, every CI runner and every backup of the repo. Deleting it in a later commit doesn't remove it from history. Anyone who can read the repo, now or in the future, can read the secrets.

Private repos don't fix this. Contractors get added, laptops get stolen, access tokens leak, and repos occasionally get made public by mistake.

Set this up once and you rarely have to think about it again:

echo ".env" >> .gitignore
echo ".env.*" >> .gitignore
echo "!.env.example" >> .gitignore
git add .gitignore .env.example
git commit -m "Ignore env files, add example"

Your .env.example lists every variable the app needs, with fake or empty values and a comment saying where to get the real one. It documents the shape of the config without exposing anything.

If a real .env was already committed, rewriting history is worth doing, but it is not enough on its own. Treat every value in that file as exposed and rotate it. The OWASP Secrets Management Cheat Sheet covers rotation and detection in more depth.

How to share a .env file securely with a one-time link

For getting one person's laptop running, a one-time link is hard to beat. The contents exist in a readable form for as long as it takes your teammate to open it, then the link stops working. Nothing lingers in Slack search or someone's inbox.

Here is the process with SecureNotes:

  1. Prepare the file. Start from .env.example and fill in development or staging values only. Remove anything the person doesn't need for their role.
  2. Paste the contents. Go to SecureNotes and create a self-destructing note. Paste the full file. Notes hold up to 10,000 characters, which covers most env files.
  3. Choose when it self-destructs. Pick 1 view and 1 hour or 24 hours, whichever comes first. One view means you'll know if anyone else got there first.
  4. Add a passcode. Set a short passcode the recipient must enter to open the note. This protects you if the link ends up in the wrong place.
  5. Turn on the read notification. SecureNotes can email you when the note is opened, so you know it arrived.
  6. Send the link. Drop it in a direct message, or let SecureNotes email it to the new hire's work address.
  7. Send the passcode another way. Say it on your onboarding call, or text it. Never in the same thread as the link.
  8. Confirm and clean up. Ask them to save it straight to .env in the project root and run chmod 600 .env. If they say the link was already used when they clicked it, rotate the secrets.

Each note is encrypted with AES-256 using its own random key before it is stored, and the link stops working once the view limit or time limit is reached. For what a one-time link does and doesn't protect against, see one-time links vs password vaults.

The env file is usually one of several things a new developer needs in week one. Onboarding a new hire: the first ten secrets they actually need covers the rest.

How to send an env file from the command line with the SecureNotes API

If you onboard people often, or you want this baked into a setup script, the free SecureNotes REST API lets you create notes without opening a browser.

The pattern below reads the file directly, builds the JSON body with jq and pipes it to curl. The secret never appears as a command-line argument, so it doesn't end up in your shell history or the process list.

# 1. Check the file fits in a single note (10,000 character limit)
wc -m .env.dev

# 2. Set the endpoint from the API docs
export SECURENOTES_ENDPOINT="<endpoint from the API docs>"

# 3. Build the request from the file and create the note
jq -Rs '{content: ., max_views: 1, expires_in: "1h"}' .env.dev \
  | curl -s -X POST "$SECURENOTES_ENDPOINT" \
      -H "Content-Type: application/json" \
      --data @-

The field names here are placeholders to show the shape of the request. Check the API docs for the exact endpoint, parameter names for views, expiry and passcode, and the format of the response that contains the link.

A few things to get right when scripting this:

  • Read from a file or stdin, not a variable you typed. SECRET=abc123 ./script.sh lands in history.
  • Print only the link. Pipe the response through jq to extract the URL so the script output doesn't echo anything else.
  • Keep the defaults strict. Hard-code one view and a short expiry so nobody accidentally creates a 30-day, 10-view link.
  • Don't log the request body in CI or wrapper scripts.

You can wrap this in a small share-env function in your dotfiles and hand it to every tech lead on the team.

When should your team use a secrets manager instead?

One-time links are for handoffs. They don't give you access control, audit logs, versioning or automatic distribution. Once you need any of those, it's time for a secrets manager such as HashiCorp Vault, AWS Secrets Manager, Google Secret Manager, Doppler, Infisical or a team password manager with CLI support.

Move to a secrets manager when:

  • More than a handful of people need the same values.
  • CI/CD pipelines or servers need the secrets, not just humans.
  • Values change often and you're tired of re-sending files.
  • You need to revoke one person's access without rotating everything.
  • Someone, such as an auditor or a customer, asks who can see production credentials.

A common setup: developers authenticate to the secrets manager with their SSO login, then run a CLI command that writes a local .env or injects variables at runtime. The one-time link then shrinks to a single job, getting a new hire the bootstrap credential for the secrets manager itself if SSO doesn't cover it.

Slack, email, repo or one-time link: how the options compare

MethodWhere the secret ends upGood forMain risk
Committed to GitEvery clone, fork and backup, foreverNothingExposure to anyone with repo access, now or later
Slack or Teams messageSearchable chat history and workspace exportsNothing secretLingers for years, visible to admins and integrations
Email attachmentBoth mailboxes, server copies, backupsNothing secretForwarding, compromised mailboxes, retention
Shared drive or wiki pageA document with shifting permissionsNon-secret setup docsAccess sprawl, copies, version history
One-time linkStored encrypted until viewed or expired, then goneBootstrapping one laptop, one-off handoffsRecipient copies it somewhere unsafe; no ongoing access control
Secrets managerA purpose-built store with access controlOngoing team and CI accessSetup effort; misconfigured permissions

If you're handing keys to someone outside the company, the trade-offs shift a little. Sharing API keys with a contractor walks through that case.

Common mistakes when you send secrets to a developer

Sending production credentials to a laptop

Most developers don't need production database passwords to write code. Give them dev or staging values and let production secrets live only in your deployment environment.

Putting the link and passcode in the same place

If both sit in one Slack DM, anyone who reads that DM has everything. Split them across channels: link in chat, passcode on a call.

Choosing long expiry and many views

A 30-day, 10-view link is a semi-permanent secret with extra steps. For an env file, one view and a short window is almost always right.

Ignoring a link that was already opened

Some chat tools fetch links to build previews, and links get forwarded. If your teammate says the note was gone before they opened it, assume someone else saw it and rotate the values.

The recipient saving it somewhere worse

A one-time link can't stop someone pasting the contents into a notes app, a personal email or an AI chat. Tell people where the file goes and why.

Forgetting to rotate when people leave

Every key on a departing developer's laptop is still valid until you change it. Keep a list of what was shared with whom so offboarding is a checklist, not guesswork.

Letting .env.example drift

When the example file is out of date, people fill the gaps by asking in public channels, and secrets end up in chat anyway. Update it in the same pull request that adds a new variable.

Frequently asked questions

Can I share a .env file over Slack if I delete the message afterwards?

Deleting helps less than you'd think. The file may already be in notifications, workspace exports, integrations or the recipient's downloads before you delete it, and some workspaces retain deleted content for admins. If you already sent a .env over Slack, delete it and rotate the secrets. Next time, send a one-time link and keep the passcode off Slack.

Is it OK to keep .env files in a private Git repository?

No. Private repos still get cloned to many laptops, mirrored to CI, backed up and shared with contractors, and their access lists change over time. Secrets in history stay readable to anyone who ever gains access. Commit a .env.example with placeholders and store real values in a secrets manager or hand them over individually.

What should go in a .env.example file?

Every variable the app reads, with a fake, empty or obviously local value, plus a short comment explaining what it is and where to get the real one. For example, STRIPE_SECRET_KEY= followed by a note pointing to the secrets manager path. Non-sensitive defaults like PORT=3000 can stay as real values.

What if my .env file is longer than 10,000 characters?

A SecureNotes note holds up to 10,000 characters, so you can split a large file across two notes, each with its own passcode. But a file that size usually contains far more than one developer needs, and it's a strong signal your team has outgrown file handoffs. Trim it to the essentials or move to a secrets manager.

How do I remove a .env file that was committed to Git?

Remove it from tracking with git rm --cached .env, add it to .gitignore, then rewrite history with a tool like git filter-repo and force-push. Ask collaborators to re-clone. Most importantly, rotate every secret the file contained, because rewriting history can't recall copies that already exist in clones, forks or CI caches.

S
SecureNotes Team

Security expert and content creator at Secure Notes. Passionate about digital privacy and secure communication.

Featured on The Logo Wall