angular / angular-cli

CLI tool for Angular
https://cli.angular.io
MIT License
26.73k stars 11.98k forks source link

Subresource integrity / filename hash inconsistency #9338

Closed karptonite closed 4 years ago

karptonite commented 6 years ago

Versions

Angular CLI: 1.6.3
Node: 9.3.0
OS: darwin x64
Angular: 5.2.0
... animations, common, compiler, compiler-cli, core, forms
... language-service, platform-browser, platform-browser-dynamic
... platform-server, router

@angular/cli: 1.6.3
@angular-devkit/build-optimizer: 0.0.36
@angular-devkit/core: 0.0.22
@angular-devkit/schematics: 0.0.42
@ngtools/json-schema: 1.1.0
@ngtools/webpack: 1.9.3
@schematics/angular: 0.1.11
@schematics/schematics: 0.0.11
typescript: 2.5.3
webpack-bundle-analyzer: 2.9.2
webpack: 3.10.0

AND

Angular CLI: 1.6.4
Node: 9.3.0
OS: darwin x64
Angular: 5.2.0
... animations, common, compiler, compiler-cli, core, forms
... language-service, platform-browser, platform-browser-dynamic
... platform-server, router

@angular/cli: 1.6.4
@angular-devkit/build-optimizer: 0.0.38
@angular-devkit/core: 0.0.25
@angular-devkit/schematics: 0.0.48
@ngtools/json-schema: 1.1.0
@ngtools/webpack: 1.9.4
@schematics/angular: 0.1.13
@schematics/schematics: 0.0.13
typescript: 2.5.3
webpack-bundle-analyzer: 2.9.2
webpack: 3.10.0

Repro steps

I don't have a minimal reproduction, but here is a gist to two yarn lockfiles: https://gist.github.com/karptonite/925a56d957a34ff65063d52e619f7fcc

Observed behavior

when building with --prod --subresource-integrity: The subresource integrity SHA hash can change without the hashed filename changing as dependencies are updated.

In the two yarn lockfiles shown, nothing that is included in polyfills changed, and the hashed filename (--output-hashing all, since --prod is set) remains unchanged between builds. However, because some other dependencies were updated (notably, the uglify version changed), the integrity SHA hash changed. That is a problem because our js is served by a CDN, which assumes that if the filename remains unchanged, it can continue to serve from the cache.

Desired behavior

When anything that can affect the content of the minimized file changes, that should change the filename hash. This could be accomplished by naming the file based on the minimized code, but it could also be as simple as hashing in the version numbers of the relevant packages involved in minimizing the code when generating the filenames.

If you are unable to reproduce this, let me know, and I'll see if I can figure out how to reproduce it. I got stuck (working in a minimal project) trying to force yarn to downgrade the version of uglify to match what is in my production yarn lock above.

karptonite commented 6 years ago

@clydin, this might be of interest to you.I believe you did the original SRI implementation?

KLuuKer commented 6 years ago

This is not a problem with SRI but really with the cache busting code, you can see this because SRI is actually doing it's job correctly (blocking code that has a incorrect hash value).

I think the cache bust calculator hashes the files BEFORE processing (ugilfy\etc) instead of after all the conversions have been run.

We basically have this problem every time we deploy because the polyfills file always stays the same but the versions of ugily and the like change (because we very aggressively update all dependancies)

KLuuKer commented 6 years ago

can we get this fixed soon? I know it's "inconvenient" and we can clear the cloudflare cache when it happens but..... when doing daily deploys with about 100 different domains it's getting past the point of "inconvenient" and more like a royal pain in the ass. o yeah then there is the whole issues of telling everyone to clear their cache because their browser is caching the files for a year.

nrandell commented 5 years ago

I've had similar issues and am currently trying a postbuild script in my package.json to update the runtime file in the html. A bit of a hack, but it may solve the problem.

const path = require('path');
const fs = require('fs');

const cheerio = require('cheerio');
const ssri = require('ssri');

const baseDir = 'dist/newu-app';

const htmlSource = path.join(baseDir, 'index.html');
const markup = fs.readFileSync(htmlSource).toString();
const $ = cheerio.load(markup);

$('script').each((index, element) => {
    const src = $(element).attr('src');
    if (src.startsWith('runtime.')) {
        const filename = path.join(baseDir, src);
        const data = fs.readFileSync(filename);
        const md5 = ssri.fromData(data, {algorithms: ['md5']}).hexDigest();
        const integrity = ssri.stringify(ssri.fromData(data, {algorithms: ['sha384']}));
        const newSrc = 'runtime.' + md5 + '.js';
        const newFilename = path.join(baseDir, newSrc);
        $(element).attr('src', newSrc);
        $(element).attr('integrity', integrity);
        fs.copyFileSync(filename, newFilename);
    }
});

const html = $.html();
fs.writeFileSync(htmlSource, html);

It seems to work for me and may help others

JohanLindvall commented 5 years ago

We are being hit by this bug too.

Consider that the runtime.js file may be in the end user's browser cache so that purging the CDN cache doesn't help.

clydin commented 5 years ago

Can you provide the version of webpack being used in the projects exhibiting the issue?

nrandell commented 5 years ago

I'm using angular cli 7.0.5 and it has pulled in webpack 4.19.1

clydin commented 5 years ago

Webpack 4.19.0 was supposed to fix the runtime chunk hashing.

Is version 4.19.1 the only version present within the project (npm ls webpack)?

Webpack is responsible for generating the filename and the hash used inside it (which is very different than the SRI hash).

nrandell commented 5 years ago

Just checked

npm ls webpack returned

`-- @angular-devkit/build-angular@0.10.3
  `-- webpack@4.19.1

I also have subresourceintegrity and service workers enabled.

matdryz commented 5 years ago

This issue is related to bug in webpack-subresource-integrity plugin, that was fixed in version 1.3.2: https://github.com/waysact/webpack-subresource-integrity/issues/101

Therefore I guess raising the version of webpack-subresource-integrity to 1.3.2 should help (it worked for me locally with npm-shrinkwrap)

KLuuKer commented 5 years ago

Can we please please fix this subresource-integrity is now useless and actually prevents the code from working correctly because the hash doesn't match

We have a very aggressive 1 year caching policy and now I'm fixing this at the crack of dawn since we have about 20+ people not being able to use our app

adarshaj commented 5 years ago

We are affected by this too. Hoping the PR can be merged soon.

fabioemoutinho commented 5 years ago

I am getting this error, which seems related to this issue: WARNING in webpack-subresource-integrity: Cannot determine asset for chunk scripts, computed="undefined", available=scripts.95488a83006a892d75cd.js. Please report this full error message along with your Webpack configuration at https://github.com/waysact/webpack-subresource-integrity/issues/new

mgechev commented 5 years ago

@fabioemoutinho did you try with the latest version of the CLI? Are you still able to reproduce the problem?

fabioemoutinho commented 5 years ago

@fabioemoutinho did you try with the latest version of the CLI? Are you still able to reproduce the problem?

@angular-devkit/architect         0.801.1
@angular-devkit/build-angular     0.802.0
@angular-devkit/build-optimizer   0.802.0
@angular-devkit/build-webpack     0.802.0
@angular-devkit/core              8.2.0
@angular-devkit/schematics        8.2.0
@angular/cdk                      8.1.1
@angular/material                 8.1.1
@angular/pwa                      0.802.0
@ngtools/webpack                  8.2.0
@schematics/angular               8.2.0
@schematics/update                0.802.0
rxjs                              6.5.2
typescript                        3.5.3
webpack                           4.38.0

npm run build -- --prod generates the warning

@mgechev my scripts.js file is composed of several js files (mostly legacy code we need in our application). It might be related to the content of the files, since they are old js code, but in that case I would need a better error message to know what is causing the problem. We use this method (scripts property in angular.json) to bundle scripts since angular 4, but the warning was not showing up until latest versions, probably ng 7+.

eseliger commented 5 years ago

I think it would be fixed by using not [hash] but [contenthash] in the filename. I don't know if this has other implications though. but after this error happening, I investigated and I found that the runtime chunk with 2 different contents had the same hash, but different integrity hashes. For us, we allow caching for all generated .js files, to speed up subsequent page loads. When the index.html references a new runtime.SAMEHASH.js with the correct integrityhash now, the old runtime.SAMEHASH.js with another integrityhash is returned from the browser cache then. Maybe it would be worth either

