Securely Serving Files via CFContent
Let's say you have an application requirement that uploads files to your web server and then lets your visitors either view or save them. They could be Documents, Spreadsheets, Photos, or anything else you can think of. However you want to be able to control who is able to access these files. How do you accomplish that with not allowing direct linking (ex. http://www.cfwebtools.com/files/xyz.docx)?
You can serve the files via a ColdFusion page. There are a few different methods to do this, and they really come down to MIME typing.
Option 1:
Allow the user to save or open any file.
<cfcontent file="#filePath#" type="application/octet-stream">
The cfheader of attachment and filename prompt the user to either save or externally open the document with the software and their computer. The client computer will determine which MIME type to use to associate with an application.
Option 2:
Allow the user to save or open only files with MIME types my server is aware of.
<cfif IsDefined("mimeType")>
<cfheader name="Content-Disposition" value="attachment; filename=#getFileFromPath(filePath)#">
<cfcontent file="#filePath#" type="#mimeType#">
<cfelse>
This type of file is not supported.
</cfif>
Now - the MIME types supported are defined in your webserver, whether it's IIS, Apache or other. Apache MIME types can be configured in the mime.types files in the httpd/conf directory. The getMimeTypes() method communicates with the web server and returns the associated MIME type for the file.
Now, be aware that there may be an issue with IIS communicating MIME types to ColdFusion on Windows 2K Server. I've had an application break using this method for additional types such as .docx extensions. I have not yet found a solution for it, and just use option #1 to work around it.
Option 3:
Allow the user to view supported types inside the browser such as MS Word documents and PDF files. If not supported in the browser, it will attempt to open the file externally.
<cfif IsDefined("mimeType")>
<cfheader name="Content-Disposition" value="inline; filename=#getFileFromPath(filePath)#">
<cfcontent file="#filePath#" type="#mimeType#">
<cfelse>
This type of file is not supported.
</cfif>
You can also define the MIME type in the code by replacing the mimeType variable with the type such as "application/msword".
These methods allow you to access any attached storage device on the server. Therefore you can save the files out of the web directory, making the file inaccessable without using your ColdFusion script. Imagine the possibilites like adding user authentication or IP restriction.


There are no comments for this entry.
[Add Comment]