-
Notifications
You must be signed in to change notification settings - Fork 794
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Enable gzip on sprockets 3.0 #26
Comments
Its noted in the Changelog that it was removed from 3.0. Outputting .gz variants by default was disabled since most web servers don't actually use them. Configurations like Apache's You'll have to implement this yourself if you want it. Meanwhile, read this fun thread why you probably don't want to deal with this. https://bz.apache.org/bugzilla/show_bug.cgi?id=39727 |
@josh Oh no, this functionality hasn't been moved to another gem or anything? We used the |
For the archives: there was some discussion here sstephenson@d388ef7. |
Wow this seems like a terrible change. Right now I'm desperately trying to figure out how to get compressed assets working again with Heroku + Cloudfront CDN. Any suggestions? |
@chrisnicola are you using Custom Origin or S3? |
@chrisnicola what I ended up doing is downgrading sprockets until a solution to this problem is outlined. I am currently using the following with great success: gem 'sprockets', '~> 2.12.3' I should note that I am using |
@chrisnicola near the botton of the discussion linked above there's a link to a gist with a Capistrano task that compresses. |
We're in the same boat using S3&cloudfront. We ended up using some custom take task like those linked but I think it would be much better to have an official replacement gem, like those usually provided for stuff removed from rails. This is particularly necessary as sprockets is seldom a direct dependency and it's very likely people will find it upgraded without knowing. At least until rails 5 sprockets-rails should depend on the replacement. Just my opinion of course but thought it was worth sharing. |
I'm using Heroku + Rails + Cloudfront. Pretty standard configuration outlined in the Heroku docs, so I'm not sure a Capistrano task is the right direction for me here. I could make a custom buildpack perhaps. For the time being I've already done as @shawndeprey suggested and downgraded, which is working as a temporary solution. There are still other issues however, for example SVG files are not compressed at all, something I just recently noticed and Google Page Insights is yelling at me about. What's worse is pre-compressing doesn't work either because of course the digests won't match. What a mess. I'm talking with Heroku about the best way forward and I'll update this when I have a better solution. Switching from Puma to Passenger might be one option. |
I really think Sprockets should do this. Why minify, concatenate, hash, ..., everything but not compress? It's a standard optimization just like the other ones, and that's the kind of thing Sprockets is about. The fact that people using Apache has borked configurations out there is not something Sprockets should care about, as stated in the linked discussion there are valid and common use cases. At most, docs could warn. Rails guides just refused Apache configs. |
It only applies to CloudFront because they because they don't support on the fly compression. Standard Apache and nginx handle transfer encoding on the fly. As do other the big CDNs like Akamai and Fastly. And Heroku itself doesn't handle encodings at all since its neither apache or nginx. $ gzip public/assets/*.{css,js} task :compress { sh "gzip public/assets/*.{css,js}" }
Rake::Task["assets:precompile"].enhance [:compress] If you're publishing to the S3 bucket you'll still need to make sure a few other header attributes at set on the uploaded content. http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/ServingCompressedFiles.html |
I don't mind writing up a "Deploying Sprockets assets to Cloudfront" guide on the wiki. Having a simple way to augment the compile task programmatically is definitely better than a magic |
That task won't generally work well, because it deletes the original files. You want the original files to be able to serve assets without compression. I link my gist here for reference. |
To CloudFront, and to the not small number of NGINX users who enable |
@josh, while I agree with @fxn, I'm curious can't we just add Again I don't see what the big deal with supporting compression is in Sprockets. I'm happy for it to be optional, but to not have the option at all makes no sense to me. |
This ended up being my solution, at least it seems to be working locally, I'll test it out with Heroku deployment next.
The |
Just a brief update, this definitely seems to have issues on Heroku. Extending the task seems to cause it to load/parse test files and test_helper has some stuff which will not run on Heroku (missing Gems). Not sure why this would cause this behaviour.
|
@chrisnicola it's convenient that both variants have the same mtime, so I run that one after |
for the best compression you must install 7z on your server task :compress_assets_7z do
on roles(:app) do
assets_path = release_path.join('public', fetch(:assets_prefix))
execute "find -L #{assets_path} \\( -name *.js -o -name *.css -o -name *.ico \\) -exec bash -c '[ ! -f {}.gz ] && 7z a -tgzip -mx=9 {}.gz {}' \\; "
end
end
after 'deploy:normalize_assets', 'compress_assets_7z' 7z has optimized version of GZIP |
If sprockets does bring back one-time compression, consider using the zopfli gem, it provides higher compression (5% saving allegedly) than gzip and is suited for one-time compression as sprockets used to do (not on-the-fly compression) https://github.com/miyucy/zopfli From https://en.wikipedia.org/wiki/Zopfli#Properties_and_use_case
|
My solution going forward has been to extend the
I hope this is helpful for others. I may release it as a gem with some ability to configure what and how files are compressed if people think that would be useful. |
I'm also confused about why this was removed, and totally agree with this comment:
I couldn't make that much sense from the link, which was given as the background / justification for this. It feels like this 9-year-old apache bug is suddenly important to make backwards-breaking changes to sprockets. Not only that, but if I understand it right, it's not even important enough for Apache to fix... btw - the documentation still says that the asset pipeline gzips files automatically. Apologies if I misunderstood something. I did try to read all related comments and make sense of it, but other than workarounds - I still can't quite understand why this change was made in the first place. |
+1 |
@gingerlime FULL ACK! Please bring gzip-support back to sprockets (at least optional)! |
+1 |
This is going to come back with a way to opt-in. |
Hi Internet friends! There were some concerns about the issue being locked on the Twitterz, so I just wanted to jump in and say a few things: First and foremost, thanks for bringing up the feature and your concrete use case! We receive a large amount of issues/pull requests/comments etc on Rails, over time, this has necessitated some "unconventional" policies which their reasons might not be immediately obvious. For example, we don't accept "cosmetic" pull requests, because over time, it has been proven that they tend to generate lots of noise and requires a disproportionate amount of time/attention that could be better spent on other things, and we think that having that policy would be better of for everyone in the community overall, even though it sometimes means that we have to turn down new contributor's hard work. We also receive a large amount of +1 comments (in various forms), which could get very distracting for everyone and adds very little value (I wish there is a less intrusive way to express interest on Github). Since Github added the locking feature, we have been experimenting with using in our workflow to improve the signal-vs-noise ratio for everyone. It is a relatively new thing for us, and like I said it's still largely an experiment, so don't have a very clear rules of when to use it. In this particular case, I agree that we tripped the sensor a bit too early, and I apologize for that. It's also worth mentioning that the use of the locking feature usually has nothing to do with the merit of the original discussion/request. The "flavor" of locking we ended up with is usually more like "seems like we have seen enough arguments from both sides to make a decision (whether for or against the original thread) and get some work done, and the thread is turning into a +1 fest while people are waiting, so let's lock it until we had a chance to discuss more or have other news to report on this front. Again, this was not explained, and I agree that the "Locked!!!" label could communicate something very different, and I would like to apologize for that as well. Going forward, we are doing two things:
Thanks again for your time and contribution! P.S. as you probably saw from @fxn's comment above, it has already been discussed elsewhere (sorry I couldn't locate the reference) that this feature will be coming back (coincidentally, that took place prior to the locking happened). |
Yeah, I wrote gzip support originally in Sprockets. As expressed in the linked discussions and the commit reverting this feature, I personally think gzipping definitely has valid use cases and is a common optimization for assets, which is the kind of thing Sprockets does. Particularly useful for NGINX users that can trivially enable So now that maintenance has shifted to the Rails team, it's going to come back with a way to opt-in (this was discussed in Campfire). |
This is fantastic news this is coming back, thank you to all the developers who are taking on the maintenance for this. @fxn is using the Zopfli higher compression gzip algo potentially part of this work? |
@eliotsykes was not aware of that algorithm, seems like it should be something to take into account definitely. |
Thanks @chancancode that's great news. As mentioned above a workaround was easily managed eventually. At this point, I am probably preaching to the choir here, but I think it goes without saying now that the original change came as a surprise of the kind that easily managed to slip into production unnoticed (that part is our fault, but in small startups these things are easy to miss when you are expecting something like this to "just work"). Obviously these things just happen with the best intentions, and blame isn't really important here. Going forward I do hope the impact of changes like these can be recognized before they are merged in. This appears to have been a breaking API change with little notification or documentation. What is more, is that even if the Apache use case makes sense to support it could have been done with a configuration flag, as was suggested. To give one example that shows the impact scope of this change, this literally breaks the standard Heroku+Rails+Cloudfront use case, which I understand to be pretty common and is basically a recommended setup for Heroku. I apologize if any of this comes off as me being entitled. I deeply appreciate all the hard work here and recognize genuine desire to improve things. My feedback is genuinely meant to try to help. |
I added gzip support for ActionDispatch::Static so it works by default out of the box on Heroku: rails/rails@cfaaacd and rails/rails@8e31fa3 If CDNs will gzip content on the fly do we have any data or benchmarks on the difference between them doing that or them serving pre-gzipped content? It looks like cloudfront doesn't gzip contents:
http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/ServingCompressedFiles.html |
CloudFront is one use case. The other one is being able to use max compression using a slow algorithm, and at the same time having your webserver do nothing. Hard to beat! |
+1 |
Locking the issue again. Please see #26 (comment) for the reason. |
Linking this to sstephenson#589 which is where gzip was removed in 3.0 |
Doing research on why/why-not we might not want to bring back gzipped assets. This was an argument against:
Sprockets server also does etag checks in sprockets/lib/sprockets/server.rb Lines 117 to 119 in 98d0ccc
The thing serving the asset should be the thing setting the etag. The bug then would be in how apache/nginx chooses the etag to use. For example we aren't setting it or using it in ActionDispatch::Static so it shouldn't be an issue. The sprockets server did implement etag support as linked above. A fix would be for it to use a different etag than the fingerprint. For example if |
I've got an implementation in #193 please take a look. @eliotsykes i'm not against using a different compression algorithm (zopfli). I'm a little wary of using that library though. It has 10k downloads on Rubygems and only 2 people have ever touched it. If it gets abandoned I don't want to be stuck maintaining a compression algorithm. A different algorithm It is worth looking into more. Could you write a small script to benchmark speed between zopfli and Since this issue is locked, you can comment on my PR #193 thanks for the suggestion. |
This is done already. Closing |
Hi, how can i enable the generate GZIP files on Sprockets 3.0?
The text was updated successfully, but these errors were encountered: