I am currently upgrading parts of an ASP.NET MVC website to be more RESTful, using ASP.NET Web API. One of the features we are moving to a more RESTful design is file upload. For the client, we are using a jquery plugin, ajaxForm, to wrap the creation of an iframe which will submit the form containing the file input element. This was working great with ASP.NET MVC.
When changing it to use our Web API endpoint, which returns a response with a Content-Type of "application/json", we noticed problems with Internet Explorer 9. It appears the ajaxForm success function was never called. From what I can tell, it appears that the iframe in IE interprets the body of a response with a Content-Type of "application/json" as a file attachment to be downloaded. This means it never fires the iframe's "loaded" event, which means the ajaxForm onload event handler will never be triggered, and our ajaxForm success function will never be called.
We noticed the issue in IE 7 as well, but we could not recreate the issue in the latest release versions of Firefox or Chrome, even when forcing them to use an iframe rather than File API with FormData.
To resolve this issue for now, I am now forcing the response Content-Type back to "text/plain", which is what we were returning previously from the ASP.NET MVC controller actions which handled file upload. This makes everything work again.
My questions:
- Is there a way I can keep the Web API response Content-Type as "application/json" and have IE interpret it correctly?
- Is there a better way of doing file upload when using IE and Web API? Maybe a different plugin or better technique?
Additional Restrictions: I cannot use ActiveX or Flash for this website. I can use a different plugin, but only if it has general cross-browser support. (IE, Chrome, Firefox, Safari, etc)
My HTML:
<form id="uploadFormId" action="" method="post" enctype="multipart/form-data" encoding="multipart/form-data">
<input type="file" name="files[]"/>
</form>
My javascript:
function onFileChange( e ) {
if ( e.type === e.originalEvent.type ) {
var filePath = $( e.currentTarget ).val();
if ( filePath !== '' ) {
$( this ).closest( 'form' ).submit();
}
}
};
$( function() {
$( '#uploadFormId' ).ajaxForm( {
url: "api/Files/1234",
dataType: 'json',
success: function ( response ) {
alert( response );
},
error: function ( xhr, status, error ) {
alert( status );
}
} );
$( '#uploadFormId input[type="file"]' ).bind( 'change', onFileChange );
});
"application/json" response headers (doesn't work in IE):
Cache-Control:no-cache
Content-Length:337
Content-Type:application/json; charset=utf-8
Date:Wed, 17 Jul 2013 13:10:47 GMT
Expires:-1
Pragma:no-cache
Server:Microsoft-IIS/8.0
X-AspNet-Version:4.0.30319
X-Powered-By:ASP.NET
"text/plain" response headers (works in IE):
Cache-Control:no-cache
Content-Length:322
Content-Type:text/plain
Date:Wed, 17 Jul 2013 13:17:24 GMT
Expires:-1
Pragma:no-cache
Server:Microsoft-IIS/8.0
X-AspNet-Version:4.0.30319
X-Powered-By:ASP.NET