1

I want to add my .htaccess code into /etc/apache2/apache2.conf.

I want to combine these:

.htaccess file.

<IfModule mod_rewrite.c>
    RewriteEngine On
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^([^\.]+)$ $1.php [NC,L]
</IfModule>

/etc/apahce2/apache2.conf file.

<Directory /var/www/>
        Options Indexes FollowSymLinks
        AllowOverride All
        Require all granted
</Directory>



Problem is I don't know where to add htaccess code. How can I combine these files?
I am using Ubuntu 18.04.
Thanks in advance!

1
  • IMHO the good way to do this is to create a virtual host and use the mod_rewrite configuration inside it.
    – ponsfrilus
    Jul 9, 2020 at 6:27

1 Answer 1

2

Assuming your .htaccess file is currently located at /var/www/.htaccess then you can literally just combine them. .htaccess and <Directory> containers share the same directory "context" - they follow the same (similar) syntax.

In other words:

<Directory /var/www/>
    Options Indexes FollowSymLinks
    AllowOverride All
    Require all granted

    <IfModule mod_rewrite.c>
        RewriteEngine On
        RewriteCond %{REQUEST_FILENAME} !-f
        RewriteRule ^([^\.]+)$ $1.php [NC,L]
    </IfModule>
</Directory>

However, if you are going to use mod_rewrite directives in a <Directory> container then you should consider disabling .htaccess altogether (ie. AllowOverride None), since .htaccess will override the <Dirctory> container (by default) and your directives will be ignored.

There is no need for the <IfModule> wrapper here since it looks like these directives are mandatory.

A couple of minor points...

  • There is no need to backslash escape a literal dot when used inside a regex character class, since it carries no special meaning here. ie. [^\.] is the same as [^.].

  • The NC flag on your RewriteRule directive is superfluous since your pattern already matches both lower and uppercase letters.

  • You explicitly enable directory indexes (Options Indexes), yet your mod_rewrite directives effectively prevent directory access anyway. You should probably disable directory indexes.

Bringing these points together, this becomes:

<Directory /var/www/>
    Options FollowSymLinks
    AllowOverride None
    Require all granted

    RewriteEngine On
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^([^.]+)$ $1.php [L]
</Directory>

An alternative approach, and possibly what @ponsfrilus was suggesting in comments, is to add your mod_rewrite directives directly to the server config (a server context) or <VirtualHost> container (a virtualhost context) - outside of the <Directory> container. (Note that if you are already using <VirtualHost> containers - preferable - then you will likely need to add these directives to the relevant <VirtualHost> container. Otherwise, directives in a server context will probably just get overridden.)

An advantage of this approach is that they can't then be overridden by .htaccess. But if you are disabling .htaccess anyway (which you probably should be - since you are moving these directives to your server config) then it doesn't really matter. Also, using mod_rewirte directives outside of a directory context is arguably "simpler".

However, the syntax of mod_rewrite directives in a server (or virtualhost) context is different to a directory context, so they need to be changed slightly.

Since directives in a server context are processed much earlier, before the request is mapped to the filesystem, you can't simply use the REQUEST_FILENAME server variable to get the requested filename (which ordinarily holds the absolute filename after the request has been mapped to the filesystem). You need to use a lookahead instead. ie. LA-U:REQUEST_FILENAME.

Also, in a server context, the URL-path that the RewriteRule pattern matches against is always a root-relative URL-path, starting with a slash. Whereas in .htaccess (a directory context), the URL-path is less the directory-prefix, so never starts with a slash. In this case, you don't actually need to change anything, but note that what happens is slightly different... in a server context you will end up rewriting to a URL-path, whereas in .htaccess you are essentially rewriting to a filesystem path (unless you've set a RewriteBase directive).

So, alternatively, the above directives could be written as:

RewriteEngine On
RewriteCond %{LA-U:REQUEST_FILENAME} !-f
RewriteRule ^([^.]+)$ $1.php [L]

<Directory /var/www/>
    Options FollowSymLinks
    AllowOverride None
    Require all granted
</Directory>
2
  • Updated my answer to include an alternative approach... by adding these directives to the server config (or virtualhost) directly. Although this isn't necessarily "better".
    – MrWhite
    Jul 9, 2020 at 11:18
  • 1
    Thanks for a really good answer and detailed explanation! I used first option and it worked very well!
    – ahmedg
    Jul 9, 2020 at 11:33

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .