'After upgrading to Angular8, AppEngine is serving scripts with the incorrect mime-type
There seems to be a change if not a bug to how Angular8 packages up index.html that is breaking my deployment.
The scripts at the bottom of the index.html in the dist folder no longer have type="text/javascript"
<script src="runtime-es2015.b1e01c6054a9feffbeda.js" type="module"></script>
<script src="polyfills-es2015.dd0ef0c762416a11ccfe.js" type="module"></script>
<script src="runtime-es5.b1e01c6054a9feffbeda.js" nomodule></script><script src="polyfills-es5.ad2e20378bba1e661425.js" nomodule></script>
<script src="scripts.03e042f1f102bf0e2ed8.js"></script><script src="main-es2015.59f62c10fb8246590dad.js" type="module"></script><script src="main-es5.d5d8d375e147ae1da6f0.js" nomodule></script></body>
After deploy, I get errors in chrome and firefox like:
Loading module from “https://yarrascrape.appspot.com/runtime-es2015.b1e01c6054a9feffbeda.js” was blocked because of a disallowed MIME type (“text/plain”).
or
Failed to load module script: The server responded with a non-JavaScript MIME type of "text/plain". Strict MIME type checking is enforced for module scripts per HTML spec.
This would likely affect different types of web servers.
I am using AppEngine with python runtime. I have attempted to set the mime type in the app.yaml with variations like:
- url: /(.*\.(js))$
secure: always
static_files: \1
upload: (.*)
http_headers:
content_type: text/javascript
- url: /(.*)
secure: always
static_files: \1
upload: (.*)
http_headers:
content_type: text/javascript
This hasn't worked. Either the approach is wrong, or my yaml is wrong.
After the build, as an experiment, I manually edited dist/index.html and inserted type="text/javascript" to all the scripts at the bottom of the file. This works, but I am looking for a viable solution.
Solution 1:[1]
My tech stack is a bit different (ie., I'm not using Python), but this may be of help:
I encountered the same issue/browser errors with a MEAN Stack app (with Angular 8/ Node v11.6.0) that I've been working on when running ng build --prod (which is supposed to run AOT- Ahead of Time Compilation by default, but it was failing to compile in a way that could be read by Chrome + Firefox for some reason that I can't explain). After visiting the Angular docs (https://angular.io/guide/aot-compiler), I tried running ng build --aot instead of ng build --prod before running my node server and the issue went away.
Hope this helps:-)
Solution 2:[2]
My Angular 13 production build .js files were statically served with text/plain mime-type by Google Cloud Platform Standard App Engine subsequently making my application fail to use them with error message:
Failed to load module script: Expected a JavaScript module script but the server responded with a MIME type of "text/plain". Strict MIME type checking is enforced for module scripts per HTML spec.
Fix was explicitly specifying mime-type for served .js files in .yaml file.
runtime: nodejs16
service: default
handlers:
# Serve all JS files with text/javascript mime-type
- url: /(.*\.js)$
static_files: dist/\1
upload: dist/(.*\.js)$
mime_type: text/javascript
# Serve all static files with urls ending with a file extension
- url: /(.*\..+)$
static_files: dist/\1
upload: dist/(.*\..+)$
# catch all handler to index.html
- url: /.*
static_files: dist/index.html
upload: dist/index.html
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | Juliette Tworsey |
| Solution 2 | Maz T |
