mkdir — Create Directories

Create directories — single dirs, nested trees and permissions set at creation time. One of the most basic, most frequently used Unix commands.

mkdir creates directories – from a single folder through nested trees to complete project structures in a single call. The key to productivity is the -p option: it creates missing parent directories along the way and reports no error if the directory already exists – ideal for scripts. With -m you set permissions right at creation time, and with brace expansion you build whole directory matrices in one command. This guide covers the basics, permissions, brace patterns, and common project layouts.

Basic Usage

mkdir <directory> — Create a single directory.

mkdir projects

mkdir <dir1> <dir2> <dir3> — Create multiple directories at once.

mkdir css js images

mkdir -v <directory> — Verbose mode. Print a message for each created directory.

mkdir -v logs backups tmp

Parent Directories

mkdir -p <path/to/directory> — Create parent directories as needed. No error if the directory already exists.

mkdir -p /var/www/html/assets/css

mkdir -p <dir1>/sub1 <dir2>/sub2 — Create multiple nested directory trees at once.

mkdir -p src/components src/utils src/hooks

mkdir -pv <path/to/directory> — Create parent directories with verbose output showing each directory created.

mkdir -pv /opt/app/config/ssl

Permissions

mkdir -m <mode> <directory> — Create a directory with specific permissions (octal mode).

mkdir -m 755 /var/www/html

mkdir -m 700 <directory> — Create a private directory. Only the owner can access it.

mkdir -m 700 ~/.ssh

mkdir -m 1777 <directory> — Create a directory with sticky bit. Users can only delete their own files.

mkdir -m 1777 /tmp/shared

mkdir -m 2775 <directory> — Create a directory with setgid. New files inherit the directory's group.

mkdir -m 2775 /var/www/shared

mkdir -pm <mode> <path/to/directory> — Create nested directories with specific permissions on the final directory.

mkdir -pm 700 ~/.config/app/secrets

Brace Expansion Patterns

mkdir -p <base>/{<dir1>,<dir2>,<dir3>} — Create multiple subdirectories using brace expansion.

mkdir -p project/{src,tests,docs}

mkdir -p <base>/{<dir1>,<dir2>}/{<sub1>,<sub2>} — Create a nested directory matrix using nested brace expansion.

mkdir -p app/{frontend,backend}/{src,tests,config}

mkdir -p <base>/{01..12} — Create numbered directories using sequence expansion.

mkdir -p archive/2024/{01..12}

mkdir -p <base>/{a..z} — Create alphabetically named directories using character ranges.

mkdir -p index/{a..z}

mkdir -p project/{src/{components,utils,hooks},public/{css,js,images},tests} — Create a complete project directory structure in one command.

mkdir -p project/{src/{components,utils,hooks},public/{css,js,images},tests}

Common Project Structures

mkdir -p <project>/{src,dist,tests,docs} — Basic project scaffold with source, build output, tests, and docs.

mkdir -p my-app/{src,dist,tests,docs}

mkdir -p <project>/{src/{css,js,images},dist,node_modules} — Frontend project structure with asset directories.

mkdir -p website/{src/{css,js,images},dist,node_modules}

mkdir -p <project>/{app/{Controllers,Models,Views},config,public,storage/{logs,cache}} — MVC web application structure.

mkdir -p my-app/{app/{Controllers,Models,Views},config,public,storage/{logs,cache}}

mkdir -p <project>/{cmd,internal,pkg,api,configs,scripts,test} — Go project standard layout.

mkdir -p my-service/{cmd,internal,pkg,api,configs,scripts,test}

Temporary Directories

mktemp -d — Create a temporary directory with a unique name in /tmp. Returns the path.

TMPDIR=$(mktemp -d); echo $TMPDIR

mktemp -d -t <template> — Create a temporary directory with a custom name prefix.

mktemp -d -t myapp-XXXXXX

mktemp -d -p <directory> — Create a temporary directory inside a specific parent directory.

mktemp -d -p /var/tmp

mktemp -d && trap 'rm -rf "$TMPDIR"' EXIT — Create a temp directory that is automatically cleaned up when the script exits.

TMPDIR=$(mktemp -d) && trap 'rm -rf "$TMPDIR"' EXIT

Common Patterns

mkdir -p <dir> && cd <dir> — Create a directory and immediately enter it.

mkdir -p ~/projects/new-app && cd ~/projects/new-app

[ -d <dir> ] || mkdir -p <dir> — Create a directory only if it does not exist (explicit check).

[ -d /var/log/app ] || mkdir -p /var/log/app

install -d -m <mode> -o <owner> -g <group> <directory> — Create a directory with permissions, owner, and group in one command.

install -d -m 755 -o www-data -g www-data /var/www/html

mkdir -p <dir> && cp <files> <dir>/ — Create destination directory and copy files into it.

mkdir -p /backup/2024 && cp *.sql /backup/2024/

for d in <list>; do mkdir -p "$d"; done — Create directories from a dynamic list or variable.

for d in dev staging prod; do mkdir -p "/deploy/$d/releases"; done

Conclusion

mkdir is one of the most basic commands there is, but two options make it far more convenient: -p creates missing parent directories and stays silent when the directory already exists (perfect for idempotent scripts), and -m sets permissions at creation time, avoiding a sensitive race condition between mkdir and a following chmod. Combined with brace expansion, you can scaffold entire project trees in a single command. For throwaway work directories, reach for mktemp -d instead of predictable names in /tmp.

Further Reading

  • touch – create empty files and set timestamps
  • rm – remove files and directories
  • ls – list directory contents