UNPKG

onvif

Version:

Client to ONVIF NVT devices Profile S: cameras

270 lines (235 loc) 8.47 kB
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <title>JSDoc: Source: events.js</title> <script src="scripts/prettify/prettify.js"> </script> <script src="scripts/prettify/lang-css.js"> </script> <!--[if lt IE 9]> <script src="//html5shiv.googlecode.com/svn/trunk/html5.js"></script> <![endif]--> <link type="text/css" rel="stylesheet" href="styles/prettify-tomorrow.css"> <link type="text/css" rel="stylesheet" href="styles/jsdoc-default.css"> </head> <body> <div id="main"> <h1 class="page-title">Source: events.js</h1> <section> <article> <pre class="prettyprint source linenums"><code>/** * @namespace cam * @description Events section for Cam class * @author Andrew D.Laptev &lt;a.d.laptev@gmail.com> * @licence MIT */ /** * @typedef {object} Cam~CreatePullPointSubscriptionResponse * @property {object} subscriptionReference * @property {string} subscriptionReference.address * @property {Date} currentTime * @property {Date} terminationTime */ /** * Events namespace for the device, stores all information about device events * @name Cam#events * @type object * @property {Cam~EventProperties} properties * @property {Cam~CreatePullPointSubscriptionResponse} subscription * @property {Date} terminationTime Time when pull-point subscription is over * @property {number} messageLimit Pull message count */ const Cam = require('./cam').Cam , cam = require('./cam') , linerase = require('./utils').linerase , url = require('url') ; /** * Event properties object * @typedef {object} Cam~EventProperties * @property {array} topicNamespaceLocation * @property {object} topicSet * @property {array} topicExpressionDialect */ /** * @callback Cam~GetEventPropertiesCallback * @property {?Error} err * @property {Cam~EventProperties} response * @property {string} response xml */ /** * Get event properties of the device. Sets `events` property of the device * @param {Cam~GetEventPropertiesCallback} callback */ Cam.prototype.getEventProperties = function(callback) { this._request({ body: this._envelopeHeader() + '&lt;GetEventProperties xmlns="http://www.onvif.org/ver10/events/wsdl"/>' + this._envelopeFooter() }, function(err, res, xml) { if (!err) { this.events.properties = linerase(res).getEventPropertiesResponse; } callback.call(this, err, err ? null : this.events.properties, xml); }.bind(this)); }; /** * Get event service capabilities * @param {function} callback */ Cam.prototype.getEventServiceCapabilities = function(callback) { this._request({ body: this._envelopeHeader() + '&lt;GetServiceCapabilities xmlns="http://www.onvif.org/ver10/events/wsdl"/>' + this._envelopeFooter() }, function(err, res, xml) { if (!err) { var data = linerase(res[0].getServiceCapabilitiesResponse[0].capabilities[0].$); } callback.call(this, err, data, xml); }.bind(this)); }; /** * Create pull-point subscription * @param {function} callback */ Cam.prototype.createPullPointSubscription = function(callback) { this._request({ body: this._envelopeHeader() + '&lt;CreatePullPointSubscription xmlns="http://www.onvif.org/ver10/events/wsdl"/>' + this._envelopeFooter() }, function(err, res, xml) { if (!err) { this.events.subscription = linerase(res[0].createPullPointSubscriptionResponse[0]); this.events.subscription.subscriptionReference.address = url.parse(this.events.subscription.subscriptionReference.address); this.events.terminationTime = _terminationTime(this.events.subscription); } callback.call(this, err, err ? null : this.events.subscription, xml); }.bind(this)); }; /** * @typedef {object} Cam~Event * @property {Date} currentTime * @property {Date} terminationTime * @property {Cam~NotificationMessage|Array.&lt;Cam~NotificationMessage>} [notificationMessage] */ /** * @typedef {object} Cam~NotificationMessage * @property {string} subscriptionReference.address Pull-point address * @property {string} topic._ Namespace of message topic * @property {object} message Message object */ /** * @callback Cam~PullMessagesResponse * @property {?Error} error * @property {Cam~Event} response Message * @property {string} xml Raw SOAP response */ /** * Pull messages from pull-point subscription * @param options * @param {number} [options.timeout=30000] * @param {number} [options.messageLimit=1] * @param {Cam~PullMessagesResponse} callback * @throws {Error} {@link Cam#events.subscription} must exists */ Cam.prototype.pullMessages = function(options, callback) { try { var urlAddress = this.events.subscription.subscriptionReference.address; } catch (e) { throw new Error('You should create pull-point subscription first!'); } this._request({ url: urlAddress , body: this._envelopeHeader() + '&lt;PullMessages xmlns="http://www.onvif.org/ver10/events/wsdl">' + '&lt;Timeout>PT' + ((options.timeout || 30000) / 1000) + 'S&lt;/Timeout>' + '&lt;MessageLimit>' + (options.messageLimit || 1) + '&lt;/MessageLimit>' + '&lt;/PullMessages>' + this._envelopeFooter() }, function(err, res, xml) { if (!err) { var data = linerase(res).pullMessagesResponse; } callback.call(this, err, data, xml); }.bind(this)); }; /** * Count time before pull-point subscription terminates * @param {Cam~CreatePullPointSubscriptionResponse} response * @returns {Date} * @private */ function _terminationTime(response) { return new Date(Date.now() - response.currentTime.getTime() + response.terminationTime.getTime()); } /** * Bind event handling to the `event` event */ Cam.prototype.on('newListener', function(name) { // if there is the first listener, start pulling if (name === 'event' &amp;&amp; this.listeners(name).length === 0) { this._eventRequest(); } }); /** * Event loop for pullMessages request * @private */ Cam.prototype._eventRequest = function() { this.events.timeout = this.events.timeout || 30000; // setting timeout this.events.messageLimit = this.events.messageLimit || 1; // setting message limit if (!this.events.terminationTime || (this.events.terminationTime &lt; Date.now() + this.events.timeout)) { // if there is no pull-point subscription or it will be dead soon, create new this.createPullPointSubscription(this._eventPull.bind(this)); } else { this._eventPull(); } }; /** * Event loop for pullMessages request * @private */ Cam.prototype._eventPull = function() { if (this.listeners('event').length) { // check for event listeners, if zero, stop pulling this.pullMessages({ timeout: this.events.timeout , messageLimit: this.events.messageLimit }, function(err, data) { if (!err) { if (data.notificationMessage) { if (!Array.isArray(data.notificationMessage)) { data.notificationMessage = [data.notificationMessage]; } data.notificationMessage.forEach(function(message) { // pull-point address check if (message.subscriptionReference.address === this.events.subscription.subscriptionReference.address.href) { /** * Indicates message from device. * @event Cam#event * @type {Cam~NotificationMessage} */ this.emit('event', message); } }.bind(this)); } this.events.terminationTime = _terminationTime(data); } this._eventRequest(); }.bind(this)); } };</code></pre> </article> </section> </div> <nav> <h2><a href="index.html">Home</a></h2><h3>Classes</h3><ul><li><a href="Cam_.html">Cam</a></li><li><a href="Discovery_.html">Discovery</a></li></ul><h3>Events</h3><ul><li><a href="Cam_.html#event:event">event</a></li><li><a href="Cam_.html#event:rawResponse">rawResponse</a></li><li><a href="Discovery_.html#event:device">device</a></li><li><a href="Discovery_.html#event:error">error</a></li></ul><h3>Namespaces</h3><ul><li><a href="cam.html">cam</a></li><li><a href="discovery.html">discovery</a></li><li><a href="utils.html">utils</a></li></ul><h3>Global</h3><ul><li><a href="global.html#guid">guid</a></li><li><a href="global.html#linerase">linerase</a></li><li><a href="global.html#parseSOAPString">parseSOAPString</a></li></ul> </nav> <br class="clear"> <footer> Documentation generated by <a href="https://github.com/jsdoc3/jsdoc">JSDoc 3.4.0</a> on Mon Jun 20 2016 15:42:17 GMT+0300 (MSK) </footer> <script> prettyPrint(); </script> <script src="scripts/linenumber.js"> </script> </body> </html>