New Case Study:See how Anthropic automated 95% of dependency reviews with Socket.Learn More
Socket
Sign inDemoInstall
Socket

ar-drone

Package Overview
Dependencies
Maintainers
1
Versions
13
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

ar-drone - npm Package Compare versions

Comparing version 0.0.1 to 0.0.2

error

54

CONTRIBUTING.md

@@ -59,52 +59,12 @@ # Contributing

### High level API
### Client API
In my first version of this library I included a high-level `Client` class
that unified access to control, video and navdata. IMO the new separation is
better, but there may still be room for a unified class that adds some sugar
and makes sure certain config values are shared (like the drone IP).
The Client API is still lacking a few important features:
I could imagine an API like this:
* `client.disableEmergency()` - this recovers a drone that is in emergency mode
by setting the REF emergency bit for a short moment. This should probably also
be done implicitly when a new client is created.
* `client.config()` - allow sending custom config values to a client. This is
needed to configure things like the 'navdata' and 'camera' settings.
```js
var client = arDrone.createClient();
// Send UDP commands to drone every 30ms
client.setInterval(30);
// Sets the 'emergency' bit in AT*REF for 1 second
client.resetEmergency();
// Takeoff
client.takeoff();
client
.after(5000, function() {
this.up = 0.5;
this.clockwise = 1;
})
.after(5000, function() {
this.hover();
})
.after(2000, function() {
this.land();
});
```
Navdata example:
```js
client.on('navdata', function(navdata) {
if (this.navdata.lowBattery) {
console.log('Low battery!');
}
});
```
And video:
```js
var stream = client.createPngStream();
```
### Parse remaining navdata options

@@ -111,0 +71,0 @@

@@ -12,8 +12,3 @@ // Run this to receive a png image stream from your drone.

