IIS Insider - November 2005
By Tom Kaminski
Compressing Files Other Than HTML and Plain Text
Q. I enabled compression on my IIS 6.0 box and noticed that my CSS and JScript files are not getting compressed. How can I enable compression for those files?
A. By default, the only static file types that IIS 6.0 is configured to compress are HTML and plain text files. Feel free to add other static files as needed. Because the files are static, any performance hit to compress them would be negligible. Additional extensions can be added manually by editing the IIS metabase. See the section of the metabase that includes the IIsCompressionScheme elements. Listed below is an example of the default compression setting:
<IIsCompressionScheme Location="/LM/W3SVC/Filters/Compression/deflate" HcCompressionDll="%windir%\system32\inetsrv\gzip.dll" HcCreateFlags="0" HcDoDynamicCompression="TRUE" HcDoOnDemandCompression="TRUE" HcDoStaticCompression="FALSE" HcDynamicCompressionLevel="0" HcFileExtensions="htm html txt" HcOnDemandCompLevel="10" HcPriority="1" HcScriptFileExtensions="asp dll exe" />
<IIsCompressionScheme Location="/LM/W3SVC/Filters/Compression/gzip" HcCompressionDll="%windir%\system32\inetsrv\gzip.dll" HcCreateFlags="1" HcDoDynamicCompression="TRUE" HcDoOnDemandCompression="TRUE" HcDoStaticCompression="TRUE" HcDynamicCompressionLevel="0" HcFileExtensions="htm html txt" HcOnDemandCompLevel="10" HcPriority="1" HcScriptFileExtensions="asp dll exe" />
In this case, you would want to modify the HcFileExtensions property for both compression schemes listed. To enable compression for Cascading Style Sheets (CSS) and JScript files, the property should be changed to:
HcFileExtensions="htm html txt css js"
Note: The HcFileExtensions property will not be available in IIS 7.0. Instead, IIS will compress files based on content types. Text content types, such as the ones mentioned in the example above, are already covered. Also, compression will be enabled by default.
Protecting Static Content Without Using Windows Authentication
Q. How do I protect static content without using Windows authentication?
A. Many times administrators and developers want to have a system protected by an alternate authentication and authorization scheme, such as user names and passwords stored in a database. While this works well for dynamic content, which can be coded to check for authorization before displaying any further HTML or executing any code, it does not work well for static file types such as Microsoft Office documents or images. There is no code being processed on the server as these files are served so this method cannot be used to directly protect these files. A simple solution to this problem is to use server code to stream the static files to the user after he or she has passed authentication and authorization. This can be done with classic ASP using the ADODB.Stream object along with Request.BinaryWrite. Here's a simple example in code using an Adobe® Acrobat'® PDF:
<% Const adTypeBinary = 1 Dim sPath Dim sFile sPath = "D:\fileshare\" sFile = document1.pdf Response.ContentType = "application/pdf" Response.AddHeader "Content-Disposition","filename=" & sFile Set oStream = Server.CreateObject("ADODB.Stream") oStream.Open oStream.Type = adTypeBinary oStream.LoadFromFile sPath & sFile Response.BinaryWrite oStream.Read objStream.Close Set objStream = Nothing %>
The first three lines of code establish a constant for the Stream object and initialize our variables. The next line of code tells the browser what MIME type is being sent. Here you would customize this with the MIME type for the file you are sending. Optionally, the next line tells the browser what file name to use in the browser window. Without this, the file name will be the URL to your ASP page. The next section of code loads your file into the Stream object and then delivers it to the browser via the BinaryWrite method.
ASP.NET works in a similar way. In this case, the .NET Framework gives us the FileStream and BinaryReader objects to handle the file. Here is an example in VB.NET code (Imports System.IO is assumed):
Dim sPath As String = "D:\fileshare\" Dim sFile As String = "document1.pdf" Response.Buffer = True Response.Clear() Response.ClearContent() Response.ClearHeaders() Response.ContentType = "application/pdf" Response.AddHeader("Content-Disposition", "filename=" & sFile) Dim fs As FileStream Dim br As BinaryReader fs = New FileStream(sPath & sFile, FileMode.Open) br = New BinaryReader(fs) Dim dataBytes As Byte() = br.ReadBytes(fs.Length - 1) Response.BinaryWrite(dataBytes) br.Close() fs.Close()
This code works in a similar manner to our classic ASP code, with the obvious difference of having to read the number of bytes with our BinaryReader in order to load the file.
Note: With the integrated pipeline in IIS 7.0, static content can be protected without having to employ the workaround mentioned above.
How to Access IIS Behind a NAT Router
Q. How do I access IIS behind a NAT router?
A. Network address translation (NAT) routers have become very common lately as they are inexpensive and offer an easy way to set up a simple network. They are often used in corporate environments to isolate a test platform and are popular with home users as an easy way to share a broadband Internet connection amongst multiple computers in the household. Difficulties arise, however, because without proper configuration, the router will block access to your IIS server. A technology called "port forwarding" is used to enable access to the server from the outside world. In simple terms, the router is instructed to forward all requests it receives on a certain port to a specific computer on its network. While the standard port for HTTP traffic is 80, this can also be used for alternate available ports.
Most NAT routers have an embedded Web server that is used for configuration. Consult your documentation for the specific URL to use to connect. Once connected, look for Port Forwarding as one of the options to configure. The common way to configure this is to identify:
The service (HTTP in this case)
The port range you want to forward (port 80 by default for Web traffic)
The IP address to which you want to route all requests (the IP address of your server)
Because you need to statically map the port forwarding, it's best to assign a static IP for your server and not rely on DHCP. This technique can also be used for other services that you want to provide, such as SMTP, NNTP, or FTP. These services would be configured in the same way, except that you would forward the appropriate ports for each service. For specific instructions for your router, consult the manufacturer's Web site. Manufacturers typically offer documentation, pointers, and answers to frequently asked questions in their support areas.
An alternate method is to place your server in what might be called the Neutral Zone. While the router will still assign a static or dynamic IP for your server, the router will not block any requests and will therefore leave your box wide open for attacks. Make sure you have either a good software or hardware firewall protecting that server.
One final note: If you are a home user, please make sure you are not violating your Internet service provider's (ISP) Terms of Service as many broadband providers prohibit their home users from running servers. In many cases, ISPs will even block inbound port 80 traffic on their networks, making port 80 unusable for this type of use.
For More Information
Submit your questions to the IIS Insider. A response is not guaranteed; however, selected questions along with the answers will be posted in a future IIS Insider column.
Visit IIS Insider column archives for a list of previous months' questions and answers.
We at Microsoft Corporation hope that the information in this work is valuable to you. Your use of the information contained in this work, however, is at your sole risk. All information in this work is provided "as is," without any warranty, whether express or implied, of its accuracy, completeness, fitness for a particular purpose, title or non-infringement, and none of the third-party products or information mentioned in the work are authored, recommended, supported or guaranteed by Microsoft Corporation. Microsoft Corporation shall not be liable for any damages you may sustain by using this information, whether direct, indirect, special, incidental or consequential, even if it has been advised of the possibility of such damages.