Create a temporary file or directory
Create a uniquely-named temp file or temp directory in a system-managed scratch location.
How to create a temporary file or directory in each shell
mktempBare `mktemp` creates a file `/tmp/tmp.XXXXXXXXXX` (8 random chars, mode 600). `mktemp -d` makes a DIRECTORY (`/tmp/tmp.XXXXXXXXXX`, mode 700). Custom template: `mktemp /tmp/mybuild.XXXXXX` — at least 3 trailing `X`s required (replaced with random chars). Honor `$TMPDIR` automatically: `mktemp -t prefix` puts file in `${TMPDIR:-/tmp}` with `prefix.XXXXXXXX`.
mktempSame external `mktemp`. macOS BSD `mktemp` requires `-t TEMPLATE` or a literal path argument — bare `mktemp` (no args) FAILS on BSD with `usage: mktemp [-d] [-q] [-u] -t prefix`. GNU `mktemp` with no args works. Portable: `mktemp /tmp/mytemp.XXXXXX` (explicit template) — works on both.
mktempSame external. Fish capture: `set -l tmpfile (mktemp)` — and ALWAYS register cleanup: `function cleanup; rm -f $tmpfile; end; trap cleanup EXIT INT TERM` — wait, fish uses `function cleanup --on-event fish_exit` instead of `trap`. Don't mix bash `trap` syntax into fish — it silently no-ops.
New-TemporaryFilepwsh 5.1+ — returns a `[FileInfo]` pointing at `$env:TEMP\tmp<XXXX>.tmp`. The file is EMPTY but already exists (TOCTOU-safe, like `mktemp`). For a temp DIRECTORY: pwsh has NO `New-TemporaryDirectory` cmdlet — write `$dir = Join-Path $env:TEMP ([System.IO.Path]::GetRandomFileName()); New-Item -ItemType Directory -Path $dir`. Or use .NET: `[System.IO.Path]::GetTempFileName()` (returns string path, file created).
set TMPFILE=%TEMP%\tmp_%RANDOM%_%TIME:~6,5%.txt && type nul > %TMPFILE%cmd has NO mktemp equivalent. The above generates a random-ish name from `%RANDOM%` (0–32767) + `%TIME%` substring. NOT cryptographically random + has collision risk (two scripts started in the same millisecond can collide). For real uniqueness shell out to pwsh: `powershell -Command "New-TemporaryFile | Select-Object -ExpandProperty FullName"`. For one-off interactive use, the random idiom is fine.
Equivalents listed for Bash, Zsh, Fish, PowerShell, cmd.exe.
Gotchas & notes
- **Security — predictable temp names = symlink attack**: `/tmp/mybuild.txt` (predictable name) on a shared system allows another user to pre-create `/tmp/mybuild.txt` as a symlink to `/etc/passwd` — your script then writes to `/etc/passwd` if it has perms. `mktemp` exists specifically to prevent this: it atomically creates the file with mode 0600 and a random name. Never write to a fixed-path temp file in a script that may run with elevated perms.
- **`$TMPDIR` vs `/tmp` vs `/var/tmp`**: macOS sets `$TMPDIR` to a per-user `/var/folders/xx/...` for sandboxing — `/tmp` is a symlink to `/private/tmp` and is system-wide (no sandbox). Linux usually has `/tmp` as tmpfs (RAM-backed, wiped on reboot) and `/var/tmp` as disk-backed (survives reboot — for downloads / partial work). Pick `$TMPDIR` for portable scripts; pick `/var/tmp` only for files that should outlive a reboot. Windows: `$env:TEMP` = `$env:USERPROFILE\AppData\Local\Temp` (per-user, disk-backed).
- **Cleanup — `trap EXIT` or `Register-ObjectEvent`**: temp files don't auto-clean. Bash idiom: `tmpfile=$(mktemp); trap "rm -f $tmpfile" EXIT INT TERM` — fires on normal exit AND on Ctrl-C. fish: `function on_exit --on-event fish_exit; rm -f $tmpfile; end`. pwsh: `try { ... } finally { Remove-Item $tmpfile -Force -ErrorAction SilentlyContinue }`. Without cleanup, `/tmp` fills with orphaned junk across crashed/killed runs. systemd-tmpfiles sweeps `/tmp` weekly on most Linux distros — relying on that is sloppy; use `trap`.
- **`mktemp -p DIR` for non-default location**: GNU `mktemp -p /mnt/bigdisk pkg.XXXXXX` creates in `/mnt/bigdisk` (useful when default `/tmp` is small / tmpfs / readonly — e.g. CI runners with 64 MB `/tmp`). pwsh: `New-Item -ItemType File -Path "D:\bigdisk\$([System.IO.Path]::GetRandomFileName())"`. Robocopy / large extracts in `/tmp` are a common ENOSPC source on minimal-disk CI containers.
Related commands
Related tasks
- Check if a file exists— Test whether a file (or directory, or symlink) exists at a path before reading, writing, or branching script logic.
- Make a script executable— Give a script the right permissions and shebang so you can run it directly (`./script.sh`) instead of through an interpreter (`bash script.sh`).