Everything on a Linux system sits in one tree of folders that starts at /. These commands tell you where you are, move you around that tree, and create, copy, move, link, find, and delete files.
Prints the full path of the folder you are currently working in.
Your shell always has a current directory, and relative paths such as notes.txt or ../logs are measured from it, so pwd is the quickest way to get your bearings after a few cd commands. If you arrived through a symbolic link, plain pwd usually shows the path through the link, while pwd -P shows where you really are on disk.
Show the directory you are in.
Show the real location with any symbolic links resolved.
- -P
- Resolve symbolic links and print the physical path.
Lists the files and folders inside a directory.
With no argument it lists the current folder. Names that start with a dot, such as .env or .gitignore, stay hidden unless you add -a, and flags can be combined, so ls -lah gives a detailed, readable listing that includes them. The tree command, which draws folders as a nested diagram, is not installed by default on most distributions, so you would have to add it with your package manager first.
Long listing with permissions, owner, size, and date, hidden files included.
Show sizes as K, M, or G instead of raw bytes.
Newest changes first, handy for spotting the file you just edited.
- -l
- Long format: one entry per line with permissions, owner, size, and modification time.
- -a
- Include hidden entries whose names begin with a dot.
- -h
- With -l, print sizes in readable units such as 4.0K or 12M.
- -t
- Sort by modification time, newest first.
Changes the directory your shell is working in.
Plain cd or cd ~ takes you home, .. means the parent folder, and cd - jumps back to wherever you were before and prints that path, which makes flipping between two places easy. cd has to be built into the shell, because a separate program cannot change the folder of the shell that started it; for the same reason, a script that calls cd leaves your terminal where it was unless you source the script.
Move into the project folder inside the current one.
Return to your home folder; plain cd does the same.
Switch back to the folder you were in before.
Creates new directories, including any missing parent folders when you add -p.
Without -p, mkdir fails if a parent in the path does not exist yet or if the folder is already there. With -p it builds the whole chain and quietly succeeds when the folder already exists, which is why scripts nearly always use it.
Create one folder in the current directory.
Shell
mkdir notes drafts archive
Create several folders at once.
Shell
mkdir -p project/src/components
Create the full path, making project and src along the way if needed.
- -p
- Create missing parent folders and do not complain if the target already exists.
- -v
- Print a line for every folder that gets created.
Creates an empty file if it does not exist, or updates the modification time of one that does.
It never changes what is inside an existing file, so it is safe to run on something you care about. People mostly use it to create placeholder files quickly, or to bump a timestamp so a build tool treats a file as changed.
Create an empty notes.txt, or refresh its timestamp if it exists.
Shell
touch index.html style.css app.js
Create several empty files in one go.
- -c
- Only update files that already exist; never create new ones.
Copies files, and whole folders when you add -r.
If the destination is an existing folder the copy goes inside it; otherwise the copy takes the destination name. Because of that rule, running the same cp -r twice nests the folder on the second run, leaving you with project-copy/project.
Careful: When a file already exists at the destination, cp replaces its contents without asking and keeps no copy of the old version. Add -i if you want to be prompted first.
Shell
cp notes.txt notes-backup.txt
Make a copy next to the original under a new name.
Shell
cp notes.txt todo.txt archive/
Copy several files into an existing folder.
Shell
cp -r project project-copy
Copy a folder and everything in it; project-copy is created if it does not exist.
Shell
cp -i draft.txt notes.txt
Ask before replacing notes.txt if it already exists.
- -r
- Copy directories and everything inside them.
- -i
- Prompt before overwriting an existing file.
- -p
- Keep the original permissions and timestamps on the copy.
- -v
- Print each file as it is copied.
Moves files or folders to a new place, which is also how you rename them.
Renaming is simply a move to a new name in the same folder, so there is no separate step for it. A move within the same filesystem is instant even for huge folders, because only the directory entry changes, and folders need no -r flag.
Careful: If something already exists at the destination name, mv replaces it silently and the replaced file cannot be recovered. Use -i to be asked or -n to leave existing files alone.
Shell
mv draft.txt notes.txt
Rename draft.txt to notes.txt.
Shell
mv notes.txt archive/
Move a file into the archive folder, keeping its name.
Shell
mv old-name/ new-name/
Rename a folder; no recursive flag is needed.
Shell
mv -n report.txt archive/
Move the file only if archive/ has no file of that name yet.
- -i
- Ask before overwriting an existing file.
- -n
- Never overwrite an existing file.
- -v
- Report each move as it happens.
Deletes files, and with -r deletes folders along with everything inside them.
rm will not delete a folder unless you give -r, and -f silences both prompts and complaints about missing paths, which is why rm -rf is common in scripts. Wildcards are expanded by the shell before rm even runs, so run ls with the same pattern first to see exactly what would go.
Careful: There is no trash on the command line: removed files are gone and ordinary tools cannot bring them back. rm -rf never asks for confirmation, so a small typo does a lot of damage; rm -rf * .log, with a stray space, deletes everything in the folder rather than just the log files.
Ask about each matching file before deleting it.
Delete a folder and all of its contents, prompting only for write-protected files.
Force-delete a build folder with no prompts and no error if it is already gone.
- -r
- Remove directories and everything beneath them.
- -f
- Never prompt, and ignore paths that do not exist.
- -i
- Confirm every single removal.
- -I
- Ask once when deleting more than three files or when recursing; less tedious than -i.
Creates a symbolic link, a small pointer that leads to another file or folder.
Opening the link opens whatever it points at, which is handy for giving a long path a short name or switching versions by repointing one link. A relative target is resolved from the folder where the link lives, not from where you ran ln, and getting that wrong is the usual reason a new link is broken. Without -s, ln makes a hard link instead: a second name for the same data that works only within one filesystem and not for folders.
Shell
ln -s ~/projects/website/docs docs
Create a link called docs in the current folder that leads to the website's docs folder.
Confirm where a link points; the listing shows docs -> and the target.
Shell
ln -sfn releases/v2 current
Repoint an existing link named current to releases/v2.
Print the fully resolved path the link leads to.
- -s
- Make a symbolic link rather than a hard link.
- -f
- Replace an existing file or link that has the same name.
- -n
- Treat an existing link to a folder as a plain file, so -f replaces the link instead of creating a new one inside the folder.
Searches a folder tree for files by name, type, age, and more, and can run a command on each result.
find walks every subfolder of the starting point and prints each match. Quote wildcard patterns such as "*.txt" so the shell hands them to find instead of expanding them itself. With -exec, {} stands for each path found: ending with \; runs the command once per file, while ending with + passes many paths per run and is much faster.
Shell
find . -name "*.txt"
Every .txt file under the current folder; -iname ignores letter case.
Shell
find . -type d -name node_modules
Find folders, not files, called node_modules.
Shell
find . -type f -mtime -7
Files modified within the last seven days.
Shell
find src -name "*.ts" -exec grep -l "TODO" {} +
List the TypeScript files that contain TODO.
- -name <pattern>
- Match the file name against a wildcard pattern, case sensitively.
- -type f|d
- Keep only regular files (f) or directories (d).
- -mtime <days>
- Filter by days since the last change: -7 means within a week, +30 means older than 30 days.
- -exec <cmd> {} +
- Run a command on the results, with {} replaced by the paths.