It appears that most plugins architected on top of node-sass
use the options object directly. Because eyeglass wants to wrap the options once per render call, this leaves eyeglass incompatible with many node-sass plugins. Instead of changing all of the plugins, this is a proposal to instead wrap node-sass using cowboy/javascript-hooker or a similar library.
Passing options
through
I discovered this issue while exploring what changes we would need to make in dlmanning/gulp-sass in order to support eyeglass. Instead of just an object literal, a function would need to be passed to gulp-sass which returns an options object. This way, during the map stream transform, a new option object would be generated each time, ensuring that eyeglass decoration works as expected.
Researching additional node-sass plugins for build systems such as sindresorhus/grunt-sass and joliss/broccoli-sass, these too would need to be updated if anything other an an Object literal was going to be passed in to the plugin.
It's my opinion that it is unreasonable to ask every node-sass plugin for a build system to support config decoration.
Alternatives
- making a X-eyeglass which in turn piped through X-sass: This thin layer of option passing would need to step in during the stream read / per file. We would need to create these per build system. Unfortunately, some build systems such as gulp use object streams which means stitching streams in the plugin which adds to the total amount of maintained code.
- utilize gulp-tap as a recipe: Specifically a solution for gulp geejs/gulp-tap would allow people to use
node-sass
directly in their projects. However, all of the sourcemap support falls apart, a major feature in gulp-sass.
- update node-sass to support a function for generating options: The cascade effect of this would be plugin authors updating in order to support this feature universally. However, adding this support be a somewhat significant feature add. I'd like to only ask for this as a last resort.
Proposal
Ideally, I'd like eyeglass to work with these sass plugins naturally without any modification to their code, or having to create & maintain separate X-eyeglass
plugins for build systems. Because the options
object is passed through directly to node-sass, we should consider addressing instead modifying the .render()
and .renderSync()
methods in node-sass.
cowboy/javascript-hooker or a similar library will allow us to cleanly proxy the render / renderSync
methods, invoking eyeglass once per call. Monkey Patch libraries also come with an API for unhooking, should a developer need to run node-sass without the eyeglass functionality.
This changes our invocation signature from
nodeSass.render(eyeglass({
/* options */
}));
to
require("eyeglass")(nodeSass); // require("eyeglass").bind(nodeSass);
nodeSass.render({
/* options */
});
require("eyeglass").unbind(nodeSass);
I'd really love to collect more thoughts on this, the idea of monkey patching in node.js (completely supported but often only used in testing), and the implications of doing an interface like this.