Linux and Unix Permissions are one of those annoying things that few people understand. They’ll cause errors when you’re coding or installing stuff, and just all around get in your way, but they’re a powerful security feature that prevents someone else, and even yourself from destroying important data. It’s time to dive deep into permissions, and learn how to use this powerful feature so you never get stuck on a permission error again.

What are Permissions?

File & folder permissions are a way for Linux & Unix to manage a users abilities to read, write, and execute files on a computer system. If a user does not have “Read” access, they can’t read that file or directory. Without “Write” access, they won’t be allowed to edit a file. Without “Execute” access, a user cannot run/execute that file.

How File & Folder Permissions Work:

Each type of access is given a value.

Access Level Value
No Permission 0
Execute 1
Write 2
Read 4

Read Access: The ability to read a file and the contents of a directory. Read Access also allows you to run “Script files” like those written in PHP, Python, Ruby, etc…

Write Access: The ability to edit a file, and add/remove files within a directory. You can edit a file you own, even if it’s inside a directory you don’t have write access to, as long as you have permissions to edit the file inside the directory.

Execute Access: The ability to change into a directory. Execute access must be set on “Binary Executables” in order to run the program. Programs like those in your /bin/ will most likely need execute access.

To give a user any possible combination of access to a specific file/folder you just add the values together like this:

Access Level Value
Execute + Write 1 + 2 = 3
Execute + Read 1 + 4 = 5
Write + Read 2 + 4 = 6
Execute + Write + Read 1 + 2 + 4 = 7

Users, Groups, and Others

Each file (and directory) has a separate permission setting for the “user/owner”, “group”, and “others”

User/Owner

The “User” portion represents the owner of the file, typically the account who created the file (but not always).

Group

Every file has an associated “Group”. Every user belongs to one or more of these Groups, and you can add or remove users to groups as you please, and create/remove groups. Any user in the Group of the file will have the “Group’s” permissions rights.

The best way do demonstrate the importance of groups is through an example, like collaborating with a partner:

If I own a file, my developer “tom” might not be able to edit the code in my project. If I put him in a group called “developer” and give the developer group read & write access, then he can help edit any files belonging to the developer group!

I do NOT want my “advertiser” being able to go into my web server and erasing or editing files on accident, so she’ll use an account with no permissions, and her user will be apart of less powerful groups, like “guests”, and “marketer”.

Others

Others is everyone else. The Guest users on your account, the user account for your dog, etc…

Let’s play around with this a little and get familiar with File permissions. Start by creating a “test” directory on your desktop and creating a file named cat.txt, and a directory called nestedFolder with your terminal.

$ cd ~/Desktop
$ mkdir test
$ touch cat.txt
$ mkdir nestedFolder

Because everything in Unix/Linux is a file, you’ll have Read, Write, and Execute options on both Directories AND files.

Now we’ll take a look at the permission rights set on the files inside the test directory. List all files inside the directory using the “ls” command with the -l flag.

Johns-MacBook-Pro:test johncurry$ ls -l
total 0
-rw-r--r--  1 johncurry  staff   0 Jul 11 06:50 cat.txt
drwxr-xr-x  2 johncurry  staff  68 Jul 11 06:50 nestedFolder
Johns-MacBook-Pro:test johncurry$ 

You should see something similar to the above. My nestedFolder line has:
“drwxr-xr-x 2 johncurry staff 68”

The “johncurry staff” section means that “johncurry” is the owner, and staff is the group.

drwxr-xr-x Can be broken up into |User|Group|Wheel

the very first space has a – or a “d”. The “d” means it’s a directory. Notice the cat.txt does not have a “d” because it’s a file.

The following three spaces represent the level of access for the USER, followed by three spaces for the GROUP, followed by three spaces for EVERYONE ELSE. Read (r) Write (w), and Execute (x) are the options. If the user doesn’t have the privilege, it will be “-“.

“rwxr-xr-x” means the USER has “rwx” The Group has “r-x”, and Others has “r-x” meaning the Group and others can only read and execute, but not write.

Now take a look at the cat.txt file and see if you can figure out what its permissions are for the user, group, and others.

Changing Permissions

Change Permissions Using Number Values:

Use the CHMOD command and set equivalent value for the permissions you desire for the User, Group, and Other. Remember, None=0, Execute=1, Write=2, Read=4

Let’s set the permissions to Read/Write/Execute for User, Read/Write for Group, and Read for Other.
If you do the math, that equates to: User-7, Group-6, Other-4. The Command to change a files permission looks like this: chmod octal filename

$ chmod 764 cat.txt ## User=rwx, Group=rw, Other=r
$ chmod 153 cat.txt ## User=x, Group=rx, Other=wx

Change File Permissions with UGOA

You can set the desired permissions using shorthand characters as well.
You decide which User type to affect with UGOA:

User Type Symbol
USER u
GROUP g
OTHERS o (lowercase letter)
ALL a

You decide HOW you would like to affect that user type by either Adding, Removing, or setting the values r, w, or x with the following:

