Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

webbluetooth

Package Overview
Dependencies
Maintainers
1
Versions
58
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

webbluetooth - npm Package Compare versions

Comparing version 1.0.4 to 1.0.5

2

examples/eddystone.js

@@ -26,3 +26,3 @@ /*

var webbluetooth = require('../');
var webbluetooth = require("../");

@@ -29,0 +29,0 @@ var eddystoneUUID = 0xFEAA;

@@ -26,5 +26,5 @@ /*

var bluetooth = require('../').bluetooth;
var bluetooth = require("../").bluetooth;
console.log('Requesting Bluetooth Devices...');
console.log("Requesting Bluetooth Devices...");
bluetooth.requestDevice({

@@ -34,19 +34,19 @@ filters:[{ services:[ "heart_rate" ] }]

.then(device => {
console.log('Found device: ' + device.name);
console.log("Found device: " + device.name);
return device.gatt.connect();
})
.then(server => {
console.log('Gatt server connected: ' + server.connected);
console.log("Gatt server connected: " + server.connected);
return server.getPrimaryService("heart_rate");
})
.then(service => {
console.log('Primary service: ' + service.uuid);
console.log("Primary service: " + service.uuid);
return service.getCharacteristic("heart_rate_measurement");
})
.then(characteristic => {
console.log('Characteristic: ' + characteristic.uuid);
console.log("Characteristic: " + characteristic.uuid);
return characteristic.startNotifications();
})
.then(characteristic => {
console.log('Notifications started');
console.log("Notifications started");

@@ -53,0 +53,0 @@ characteristic.addEventListener("characteristicvaluechanged", event => {

@@ -26,9 +26,9 @@ /*

var Bluetooth = require('../').Bluetooth;
var Bluetooth = require("../").Bluetooth;
var bluetoothDevices = [];
process.stdin.setEncoding('utf8');
process.stdin.on('readable', () => {
process.stdin.setEncoding("utf8");
process.stdin.on("readable", () => {
var input = process.stdin.read();
if (input === '\u0003') {
if (input === "\u0003") {
process.exit();

@@ -56,3 +56,7 @@ } else {

bluetoothDevices.push({ id: bluetoothDevice.id, select: selectFn });
console.log(bluetoothDevices.length + ": " + bluetoothDevice.name);
if (bluetoothDevice._serviceUUIDs.length) {
console.log("\tAdvertising: " + bluetoothDevice._serviceUUIDs);
}
}

@@ -59,0 +63,0 @@

@@ -42,3 +42,3 @@ "use strict";

this.charNotifies = {};
this.foundFn = null;
this.discoverFn = null;
this.initialised = false;

@@ -61,3 +61,6 @@ this.enabled = false;

return completeFn();
noble.on("discover", this.discover.bind(this));
noble.on("discover", deviceInfo => {
if (this.discoverFn)
this.discoverFn(deviceInfo);
});
this.initialised = true;

@@ -89,40 +92,52 @@ completeFn();

}
discover(deviceInfo) {
if (this.foundFn) {
const deviceID = (deviceInfo.address && deviceInfo.address !== "unknown") ? deviceInfo.address : deviceInfo.id;
if (!this.deviceHandles[deviceID])
this.deviceHandles[deviceID] = deviceInfo;
const serviceUUIDs = [];
if (deviceInfo.advertisement.serviceUuids) {
deviceInfo.advertisement.serviceUuids.forEach(serviceUUID => {
serviceUUIDs.push(helpers_1.getCanonicalUUID(serviceUUID));
});
}
const manufacturerData = new Map();
if (deviceInfo.advertisement.manufacturerData) {
// First 2 bytes are 16-bit company identifier
let company = deviceInfo.advertisement.manufacturerData.readUInt16LE(0);
company = ("0000" + company.toString(16)).slice(-4);
// Remove company ID
const buffer = deviceInfo.advertisement.manufacturerData.slice(2);
manufacturerData.set(company, this.bufferToDataView(buffer));
}
const serviceData = new Map();
if (deviceInfo.advertisement.serviceData) {
deviceInfo.advertisement.serviceData.forEach(serviceAdvert => {
serviceData.set(helpers_1.getCanonicalUUID(serviceAdvert.uuid), this.bufferToDataView(serviceAdvert.data));
});
}
this.foundFn({
id: deviceID,
name: deviceInfo.advertisement.localName,
_serviceUUIDs: serviceUUIDs,
adData: {
rssi: deviceInfo.rssi,
txPower: deviceInfo.advertisement.txPowerLevel,
serviceData: serviceData,
manufacturerData: manufacturerData
}
validDevice(deviceInfo, serviceUUIDs) {
if (serviceUUIDs.length === 0) {
// Match any device
return true;
}
if (!deviceInfo.advertisement.serviceUuids) {
// No advertised services, no match
return false;
}
const advertisedUUIDs = deviceInfo.advertisement.serviceUuids.map(serviceUUID => {
return helpers_1.getCanonicalUUID(serviceUUID);
});
return serviceUUIDs.some(serviceUUID => {
// An advertised UUID matches our search UUIDs
return (advertisedUUIDs.indexOf(serviceUUID) >= 0);
});
}
deviceToBluetoothDevice(deviceInfo) {
const deviceID = (deviceInfo.address && deviceInfo.address !== "unknown") ? deviceInfo.address : deviceInfo.id;
const serviceUUIDs = [];
if (deviceInfo.advertisement.serviceUuids) {
deviceInfo.advertisement.serviceUuids.forEach(serviceUUID => {
serviceUUIDs.push(helpers_1.getCanonicalUUID(serviceUUID));
});
}
const manufacturerData = new Map();
if (deviceInfo.advertisement.manufacturerData) {
// First 2 bytes are 16-bit company identifier
const company = deviceInfo.advertisement.manufacturerData.readUInt16LE(0);
// Remove company ID
const buffer = deviceInfo.advertisement.manufacturerData.slice(2);
manufacturerData.set(("0000" + company.toString(16)).slice(-4), this.bufferToDataView(buffer));
}
const serviceData = new Map();
if (deviceInfo.advertisement.serviceData) {
deviceInfo.advertisement.serviceData.forEach(serviceAdvert => {
serviceData.set(helpers_1.getCanonicalUUID(serviceAdvert.uuid), this.bufferToDataView(serviceAdvert.data));
});
}
return {
id: deviceID,
name: deviceInfo.advertisement.localName,
_serviceUUIDs: serviceUUIDs,
adData: {
rssi: deviceInfo.rssi,
txPower: deviceInfo.advertisement.txPowerLevel,
serviceData: serviceData,
manufacturerData: manufacturerData
}
};
}

@@ -140,15 +155,12 @@ getEnabled(completeFn) {

startScan(serviceUUIDs, foundFn, completeFn, errorFn) {
if (serviceUUIDs.length === 0) {
this.foundFn = foundFn;
}
else {
this.foundFn = device => {
serviceUUIDs.forEach(serviceUUID => {
if (device._serviceUUIDs.indexOf(serviceUUID) >= 0) {
foundFn(device);
return;
}
});
};
}
this.discoverFn = deviceInfo => {
if (this.validDevice(deviceInfo, serviceUUIDs)) {
const device = this.deviceToBluetoothDevice(deviceInfo);
if (!this.deviceHandles[device.id]) {
this.deviceHandles[device.id] = deviceInfo;
// Only call the found function the first time we find a valid device
foundFn(device);
}
}
};
this.init(() => {

@@ -158,3 +170,5 @@ this.deviceHandles = {};

if (this.state === true) {
noble.startScanning([], false, this.checkForError(errorFn, completeFn));
// Noble doesn't correctly match short and canonical UUIDs on Linux, so we need to check ourselves
// Continually scan to pick up all advertised UUIDs
noble.startScanning([], true, this.checkForError(errorFn, completeFn));
}

@@ -173,3 +187,3 @@ else {

stopScan(_errorFn) {
this.foundFn = null;
this.discoverFn = null;
noble.stopScanning();

@@ -176,0 +190,0 @@ }

@@ -98,4 +98,6 @@ "use strict";

return resolve(this.characteristics);
// Canonical-ize characteristic
characteristic = helpers_1.getCharacteristicUUID(characteristic);
const filtered = this.characteristics.filter(characteristicObject => {
return (characteristicObject.uuid === helpers_1.getCharacteristicUUID(characteristic));
return (characteristicObject.uuid === characteristic);
});

@@ -102,0 +104,0 @@ if (filtered.length !== 1)

{
"name": "webbluetooth",
"version": "1.0.4",
"version": "1.0.5",
"description": "Node.js implementation of the Web Bluetooth Specification",

@@ -5,0 +5,0 @@ "homepage": "https://github.com/thegecko/webbluetooth",

@@ -68,3 +68,3 @@ /*

private charNotifies: {} = {};
private foundFn: (device: Partial<BluetoothDevice>) => void = null;
private discoverFn: (device: noble.Peripheral) => void = null;
private initialised: boolean = false;

@@ -89,5 +89,7 @@ private enabled: boolean = false;

private init(completeFn: () => any) {
private init(completeFn: () => any): void {
if (this.initialised) return completeFn();
noble.on("discover", this.discover.bind(this));
noble.on("discover", deviceInfo => {
if (this.discoverFn) this.discoverFn(deviceInfo);
});
this.initialised = true;

@@ -108,3 +110,3 @@ completeFn();

private bufferToDataView(buffer) {
private bufferToDataView(buffer: Buffer): DataView {
// Buffer to ArrayBuffer

@@ -115,3 +117,3 @@ const arrayBuffer = new Uint8Array(buffer).buffer;

private dataViewToBuffer(dataView) {
private dataViewToBuffer(dataView: DataView): Buffer {
// DataView to TypedArray

@@ -122,43 +124,61 @@ const typedArray = new Uint8Array(dataView.buffer);

private discover(deviceInfo) {
if (this.foundFn) {
const deviceID = (deviceInfo.address && deviceInfo.address !== "unknown") ? deviceInfo.address : deviceInfo.id;
if (!this.deviceHandles[deviceID]) this.deviceHandles[deviceID] = deviceInfo;
private validDevice(deviceInfo: noble.Peripheral, serviceUUIDs: Array<string>): boolean {
if (serviceUUIDs.length === 0) {
// Match any device
return true;
}
const serviceUUIDs = [];
if (deviceInfo.advertisement.serviceUuids) {
deviceInfo.advertisement.serviceUuids.forEach(serviceUUID => {
serviceUUIDs.push(getCanonicalUUID(serviceUUID));
});
}
if (!deviceInfo.advertisement.serviceUuids) {
// No advertised services, no match
return false;
}
const manufacturerData = new Map();
if (deviceInfo.advertisement.manufacturerData) {
// First 2 bytes are 16-bit company identifier
let company = deviceInfo.advertisement.manufacturerData.readUInt16LE(0);
company = ("0000" + company.toString(16)).slice(-4);
// Remove company ID
const buffer = deviceInfo.advertisement.manufacturerData.slice(2);
manufacturerData.set(company, this.bufferToDataView(buffer));
}
const advertisedUUIDs = deviceInfo.advertisement.serviceUuids.map(serviceUUID => {
return getCanonicalUUID(serviceUUID);
});
const serviceData = new Map();
if (deviceInfo.advertisement.serviceData) {
deviceInfo.advertisement.serviceData.forEach(serviceAdvert => {
serviceData.set(getCanonicalUUID(serviceAdvert.uuid), this.bufferToDataView(serviceAdvert.data));
});
}
return serviceUUIDs.some(serviceUUID => {
// An advertised UUID matches our search UUIDs
return (advertisedUUIDs.indexOf(serviceUUID) >= 0);
});
}
this.foundFn({
id: deviceID,
name: deviceInfo.advertisement.localName,
_serviceUUIDs: serviceUUIDs,
adData: {
rssi: deviceInfo.rssi,
txPower: deviceInfo.advertisement.txPowerLevel,
serviceData: serviceData,
manufacturerData: manufacturerData
}
private deviceToBluetoothDevice(deviceInfo): Partial<BluetoothDevice> {
const deviceID = (deviceInfo.address && deviceInfo.address !== "unknown") ? deviceInfo.address : deviceInfo.id;
const serviceUUIDs = [];
if (deviceInfo.advertisement.serviceUuids) {
deviceInfo.advertisement.serviceUuids.forEach(serviceUUID => {
serviceUUIDs.push(getCanonicalUUID(serviceUUID));
});
}
const manufacturerData = new Map();
if (deviceInfo.advertisement.manufacturerData) {
// First 2 bytes are 16-bit company identifier
const company = deviceInfo.advertisement.manufacturerData.readUInt16LE(0);
// Remove company ID
const buffer = deviceInfo.advertisement.manufacturerData.slice(2);
manufacturerData.set(("0000" + company.toString(16)).slice(-4), this.bufferToDataView(buffer));
}
const serviceData = new Map();
if (deviceInfo.advertisement.serviceData) {
deviceInfo.advertisement.serviceData.forEach(serviceAdvert => {
serviceData.set(getCanonicalUUID(serviceAdvert.uuid), this.bufferToDataView(serviceAdvert.data));
});
}
return {
id: deviceID,
name: deviceInfo.advertisement.localName,
_serviceUUIDs: serviceUUIDs,
adData: {
rssi: deviceInfo.rssi,
txPower: deviceInfo.advertisement.txPowerLevel,
serviceData: serviceData,
manufacturerData: manufacturerData
}
};
}

@@ -178,15 +198,14 @@

if (serviceUUIDs.length === 0) {
this.foundFn = foundFn;
} else {
this.foundFn = device => {
serviceUUIDs.forEach(serviceUUID => {
if (device._serviceUUIDs.indexOf(serviceUUID) >= 0) {
foundFn(device);
return;
}
});
};
}
this.discoverFn = deviceInfo => {
if (this.validDevice(deviceInfo, serviceUUIDs)) {
const device = this.deviceToBluetoothDevice(deviceInfo);
if (!this.deviceHandles[device.id]) {
this.deviceHandles[device.id] = deviceInfo;
// Only call the found function the first time we find a valid device
foundFn(device);
}
}
};
this.init(() => {

@@ -196,3 +215,5 @@ this.deviceHandles = {};

if (this.state === true) {
noble.startScanning([], false, this.checkForError(errorFn, completeFn));
// Noble doesn't correctly match short and canonical UUIDs on Linux, so we need to check ourselves
// Continually scan to pick up all advertised UUIDs
noble.startScanning([], true, this.checkForError(errorFn, completeFn));
} else {

@@ -209,3 +230,3 @@ errorFn("adapter not enabled");

public stopScan(_errorFn?: (errorMsg: string) => void): void {
this.foundFn = null;
this.discoverFn = null;
noble.stopScanning();

@@ -212,0 +233,0 @@ }

@@ -72,3 +72,3 @@ /*

rssi?: number;
txPower?: null;
txPower?: number;
serviceData?: Map<string, DataView>;

@@ -75,0 +75,0 @@ manufacturerData?: Map<string, DataView>;

@@ -125,4 +125,7 @@ /*

// Canonical-ize characteristic
characteristic = getCharacteristicUUID(characteristic);
const filtered = this.characteristics.filter(characteristicObject => {
return (characteristicObject.uuid === getCharacteristicUUID(characteristic));
return (characteristicObject.uuid === characteristic);
});

@@ -129,0 +132,0 @@

@@ -37,3 +37,3 @@ /// <reference types="node" />

private charNotifies;
private foundFn;
private discoverFn;
private initialised;

@@ -48,3 +48,4 @@ private enabled;

private dataViewToBuffer(dataView);
private discover(deviceInfo);
private validDevice(deviceInfo, serviceUUIDs);
private deviceToBluetoothDevice(deviceInfo);
getEnabled(completeFn: (enabled: boolean) => void): void;

@@ -51,0 +52,0 @@ startScan(serviceUUIDs: Array<string>, foundFn: (device: Partial<BluetoothDevice>) => void, completeFn?: () => void, errorFn?: (errorMsg: string) => void): void;

@@ -39,3 +39,3 @@ import { EventDispatcher } from "./dispatcher";

rssi?: number;
txPower?: null;
txPower?: number;
serviceData?: Map<string, DataView>;

@@ -42,0 +42,0 @@ manufacturerData?: Map<string, DataView>;

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