var fs = require('fs'); var assert = require('assert'); var sinon = require('sinon'); var gpio = require('../lib/gpio'); function read(file, fn) { fs.readFile(file, "utf-8", function(err, data) { if(!err && typeof fn === "function") fn(data); }); } // remove whitespace function rmws(str) { return str.replace(/\s+/g, ''); } describe('GPIO', function() { var gpio4; before(function(done) { gpio4 = gpio.export(4, { direction: 'out', ready: done }); }); after(function() { gpio4.unexport(); }); describe('Header Direction Out', function() { describe('initializing', function() { it('should open specified header', function(done) { read('/sys/class/gpio/gpio4/direction', function(val) { assert.equal(rmws(val), 'out'); done(); }); }); }); describe('#set', function() { it('should set header value to high', function(done) { gpio4.set(function() { read('/sys/class/gpio/gpio4/value', function(val) { assert.equal(rmws(val), '1'); done(); }); }); }); }); describe('#reset', function() { it('should set header value to low', function(done) { gpio4.reset(function() { read('/sys/class/gpio/gpio4/value', function(val) { assert.equal(rmws(val), '0'); done(); }); }); }); }); describe('#on :change', function() { it('should fire callback when value changes', function(done) { var callback = sinon.spy(); gpio4.on('change', callback); // set, then reset gpio4.set(function() { gpio4.reset(); }); // set and reset is async, wait some time before running assertions setTimeout(function() { assert.ok(callback.calledTwice); done(); gpio4.removeListener('change', callback); }, 10); }); }); }); // For these tests, make sure header 4 is connected to header 25 // header 25 is exported with direction "out" and header 4 is used // to simulate a hardware interrupt describe('Header Direction In', function() { var gpio25; before(function(done) { gpio25 = gpio.export(25, { direction: 'in', ready: done }); }); after(function() { gpio25.unexport(); }); describe('#on :change', function() { it('should respond to hardware set', function(done) { var callback = sinon.spy(); gpio25.on('change', callback); // wait a little before setting setTimeout(function() { gpio4.set(); }, 500); // filewatcher has default interval of 100ms setTimeout(function() { assert.equal(gpio25.value, 1); assert.ok(callback.calledOnce); gpio25.removeListener('change', callback); done(); }, 600); }); it('should respond to hardware reset', function(done) { var callback = sinon.spy(); gpio25.on('change', callback); // wait a little before setting setTimeout(function() { gpio4.reset(); }, 500); // filewatcher has default interval of 100ms setTimeout(function() { assert.equal(gpio25.value, 0); assert.ok(callback.calledOnce); gpio25.removeListener('change', callback); done(); }, 600); }); }); }); });