Linux File and Directory Actions

Windows powershell and Git Bash require additional programs such as rsnyc and scp for many of these actions to work.

Command Description
touch [file] Create an empty file
cp [source] [destination] Copy files/directories
mv [source] [destination] Move/rename files/directories
rm [file] Remove files
rm -r [directory] Remove directories (recursively)
rm -rf [directory] Remove directories (skip confirmation)
cat [file] Concatenate and display file content
head [file] Display the beginning of a file
tail [file] Display the end of a file

File paths

Windows uses backslashes \ to separate file paths, while Linux uses forward slashes /. This means that when you are working with file paths in the command line, you need to use forward slashes even if you are using Windows.

Git bash can use either the Windows or Linux path format, but Powershell requires the Windows path format.

# Windows path
C:/Users/username/Desktop
# Linux (WSL) path
/c/Users/username/Desktop

Copy with scp

Syntax: scp [options] source destination

Note: when using scp you can add -r recursive flag to copy the entire directory, however, the scp command can be slow and inefficient when copying large directories. You can use the rsync command instead.

# Copy file from the server
scp user@45.79.239.101:/home/username/abc.txt /c/Users/username

# Copy file to the server
scp /c/Users/username user@45.79.239.101:/home/username/abc.txt

Copying with rsync

Syntax rsync [options] source destination

rsync uses a smart algorithm to only copy files that have changed, so subsequent uploads and downloads will be much faster than the initial transfer.

https://www.youtube.com/watch?v=Pygr_TpZRpM&ab_channel=TonyTeachesTech

# copy directory from server
rsync -avz user@45.79.239.101:/home/username /c/Users/username


-a Archive mode, which preserves various attributes of the files such as permissions, ownership, timestamps, etc.
-v Verbose mode, providing detailed information about the files being transferred.
-z Enables compression during the transfer, reducing the amount of data sent over the network.

--delete-excluded also delete excluded files from destination dirs
--delete delete extraneous files from destination dirs
--dry-run overview of what will be copied
--exclude exclude files or directories from the transfer

--partial keep partially transferred files
--progress show progress during transfer
-P is the same as --partial --progress

Renaming Multiple Files (script)

https://linuxconfig.org/how-to-rename-multiple-files-on-linux

# rename multiple files at once.

# append .bak to every file that begins with the pattern 'my_file'.
find . -type f -name 'my_file*' -print0 | xargs --null -I{} mv {} {}.bak

# append '_backup' to all files that end in the .txt extension.
find . -name "*.txt" -exec mv {} {}_backup \;

# We can also use xargs to do the same thing. ?? not tested
ls *.txt | xargs -I{} mv {} {}_backup

# find . -type f -maxdepth [depth] -name "[filepattern]" | while read FNAME; do mv "$FNAME" "${FNAME//search/replace}"; done

# find all named ...
find . -type f -name "my_file*" | while read FNAME; do mv "$FNAME" "${FNAME//my_file/new_name}"; done
# find all named with extention ...
find . -type f -name "my_file*.php" | while read FNAME; do mv "$FNAME" "${FNAME//my_file/new_name}"; done
# set max directory depth
find . -maxdepth 2 -type f -name "my_file*" | while read FNAME; do mv "$FNAME" "${FNAME//my_file/new_name}"; done

Change File Extensions (script)

# add a .txt file extension to all files in your present working directory.
for i in $( ls ); do mv $i $i.txt; done
# remove a file extension from all files in your present working directory.
for i in $( ls *.txt ); do mv $i ${i%.*}; done
# change extension from .log to .txt.
for i in *.log; do mv -- "$i" "${i%.log}.txt"; done

Counting Files and Directories

# Count the number of line in a file
wc -l file.txt
# Count the number of files in a directory
ls -1 | wc -l
# Count the number of files in a directory (including subdirectories)
find . -type f | wc -l

Excluding Files and Directories

# Count the number of files in a directory (excluding files with a specific extension)
find . -type f -not -name '*.txt' | wc -l
# Count the number of files in a directory (excluding files with a specific name)
find . -type f -not -name 'file.txt' | wc -l
# Count excluding directory
find . -type d -not -path "./node_modules/*"  wc -l
# Count excluding multiple directories
find . -type d -not -path "./node_modules/*" -not -path "./.git/*" -not -path "./.vscode/*"| wc -l

Excluding Hidden Files and Directories


find . -type d \( -path ./folder_to_exclude -o -path ./another_folder_to_exclude \) -prune -o -name '*.ts' -exec wc -l {} \;


# Count the number of files in a directory (excluding hidden files)
ls -1 | grep -v '^\.' | wc -l
# Count the number of directories in a directory (excluding hidden directories)
ls -1 | grep -v '^\.' | wc -l

Count the number of directories in a directory (including subdirectories)

find . -type d | wc -l

Count the number of files in a directory (including subdirectories) (excluding hidden files)

find . -type f -not -path '*/\.*' | wc -l

Count the number of directories in a directory (including subdirectories) (excluding hidden directories)

find . -type d -not -path '*/\.*' | wc -l

Count the number of files in a directory (including subdirectories) (excluding hidden files) (excluding files with a specific extension)

find . -type f -not -path '*/\.*' -not -name '*.txt' | wc -l

Count the number of directories in a directory (including subdirectories) (excluding hidden directories) (excluding directories with a specific name)

find . -type d -not -path '*/\.*' -not -name 'node_modules' | wc -l

Count the number of files in a directory (including subdirectories) (excluding hidden files) (excluding files with a specific extension) (excluding files with a specific name)


find . -type f -not -path '*/\.*' -not -name '*.txt' -not -name 'file.txt' | wc -l

Count the number of directories in a directory (including subdirectories) (excluding hidden directories) (excluding directories with a specific name) (excluding directories with a specific name)

find . -type d -not -path '*/\.*' -not -name 'node_modules' -not -name 'vendor' | wc -l

Trouble Shooting

Add rsync to Git Bash

  1. Download rsync from the MSYS2 package repository

Install MSYS2 with rsync and openssh (includes scp)

MSYS2 is a collection of tools and libraries providing you with an easy-to-use environment for building, installing and running native Windows software.

  1. Download and Install MSYS2:
  2. Open the MSYS2 shell and update the Package Database:
pacman -Syu
  1. Install rsync and openssh (which includes scp):
pacman -S rsync openssh