Apache .htaccess: 403 Forbidden

Diagnose and fix the Apache 403 Forbidden error caused by .htaccess misconfigurations, incorrect file permissions, or missing index files.

Apache HTTP Server returns a 403 Forbidden error when a .htaccess directive, file permission, or directory configuration blocks the client from accessing the requested resource.

The 403 Forbidden error appears in several variations depending on the Apache configuration and browser:

  • "Forbidden. You don't have permission to access this resource."
  • "HTTP Error 403 -- Forbidden"
  • "403 Forbidden: Request forbidden by administrative rules."
  • "Access Denied: You don't have permission to access"

When Apache .htaccess Produces the 403 Forbidden Error

Apache HTTP Server returns a 403 Forbidden response when the server understands the request but refuses to authorize it. The .htaccess file triggers this error when an access control directive explicitly denies the client, or when the operating system prevents Apache from reading the requested file.

Apache HTTP Server also returns 403 Forbidden when no index file exists in a directory and the Options -Indexes directive prevents directory listing. The server can locate the directory but has no file to serve and no permission to list the directory contents.

What Causes the 403 Forbidden Error in Apache .htaccess

Incorrect file or directory permissions cause Apache to return 403 Forbidden.Apache HTTP Server runs as a specific system user (typically www-data on Debian/Ubuntu or apache on CentOS/RHEL). The server process needs read permission on every file and execute permission on every directory in the request path. If the OS denies read access, Apache returns 403 regardless of .htaccess content.

A Require all denied directive in .htaccess causes Apache to return 403 Forbidden.The mod_authz_core module in Apache 2.4 evaluates Require directives to determine access. A Require all denied directive in any .htaccess file along the directory path blocks all requests to that directory and its children. The legacy Deny from all directive from mod_access_compat produces the same result.

A missing index file combined with Options -Indexes causes Apache to return 403 Forbidden.Apache HTTP Server attempts to serve index.html, index.php, or another DirectoryIndex file when a client requests a directory. If no index file exists and Options -Indexes prevents automatic directory listing, Apache has no content to serve and returns 403.

How to Fix the 403 Forbidden Error in Apache .htaccess

  1. Verify that the document root directory exists. Apache HTTP Server returns 403 if the DocumentRoot directory is missing or inaccessible.

    ls -la /var/www/example_com/

    The public_html/ (or html/) directory must exist and be readable by the Apache process user.

  2. Set correct directory and file permissions. Apache requires 755 permissions on directories (read + execute for all, write for owner) and 644 on files (read for all, write for owner).

    chmod 755 /var/www/example_com/public_html/
    chmod 644 /var/www/example_com/public_html/.htaccess

    Apply permissions recursively to fix nested directories:

    find /var/www/example_com/public_html/ -type d -exec chmod 755 {} \;
    find /var/www/example_com/public_html/ -type f -exec chmod 644 {} \;
  3. Verify that an index file exists in the directory. Apache HTTP Server looks for files specified in the DirectoryIndex directive. Create an index.html or index.php file if none exists.

    ls /var/www/example_com/public_html/index.*
  4. Check the .htaccess file for access control directives that block requests. Open the .htaccess file and look for Require all denied, Deny from all, or Require not ip directives that match the client's IP address.

    Temporarily empty the .htaccess file to confirm it is the source of the 403 error. If the error disappears, re-add directives one at a time to identify the offending rule.

  5. Verify the file ownership. The Apache process user must own (or have group access to) the files in the document root. Set ownership to the Apache user:

    On Debian and Ubuntu:

    sudo chown -R www-data:www-data /var/www/example_com/public_html/

    On CentOS and RHEL:

    sudo chown -R apache:apache /var/www/example_com/public_html/

How to Verify the 403 Forbidden Fix

Open a browser and navigate to the URL that returned the 403 error. Apache HTTP Server serves the requested page when the permissions and .htaccess directives are correct.

Check the Apache error log for remaining 403 entries. The error log provides the exact reason Apache denied the request:

tail -f /var/log/apache2/error.log

On CentOS and RHEL:

tail -f /var/log/httpd/error_log

Edge Cases and Variations

SELinux blocks Apache access on CentOS and RHEL.SELinux enforces mandatory access controls beyond standard file permissions. Apache HTTP Server returns 403 even with correct file permissions if the SELinux context is wrong. Check the SELinux audit log and restore the correct context:

sudo restorecon -Rv /var/www/example_com/public_html/

WordPress plugins cause 403 Forbidden through .htaccess modifications.Some WordPress security and caching plugins add restrictive directives to .htaccess. Disable plugins one by one to identify which plugin added the blocking rule. Check .htaccess for plugin-generated comment blocks.

Apache returns 403 for symbolic links.If the document root or any subdirectory contains symbolic links, Apache requires Options +FollowSymLinks in the .htaccess file or server configuration. Without this option, Apache refuses to follow symlinks and returns 403.

Apache .htaccess: 500 Internal Server Error-- Apache returns a 500 error when .htaccess contains a syntax error or references a disabled module. A 500 error indicates a server-side parsing failure, while a 403 error indicates a deliberate access denial.