IIS – How to Serve Static .gltf Files

iisstatic-content

I am using three.js library with GLTFLoader.js. I downloaded some free 3D model with .gltf extension (it also came with a .bin file, and a folder with textures).

I can access every other file in this folder from IIS (10) as static content, except for the .gltf file which returns the 404 page.

I have added MIME mapping to IIS everywhere at this point (web.config for the ASP.NET Core 2.2 site, top level of IIS, site level of IIS). It is model/gltf+json. I tried application/json and application/octet-stream just in case. It returns 404 in all situations.

I tried allowing the server to serve all static files with a wildcard MIME mapping. Even this fails.

If I rename the .gltf file to .json, it works fine.

I tried FailedRequestTracing, which provided me with a huge xml file. Going through that revealed nothing enlightening to me, but maybe I just don't know enough about inner workings of IIS.

Same trouble on IISExpress (ran from Visual Studio 2019).

I tried converting .gltf to .glb using https://glb-packer.glitch.me/ but .glb extension exhibits the same issue with IIS -> 404.

Restarting IIS with iisreset /restart didn't help.

I am not using any URL rewrite rules.

Adding the option ServeUnknownFileTypes = true to StaticFiles middleware made no difference.

Have you encountered a problem like this before? Any suggestions as to what to try next?

UPDATE: I have managed to narrow down the problem to AspNetCoreModuleV2 handler. When not present, .gltf file is served correctly. Now, I do need this module to run, so that's a problem.

UPDATE: figured it out finally… I'll post an answer for the next unfortunate soul to stumble upon this.

Best Answer

Turned out I am using a custom FileServerProvider because I need IoC container to inject it into some controllers later on. (Similar fix works on UseStaticFiles() in Configure method, if the .gltf is in wwwroot.)

In ConfigureServices:

var fileProviderOptions = new FileServerOptions
{
    FileProvider = new PhysicalFileProvider(_ContentStorePath),
    RequestPath = new PathString("/ContentStore")
};
fileProviderOptions.StaticFileOptions.ContentTypeProvider = new FileExtensionContentTypeProvider();
((FileExtensionContentTypeProvider)fileProviderOptions
    .StaticFileOptions.ContentTypeProvider).Mappings[".gltf"] = "model/gltf+json";
services.AddSingleton<IFileServerProvider>(new FileServerProvider(
    new List<FileServerOptions> { fileProviderOptions }
));

So, I had to tell it what gltf is in code. StaticFileOptions is read-only, and ContentTypeProvider is an interface, so a few hoops need jumping through.

In retrospect, maybe this question was better suited to StackOverflow after all.