Skip to content

Commit

Permalink
Merge pull request #570 from tessel/jon-expose-api
Browse files Browse the repository at this point in the history
Exposes the CLI as an API
  • Loading branch information
rwaldron committed Feb 17, 2016
2 parents 3e100a1 + 1c6b38e commit 9f5ac19
Show file tree
Hide file tree
Showing 6 changed files with 151 additions and 5 deletions.
18 changes: 18 additions & 0 deletions index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
// The controller is used for standard Tessel commands
// like Tessel.get, Tessel.list, Tessel.deploy, etc.
module.exports = require('./lib/controller');
// Commands give deeper access to all the standard shell commands
// that we run to execute larger sequences
module.exports.commands = require('./lib/tessel/commands');
// Exporting Tessel allows consumers to compose their own
// functions onto the prototype
module.exports.Tessel = require('./lib/tessel/tessel');
// The seeker allows consumers to have a long running discovery
// process and take action as Tessels are connected/disconnected
module.exports.discovery = require('./lib/discover').TesselSeeker;
// The USBConnection libray lets consumers turn arbitrary USB devices
// into USBConnection objects to be used in Tessel creation.
module.exports.USBConnection = require('./lib/usb_connection').USBConnection;
// The LANConnection libray lets consumers turn arbitrary LAN devices
// into LANConnection objects to be used in Tessel creation.
module.exports.LANConnection = require('./lib/lan_connection').LANConnection;
7 changes: 3 additions & 4 deletions lib/controller.js
Original file line number Diff line number Diff line change
Expand Up @@ -115,14 +115,14 @@ Tessel.list = function(opts) {
} else if (foundTessels.length === 1) {
// Close all opened connections and resolve
controller.closeTesselConnections(foundTessels)
.then(resolve);
.then(() => resolve(foundTessels));
}
// If we have only one Tessel or two Tessels with the same name (just USB and LAN)
else if (foundTessels.length === 1 ||
(foundTessels.length === 2 && foundTessels[0].name === foundTessels[1].name)) {
// Close all opened connections and resolve
controller.closeTesselConnections(foundTessels)
.then(resolve);
.then(() => resolve(foundTessels));
}
// Otherwise
else {
Expand All @@ -143,8 +143,7 @@ Tessel.list = function(opts) {
// Helpful instructions on how to switch
logs.info('Set default Tessel with environment variable (e.g. "export TESSEL=bulbasaur") or use the --name flag.');
// Close all opened connections and resolve
controller.closeTesselConnections(foundTessels)
.then(resolve);
controller.closeTesselConnections(foundTessels).then(() => resolve(foundTessels));
});
}
});
Expand Down
2 changes: 2 additions & 0 deletions lib/lan_connection.js
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,8 @@ LAN.Scanner.prototype.stop = function() {

module.exports.startScan = startScan;
module.exports.stopScan = stopScan;
// Exported for CLI API Consumers
module.exports.LANConnection = LAN.Connection;

if (global.IS_TEST_ENV) {
module.exports.LAN = LAN;
Expand Down
2 changes: 2 additions & 0 deletions lib/usb_connection.js
Original file line number Diff line number Diff line change
Expand Up @@ -409,6 +409,8 @@ module.exports.startScan = startScan;
module.exports.stopScan = stopScan;
module.exports.TESSEL_VID = TESSEL_VID;
module.exports.TESSEL_PID = TESSEL_PID;
// Exported for CLI API Consumers
module.exports.USBConnection = USB.Connection;

if (global.IS_TEST_ENV) {
module.exports.USB = USB;
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"name": "t2-cli",
"version": "0.0.10",
"description": "The starting point of Tessel 2's command line interface",
"main": "./bin/tessel-2.js",
"main": "./index.js",
"scripts": {
"test": "grunt test",
"postinstall": "t2 install-drivers || true"
Expand Down
125 changes: 125 additions & 0 deletions test/unit/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
var api = require('../../index');

exports['API Surface'] = {
setUp: function(done) {
done();
},
tearDown: function(done) {
done();
},
ensureExistence: function(test) {
test.ok(api === controller);
test.ok(api === controller);
test.ok(api.commands === commands);
test.ok(api.Tessel === Tessel);
test.ok(api.USBConnection === USB.Connection);
test.ok(api.LANConnection === LAN.Connection);
test.done();
}
};

exports['CLI.list'] = {
setUp: function(done) {
this.sandbox = sinon.sandbox.create();
this.logsWarn = this.sandbox.stub(logs, 'warn', function() {});
this.logsInfo = this.sandbox.stub(logs, 'info', function() {});
this.logsBasic = this.sandbox.stub(logs, 'basic', function() {});
this.closeConnections = this.sandbox.stub(controller, 'closeTesselConnections').returns(Promise.resolve());
var test = this;
this.seeker = this.sandbox.stub(discover, 'TesselSeeker', function Seeker() {
this.start = (options) => {
test.activeSeeker = this;
setTimeout(() => this.stop(), options.timeout);
return this;
};
this.stop = function() {
this.emit('end');
return this;
};
});

util.inherits(this.seeker, Emitter);
done();
},
tearDown: function(done) {
this.sandbox.restore();
done();
},
rejectWithNoTessels: function(test) {
test.expect(1);
api.list({
timeout: 0.0001,
usb: true
})
.then(() => {
test.fail('Should not have returned any Tessels');
test.done();
})
.catch((err) => {
test.ok(err);
test.done();
});
},
resolveWithOneTessel: function(test) {
// Create a new Tessel
var tessel = new Tessel({
connectionType: 'USB'
});
tessel.name = 'TestTessel';

api.list({
timeout: 0.1,
usb: true
})
.then((tessels) => {
test.ok(tessels.length === 1);
test.ok(tessels[0].name === tessel.name);
test.done();
})
.catch(() => {
test.fail('Should not have rejected with one Tessel available');
test.done();
});

// Emit the Tessel
setImmediate(() => {
this.activeSeeker.emit('tessel', tessel);
});
},

resolveWithMultipleTessels: function(test) {
// Create a new Tessel
var tessel1 = new Tessel({
connectionType: 'USB'
});

tessel1.name = 'TestTessel1';

// Create a new Tessel
var tessel2 = new Tessel({
connectionType: 'LAN'
});

tessel2.name = 'TestTessel2';

api.list({
timeout: 0.1
})
.then((tessels) => {
test.ok(tessels.length === 2);
test.ok(tessels[0].name === tessel1.name);
test.ok(tessels[1].name === tessel2.name);
test.done();
})
.catch(() => {
test.fail('Should not have rejected with one Tessel available');
test.done();
});

// Emit the Tessel
setImmediate(() => {
this.activeSeeker.emit('tessel', tessel1);
this.activeSeeker.emit('tessel', tessel2);
});
}
};

0 comments on commit 9f5ac19

Please sign in to comment.