I have following configuration:
Cloudfront - ELB - AutoScalingGroup - EC2s
- Cloudfront serves
file-[hash].js
files (with chunkhash in their names) from custom origin (ELB). - EC2s serve the
file-[hash].js
files for Cloudfront plus dynamically generatedindex.html
file that points to appropriate.js
file at Cloudfront. - ELB has connection draining enabled.
Everything works fine until a Cloudformation deployment with a changed asset is triggered (let's say from file-1.js
to file-2.js
) - when the new version is being switched on, there is a short time window when browser gets the new index.html
file pointing to file-2.js
, but when it tries to download file-2.js
it gets 404 from Cloudfront, thus showing an error to the user.
I understand this is because how blue/green deployment works - i.e. there is a time when two versions of the application works simultaneously and ELB can redirect one request to the new version (request for index.html
from the browser) and second one to the old version (request for file-2.js
from Cloudfront).
Cloudfront docs say that you should "host and serve the same content on all servers.", but how can I achieve that during the deployment? Is it possible to enforce that only single version of application is accessible through ELB at any given time, so that Cloudfront never gets 404 for the new assets?
If not, are there any other options to solve this, apart from switching from custom origin to S3? (would like to avoid it due to deployment / maintenance complexity)
Note switching from update policy AutoScalingRollingUpdate to AutoScalingReplacingUpdate did not help:
asg: Type: AWS::AutoScaling::AutoScalingGroup CreationPolicy: ResourceSignal: Count: Ref: 2 Timeout: PT10M UpdatePolicy: AutoScalingReplacingUpdate: WillReplace: true
Cache-Control: no-cache=set-cookie
)