Action Symbol
ADD +
REMOVE
SET =

Decide the permission settings for that user type with r, w, x. Read (r), Write (w), Execute (x).

Here’s a couple examples:

test johncurry$ ls -l #start with no permissions on anything
total 0
----------  1 johncurry  staff  0 Jul 11 06:50 cat.txt
test johncurry$ chmod u=rw cat.txt  # set User to read,write
test johncurry$ ls -l
total 0
-rw-------  1 johncurry  staff  0 Jul 11 06:50 cat.txt # rw in users.
test johncurry$ chmod o+rx cat.txt   # add read, execute to Others group
test johncurry$ ls -l
total 0
-rw----r-x  1 johncurry  staff  0 Jul 11 06:50 cat.txt
test johncurry$ chmod o-x cat.txt    # remove execute from Others group
test johncurry$ ls -l
total 0
-rw----r--  1 johncurry  staff  0 Jul 11 06:50 cat.txt
test johncurry$ chmod o=wx cat.txt   # set Others Group to Write, Execute
test johncurry$ ls -l
total 0
-rw-----wx  1 johncurry  staff  0 Jul 11 06:50 cat.txt
test johncurry$ chmod u+x,g=rw,o=rx cat.txt  # commands separated by comma
test johncurry$ ls -l
total 0
-rwxrw-r-x  1 johncurry  staff  0 Jul 11 06:50 cat.txt
test johncurry$ chmod u-rwx,g-rw,o-rx cat.txt 
test johncurry$ ls -l
total 0
----------  1 johncurry  staff  0 Jul 11 06:50 cat.txt
test johncurry$ chmod a=rwx cat.txt  # set ALL to have read, write, execute
test johncurry$ ls -l
total 0
-rwxrwxrwx  1 johncurry  staff  0 Jul 11 06:50 cat.txt

Changing File’s Owner & Group

To change the owner of the file, run the command $ sudo chown theOwner filename.

To change the group the file belongs to, run $ sudo chgrp theGroup filename.

To change the owner AND the group in one line, run $ sudo chown theOwner:theGroup filename.

Note: The group must exist first. Learn how create groups below.

test johncurry$ ls -l
total 0
-rwxrwxrwx  1 johncurry  staff    0 Jul 11 06:50 cat.txt
drwxr-xr-x  3 johncurry  staff  102 Jul 11 09:31 nestedFolder
test johncurry$ sudo chown bunny cat.txt 
test johncurry$ ls -l
total 0
-rwxrwxrwx  1 bunny      staff    0 Jul 11 06:50 cat.txt  # owner is bunny, group is staff
drwxr-xr-x  3 johncurry  staff  102 Jul 11 09:31 nestedFolder
test johncurry$ sudo chown bunny:bunny nestedFolder/ 
test johncurry$ ls -l
total 0
-rwxrwxrwx  1 bunny  staff    0 Jul 11 06:50 cat.txt
drwxr-xr-x  3 bunny  bunny  102 Jul 11 09:31 nestedFolder  # owner is bunny, group is bunny

Note: You can do any of these operations RECURSIVELY with the -R (Capital R!) flag

$ sudo chmod -R 777 test/  #changes EVERYTHING in the test/ to rwxrwxrwx (very bad don't do this)
$ sudo chown -R bunny:bunny test/   #changes EVERYTHING in test/ to bunny as owner & group

Adding/Removing Users & Groups on Linux

to view groups a user is in:

$ groups        # view groups the current user is in
$ groups bunny  # view groups that the user "bunny" is in

To Add a user “bunny” and set the password, run:

$ useradd bunny
$ passwd bunny

To Remove a user “bunny”, run:

$ userdel -r bunny   # -r removes the files associated with the user

To create a new group called “bunny”, run:

$ sudo groupadd bunny

To Add the user “john” to the group bunny, run:

$ sudo usermod -a -G bunny john

To Remove the user “john” from the group bunny, run:

$ sudo gpasswd -d john bunny

To Delete the group “bunny”

$ sudo groupdel bunny

I encourage you to read the friendly manual to learn more about each command, and the flags accompanying the command. Do this with $ man nameOfCommand

Want More Tutorials?

Subscribe to our NewsLetter to get our latest Tutorials, Courses, product & tool reviews, and more! We don't email very often. When we do, it'll be good!

Adding/removing Users & Groups on Mac

Adding new Users & Groups is simple on a Mac, but some common linux commands don’t appear to work out of the box, so we mac users will submit to their power, and do it their way.

Step 1. Click on the Apple Icon > System Preferences > Users & Groups

Step 2. Click the little Lock icon to unlock the page so you can edit users/groups

Step 3. Click the + icon to add a new user/group

Step 4. Select the correct option from the “New Account” drop down.

Step 5. Fill in the info & hit “Create user”, or “Create Group” or whatever it says. Don’t add an “administrator” user unless you absolutely need to.

Do these steps as necessary until you have the users & groups you need.

