A more neat and elegant solution:
NOTICE: The file extension .gzip seems strange, in general, we name a gziped file as .gz, so in this example, we use .gz instead .gzip, if you insist on .gzip, just replace all the extensions in the following config file.
Code first, this is what all we need for web.config
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<system.webServer>
<staticContent>
<remove fileExtension=".js.gz" />
<remove fileExtension=".css.gz" />
<remove fileExtension=".png.gz" />
<remove fileExtension=".jpg.gz" />
<remove fileExtension=".gif.gz" />
<remove fileExtension=".svg.gz" />
<remove fileExtension=".html.gz" />
<remove fileExtension=".json.gz" />
<mimeMap fileExtension=".js.gz" mimeType="application/javascript" />
<mimeMap fileExtension=".css.gz" mimeType="text/css" />
<mimeMap fileExtension=".png.gz" mimeType="image/png" />
<mimeMap fileExtension=".jpg.gz" mimeType="image/jpeg" />
<mimeMap fileExtension=".gif.gz" mimeType="image/gif" />
<mimeMap fileExtension=".svg.gz" mimeType="image/svg+xml" />
<mimeMap fileExtension=".html.gz" mimeType="text/html" />
<mimeMap fileExtension=".json.gz" mimeType="application/json" />
</staticContent>
<rewrite>
<outboundRules rewriteBeforeCache="true">
<rule name="Custom gzip file header">
<match serverVariable="RESPONSE_CONTENT_ENCODING" pattern=".*" />
<conditions>
<add input="{REQUEST_URI}" pattern="\.gz$" />
</conditions>
<action type="Rewrite" value="gzip"/>
</rule>
</outboundRules>
<rules>
<rule name="Rewrite gzip file">
<match url="(.*)"/>
<conditions>
<add input="{HTTP_ACCEPT_ENCODING}" pattern="gzip" />
<add input="{REQUEST_FILENAME}.gz" matchType="IsFile" />
</conditions>
<action type="Rewrite" url="{R:1}.gz" />
</rule>
</rules>
</rewrite>
</system.webServer>
</configuration>
And, here are how it works:
In order to achieve a successful gziped data transmission, we need:
- Client side accept gziped data,
Accept-Encoding
- Response with a header with
Content-Encoding
- Proper MIME type, as the original file is, BUT NOT
application/gzip
- Gziped file
The four conditions must be satisfied at the same time.
If you send an uncompressed file with Content-Encoding: gzip, the browser will return an error;
If you send a compressed file without a Content-Encoding header, or a mismatched MIME type, the page may return some Zenith Star's text.
So what we are doing is:
- Redefine each type of gziped file's MIME
- If the client side accept a gziped file, then redirect the response file to a gziped version on the server side directly (not 302/303/307 response)
- Rewrite the header of the response header of
Content-Encoding, only if the client side send the header Accept-Encoding
This solution works on my IIS7, not sure if it will also work on IIS10.
If you met any problem, let me know :D