Switching from Ruby Sass to LibSass

If you’ve been following the recent major announcements from the Sass community, you may have seen the huge LibSass 3.0 announcement at SassConf 2014.

For some time now, the Sass Ruby gem has been getting more advanced features, while LibSass has been updated less quickly. This means that many people using LibSass to compile their Sass (usually through node-sass in a Grunt/Gulp workflow) have been unable to use cutting edge Sass tools like the ones you keep reading about here on SitePoint.

The big announcement is that Ruby Sass will now wait for feature parity with LibSass, then they’ll be maintained at the same speed as much as possible. LibSass 3.0 is out now and you can integrate it into your task runners with the most recent node-sass version.

What makes LibSass so important, however? The biggest advantage over Ruby Sass is that it’s faster – much faster. If faster complile times sound good to you, here’s a good introduction to installing LibSass.

In this article, I’m going to be really practical: I’m going to share all the “gotchas” I discovered when I tried compiling my mixin library with LibSass. While LibSass 3.0 is close to Ruby Sass 3.4.6, there are several things that don’t work identically. You may not face all of these in your Sass, but if you do run into these little bugs, I hope this list helps you troubleshoot them.

Don’t test with @if not ...

In Ruby Sass, @if not not index($list, $value) {} was a clever way to ensure that a value was in a list. I’ve been using this condition in my Ruby Sass projects since Hugo suggested it to force the condition to evaluate a true boolean value.

However, in LibSass not does not work, so this method appears to always evaluate to true. In LibSass, you can workaround this problem by using one of the following:

@error doesn’t work.

In Ruby Sass, @error prints an error to the console and stops the compiler. It also allows you to interpolate variables into a helpful error message.

However, in LibSass, the @error line will simply be printed to the compiled output as though it were a CSS declaration line. Because it’s simply being printed to output, it won’t interpolate variables if they’re inside of quotes. I suppose you could still use the broken @error directive and search your output for ‘@error’. If so, you could workaround the variable interpolation issue with string concatenation:

selector-*() functions with & aren’t supported.

If you’re one of the rare people who has found a good use case for the new selector- functions in Sass 3.4, those won’t follow you into LibSass. I don’t have a work-around to suggest for that, other than “review your nesting strategy” (which would probably remove a need for selector interpolation entirely).

The @at-root directive doesn’t work.

Ruby Sass allows you to use @at-root to move a nested selector out of its nesting context. LibSass, however, treats @at-root like a selector string and prints it to the stylesheet:

Maps, as you’ve gathered by now, are largely on par between Libsass 3 and Ruby Sass. Enjoy using them!

Extend

Another major addition to LibSass 3 is @extend support. I’m not aware of any differences between Ruby Sass and LibSass on this now, but it’s a substantial enough upgrade that it deserves to be mentioned here.

Conclusion

The speed improvements you’ll get from switching to LibSass are huge. However, there are still a few areas where LibSass features are not on par with features Ruby Sass 3.4+. If your mixin library depends on those specific features, hold off on updating for now.

If you’ve moved to LibSass and found other issues or some other syntax tweaks or workarounds, please share those in the comments!

James is a Senior Front-End Developer with almost 10 years total experience in freelance, contract, and agency work. He has spoken at conferences, including local WordPress meet-ups and the online WP Summit. James's favorite parts of web development include creating meaningful animations, presenting unique responsive design solutions, and pushing Sass’s limits to write powerful modular CSS. You can find out more about James at jamessteinbach.com.

Free Guide:

7 Habits of Successful CTOs

"What makes a great CTO?" Engineering skills? Business savvy? An innate tendency to channel a mythical creature (ahem, unicorn)? All of the above? Discover the top traits of the most successful CTOs in this free guide.

Does anyone know if the new Libsass release supports susy now? I’d love to stick with libsass and also use susy!

Alexadark

Hi, the new susy version is compatible with libsass: http://susydocs.oddbird.net/en/latest/changelog/
discover that yesterday.
if you use codekit like me, you will need to install susy manually, as the codekit version is not up to date.
Also remove breakpoint that is not compatible with libsass, and susy-breakpoint is now build in susy.
just pass from 7s to 1s, so happy!!!
enjoy :-)
I also use bourbon, and the last version is not compatible with libsass, so i install an older version, and everything works fine :-)

Sp

Anyone found a work around for – @at-root property, if you have please let me know.

Gregor Albrecht

Thanks! Just switched back to ruby sass to try out susy and it’s just not the same… Gonna try your approach next!

Alexadark

btw, i try again with codekit and their version of susy and it works, but you have to delete breakpoint as it doesn’t support libsass, and not needed anymore in the last version of susy

If you extend a non existing placeholder class in libsass not even a warning will be output. This can be annoying after refactoring or putting in a small typo.
E.g. %foo { … } .class { @extend %fooo; } will build with success while Ruby Sass will abort.

http://505labs.com Ben Mirkhah

Nice article, for the record Susy2 now works just fine with libsass: 3.2.4-26