eseliger commented 5 years ago

Ahh I just saw the contenthash is already being used, I inferred it can't be since the hashes were the same ..

At least I'll share data to reproduce below, maybe someone can see what I'm missing

index.html no caching *.js 7 days caching

cached runtime

!function(e){function r(r){for(var H,c,a=r[0],f=r[1],S=r[2],d=0,u=[];d<a.length;d++)t[c=a[d]]&&u.push(t[c][0]),t[c]=0;for(H in f)Object.prototype.hasOwnProperty.call(f,H)&&(e[H]=f[H]);for(i&&i(r);u.length;)u.shift()();return o.push.apply(o,S||[]),n()}function n(){for(var e,r=0;r<o.length;r++){for(var n=o[r],H=!0,c=1;c<n.length;c++)0!==t[n[c]]&&(H=!1);H&&(o.splice(r--,1),e=a(a.s=n[0]))}return e}var H={},t={4:0},o=[],c={0:"sha384-aayR7t8JlYVLi9WFgRUvUnLCKjvKw8vXfzkq+EIFqlCzGDkLYHisldg/P/5IwYlI",1:"sha384-MQVzu5lWMaH1uw3mNDiPV1kVD9bc/SYjQ4Va+kzFqJ0P4ko93rJrlG84ESFHzJh4",2:"sha384-s+9LokMi/iyW/YzeSqJZYZD2W+BpO/0074NW6K04k8dnBLREwcfD0j7g3b0T8pVW",3:"sha384-HVpBgcW4FphxT8m2FToqyp/jU+w6MRUOal7Mqlfa2bWBcaUf/fP8RhdN06JOoZee",5:"sha384-kzmiVfVJo70lvXQlvGDZEZUqpgKwBHlukYu0hCfZHSVAOn/AtYF/2qV+uhWr5CaN",6:"sha384-Wh6Pq5TE/hBlMq9y8J6PrE42JWnb6LH4oumrq/F6ob6nU6kXtGp6zBwWVkV7td65",7:"sha384-Q3/nWTaWs7+Xrvc8SpHUFhPeuH2JQlDDDvSOQTOrkRxlf4ehDwq1xtDFQ+KU3IC6",8:"sha384-jh+CRry1dxmvS6sU311vAfHlnsMmhscsQeBlkkTtxDCU0OO/rxfm9ogCZzMQIs4p",9:"sha384-CjTHfFi/Skf89p+iq3H6Rf5NJKEGpOvLFT/jFWXSWwbofNO+AtGPoj+/RS0MsQBQ",10:"sha384-yY6j9oMjgSIOuMFVz7IKkkZstzQAFSzuGTB4jBchblABBYwYXMmcIwKWyj5m10YD",11:"sha384-33S8xMGATzGCts9wqfF3oVfIzp+Ly7uz3TTUkD9HhQF0QpeY0dDwptPi2VkgLWVm",12:"sha384-j7AM4wPktT3QcYU/IQjU7WVUvr+FsGnrikrJPk03N9UAJ3HXxtBJkkfG4NS+hr9z",13:"sha384-XmtYX8znMwLP6Yyxbr/W5xx9pbUYQXMoSXXR0nUbhR6FPtxu4nJVTfrntphCz3DQ",14:"sha384-gOx9NtWSHQZnv4BWIYwE21PcA0WFcRA759ODfY8BtEujU/SFPtRQdYNuHE5UrcOW",15:"sha384-/YeLUiswuSDAmM8A6KLFuOLZv02tYVhTs5hi97xNXGcN6DDJRduMhXbPBAY6Q2+6",16:"sha384-z5w59blbp//3jbXjKwDdLtWpRHgv/PLGZaYGtATMib8lmIE3uJmQau/FEg4dGf3W",17:"sha384-35lvjg8x/9652CEYDXH3Ej43HSWVvH5sphMXDJ5GfQZsquWoCbpPz4uYRZ6qudgK",18:"sha384-fSsaRpIdCTs7KEUfaXiNFClt6jMtLLux+N/UPK+fUqtcg6zMtIMsVnbqBQIpMAxs",19:"sha384-Djh3mZh30PrkShZ8Pquz0hE0dw2uL8xkGmPgtaRZMOFW5Cv0xjAB9zPbjBCMphDZ",20:"sha384-Tw1ggSKQgq7djaTyt/u8w0u9IUh++t8wn8AQWE6wJDGILgKnj18gqC2uNS6K3RLO",21:"sha384-L66hQ4c3nzeO7927FLwBtlikfK7vCe0AGryQucBSgb5h/4ANPt6jld8EliqB8Mtz",22:"sha384-XKgxrymHr8CLH4eWMPpMgCoKteebyOIzFE7UIh+4DNO08inWIWFrzbJEvSqDFb4H",23:"sha384-EvMjTT/YGHaOnrP4FnXGYy+7K6pzDF0LozFn2H87IwVJG0D92r7F+1D/Fx4HLFmL",24:"sha384-eT7dkN4RJc1rs74+vH2MiptWcTx8IIGNDFoFq9BRzEVgAq0hAFhOhtWQJjSvypU1",25:"sha384-/R7uAlHnB9NPFMsh8hP0S6jJ/7vwBfrqFaR/CB/1UjGpTBB4An0srxXBkoexFMDa",26:"sha384-YfsmlN+NBI4KUtMw9rpvR9dLUylwNgXX6Ay7bTfRKsuUeaZjS8aZhQklNE0sbQQt",27:"sha384-2KGbGdsnvRAqQsMngRltJMzw7/+wrYwke3cDLJd9+hrj0q8QEhYllx3NchHg+JjM",28:"sha384-syR+Lok8ndnMmlh3aPbbh7QlBLKT6DEDR1DbGDKq1l6mTcCci5pC/Vp2rjK99eYM",29:"sha384-lebmdzvkaIYlDyD0bWvkUjpCCf01Wv4QcFw923eJt1lKIlUJnZSPSaNr5eyFzMEf",30:"sha384-ywExl4d0EPJWTLK09ZJBVhxopq2aftCYxU69HqiZTFQlzvqwMdk7ouQaf6toa1iM",31:"sha384-JahjUAiy2jr8hkliz+RAa5QpXNP6V88u0b0DBLMofFSopSb1bTllAzN7mIMR7u8v",32:"sha384-zK/oS3Fy+7Sc/yTVI6nzrZxtEo+D2YmWwQFrsPPFpVjNoSjfFoJKS625NIaTz6GT",33:"sha384-gtMDyU7oo6UNpVKSaBs18jCfrj62yPbqBLipLBw8q2c1I9qjETq7AVC9XbmNrUIZ",34:"sha384-c7e5NvztwLdBOqlzu6b+TdmN/MxvJEnWjJO8qjZAfSb2RWfSFvIzA9RVDdUcSgSc",35:"sha384-LPtIKkYHWMz9DuCldZMoM6fckK8SB+g89oRTmS7VWZSIKrrzJxWPRBCLSywwlZ2r",36:"sha384-JedFUrpAQFAjrO7PfFbYfrOLnrtp5rVzxhIHR3J+A4g8wQa58+jHCN2aBBESB7sw"};function a(r){if(H[r])return H[r].exports;var n=H[r]={i:r,l:!1,exports:{}};return e[r].call(n.exports,n,n.exports,a),n.l=!0,n.exports}a.e=function(e){var r=[],n=t[e];if(0!==n)if(n)r.push(n[2]);else{var H=new Promise(function(r,H){n=t[e]=[r,H]});r.push(n[2]=H);var o,f=document.createElement("script");f.charset="utf-8",f.timeout=120,a.nc&&f.setAttribute("nonce",a.nc),f.src=function(e){return a.p+""+({0:"common"}[e]||e)+"."+{0:"39ed0ced8453662e17ad",1:"774df27269c6495e5488",2:"077615ce03357384fb8e",3:"8a03b755bbaa38581f6e",5:"e53e2e41fba7c0ad7e0a",6:"93b337261ddec8cdb5e0",7:"de09cbcf67b239e0ed2f",8:"0b35341d4577a0dc210e",9:"739f41a2c84427b7ac18",10:"d0eeb130c50eb62b203b",11:"cd75b63f84dda66b06fc",12:"fe7e1dbc2f8d5cf38782",16:"740592699feda9530474",17:"6634b5441f9b49910b50",18:"facb49809663ac8f2cdd",19:"e930d182b8935cea7b8d",20:"7533d0794808ef9acddc",21:"ba47f6e9a8fb1c803066",22:"34c78d72abcc812f9c8d",23:"042daba33b98e9018c0d",24:"e24b1161425e52536205",25:"ee97dc53b271c0324cf1",26:"83a130c42b826619a430",27:"538fd2208aa2c460a943",28:"eee515deb8c1f41cd148",29:"eb344166eae9590fcd1b",30:"259de3d2b591038503af",31:"2fcbb89fe365db8342e1",32:"04aa60e7d170ece6dcaa",33:"0bf87971c27659c3f7aa",34:"2599c5595e536bf62c0f",35:"58fd25aba11313a666a4",36:"59b686444dd08c0abbe1"}[e]+".js"}(e),0!==f.src.indexOf(window.location.origin+"/")&&(f.crossOrigin="anonymous");var S=new Error;o=function(r){f.onerror=f.onload=null,clearTimeout(d);var n=t[e];if(0!==n){if(n){var H=r&&("load"===r.type?"missing":r.type),o=r&&r.target&&r.target.src;S.message="Loading chunk "+e+" failed.\n("+H+": "+o+")",S.name="ChunkLoadError",S.type=H,S.request=o,n[1](S)}t[e]=void 0}};var d=setTimeout(function(){o({type:"timeout",target:f})},12e4);f.onerror=f.onload=o,f.integrity=c[e],f.crossOrigin="anonymous",document.head.appendChild(f)}return Promise.all(r)},a.m=e,a.c=H,a.d=function(e,r,n){a.o(e,r)||Object.defineProperty(e,r,{enumerable:!0,get:n})},a.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},a.t=function(e,r){if(1&r&&(e=a(e)),8&r)return e;if(4&r&&"object"==typeof e&&e&&e.__esModule)return e;var n=Object.create(null);if(a.r(n),Object.defineProperty(n,"default",{enumerable:!0,value:e}),2&r&&"string"!=typeof e)for(var H in e)a.d(n,H,(function(r){return e[r]}).bind(null,H));return n},a.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return a.d(r,"a",r),r},a.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},a.p="",a.oe=function(e){throw console.error(e),e};var f=window.webpackJsonp=window.webpackJsonp||[],S=f.push.bind(f);f.push=r,f=f.slice();for(var d=0;d<f.length;d++)r(f[d]);var i=S;n()}([]);
//# sourceMappingURL=runtime.6a8025c3ecb850393dc9.js.map

