Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Add `bin/oven`, update readme, change function name.

  • Loading branch information...
commit 0b43aee9299ed06a890e3667114e64926f84764a 1 parent f2f99e3
@brianloveswords brianloveswords authored
View
55 README.md
@@ -1,8 +1,55 @@
# openbadges-bakery [![Build Status](https://secure.travis-ci.org/mozilla/openbadges-bakery.png)](http://travis-ci.org/mozilla/openbadges-bakery)
-Provides two methods:
+# Install
+```bash
+$ npm install openbadges-bakery
+```
+# CLI Usage
+
+## Baking
+
+```bash
+$ oven [--in path/to/image.png] [--out path/to/baked-image.png] <data>
+```
+If `--out` is not set, the baked image will print to stdout.
+
+The input file can also be piped into stdin.
-```js
-bakery.bake(buffer | stream, callback);
-bakery.debake(buffer | stream, callback);
+```bash
+$ cat path/to/image.png | oven <data> > path/to/baked-image.png
```
+## Extracting
+
+```bash
+$ oven [--in path/to/image.png] --extract
+```
+
+Same as above, you can also pipe a file to stdin. The data will be printed to stdout.
+
+# Libary Usage
+
+## bakery.bake(options callback);
+
+Bakes some data into an image.
+
+Options are
+- `image`: either a buffer or a stream representing the PNG to bake
+- `data`: the data to put into the badge. At this point, it should likely be a URL pointing to a badge assertion
+
+`callback` has the signature `function(err, imageData)`
+
+## bakery.debake(image, callback);
+
+Gets the URL from a baked badge and attempts to retreive the assertion
+at the other end.
+
+`image` should be a stream or a buffer
+
+`callback` has the signature `function (err, object)` where `object` is expected to be a OpenBadges assertion.
+
+## bakery.extract(image, callback)
+
+Gets the data from the baked badge.
+
+`callback` has the signature `function (err, data)`
+
View
57 bin/oven
@@ -0,0 +1,57 @@
+#!/usr/bin/env node
+
+const fs = require('fs');
+const argv = require('optimist').argv;
+const stdout = process.stdout;
+const stdin = process.stdin;
+const stderr = process.stderr;
+const bakery = require('../');
+const path = require('path');
+const url = argv._[0];
+const infile = argv.in||argv.infile;
+const outfile = argv.out||argv.outfile;
+const extract = argv.extract;
+
+function log(msg) {
+ stderr.write(msg + '\n');
+}
+
+if (!url && !extract) {
+ log('You must pass a url to bake into the image');
+ process.exit(1);
+}
+
+var stream;
+if (infile) {
+ stream = fs.createReadStream(path.resolve(infile));
+} else {
+ stdin.resume();
+ stream = stdin;
+}
+
+if (extract) {
+ bakery.extract(stream, function done(err, data) {
+ if (err) {
+ log('there was an error:', err.message);
+ process.exit(1);
+ }
+ stdout.write(data + '\n');
+ process.exit(1);
+ })
+}
+
+bakery.bake({
+ image: stream,
+ url: url
+}, function done(err, baked) {
+ if (err) {
+ log('there was an error:', err.message);
+ process.exit(1);
+ }
+ if (outfile) {
+ fs.writeFileSync(path.resolve(outfile), baked)
+ } else {
+ stdout.write(baked);
+ }
+ process.exit(0);
+});
View
38 lib/bakery.js → index.js
@@ -6,12 +6,12 @@
* Licensed under the MPL 2.0 license.
*/
-var util = require('util');
-var streampng = require('streampng');
-var request = require('request');
-var urlutil = require('url');
+const util = require('util');
+const streampng = require('streampng');
+const request = require('request');
+const urlutil = require('url');
-var KEYWORD = 'openbadges';
+const KEYWORD = 'openbadges';
function createChunk(url) {
return streampng.Chunk.tEXt({
@@ -21,11 +21,13 @@ function createChunk(url) {
}
exports.bake = function bake(options, callback) {
- var buffer = options.image;
- var png = streampng(buffer);
- // #TODO: make sure the url is set
- var chunk = createChunk(options.url);
+ const buffer = options.image;
+ const data = options.url || options.data;
+ const png = streampng(buffer);
+ const chunk = createChunk(data);
var existingChunk;
+ if (!data)
+ return callback(new Error('must pass a `data` or `url` option'));
png.inject(chunk, function (txtChunk) {
if (txtChunk.keyword === KEYWORD) {
existingChunk = txtChunk;
@@ -33,8 +35,8 @@ exports.bake = function bake(options, callback) {
}
});
if (existingChunk) {
- var msg = util.format('This image already has a chunk with the `%s` keyword (contains: %j)', KEYWORD, chunk.text);
- var error = new Error(msg);
+ const msg = util.format('This image already has a chunk with the `%s` keyword (contains: %j)', KEYWORD, chunk.text);
+ const error = new Error(msg);
error.code = 'IMAGE_ALREADY_BAKED';
error.contents = existingChunk.text;
return callback(error);
@@ -42,8 +44,8 @@ exports.bake = function bake(options, callback) {
return png.out(callback);
};
-exports.getBakedData = function getBakedData(img, callback) {
- var png = streampng(img);
+exports.extract = function extract(img, callback) {
+ const png = streampng(img);
var found = false;
function textListener(chunk) {
@@ -56,7 +58,7 @@ exports.getBakedData = function getBakedData(img, callback) {
function endListener() {
if (!found) {
- var error = new Error('Image does not have any baked in data.');
+ const error = new Error('Image does not have any baked in data.');
error.code = 'IMAGE_UNBAKED';
return callback(error);
}
@@ -68,7 +70,7 @@ exports.getBakedData = function getBakedData(img, callback) {
exports.debake = function debake(image, callback) {
- exports.getBakedData(image, function (error, url) {
+ exports.extract(image, function (error, url) {
if (error)
return callback(error);
@@ -78,8 +80,8 @@ exports.debake = function debake(image, callback) {
return callback(error);
}
- var status = response.statusCode;
- var type = response.headers['content-type'];
+ const status = response.statusCode;
+ const type = response.headers['content-type'];
if (status == 200 && type == 'application/json')
return exports.parseResponse(body, url, callback);
@@ -104,7 +106,7 @@ exports.parseResponse = function parseResponse(body, url, callback) {
return callback(null, obj);
};
-var errors = {
+const errors = {
request: function (original, url) {
var msg = util.format('There was an error initiating the request: %s', original.message);
var error = new Error(msg);
View
6 package.json
@@ -2,13 +2,15 @@
"name": "openbadges-bakery",
"version": "0.1.1",
"description": "Tools for baking and debaking openbadge images",
- "main": "lib/bakery.js",
+ "main": "index.js",
"directories": {
"test": "test"
},
+ "bin": "bin/oven",
"dependencies": {
"request": "~2.11.4",
- "streampng": "~0.1.1"
+ "streampng": "~0.1.1",
+ "optimist": "~0.3.5"
},
"devDependencies": {
"oneshot": "~0.1.0",
View
6 test/bakery.test.js
@@ -5,7 +5,7 @@ var pathutil = require('path');
var urlutil = require('url');
var oneshot = require('oneshot');
-var bakery = require('../lib/bakery');
+var bakery = require('..');
var IMG_PATH = pathutil.join(__dirname, 'testimage.png');
var ASSERTION_URL = "http://example.org";
@@ -70,7 +70,7 @@ test('bakery.bake: takes a buffer', function (t) {
bakery.bake(options, function (err, baked) {
t.notOk(err, 'should not have an error');
t.ok(baked, 'should get back some data');
- bakery.getBakedData(baked, function (err, url) {
+ bakery.extract(baked, function (err, url) {
t.notOk(err, 'there should be a matching tEXt chunk');
t.same(url, ASSERTION_URL, 'should be able to find the url');
t.end();
@@ -87,7 +87,7 @@ test('bakery.bake: takes a stream', function (t) {
bakery.bake(options, function (err, baked) {
t.notOk(err, 'should not have an error');
t.ok(baked, 'should get back some data');
- bakery.getBakedData(baked, function (err, url) {
+ bakery.extract(baked, function (err, url) {
t.notOk(err, 'there should be a matching tEXt chunk');
t.same(url, ASSERTION_URL, 'should be able to find the url');
t.end();
View
BIN  test/unbaked.png
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.

0 comments on commit 0b43aee

Please sign in to comment.
Something went wrong with that request. Please try again.