Last active
September 10, 2020 12:54
-
-
Save ProLoser/6181026 to your computer and use it in GitHub Desktop.
Elegant cache-busting for AngularJS HTML assets
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
anglar.module('myApp',['ui']).config(["$provide", function($provide) { | |
return $provide.decorator("$http", ["$delegate", function($delegate) { | |
var get = $delegate.get; | |
$delegate.get = function(url, config) { | |
// Check is to avoid breaking AngularUI ui-bootstrap-tpls.js: "template/accordion/accordion-group.html" | |
if (!~url.indexOf('template/')) { | |
// Append ?v=[cacheBustVersion] to url | |
url += (url.indexOf("?") === -1 ? "?" : "&"); | |
url += "v=" + cacheBustVersion; | |
} | |
return get(url, config); | |
}; | |
return $delegate; | |
}]); | |
}]); |
@ericjames: I've done it this way
- Have Grunt get the buildVersion from AssemblyInfo (if available) or generate a unique string if version could not be extracted.
- Have Grunt build a file "config.js" using Node package "ngconstant"
- Configure ngconstant to add a "ENV"-parameter with eg. a property BuildNo set to the buildVersion in the config.js file (creates a module called "config" with an Angular-constant "ENV")
- The ENV-constant can then be injected in any app.module config-section and you can access ENV.BuildNo
If you have a localhost-target in your gruntfile, consider setting BuildNo to a fixed value, so you browser is not busted locally.
Great and simple!
Hi. Thank you for writing this. It has really helped me. I was just wondering if anyone could help in getting my Karma test to work for this? I am using the server to create a cache bust constant every time I run a build. I then pass this constant into the .config.
I have tried adding it where the constants required in a service would go, but I guess that the Constant needs to get to the module prior to running a service as it runs during the configuration phase?
Chrome 58.0.3029 (Windows 10 0.0.0) View Service setShowDeleted method Return 0 if undefined FAILED
Error: [$injector:modulerr] Failed to instantiate module homer due to:
Error: [$injector:unpr] Unknown provider: CACHE_BUST
http://errors.angularjs.org/1.6.3/$injector/unpr?p0=CACHE_BUST
at resources/bower_components/angular/angular.js:66:12
at resources/bower_components/angular/angular.js:4789:19
at getService (resources/bower_components/angular/angular.js:4944:32)
at injectionArgs (resources/bower_components/angular/angular.js:4969:58)
at Object.invoke (resources/bower_components/angular/angular.js:4995:18)
at runInvokeQueue (resources/bower_components/angular/angular.js:4890:35)
at resources/bower_components/angular/angular.js:4900:11
at forEach (resources/bower_components/angular/angular.js:402:20)
at loadModules (resources/bower_components/angular/angular.js:4880:5)
at Object.createInjector [as injector] (resources/bower_components/angular/angular.js:4802:19)
<script>
angular.module("homer")
.constant("CSRF_TOKEN", "{{ csrf_token() }}")
.constant("CACHE_BUST", "[token created by server goes here]"));
</script>
.config(["$provide", "CACHE_BUST", function($provide, CACHE_BUST) {
return $provide.decorator("$http", ["$delegate", function($delegate) {
var get = $delegate.get;
$delegate.get = function(url, config) {
// Check is to avoid breaking AngularUI ui-bootstrap-tpls.js: "template/accordion/accordion-group.html"
if (!~url.indexOf('template/') && !~url.indexOf('ui-grid')) {
// Append ?v=[cacheBustVersion] to url
url += (url.indexOf("?") === -1 ? "?" : "&");
url += "v=" + CACHE_BUST;
}
return get(url, config);
};
return $delegate;
}]);
}])
angular.module('homer').factory('VatBandPusherService', VatBandPusherService)
VatBandPusherService.$inject = ['$rootScope', 'PusherService', 'UiGridService']
function VatBandPusherService($rootScope, PusherService, UiGridService) {
VatBandPusherService.config = function(scope, idName) {
// Broadcasting Methods
var pusher = PusherService.createNewInstance();
var my_channel = pusher.subscribe('private-VatBand');
...
return;
};
return VatBandPusherService;
};
describe('VatBandPusherService Test', function () {
var VatBandPusherService, PusherService, mockPusherService;
beforeEach(function() {
module('homer', function($provide) {
$provide.constant('CSRF_TOKEN', 'MOCK_CONSTANT'); // This is working
$provide.constant('CACHE_BUST', 'MOCK_CONSTANT'); // This is not working
var mockPusherService= {
createNewInstance: function () {
return 'mockReturnValue';
}
};
$provide.constant('PusherService', mockPusherService);
});
});
beforeEach(inject(function (_VatBandPusherService_) {
VatBandPusherService = _VatBandPusherService_;
}));
// A simple test to verify the factory exists
it('Service should exist', function() {
expect(VatBandPusherService).toBeDefined();
});
});
Any ideas would be much appreciated.
not to be a jerk but typo on line 1 😄
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Cool now just how do we get
cacheBustVersion