actual runtime

!function(e){function r(r){for(var H,c,a=r[0],f=r[1],S=r[2],d=0,u=[];d<a.length;d++)t[c=a[d]]&&u.push(t[c][0]),t[c]=0;for(H in f)Object.prototype.hasOwnProperty.call(f,H)&&(e[H]=f[H]);for(i&&i(r);u.length;)u.shift()();return o.push.apply(o,S||[]),n()}function n(){for(var e,r=0;r<o.length;r++){for(var n=o[r],H=!0,c=1;c<n.length;c++)0!==t[n[c]]&&(H=!1);H&&(o.splice(r--,1),e=a(a.s=n[0]))}return e}var H={},t={4:0},o=[],c={0:"sha384-aayR7t8JlYVLi9WFgRUvUnLCKjvKw8vXfzkq+EIFqlCzGDkLYHisldg/P/5IwYlI",1:"sha384-MQVzu5lWMaH1uw3mNDiPV1kVD9bc/SYjQ4Va+kzFqJ0P4ko93rJrlG84ESFHzJh4",2:"sha384-s+9LokMi/iyW/YzeSqJZYZD2W+BpO/0074NW6K04k8dnBLREwcfD0j7g3b0T8pVW",3:"sha384-HVpBgcW4FphxT8m2FToqyp/jU+w6MRUOal7Mqlfa2bWBcaUf/fP8RhdN06JOoZee",5:"sha384-kzmiVfVJo70lvXQlvGDZEZUqpgKwBHlukYu0hCfZHSVAOn/AtYF/2qV+uhWr5CaN",6:"sha384-Wh6Pq5TE/hBlMq9y8J6PrE42JWnb6LH4oumrq/F6ob6nU6kXtGp6zBwWVkV7td65",7:"sha384-Q3/nWTaWs7+Xrvc8SpHUFhPeuH2JQlDDDvSOQTOrkRxlf4ehDwq1xtDFQ+KU3IC6",8:"sha384-jh+CRry1dxmvS6sU311vAfHlnsMmhscsQeBlkkTtxDCU0OO/rxfm9ogCZzMQIs4p",9:"sha384-CjTHfFi/Skf89p+iq3H6Rf5NJKEGpOvLFT/jFWXSWwbofNO+AtGPoj+/RS0MsQBQ",10:"sha384-yY6j9oMjgSIOuMFVz7IKkkZstzQAFSzuGTB4jBchblABBYwYXMmcIwKWyj5m10YD",11:"sha384-33S8xMGATzGCts9wqfF3oVfIzp+Ly7uz3TTUkD9HhQF0QpeY0dDwptPi2VkgLWVm",12:"sha384-j7AM4wPktT3QcYU/IQjU7WVUvr+FsGnrikrJPk03N9UAJ3HXxtBJkkfG4NS+hr9z",13:"sha384-IAj4ed/3ci5j2WNXKebZrDt/upGZ2AEnlxT7UXJN9kCGmRHWL11xHr3snaFsROCs",14:"sha384-gOx9NtWSHQZnv4BWIYwE21PcA0WFcRA759ODfY8BtEujU/SFPtRQdYNuHE5UrcOW",15:"sha384-/YeLUiswuSDAmM8A6KLFuOLZv02tYVhTs5hi97xNXGcN6DDJRduMhXbPBAY6Q2+6",16:"sha384-z5w59blbp//3jbXjKwDdLtWpRHgv/PLGZaYGtATMib8lmIE3uJmQau/FEg4dGf3W",17:"sha384-35lvjg8x/9652CEYDXH3Ej43HSWVvH5sphMXDJ5GfQZsquWoCbpPz4uYRZ6qudgK",18:"sha384-fSsaRpIdCTs7KEUfaXiNFClt6jMtLLux+N/UPK+fUqtcg6zMtIMsVnbqBQIpMAxs",19:"sha384-Djh3mZh30PrkShZ8Pquz0hE0dw2uL8xkGmPgtaRZMOFW5Cv0xjAB9zPbjBCMphDZ",20:"sha384-Tw1ggSKQgq7djaTyt/u8w0u9IUh++t8wn8AQWE6wJDGILgKnj18gqC2uNS6K3RLO",21:"sha384-L66hQ4c3nzeO7927FLwBtlikfK7vCe0AGryQucBSgb5h/4ANPt6jld8EliqB8Mtz",22:"sha384-XKgxrymHr8CLH4eWMPpMgCoKteebyOIzFE7UIh+4DNO08inWIWFrzbJEvSqDFb4H",23:"sha384-EvMjTT/YGHaOnrP4FnXGYy+7K6pzDF0LozFn2H87IwVJG0D92r7F+1D/Fx4HLFmL",24:"sha384-eT7dkN4RJc1rs74+vH2MiptWcTx8IIGNDFoFq9BRzEVgAq0hAFhOhtWQJjSvypU1",25:"sha384-/R7uAlHnB9NPFMsh8hP0S6jJ/7vwBfrqFaR/CB/1UjGpTBB4An0srxXBkoexFMDa",26:"sha384-YfsmlN+NBI4KUtMw9rpvR9dLUylwNgXX6Ay7bTfRKsuUeaZjS8aZhQklNE0sbQQt",27:"sha384-2KGbGdsnvRAqQsMngRltJMzw7/+wrYwke3cDLJd9+hrj0q8QEhYllx3NchHg+JjM",28:"sha384-syR+Lok8ndnMmlh3aPbbh7QlBLKT6DEDR1DbGDKq1l6mTcCci5pC/Vp2rjK99eYM",29:"sha384-lebmdzvkaIYlDyD0bWvkUjpCCf01Wv4QcFw923eJt1lKIlUJnZSPSaNr5eyFzMEf",30:"sha384-ywExl4d0EPJWTLK09ZJBVhxopq2aftCYxU69HqiZTFQlzvqwMdk7ouQaf6toa1iM",31:"sha384-JahjUAiy2jr8hkliz+RAa5QpXNP6V88u0b0DBLMofFSopSb1bTllAzN7mIMR7u8v",32:"sha384-zK/oS3Fy+7Sc/yTVI6nzrZxtEo+D2YmWwQFrsPPFpVjNoSjfFoJKS625NIaTz6GT",33:"sha384-gtMDyU7oo6UNpVKSaBs18jCfrj62yPbqBLipLBw8q2c1I9qjETq7AVC9XbmNrUIZ",34:"sha384-c7e5NvztwLdBOqlzu6b+TdmN/MxvJEnWjJO8qjZAfSb2RWfSFvIzA9RVDdUcSgSc",35:"sha384-LPtIKkYHWMz9DuCldZMoM6fckK8SB+g89oRTmS7VWZSIKrrzJxWPRBCLSywwlZ2r",36:"sha384-JedFUrpAQFAjrO7PfFbYfrOLnrtp5rVzxhIHR3J+A4g8wQa58+jHCN2aBBESB7sw"};function a(r){if(H[r])return H[r].exports;var n=H[r]={i:r,l:!1,exports:{}};return e[r].call(n.exports,n,n.exports,a),n.l=!0,n.exports}a.e=function(e){var r=[],n=t[e];if(0!==n)if(n)r.push(n[2]);else{var H=new Promise(function(r,H){n=t[e]=[r,H]});r.push(n[2]=H);var o,f=document.createElement("script");f.charset="utf-8",f.timeout=120,a.nc&&f.setAttribute("nonce",a.nc),f.src=function(e){return a.p+""+({0:"common"}[e]||e)+"."+{0:"39ed0ced8453662e17ad",1:"774df27269c6495e5488",2:"077615ce03357384fb8e",3:"8a03b755bbaa38581f6e",5:"e53e2e41fba7c0ad7e0a",6:"93b337261ddec8cdb5e0",7:"de09cbcf67b239e0ed2f",8:"0b35341d4577a0dc210e",9:"739f41a2c84427b7ac18",10:"d0eeb130c50eb62b203b",11:"cd75b63f84dda66b06fc",12:"fe7e1dbc2f8d5cf38782",16:"740592699feda9530474",17:"6634b5441f9b49910b50",18:"facb49809663ac8f2cdd",19:"e930d182b8935cea7b8d",20:"7533d0794808ef9acddc",21:"ba47f6e9a8fb1c803066",22:"34c78d72abcc812f9c8d",23:"042daba33b98e9018c0d",24:"e24b1161425e52536205",25:"ee97dc53b271c0324cf1",26:"83a130c42b826619a430",27:"538fd2208aa2c460a943",28:"eee515deb8c1f41cd148",29:"eb344166eae9590fcd1b",30:"259de3d2b591038503af",31:"2fcbb89fe365db8342e1",32:"04aa60e7d170ece6dcaa",33:"0bf87971c27659c3f7aa",34:"2599c5595e536bf62c0f",35:"58fd25aba11313a666a4",36:"59b686444dd08c0abbe1"}[e]+".js"}(e),0!==f.src.indexOf(window.location.origin+"/")&&(f.crossOrigin="anonymous");var S=new Error;o=function(r){f.onerror=f.onload=null,clearTimeout(d);var n=t[e];if(0!==n){if(n){var H=r&&("load"===r.type?"missing":r.type),o=r&&r.target&&r.target.src;S.message="Loading chunk "+e+" failed.\n("+H+": "+o+")",S.name="ChunkLoadError",S.type=H,S.request=o,n[1](S)}t[e]=void 0}};var d=setTimeout(function(){o({type:"timeout",target:f})},12e4);f.onerror=f.onload=o,f.integrity=c[e],f.crossOrigin="anonymous",document.head.appendChild(f)}return Promise.all(r)},a.m=e,a.c=H,a.d=function(e,r,n){a.o(e,r)||Object.defineProperty(e,r,{enumerable:!0,get:n})},a.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},a.t=function(e,r){if(1&r&&(e=a(e)),8&r)return e;if(4&r&&"object"==typeof e&&e&&e.__esModule)return e;var n=Object.create(null);if(a.r(n),Object.defineProperty(n,"default",{enumerable:!0,value:e}),2&r&&"string"!=typeof e)for(var H in e)a.d(n,H,(function(r){return e[r]}).bind(null,H));return n},a.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return a.d(r,"a",r),r},a.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},a.p="",a.oe=function(e){throw console.error(e),e};var f=window.webpackJsonp=window.webpackJsonp||[],S=f.push.bind(f);f.push=r,f=f.slice();for(var d=0;d<f.length;d++)r(f[d]);var i=S;n()}([]);
//# sourceMappingURL=runtime.6a8025c3ecb850393dc9.js.map

