Score:1

mod_rewrite rules on subdirectory not woring due to parent rules

ph flag

My application lives in one directory and is served from a public folder, and I have an API endpoint in a sub-directory of public, both of which are redirected to their own respective index.php files. Until a recent server migration everything was working great. Now though, the API requests are being intercepted by the parent directory. Here are the vhost <directory...> segments in question...

    # application root
    <Directory "/path/to/app">
        Options FollowSymLinks
        AllowOverride None
        Require all granted
    </Directory>

    # public root
    <Directory /path/to/app/public>
        RewriteBase /
        RewriteCond %{REQUEST_FILENAME} -s [OR]
        RewriteCond %{REQUEST_FILENAME} -l [OR]
        RewriteCond %{REQUEST_FILENAME} -d
        RewriteRule ^.*$ - [NC,L]
        RewriteRule ^.*\.(media.php|png|jpg|gif|ico)$ media.php [NC,L]
        RewriteRule ^.*\.(xml|txt|css|js)$ static.php [NC,L]
        RewriteRule ^.*$ index.php/ [NC,L]
        errordocument 404 /error.php?id=404
    </Directory>

    # API
    <Directory /path/to/app/public/api>
        Header set Access-Control-Allow-Methods "PUT, GET, POST, DELETE, HEAD, OPTIONS"
        RewriteCond %{HTTP:Authorization} ^(.*)
        RewriteRule .* - [e=HTTP_AUTHORIZATION:%1]
        RewriteRule ^(.*)$ index.php [L,NC]
    </Directory>

I'm using Apache 2.4.53. The /path/to/app/public directives are working as expected, any media file extensions are redirected to media.php, any text based files are redirected to static.php, and everything else is sent to index.php with a 404 error fallback.

If I request mydomain.com/api/ alone I get the proper API specific error message, because the ./api/ directory physically exists. But as soon as I request a proper endpoint like mydomain.com/api/v1.0/some-enddpoint/ which should be captured and redirected at the ./api/index.php file, I'm getting a 404 error which is coming from the parent directory.

Appreciate any help!

kz flag
What was the Apache version of the old server?
ph flag
@MrWhite Sadly it was on a machine I no longer have access to at EC2, I looked before posting to see if I could find any breaking changes. I'm pretty positive it was 2.4.x as there are a number of other syntax uses that point to it that wouldn't have worked under 2.2.x.
Score:1
kz flag

It looks like your <Directory /path/to/app/public/api> container is inheriting the RewriteBase directive from the parent <Directory /path/to/app/public> container. This will happen if RewriteOptions MergeBase is set, or possibly other options relating to inheritance.

It doesn't look like you need the RewriteBase / directive in the <Directory /path/to/app/public> container, so you could simply remove it. However, check to see if you have defined this elsewhere in the config.

Alternatively, set a RewriteBase /api in the <Directory /path/to/app/public/api> container. OR, prefix the substitution string with the full URL-path, for example:

RewriteRule . /api/index.php [END]

I also reduced ^(.*)$ to simply ., since you only need this to be processed for non-empty URL-paths and you should be using the END flag, instead of L to prevent an unnecessary loop by the rewrite engine. (The NC flag is also superfluous.)

If I request example.com/api/ alone I get the proper API specific error message, because the ./api/ directory physically exists.

In this case, index.php is likely be served by mod_dir (DirectoryIndex), not mod_rewrite.

ph flag
Tried with both having defined `RewriteBase` directives, and both without, and neither method had any effect. I've disabled the HTTP Auth lines to ensure they're not interfering, but the parent is still catching the API calls before they can get to the API redirect. I tried re-ordering the two directory blocks just in case, but still nothing. It seems like the api's dir block is not matching anything beyond `.../api/` so I'm trying wildcards/regex there right now to see if I can get something to match.
ph flag
I'm starting to think that there's an error in the application rather than in the vhost config, the same config is working on an older version of the app code on another server. I think I've misinterpreted the symptom. Appreciate your help though, I'll test the other suggestions you made regarding simplifying the directives!
kz flag
@oucil presumably you are restarting Apache after each change to the server config? That HTTP Auth directive is simply setting an env var. You are also missing the `RewriteEngine On` directive. This should really be included in each `<Directory>` block (although it’s possible that it is enabled in a parent config). If the rewrite engine is not enabled for the `api` subdirectory then you will get the same symptoms.
ph flag
FFS, I had deleted the `RewriteEngine On` with an older rule not realizing it was in that block, ugh. Everything is working as expected again with it back in place. Really appreciate your help, sometimes it's just an extra set of eyes that makes the difference!
I sit in a Tesla and translated this thread with Ai:

mangohost

Post an answer

Most people don’t grasp that asking a lot of questions unlocks learning and improves interpersonal bonding. In Alison’s studies, for example, though people could accurately recall how many questions had been asked in their conversations, they didn’t intuit the link between questions and liking. Across four studies, in which participants were engaged in conversations themselves or read transcripts of others’ conversations, people tended not to realize that question asking would influence—or had influenced—the level of amity between the conversationalists.