From 4b72a181ddb4d733fab23d6dbe18b38b2c41de67 Mon Sep 17 00:00:00 2001 From: Brian Sipple Date: Mon, 5 Sep 2016 20:35:17 -0700 Subject: [PATCH] support for per-file configuration --- README.md | 36 ++++++++++++++++++------------------ index.js | 36 +++++++++++++++++++----------------- test/index.test.js | 26 ++++++++++++++++++++++++-- 3 files changed, 61 insertions(+), 37 deletions(-) diff --git a/README.md b/README.md index b6b2717..9ffb41a 100644 --- a/README.md +++ b/README.md @@ -43,24 +43,6 @@ Within your markup, you should now be able to "use" each symbol inside of other - `options` {Object}: [Options for `broccoli-svgstore`](#options) -- `fileSettings` {Object}: a hash of per-file settings. -That is, each root key should correspond to a file name of an SVG that -will be found in this node. It's value should then be an Object with any of the following settings: - + `id` {string}: A custom id to be used for this SVG's final ``. - + `svgstoreOpts` {Object}: same as [`options.svgstoreOpts`](#options), but scoped to the file - - Example usage: - - ```javascript - var outputNode = svgstore(inputNodes, { - outputFile: "/assets/icons.svg", - fileSettings: { - twitter: { id: 'tweet' }, - menu: { id: 'hamburger', svgstoreOpts: { customSymbolAttrs: ['preserveAspectRatio'] } } - } - }); - ``` - ### Options - `outputFile` {string}: The name of the file -- including any directory path -- [to which output will be written](https://github.com/broccolijs/broccoli-plugin#pluginprototypebuild) @@ -81,3 +63,21 @@ will be found in this node. It's value should then be an Object with any of the Required: `false` Default: `{}` +- `fileSettings` {Object}: a hash of per-file settings. +That is, each root key should correspond to a file name of an SVG that +will be found in this node. It's value should then be an Object with any of the following settings: + + `id` {string}: A custom id to be used for this SVG's final ``. + + `svgstoreOpts` {Object}: same as `options.svgstoreOpts`, but scoped to the file + + Example usage: + + ```javascript + var outputNode = svgstore(inputNodes, { + outputFile: "/assets/icons.svg", + fileSettings: { + twitter: { id: 'tweet' }, + menu: { id: 'hamburger', svgstoreOpts: { customSymbolAttrs: ['preserveAspectRatio'] } } + } + }); + ``` + diff --git a/index.js b/index.js index 74ee2c8..cebf3dc 100644 --- a/index.js +++ b/index.js @@ -45,33 +45,35 @@ SvgProcessor.prototype = Object.create(CachingWriter.prototype); SvgProcessor.prototype.constructor = SvgProcessor; SvgProcessor.prototype.description = 'svgstore'; -SvgProcessor.prototype.build = function () { +/** + * Overrides broccoli-plugin's `build' function. + * @see: https://github.com/broccolijs/broccoli-plugin#pluginprototypebuild + */ +SvgProcessor.prototype.build = function() { var svgOutput = svgstore(this._options.svgstoreOpts); + var fileSettings = this._options.fileSettings || {}; try { - var srcDir; - var inputFiles; - var inputFileName; - var inputFilePath; - var stat; - var fileContents; - var svgId; - + // iterate through `inputPaths` of our `inputNodes` (`inputPaths` is an array of + // paths on disk corresponding to each node in `inputNodes`) for (var i = 0, l = this.inputPaths.length; i < l; i++) { - srcDir = this.inputPaths[i]; - inputFiles = helpers.multiGlob(["**/*.svg"], { cwd: srcDir }); + var srcDir = this.inputPaths[i]; + var inputFiles = helpers.multiGlob(["**/*.svg"], { cwd: srcDir }); for (var j = 0, ll = inputFiles.length; j < ll; j++) { - inputFileName = inputFiles[j]; - inputFilePath = path.join(srcDir, inputFileName); - stat = fs.statSync(inputFilePath); + var inputFileName = inputFiles[j]; + var inputFilePath = path.join(srcDir, inputFileName); + var stat = fs.statSync(inputFilePath); if (stat && stat.isFile()) { - fileContents = fs.readFileSync(inputFilePath, { encoding: 'utf8' }); - svgId = inputFileName.replace(/\.[^\.]+$/, ''); + var fileNameWithoutExtension = inputFileName.replace(/\.[^\.]+$/, ''); + var fileContents = fs.readFileSync(inputFilePath, { encoding: 'utf8' }); + var inputFileSettings = fileSettings[fileNameWithoutExtension] || {}; + var svgId = inputFileSettings.id || fileNameWithoutExtension; + var fileSVGStoreOpts = inputFileSettings.svgstoreOpts || {}; - svgOutput.add(svgId, fileContents); + svgOutput.add(svgId, fileContents, fileSVGStoreOpts); } } } diff --git a/test/index.test.js b/test/index.test.js index d05d9e0..b464f27 100644 --- a/test/index.test.js +++ b/test/index.test.js @@ -1,3 +1,5 @@ +'use strict'; + var path = require('path'); var fs = require('fs'); var expect = require('chai').expect; @@ -28,7 +30,8 @@ function makeBuilderFromInputNodes(inputNodes, options) { var svgProcessor = new SvgProcessor(inputNodes, { outputFile: options.outputFile || OUTPUT_FILE, annotation: options.annotation || 'SVGStore Processor -- Tests', - svgstoreOpts: options.svgstoreOpts || {} + svgstoreOpts: options.svgstoreOpts || {}, + fileSettings: options.fileSettings || {} }); return new broccoli.Builder(svgProcessor); @@ -40,7 +43,6 @@ function loadSVG(filePath) { } function testForSymbols($loadedSVG, expectedSymbolIds) { - // test proper structure var $svg = $loadedSVG('svg'); @@ -156,6 +158,26 @@ describe('SVGProcessor', function () { expect($('symbol').attr('x-custom-attr')).to.equal(CUSTOM_ATTR_VALUES['x-custom-attr']); }); }); + + it('enables per-file configuration via a `fileSettings` hash', function() { + var inputNodes = [SOURCE_DIR_GROUP_1]; + var customIDs = ['customID-1', 'customID-2', 'customID-3']; + var fileSettings = { + [ID_MANIFEST[SOURCE_DIR_GROUP_1][0]]: { id: customIDs[0] }, + [ID_MANIFEST[SOURCE_DIR_GROUP_1][1]]: { id: customIDs[1] }, + [ID_MANIFEST[SOURCE_DIR_GROUP_1][2]]: { id: customIDs[2] } + }; + + builder = makeBuilderFromInputNodes(inputNodes, { fileSettings }); + + return builder.build().then(function (results) { + var outputDestination = path.join(results.directory, path.normalize(OUTPUT_FILE)); + var symbolIds = customIDs.concat(ID_MANIFEST[SOURCE_DIR_GROUP_1][3]); + + var $ = loadSVG(outputDestination); + testForSymbols($, symbolIds); + }); + }); }); });