# Laravel File Permissions: How to Fix World-Writable Files and Secure Your Filesystem

> Files with 777 or 666 permissions let any user on the server read, write, or execute them. Set restrictive permissions to prevent unauthorized modification.

**Severity:** high | **Category:** Infrastructure Security

---

## The Issue

World-writable files (permissions 777 or 666) allow any user on the server to read, modify, or execute them. On shared hosting or compromised servers, this means an attacker who gains access to any account can modify your application code, configuration, or data. The most dangerous cases are writable .env files (credential theft), writable PHP files (code injection), and writable config files (application takeover).

## Steps to Fix

### 1. Set correct permissions for Laravel directories

Apply the recommended Laravel permissions:

# Directories: 755 (owner: rwx, group: rx, others: rx)
find /var/www/yourapp -type d -exec chmod 755 {} \;

# Files: 644 (owner: rw, group: r, others: r)
find /var/www/yourapp -type f -exec chmod 644 {} \;

# Storage and cache need to be writable by the web server
chmod -R 775 storage/ bootstrap/cache/

# .env should be readable only by the owner
chmod 600 .env

### 2. Set correct ownership

Files should be owned by your deploy user, with the web server group:

# Set ownership (replace 'deploy' and 'www-data' with your users)
chown -R deploy:www-data /var/www/yourapp

# Storage needs web server write access
chown -R deploy:www-data storage/ bootstrap/cache/

Common web server users:
- Ubuntu/Debian with Nginx: www-data
- Ubuntu/Debian with Apache: www-data
- CentOS with Nginx: nginx
- Laravel Forge: forge

### 3. Find and fix world-writable files

Search for overly permissive files:

# Find all world-writable files
find /var/www/yourapp -perm -o+w -type f -not -path '*/storage/*' -not -path '*/bootstrap/cache/*'

# Find all 777 directories
find /var/www/yourapp -perm 777 -type d

Fix any results by applying the correct permissions from step 1.

## Verification

Run the permission check:

find /var/www/yourapp -perm -o+w -type f -not -path '*/storage/*' -not -path '*/bootstrap/cache/*' -not -path '*/node_modules/*'

This should return no results. Also verify .env permissions:

stat -c '%a %n' .env
# Should show 600 .env

Run php artisan stackshield:scan --check=SS022 to verify.

## Prevention

Set a umask in your deployment script (umask 022). Use a deployment tool like Envoyer or Forge that sets permissions correctly. Never use chmod 777 as a quick fix — diagnose the actual permission issue instead. Add a permission check to your deployment script.

---

## Frequently Asked Questions

### Why does Laravel need storage/ to be writable?

Laravel writes session files, cache data, compiled views, and log files to storage/. The web server process needs write access to these directories. Use 775 with proper group ownership rather than 777.

### Is chmod 777 ever acceptable?

No. There is always a better solution. If you need a directory writable by the web server, use proper group ownership (chown :www-data) with 775 permissions. If you need a file writable by a cron job, run the cron as the correct user.

### How do I quickly audit file permissions across my entire Laravel installation?

Run find /var/www/yourapp -perm -o+w -type f -not -path "*/storage/*" -not -path "*/bootstrap/cache/*" -not -path "*/node_modules/*" to find world-writable files outside legitimate writable directories. Run find /var/www/yourapp -perm 777 -type d for world-writable directories. Both should return no results. Add these checks to your deployment pipeline as a post-deploy verification step.

### What permissions should the public/ directory have?

The public/ directory should be 755 (owner: rwx, group: rx, others: rx) with files at 644. The web server needs read access to serve static files but should never need write access to public/. Uploaded files should be stored in storage/app/public/ and served via the storage symlink, not written directly to public/uploads/.

### Is it safe to run the web server as root to avoid permission issues?

Never. Running a web server as root means any vulnerability — a file inclusion bug, a code execution flaw, or a compromised package — executes with full system privileges. The web server user should be www-data or nginx with minimal filesystem permissions. Permission issues should always be resolved through correct ownership and group configuration, not by elevating the web server's privileges.