pngStream
.on('connect', function() {
console.log('Connected');
})
.on('disconnect', function(err) {
console.log('Disconnected: ' + err);
})
.on('error', console.log)
.on('data', function(pngBuffer) {

@@ -24,5 +19,5 @@ lastPng = pngBuffer;

var server = http.createServer(function(req, res) {
if (!pngStream.connected) {
if (!lastPng) {
res.writeHead(503);
res.end('PngStream is currently not connected.');
res.end('Did not receive any png data yet.');
return;

@@ -29,0 +24,0 @@ }

@@ -14,4 +14,2 @@ // Run this to receive the raw video stream from your drone as buffers.

video.on('data', function(buffer) {
console.log(buffer);
});
video.on('data', console.log);
var arDrone = exports;
exports.Client = require('./lib/Client');
exports.UdpControl = require('./lib/control/UdpControl');

@@ -7,2 +8,8 @@ exports.PngStream = require('./lib/video/PngStream');

exports.createClient = function(options) {
var client = new arDrone.Client(options);
client.resume();
return client;
};
exports.createUdpControl = function(options) {

@@ -14,3 +21,3 @@ return new arDrone.UdpControl(options);

var stream = new arDrone.PngStream(options);
stream.start();
stream.resume();
return stream;

@@ -17,0 +24,0 @@ };

@@ -49,14 +49,40 @@ var AtCommand = require('./AtCommand');

args[alias.index] = value;
args[alias.index] = at.floatString(value);
args[0] = args[0] | PCMD_FLAGS.progressive;
}
for (var i = 1; i < args.length; i++) {
args[i] = at.floatString(args[i]);
return this.raw('PCMD', args);
};
AtCommandCreator.prototype.config = function(name, value) {
return this.raw('CONFIG', '"' + name + '"', '"' + value + '"');
};
AtCommandCreator.prototype.animateLeds = function(name, hz, duration) {
// Default animation
name = name || 'redSnake';
hz = hz || 2;
duration = duration || 3;
var animationId = LED_ANIMATIONS.indexOf(name);
if (animationId < 0) {
throw new Error('Unknown led animation: ' + name);
}
hz = at.floatString(hz);
return this.raw('PCMD', args);
var params = [animationId, hz, duration].join(',');
return this.config('leds:leds_anim', params);
};
AtCommandCreator.prototype.animate = function(name, duration) {
var animationId = ANIMATIONS.indexOf(name);
if (animationId < 0) {
throw new Error('Unknown animation: ' + name);
}
var params = [animationId, duration].join(',');
return this.config('control:flight_anim', params);
};
// Constants

@@ -81,3 +107,52 @@

clockwise : {index: 4, invert: false},
counterclockwise : {index: 4, invert: true},
counterClockwise : {index: 4, invert: true},
};
// from ARDrone_SDK_2_0/ControlEngine/iPhone/Release/ARDroneGeneratedTypes.h
var LED_ANIMATIONS = exports.LED_ANIMATIONS = [
'blinkGreenRed',
'blinkGreen',
'blinkRed',
'blinkOrange',
'snakeGreenRed',
'fire',
'standard',
'red',
'green',
'redSnake',
'blank',
'rightMissile',
'leftMissile',
'doubleMissile',
'frontLeftGreenOthersRed',
'frontRightGreenOthersRed',
'rearRightGreenOthersRed',
'rearLeftGreenOthersRed',
'leftGreenRightRed',
'leftRedRightGreen',
'blinkStandard',
];
// from ARDrone_SDK_2_0/ControlEngine/iPhone/Release/ARDroneGeneratedTypes.h
var ANIMATIONS = exports.ANIMATIONS = [
'phiM30Deg',
'phi30Deg',
'thetaM30Deg',
'theta30Deg',
'theta20degYaw200deg',
'theta20degYawM200deg',
'turnaround',
'turnaroundGodown',
'yawShake',
'yawDance',
'phiDance',
'thetaDance',
'vzDance',
'wave',
'phiThetaMixed',
'doublePhiThetaMixed',
'flipAhead',
'flipBehind',
'flipLeft',
'flipRight',
];

@@ -14,10 +14,11 @@ var Stream = require('stream').Stream;

this.readable = true;
this._socket = options.socket || dgram.createSocket('udp4');
this._port = options.port || constants.ports.NAVDATA;
this._ip = options.ip || constants.DEFAULT_DRONE_IP;
this._initialized = false;
this._parseNavdata = options.parser || parseNavdata;
this._timeout = options.timeout || 100;
this._timer = undefined;
this.readable = true;
this._socket = options.socket || dgram.createSocket('udp4');
this._port = options.port || constants.ports.NAVDATA;
this._ip = options.ip || constants.DEFAULT_DRONE_IP;
this._initialized = false;
this._parseNavdata = options.parser || parseNavdata;
this._timeout = options.timeout || 100;
this._timer = undefined;
this._sequenceNumber = 0;
}

@@ -58,4 +59,19 @@

UdpNavdataStream.prototype._handleMessage = function(buffer) {
this.emit('data', this._parseNavdata(buffer));
try {
var navdata = this._parseNavdata(buffer);
} catch (err) {
// avoid 'error' causing an exception when nobody is listening
if (this.listeners('error').length > 0) {
this.emit('error', err);
}
return;
}
// Ignore out of order messages
if (navdata.sequenceNumber > this._sequenceNumber) {
this._sequenceNumber = navdata.sequenceNumber;
this.emit('data', navdata);
}
this._setTimeout();
};

@@ -65,2 +65,6 @@ // The AR Drone 2.0 allows a tcp client to receive H264 (MPEG4.10 AVC) video

if (this._frame.signature !== 'PaVE') {
this.emit('error', new Error('Invalid signature: ' + JSON.stringify(this._frame.signature)));
}
this._state = 'payload';

@@ -84,1 +88,5 @@ break;

};
PaVEParser.prototype.end = function() {
// nothing to do, just here so pipe() does not complain
};

@@ -11,3 +11,3 @@ // Converts a video stream into a stream of png buffers. Each 'data' event

var spawn = require('child_process').spawn;
var PngSplitter = require('../PngSplitter');
var PngSplitter = require('./PngSplitter');

@@ -91,4 +91,9 @@ module.exports = PngEncoder;

PngEncoder.prototype.end = function() {
// No data handled yet? Nothing to do for ending.
if (!this._ffmpeg) {
return;
}
this._ending = true;
this._ffmpeg.stdin.end();
};

@@ -1,7 +0,7 @@

var TcpVideoStream = require('./TcpVideoStream');
var PngSplitter = require('../PngSplitter');
var spawn = require('child_process').spawn;
var Stream = require('stream').Stream;
var util = require('util');
PngStream.TcpVideoStream = require('./TcpVideoStream');
PngStream.PngEncoder = require('./PngEncoder');
var Stream = require('stream').Stream;
var util = require('util');
module.exports = PngStream;

@@ -14,6 +14,30 @@ util.inherits(PngStream, Stream);

this.readable = true;
this.readable = true;
this._options = options;
this._tcpVideoStream = null;
this._pngEncoder = null;
}
PngStream.prototype.start = function() {
PngStream.prototype.resume = function() {
this._resume();
};
PngStream.prototype._resume = function() {
var self = this;
this._tcpVideoStream = new PngStream.TcpVideoStream(this._options);
this._pngEncoder = new PngStream.PngEncoder(this._options);
this._tcpVideoStream.on('error', function(err) {
self._pngEncoder.end();
self._resume();
if (self.listeners('error').length > 0) {
self.emit('error', err);
}
});
this._tcpVideoStream.connect();
this._tcpVideoStream.pipe(this._pngEncoder);
this._pngEncoder.on('data', this.emit.bind(this, 'data'));
};

@@ -5,3 +5,3 @@ {

"description": "A node.js client for controlling Parrot AR Drone 2.0 quad-copters.",
"version": "0.0.1",
"version": "0.0.2",
"homepage": "https://github.com/felixge/node-ar-drone",

@@ -8,0 +8,0 @@ "repository": {

@@ -29,4 +29,184 @@ # ar-drone

## Control
## Status
This module is still under [heavy development](./node-ar-drone/blob/master/CONTRIBUTING.md), so please don't be suprised if
you find some functionality missing or undocumented.
However, the documented parts are tested and should work well for most parts.
## Client
This module exposes a high level Client API that tries to support all drone
features, while making them easy to use.
The best way to get started is to create a `repl.js` file like this:
```js
var arDrone = require('ar-drone');
var client = arDrone.createClient();
client.createRepl();
```
Using this REPL, you should be able to have some fun:
```js
$ node repl.js
// Make the drone takeoff
drone> takeoff()
true
// Wait for the drone to takeoff
drone> clockwise(0.5)
0.5
// Let the drone spin for a while
drone> land()
true
// Wait for the drone to land
```
Now you could write an autonomous program that does the same:
```js
var arDrone = require('ar-drone');
var client = arDrone.createClient();
client.takeoff();
client
.after(5000, function() {
this.clockwise(0.5);
})
.after(3000, function() {
this.stop();
this.land();
});
```
Ok, but what if you want to make your drone to interact with something? Well,
you could start by looking at the sensor data:
```js
client.on('navdata', console.log);
```
Not all of this is handled by the Client library yet, but you should at the
very least be able to receive `droneState` and `demo` data.
A good initial challenge might be to try flying to a certain altitude based
on the `navdata.demo.altitudeMeters` property.
Once you have manged this, you may want to try looking at the camera image. Here
is a simple way to get this as PngBuffers (requires a recent ffmpeg version to
be found in your `$PATH`):
```js
var pngStream = client.createPngStream();
pngStream.on('data', console.log);
```
Your first challenge might be to expose these png images as a node http web
server. Once you have done that, you should try feeding them into the
[opencv](https://npmjs.org/package/opencv) module.
### Client API
#### arDrone.createClient([options])
Returns a new `Client` object. `options` include:
* `ip`: The IP of the drone. Defaults to `'192.168.1.1'`.
#### client.createREPL()
Launches an interactive interface with all client methods available in the
active scope. Additionally `client` resolves to the `client` instance itself.
#### client.createPngStream()
Returns a `PngStream` object that emits individual png image buffers as `'data'`
events.
#### client.takeoff()
Sets the internal `fly` state to `true`.
#### client.land()
Sets the internal `fly` state to `false`.
#### client.up(speed) / client.down(speed)
Makes the drone gain or reduce altitude. `speed` can be a value from `0` to `1`.
#### client.clockwise(speed) / client.counterClockwise(speed)
Causes the drone to spin. `speed` can be a value from `0` to `1`.
#### client.front(speed) / client.back(speed)
Controls the pitch, which a horizontal movement using the camera
as a reference point. `speed` can be a value from `0` to `1`.
#### client.left(speed) / client.right(speed)
Controls the roll, which is a horizontal movement using the camera
as a reference point. `speed` can be a value from `0` to `1`.
#### client.stop()
Sets all drone movement commands to `0`, making it effectively hover in place.
#### client.animate(animation, duration)
Performs a pre-programmed flight sequence for a given `duration` (in ms).
`animation` can be one of the following:
```js
['phiM30Deg', 'phi30Deg', 'thetaM30Deg', 'theta30Deg', 'theta20degYaw200deg',
'theta20degYawM200deg', 'turnaround', 'turnaroundGodown', 'yawShake',
'yawDance', 'phiDance', 'thetaDance', 'vzDance', 'wave', 'phiThetaMixed',
'doublePhiThetaMixed', 'flipAhead', 'flipBehind', 'flipLeft', 'flipRight']
```
Example:
```js
client.animate('flipLeft', 15);
```
Please note that the drone will need a good amount of altitude and headroom
to perform a flip. So be careful!
#### client.animateLeds(animation, hz, duration)
Performs a pre-programmed led sequence at given `hz` frequency and `duration`
(in sec!). `animation` can be one of the following:
```js
['blinkGreenRed', 'blinkGreen', 'blinkRed', 'blinkOrange', 'snakeGreenRed',
'fire', 'standard', 'red', 'green', 'redSnake', 'blank', 'rightMissile',
'leftMissile', 'doubleMissile', 'frontLeftGreenOthersRed',
'frontRightGreenOthersRed', 'rearRightGreenOthersRed',
'rearLeftGreenOthersRed', 'leftGreenRightRed', 'leftRedRightGreen',
'blinkStandard']
```
Example:
```js
client.animateLeds('blinkRed', 5, 2)
```
#### client.disableEmergency()
Causes the emergency REF bit to be set to 1 until
`navdata.droneState.emergencyLanding` is 0. This recovers a drone that has
flipped over and is showing red lights to be flyable again and show green
lights. It is also done implicitly when creating a new high level client.
## UdpControl
This is a low level API. If you prefer something simpler, check out the Client
docs.
The drone is controlled by sending UDP packets on port 5556. Because UDP

@@ -50,3 +230,3 @@ does not guarantee message ordering or delivery, clients must repeatedly send

var arDrone = require('ar-drone');
var control = drone.createUdpControl();
var control = arDrone.createUdpControl();

@@ -86,3 +266,3 @@ setInterval(function() {

var arDrone = require('ar-drone');
var control = drone.createUdpControl();
var control = arDrone.createUdpControl();
var start = Date.now();

@@ -160,3 +340,3 @@

* `up` or `down`: Gain or reduce altitude.
* `clockwise` or `counterclockwise`: Rotate around the center axis.
* `clockwise` or `counterClockwise`: Rotate around the center axis.

@@ -173,6 +353,6 @@ The values for each option are the speed to use for the operation and can range

Documentation to be written ...
@TODO Document the low level video API.
## Navdata
Documentation to be written ...
@TODO Document the low level navdata API.

@@ -8,14 +8,14 @@ var common = require('../../common');

test('AtCommandCreator', {
before: function() {
this.creator = new AtCommandCreator();
},
'command.number keeps incrementing': function() {
var creator = new AtCommandCreator();
assert.equal(creator.ref().number, 0);
assert.equal(creator.ref().number, 1);
assert.equal(creator.ref().number, 2);
assert.equal(this.creator.ref().number, 0);
assert.equal(this.creator.ref().number, 1);
assert.equal(this.creator.ref().number, 2);
},
'raw': function() {
var creator = new AtCommandCreator();
var cmd = creator.raw('FOO', 1, 2, 3);
var cmd = this.creator.raw('FOO', 1, 2, 3);
assert.equal(cmd.type, 'FOO');

@@ -25,3 +25,3 @@ assert.deepEqual(cmd.args, [1, 2, 3]);

// An array can be given as well
var cmd = creator.raw('FOO', [1, 2, 3]);
var cmd = this.creator.raw('FOO', [1, 2, 3]);
assert.equal(cmd.type, 'FOO');

@@ -32,5 +32,3 @@ assert.deepEqual(cmd.args, [1, 2, 3]);

'ref': function() {
var creator = new AtCommandCreator();
var cmd = creator.ref();
var cmd = this.creator.ref();
assert.equal(cmd.type, 'REF');

@@ -40,6 +38,6 @@ assert.equal(cmd.args.length, 1);

var cmd = creator.ref({fly: true});
var cmd = this.creator.ref({fly: true});
assert.ok(cmd.args[0] & AtCommandCreator.REF_FLAGS.takeoff);
var cmd = creator.ref({emergency: true});
var cmd = this.creator.ref({emergency: true});
assert.ok(cmd.args[0] & AtCommandCreator.REF_FLAGS.emergency);

@@ -49,5 +47,3 @@ },

'pcmd': function() {
var creator = new AtCommandCreator();
var cmd = creator.pcmd();
var cmd = this.creator.pcmd();
assert.equal(cmd.type, 'PCMD');

@@ -59,13 +55,13 @@ assert.equal(cmd.args.length, 5);

var val = 0.75;
assert.equal(creator.pcmd({left: val}).args[1], at.floatString(-val));
assert.equal(creator.pcmd({right: val}).args[1], at.floatString(val));
assert.equal(creator.pcmd({front: val}).args[2], at.floatString(-val));
assert.equal(creator.pcmd({back: val}).args[2], at.floatString(val));
assert.equal(creator.pcmd({up: val}).args[3], at.floatString(val));
assert.equal(creator.pcmd({down: val}).args[3], at.floatString(-val));
assert.equal(creator.pcmd({clockwise: val}).args[4], at.floatString(val));
assert.equal(creator.pcmd({counterclockwise: val}).args[4], at.floatString(-val));
assert.equal(this.creator.pcmd({left: val}).args[1], at.floatString(-val));
assert.equal(this.creator.pcmd({right: val}).args[1], at.floatString(val));
assert.equal(this.creator.pcmd({front: val}).args[2], at.floatString(-val));
assert.equal(this.creator.pcmd({back: val}).args[2], at.floatString(val));
assert.equal(this.creator.pcmd({up: val}).args[3], at.floatString(val));
assert.equal(this.creator.pcmd({down: val}).args[3], at.floatString(-val));
assert.equal(this.creator.pcmd({clockwise: val}).args[4], at.floatString(val));
assert.equal(this.creator.pcmd({counterClockwise: val}).args[4], at.floatString(-val));
// test multiple aliases togeter
var cmd = creator.pcmd({left: 0.1, clockwise: 0.3});
var cmd = this.creator.pcmd({left: 0.1, clockwise: 0.3});
assert.equal(cmd.args[1], at.floatString(-0.1));

@@ -75,9 +71,61 @@ assert.equal(cmd.args[4], at.floatString(0.3));

// test progressive bit being unset when no aliases are provided
var cmd = creator.pcmd();
var cmd = this.creator.pcmd();
assert.equal(cmd.args[0] & AtCommandCreator.PCMD_FLAGS.progressive, false);
// test progressive bit being set automatically
var cmd = creator.pcmd({left: 0.1});
var cmd = this.creator.pcmd({left: 0.1});
assert.ok(cmd.args[0] & (1 << 0));
},
'config': function() {
var cmd = this.creator.config('foo', 'bar');
assert.equal(cmd.type, 'CONFIG');
assert.equal(cmd.args.length, 2);
assert.equal(cmd.args[0], '"foo"');
assert.equal(cmd.args[1], '"bar"');
},
'animateLeds() works as expected': function() {
var hz = 3;
var duration = 3;
var cmd = this.creator.animateLeds('blinkGreen', hz, duration);
var expected = '1,' + at.floatString(hz) + ',' + duration;
assert.equal(cmd.type, 'CONFIG');
assert.equal(cmd.args.length, 2);
assert.equal(cmd.args[0], '"leds:leds_anim"');
assert.equal(cmd.args[1], '"' + expected + '"');
},
'animateLeds() does a red snake at 2 hz for 3s by default': function() {
var cmd = this.creator.animateLeds();
var expected = '9,' + at.floatString(2) + ',' + 3;
assert.equal(cmd.args[1], '"' + expected + '"');
},
'animateLeds() throws an error for unknown animations': function() {
var self = this;
assert.throws(function() {
self.creator.animateLeds('does not exist');
},/animation/);
},
'animate() works as expected': function() {
var duration = 2000;
var cmd = this.creator.animate('yawShake', duration);
var expected = '8,' + duration;
assert.equal(cmd.type, 'CONFIG');
assert.equal(cmd.args.length, 2);
assert.equal(cmd.args[0], '"control:flight_anim"');
assert.equal(cmd.args[1], '"' + expected + '"');
},
'animate() throws an error for unknown animations': function() {
var self = this;
assert.throws(function() {
self.creator.animate('does not exist');
},/animation/);
},
});

@@ -88,2 +88,3 @@ var common = require('../../common');

this.fakeParser.returns({});
this.fakeSocket.emit('message', new Buffer(0));

@@ -98,6 +99,5 @@

'incoming messages are parsed': function() {
var fakeBuffer = new Buffer([1, 2, 3]);
var fakeNavdata = {fake: 'navdata'};
var fakeNavdata = {fake: 'navdata', sequenceNumber: 1};
var dataSpy = sinon.spy();

@@ -119,2 +119,58 @@

'old navdata messages are ignored': function() {
var fakeNavdataA = {sequenceNumber: 1};
var fakeNavdataB = {sequenceNumber: 2};
var fakeNavdataC = {sequenceNumber: 3};
this.fakeParser.withArgs(1).returns(fakeNavdataA);
this.fakeParser.withArgs(2).returns(fakeNavdataB);
this.fakeParser.withArgs(3).returns(fakeNavdataC);
var dataSpy = sinon.spy();
this.stream.on('data', dataSpy);
this.stream.resume();
this.fakeSocket.emit('message', 1);
this.fakeSocket.emit('message', 3);
this.fakeSocket.emit('message', 2);
assert.equal(this.fakeParser.callCount, 3);
assert.equal(dataSpy.callCount, 2);
assert.equal(dataSpy.getCall(0).args[0].sequenceNumber, 1);
assert.equal(dataSpy.getCall(1).args[0].sequenceNumber, 3);
},
'navdata errors are ignored by default': function() {
this.fakeParser.throws(new Error('bad'));
var dataSpy = sinon.spy();
this.stream.on('data', dataSpy);
this.stream.resume();
this.fakeSocket.emit('message', 1);
assert.equal(this.fakeParser.callCount, 1);
assert.equal(dataSpy.callCount, 0);
},
'navdata errors are emitted if there is an error handler': function() {
var fakeErr = new Error('bad');
this.fakeParser.throws(fakeErr);
var dataSpy = sinon.spy();
var errorSpy = sinon.spy();
this.stream.on('data', dataSpy);
this.stream.on('error', errorSpy);
this.stream.resume();
this.fakeSocket.emit('message', 1);
assert.equal(this.fakeParser.callCount, 1);
assert.equal(dataSpy.callCount, 0);
assert.equal(errorSpy.callCount, 1);
assert.strictEqual(errorSpy.getCall(0).args[0], fakeErr);
},
'destroy() cleans up': function() {

@@ -121,0 +177,0 @@ this.stream.destroy();

@@ -9,15 +9,23 @@ var common = require('../common');

before: function() {
sinon.stub(arDrone.PngStream.prototype, 'start');
sinon.stub(arDrone.PngStream.prototype, 'resume');
sinon.stub(arDrone.UdpNavdataStream.prototype, 'resume');
sinon.stub(arDrone.Client.prototype, 'resume');
},
after: function() {
arDrone.PngStream.prototype.start.restore();
arDrone.PngStream.prototype.resume.restore();
arDrone.UdpNavdataStream.prototype.resume.restore();
arDrone.Client.prototype.resume.restore();
},
'createClient': function() {
var client = arDrone.createClient();
assert.ok(client instanceof arDrone.Client);
assert.equal(client.resume.callCount, 1);
},
'createPngStream': function() {
var pngStream = arDrone.createPngStream();
assert.ok(pngStream instanceof arDrone.PngStream);
assert.equal(pngStream.start.callCount, 1);
assert.equal(pngStream.resume.callCount, 1);
},

@@ -24,0 +32,0 @@

@@ -6,14 +6,17 @@ var common = require('../../common');

var fs = require('fs');
var sinon = require('sinon');
var fixture = fs.readFileSync(common.fixtures + '/pave.bin');
test('PaVEParser', {
before: function() {
this.parser = new PaVEParser();
},
'parses fixture properly': function() {
var parser = new PaVEParser();
var frames = [];
parser.on('data', function(frame) {
this.parser.on('data', function(frame) {
frames.push(frame);
});
parser.write(fixture);
this.parser.write(fixture);

@@ -51,2 +54,21 @@ assert.equal(frames.length, 20);

},
'emits error on bad signature': function() {
var buffer = new Buffer(64);
// should be PaVE, not fuck
buffer.write('fuck');
var errorStub = sinon.stub();
this.parser.on('error', errorStub);
this.parser.write(buffer);
assert.equal(errorStub.callCount, 1);
assert.equal(/signature/i.test(errorStub.getCall(0).args[0]), true);
},
'end method exists, but does nothing': function() {
this.parser.end();
},
});

@@ -197,2 +197,6 @@ var common = require('../../common');

},
'end() does not do anything if there is no ffmpeg yet': function() {
this.encoder.end();
},
});
var common = require('../../common');
var assert = require('assert');
var test = require('utest');
//var sinon = require('sinon');
//var EventEmitter = require('events').EventEmitter;
var PngStream = require(common.lib + '/video/PngStream');
var sinon = require('sinon');
var PngStream = require(common.lib + '/video/PngStream');
var TcpVideoStream = PngStream.TcpVideoStream;
var PngEncoder = PngStream.PngEncoder;
test('PngStream', {
before: function() {
this.stream = new PngStream();
PngStream.TcpVideoStream = sinon.stub();
PngStream.PngEncoder = sinon.stub();
this.tcpVideoStream = new TcpVideoStream();
this.pngEncoder = new PngEncoder();
PngStream.TcpVideoStream.returns(this.tcpVideoStream);
PngStream.PngEncoder.returns(this.pngEncoder);
this.fakeOptions = {};
this.stream = new PngStream(this.fakeOptions);
},

@@ -17,2 +28,73 @@

},
'resume connects new TcpVideoStream': function() {
sinon.stub(this.tcpVideoStream, 'connect');
this.stream.resume();
assert.equal(PngStream.TcpVideoStream.callCount, 1);
assert.strictEqual(PngStream.TcpVideoStream.getCall(0).args[0], this.fakeOptions);
assert.equal(this.tcpVideoStream.connect.callCount, 1);
},
'resume passes TcpVideoStream data through PngEncoder': function() {
sinon.stub(this.tcpVideoStream, 'connect');
this.stream.resume();
assert.equal(PngStream.TcpVideoStream.callCount, 1);
assert.equal(PngStream.PngEncoder.callCount, 1);
assert.strictEqual(PngStream.TcpVideoStream.getCall(0).args[0], this.fakeOptions);
assert.strictEqual(PngStream.PngEncoder.getCall(0).args[0], this.fakeOptions);
sinon.stub(this.pngEncoder, 'write');
var fakeData = new Buffer([1]);
this.tcpVideoStream.emit('data', fakeData);
assert.equal(this.pngEncoder.write.callCount, 1);
assert.strictEqual(this.pngEncoder.write.getCall(0).args[0], fakeData);
var dataStub = sinon.stub();
this.stream.on('data', dataStub);
var fakePng = new Buffer([2]);
this.pngEncoder.emit('data', fakePng);
assert.equal(dataStub.callCount, 1);
assert.strictEqual(dataStub.getCall(0).args[0], fakePng);
},
'TcpVideoStream stream errors cause a new tcpVideoStream to be created': function() {
sinon.stub(this.tcpVideoStream, 'connect');
sinon.stub(this.pngEncoder, 'end');
this.stream.resume();
var tcpVideoStream2 = new TcpVideoStream();
sinon.stub(tcpVideoStream2, 'connect');
PngStream.TcpVideoStream.returns(tcpVideoStream2);
var fakeErr = new Error('bad shit');
this.tcpVideoStream.emit('error', fakeErr);
assert.equal(tcpVideoStream2.connect.callCount, 1);
assert.equal(this.pngEncoder.end.callCount, 1);
},
'emits "error" events if there is a listener': function() {
sinon.stub(this.tcpVideoStream, 'connect');
sinon.stub(this.pngEncoder, 'end');
var errStub = sinon.stub();
this.stream.on('error', errStub);
this.stream.resume();
var fakeErr = new Error('bad shit');
this.tcpVideoStream.emit('error', fakeErr);
assert.equal(errStub.callCount, 1);
assert.strictEqual(errStub.getCall(0).args[0], fakeErr);
},
});

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc