diff --git a/.gitignore b/.gitignore index 90b21a4b..4dbe41f8 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,5 @@ +vendor + ### Node ### # Logs logs *.log npm-debug.log* yarn-debug.log* yarn-error.log* diff --git a/README.md b/README.md index 1376d702..4e9dc8b4 100644 --- a/README.md +++ b/README.md @@ -17,9 +17,11 @@ SVG-based [LQIP](https://www.guypo.com/introducing-lqip-low-quality-image-placeh | Size: | 442B (gz: 372B) | 937B (gz: 487B) | 3273B (gz: 1394B)- 50 triangles | ## Requirements -* Node.js >= v.6 (https://nodejs.org/en/) +* Node.js >= v6 (https://nodejs.org/en/) + +### Non-64bit operating systems need: * Golang (https://golang.org/doc/install) -* Primitive (https://github.com/fogleman/primitive) +* Primitive (https://github.com/fogleman/primitive) (`go get -u github.com/fogleman/primitive`) After installing Primitive, you may also need to add the path to the ```Primitive``` binary file. diff --git a/package.json b/package.json index 7d158a13..7e4be567 100644 --- a/package.json +++ b/package.json @@ -7,8 +7,14 @@ "sqip": "./src/cli.js" }, "scripts": { - "test": "echo \"Error: no test specified\" && exit 1" + "test": "echo \"Error: no test specified\" && exit 1", + "prepare": "npm run build-vendor", + "build-vendor": "node scripts/bundle-vendor.js" }, + "files": [ + "src", + "vendor" + ], "keywords": [ "lqip", "svg", diff --git a/scripts/bundle-vendor.js b/scripts/bundle-vendor.js new file mode 100644 index 00000000..5b7ca332 --- /dev/null +++ b/scripts/bundle-vendor.js @@ -0,0 +1,27 @@ +const { execSync } = require("child_process"); + +const builds = [ + { + os: "darwin", + arch: "amd64", + filename: "primitive-darwin-x64" + }, + { + os: "linux", + arch: "amd64", + filename: "primitive-linux-x64" + }, + { + os: "windows", + arch: "amd64", + filename: "primitive-win32-x64" + } +]; +builds.forEach(build => { + const { os, arch, filename } = build; + console.log(`Building primitive executable for ${os} (${arch})`); + execSync( + `env GOOS=${os} GOARCH=${arch} go build -o vendor/${filename} github.com/fogleman/primitive` + ); + console.log("done"); +}); diff --git a/src/index.js b/src/index.js index f83f6591..6ef14c8f 100644 --- a/src/index.js +++ b/src/index.js @@ -30,6 +30,9 @@ const svgo = require('svgo'); // Define a a temp file, ideally on a RAMdisk that Primitive can write to const primitive_output_file = os.tmpdir() + '/primitive_tempfile.svg'; +const VENDOR_DIR = path.resolve(__dirname, '..', 'vendor') +let primitiveExecutable = 'primitive' + // Use 'argv' to set up all available commandline parameters that shall be available when running sqip const argvOptions = [{ name: 'numberOfPrimitives', @@ -71,6 +74,13 @@ const getArguments = () => argv.option(argvOptions).run(); // Sanity check: use the exit state of 'type' to check for Primitive availability const checkForPrimitive = (shouldThrow = false) => { + const primitivePath = path.join(VENDOR_DIR, `primitive-${os.platform()}-${os.arch()}`) + + if (fs.existsSync(primitivePath)) { + primitiveExecutable = primitivePath + return + } + const errorMessage = "Please ensure that Primitive (https://github.com/fogleman/primitive, written in Golang) is installed and globally available"; try { if (process.platform === 'win32') { @@ -121,7 +131,7 @@ const findLargerImageDimension = ({ width, height }) => width > height ? width : // Run Primitive with reasonable defaults (rectangles as shapes, 9 shaper per default) to generate the placeholder SVG const runPrimitive = (filename, { numberOfPrimitives = 8, mode = 0 }, primitive_output, dimensions) => { - child_process.execSync(`primitive -i ${filename} -o ${primitive_output} -n ${numberOfPrimitives} -m ${mode} -s ${findLargerImageDimension(dimensions)}`); + child_process.execSync(`${primitiveExecutable} -i ${filename} -o ${primitive_output} -n ${numberOfPrimitives} -m ${mode} -s ${findLargerImageDimension(dimensions)}`); } // Read the Primitive-generated SVG so that we can continue working on it