in actual index.html

<script src="runtime.6a8025c3ecb850393dc9.js" crossorigin="anonymous" type="module" integrity="sha384-EYIyRKwNC5wgFq/oLdA8qSgJIsG+IdpnW8GNIN9y+RIyxx031LMQT84jqX84oicp"></script>

sha384 sums: cached: VDinAQO6iY5043Owfl98myR/zDHxFa9Q0jmbWqE1YxjijsC49QdU2tDIw0775Biw base64: actual: gyhzYjNbRNkm0kVr49UbYE+nlkhh8oeH2mMogqSClQCO/fgki/miELyW/YJhdIri

for some reason, they both don't match the integrity hash from the index.html

Chrome 76 output:

(index):1 Failed to find a valid digest in the 'integrity' attribute for resource 'REDACTED/runtime.6a8025c3ecb850393dc9.js' with computed SHA-256 integrity 'Jm7DCdAQtJq/0IZuDjLerUcS6Mvbqxr8sLcPACeO+dw='. The resource has been blocked.
clydin commented 5 years ago

It's actually using chunkhash right now and not contenthash (which didn't exist at the time the configuration was originally written). From the documentation, the differences aren't readily apparent. From reading through the code, neither appear to directly hash the output files as the SRI code does.

The change to contenthash could be tried locally by changing the following file inside node modules: node_modules/@angular-devkit/build-angular/src/angular-cli-files/models/webpack-configs/utils.js. In the getOutputHashFormat function, the entries for chunk would need to be changed.

