4

Having created an example Blazor WebAssembly application, I deployed it to both an IIS and an Apache for testing purposes.

When publishing the application, it generated a folder "wwwroot" and a file "web.config":

enter image description here

The "wwwroot" folder contains the whole application:

enter image description here

When deploying to IIS, everything works fine.

What I'm currently struggling with is to deploy to Apache.

The "web.config" file contains two rewrite rules.

Rule 1:

<rule name="Serve subdir">
    <match url=".*" />
    <action type="Rewrite" url="wwwroot\{R:0}" />
</rule>

Rule 2:

<rule name="SPA fallback routing" stopProcessing="true">
    <match url=".*" />
    <conditions logicalGrouping="MatchAll">
        <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
    </conditions>
    <action type="Rewrite" url="wwwroot\" />
</rule>

I've tried several things to get at least rule 1 working with mod_rewrite, like e.g.:

RewriteEngine on
RewriteRule ^.*?$ /wwwroot [QSA]

But I either get 404 or endless redirects.

My question

How to convert above rule 1 and rule 2 to Apache mod_rewrite configurations?


Update 1

I do think this one is a valid replacement for rule 1:

RewriteEngine on
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteRule (.*) /wwwroot/$1 [L]

I've got it from this Super User answer.

Update 2

There is a Microsoft documentation on how to host on Apache but it is missing the rewrite parts.

Update 3

Based on the above Microsoft document, I was able to resolve it:

  1. Do not put the "wwwroot" folder into the root folder of the Apache website.

  2. Instead, place the content of the "wwwroot" folder directly into the root folder of the Apache website.

  3. Do not put any mod_rewrite rules at all to the ".htaccess" file.

  4. Add this directive to the ".htaccess" file:

    ErrorDocument 404 /index.html
    

The complete, minimal ".htaccess" file for my test application looks like this:

ErrorDocument 404 /index.html

AddType application/wasm .wasm
AddType application/octet-stream .dll

<IfModule mod_deflate.c>
    AddOutputFilterByType DEFLATE text/css
    AddOutputFilterByType DEFLATE application/javascript
    AddOutputFilterByType DEFLATE text/html
    AddOutputFilterByType DEFLATE application/octet-stream
    AddOutputFilterByType DEFLATE application/wasm
    <IfModule mod_setenvif.c>
        BrowserMatch ^Mozilla/4 gzip-only-text/html
        BrowserMatch ^Mozilla/4.0[678] no-gzip
        BrowserMatch bMSIE !no-gzip !gzip-only-text/html
  </IfModule>
</IfModule>

Update 4

Above example was for running the Blazor WebAssembly application directly from the root folder of an Apache website.

If you instead want to run it from a subfolder (let's say "/myappinfolder") some things have to be changed:

  1. Move all files, including the ".htaccess" file, into the subfolder "myappinfolder".

  2. Modify the ErrorDocument directive in the ".htaccess" file to:

    ErrorDocument 404 /myappinfolder/index.html
    
  3. Change the base href in the "index.html" file to:

    <base href="/myappinfolder/" />
    

Update 5

Instead of using the ErrorDocument Apache directive, another option is to use the FallbackResource Apache directive instead:

FallbackResource /myappinfolder/index.html

The FallbackResource has the advantage that it keeps the HTTP method (e.g. POST or GET) when forwarding the request to the configured URL ("/myappinfolder/index.html" in my example).

Whereas ErrorDocument always forwards the request to the configured URL ("/myappinfolder/index.html" in my example) with a GET HTTP method.

(Idea from this SO answer)

Uwe Keim
  • 39,551
  • 56
  • 175
  • 291

0 Answers0