(Mac) Check which groups your user belongs to, run:

$ groups
staff com.apple.sharepoint.group.2 everyone localaccounts _appserverusr admin _appserveradm _lpadmin com.apple.sharepoint.group.1 _appstore _lpoperator _developer com.apple.access_ftp com.apple.access_screensharing com.apple.access_ssh com.apple.sharepoint.group.3
$ groups bunny  # check groups the user bunny belongs to

(Mac) To ADD a user to a group, run:

$ dseditgroup -p -o edit -a userToAdd -t user group

to add the user “johncurry” to the group “bunny” that would look like:

$ dseditgroup -p -o edit -a johncurry -t user bunny

“-p”
Give prompt for password

“-o”
is “operation” and edit is the parameter. So “-o edit” is “edit operation”

“-a userToAdd”
-a is “add” and the “userToAdd” should be replaced with the user you wish to add

“-t user group”

-t is the type of record to be added. “-t user” means add a user to the group, and “group is the group to add the user to.

Let’s verify that “johncurry” is in the “bunny” group by running $ groups

$ groups
staff com.apple.sharepoint.group.2 bunny everyone localaccounts _appserverusr admin _appserveradm _lpadmin com.apple.sharepoint.group.1 _appstore _lpoperator _developer com.apple.access_ftp com.apple.access_screensharing com.apple.access_ssh com.apple.sharepoint.group.3

Yay! “bunny” is the third option for me, so I’m in the bunny group!

(Mac) How to Remove a User From a Group

To REMOVE “johncurry” from the “bunny” group, all you do is replace the -a flag with a -d flag. -a is add, and -d is delete!

dseditgroup -p -o edit -d johncurry -t user bunny

Poof! It’s gone!

Read the manual page for the command $ dseditgroup for more info. To view the manual, run:

$ man dseditgroup

Sudo & Wheel

We have one more important topic. Sudo & WHEEL. Sudo stands for “SUperuser DO”. It’s where a normal user is given super powers aka “super administrator access”, meaning they can act as root. A SUDO command will look like this:

$ sudo do-something-important

root has virtually no limits, so you can accidentally destroy your entire computer with one bad command. Because it’s so dangerous to run around as the root user, you should give your main user “SUDO” access, and only run commands as root when absolutely necessary.

Regular users do NOT have SUDO access unless you explicitly add them to a group with SUDO access.

Giving a user SUDO access

If you try to run a command as sudo without sudo access, you’ll get an error like this: Username is not in the sudoers file. This incident will be reported.

Here’s how you fix the error by giving a user SUDO access. (You only give accounts sudo if they NEED it)

The /etc/sudoers file.

The sudoers file is a list of all the groups & users that have access to the “sudo” command. You can only edit this file by running “$ visudo” or “$ sudo visudo” from your terminal. This editor verifies there are no errors, which could seriously harm your computer. If an error warning pops up, press “x” to exit without saving or “e” to re-edit the file.

Let’s go ahead and take a look at our /etc/sudoers file. From the command line, run one of the following:

$ sudo visudo  #run this on a mac, or as a non-root user with admin privileges
$ visudo       # as a root user.

You’ll want to look for code that looks something like this (maybe not exact):

##
## User privilege specification
##
root ALL=(ALL) ALL
%admin  ALL=(ALL) ALL

## Uncomment to allow members of group wheel to execute any command
# %wheel ALL=(ALL) ALL

## Same thing without a password
# %wheel ALL=(ALL) NOPASSWD: ALL

## Uncomment to allow members of group sudo to execute any command
# %sudo ALL=(ALL) ALL

In this code, you’ll notice my %admin line is set to ALL=(ALL) ALL and it’s uncommented. (The # is a comment). Because %admin is uncommented, and set the way it is, the admin group and all users inside admin group will have SUDO privileges. If I need the wheel group to have sudo privileges, then all I need to do is uncomment the # %wheel ALL=(ALL) ALL line and add the user to the wheel group.

Thoughts on Security

Unfortunately I’m not a security guru, but Linux permissions are a very basic security feature. The idea is to only give people access to stuff you want them to have access to. On a personal computer, you don’t want your grandma accidentally finding her way into your local server and deleting a bunch of stuff. So give her account no permissions on sensitive files, and don’t put her in any important groups.

It also protects you from yourself. Running around your filesystem as root you may destroy something with a single typo. At least force yourself to use SUDO when doing dangerous stuff.

Conclusion

I think that’s everything. If you understand how to add/remove groups, add/remove users to groups, change the files ownership and group, change the access rights of each user, and add/remove users to the sudoers file, then you have a great understanding of Unix/Linux permissions, which will make your computer and servers much more secure, and you’ll never have to be confused by them again. Is there anything I missed? Let me know in the comments!

Reading Makes You Smarter!

Check out our recommended reading! We've chosen a variety of books covering a lot of different topics from Security, Functional programming, clean code, design, Computer Networking and more.

Learn to Code! Get Free Tutorials & Courses Straight to Your inbox!