eseliger commented 5 years ago

@clydin I tried it with no success, I cannot confirm the hash is changed... The integrity is still changing but chunk hash ain't 🤔

eseliger commented 5 years ago

I found this happening when the main bundle changes, the main's filename is changing, so is it's integrity, which is also changing in the runtime chunk but is not reflected in the runtime chunks hash. If someone got an idea, happy to dive deeper ..

fabioemoutinho commented 5 years ago

Shouldn't the server return the new resource, not a 304 response, even with the same filename? @eseliger

eseliger commented 5 years ago

Yes, but with cache-control headers with set max-age it won't even send the request at all, correct me if I'm wrong

fabioemoutinho commented 5 years ago

You are right. Would angular's service workers solve this issue if you dropped max-age headers?

eseliger commented 5 years ago

hmm, might be 🤔If I find some time, I'll give it a try! But for all files that map to index.html, we currently have no-cache, only for bundle files, so I think there will be implications of older versions being still served from the worker.. 🤔

But I think this is still an issue, that integrities can change while chunk hashes remain the same 🤔

alan-agius4 commented 4 years ago

Is this still reproducible with Angular CLI version 9?

alan-agius4 commented 4 years ago

Closing as there was no further communication.

If the problem persists please file a new issue with a minimal reproduction. Thanks

angular-automatic-lock-bot[bot] commented 4 years ago

This issue has been automatically locked due to inactivity. Please file a new issue if you are encountering a similar or related problem.

Read more about our automatic conversation locking policy.

This action has been performed automatically by a bot.