usb 2.9.0 → 2.11.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +10 -0
- package/README.md +6 -0
- package/binding.gyp +1 -1
- package/dist/index.js +35 -113
- package/dist/index.js.map +1 -1
- package/dist/usb/bindings.js +2 -2
- package/dist/usb/bindings.js.map +1 -1
- package/dist/usb/capability.js +3 -4
- package/dist/usb/capability.js.map +1 -1
- package/dist/usb/device.js +101 -123
- package/dist/usb/device.js.map +1 -1
- package/dist/usb/endpoint.d.ts +2 -1
- package/dist/usb/endpoint.js +74 -98
- package/dist/usb/endpoint.js.map +1 -1
- package/dist/usb/index.js +26 -59
- package/dist/usb/index.js.map +1 -1
- package/dist/usb/interface.js +41 -44
- package/dist/usb/interface.js.map +1 -1
- package/dist/webusb/index.js +169 -355
- package/dist/webusb/index.js.map +1 -1
- package/dist/webusb/webusb-device.js +367 -751
- package/dist/webusb/webusb-device.js.map +1 -1
- package/package.json +5 -5
- package/prebuilds/android-arm/node.napi.armv7.node +0 -0
- package/prebuilds/android-arm64/node.napi.armv8.node +0 -0
- package/prebuilds/darwin-x64+arm64/node.napi.node +0 -0
- package/prebuilds/linux-arm/node.napi.armv6.node +0 -0
- package/prebuilds/linux-arm/node.napi.armv7.node +0 -0
- package/prebuilds/linux-arm64/node.napi.armv8.node +0 -0
- package/prebuilds/linux-ia32/node.napi.node +0 -0
- package/prebuilds/linux-x64/node.napi.glibc.node +0 -0
- package/prebuilds/linux-x64/node.napi.musl.node +0 -0
- package/prebuilds/win32-ia32/node.napi.node +0 -0
- package/prebuilds/win32-x64/node.napi.node +0 -0
- package/src/device.cc +5 -3
- package/test/usb.coffee +25 -4
- package/test/worker.cjs +5 -1
package/dist/webusb/index.js
CHANGED
|
@@ -1,157 +1,57 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
var __extends = (this && this.__extends) || (function () {
|
|
3
|
-
var extendStatics = function (d, b) {
|
|
4
|
-
extendStatics = Object.setPrototypeOf ||
|
|
5
|
-
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
|
|
6
|
-
function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; };
|
|
7
|
-
return extendStatics(d, b);
|
|
8
|
-
};
|
|
9
|
-
return function (d, b) {
|
|
10
|
-
if (typeof b !== "function" && b !== null)
|
|
11
|
-
throw new TypeError("Class extends value " + String(b) + " is not a constructor or null");
|
|
12
|
-
extendStatics(d, b);
|
|
13
|
-
function __() { this.constructor = d; }
|
|
14
|
-
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
|
|
15
|
-
};
|
|
16
|
-
})();
|
|
17
|
-
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
18
|
-
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
19
|
-
return new (P || (P = Promise))(function (resolve, reject) {
|
|
20
|
-
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
21
|
-
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
22
|
-
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
23
|
-
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
24
|
-
});
|
|
25
|
-
};
|
|
26
|
-
var __generator = (this && this.__generator) || function (thisArg, body) {
|
|
27
|
-
var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;
|
|
28
|
-
return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
|
|
29
|
-
function verb(n) { return function (v) { return step([n, v]); }; }
|
|
30
|
-
function step(op) {
|
|
31
|
-
if (f) throw new TypeError("Generator is already executing.");
|
|
32
|
-
while (_) try {
|
|
33
|
-
if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
|
|
34
|
-
if (y = 0, t) op = [op[0] & 2, t.value];
|
|
35
|
-
switch (op[0]) {
|
|
36
|
-
case 0: case 1: t = op; break;
|
|
37
|
-
case 4: _.label++; return { value: op[1], done: false };
|
|
38
|
-
case 5: _.label++; y = op[1]; op = [0]; continue;
|
|
39
|
-
case 7: op = _.ops.pop(); _.trys.pop(); continue;
|
|
40
|
-
default:
|
|
41
|
-
if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
|
|
42
|
-
if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
|
|
43
|
-
if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
|
|
44
|
-
if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
|
|
45
|
-
if (t[2]) _.ops.pop();
|
|
46
|
-
_.trys.pop(); continue;
|
|
47
|
-
}
|
|
48
|
-
op = body.call(thisArg, _);
|
|
49
|
-
} catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
|
|
50
|
-
if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
|
|
51
|
-
}
|
|
52
|
-
};
|
|
53
|
-
var __values = (this && this.__values) || function(o) {
|
|
54
|
-
var s = typeof Symbol === "function" && Symbol.iterator, m = s && o[s], i = 0;
|
|
55
|
-
if (m) return m.call(o);
|
|
56
|
-
if (o && typeof o.length === "number") return {
|
|
57
|
-
next: function () {
|
|
58
|
-
if (o && i >= o.length) o = void 0;
|
|
59
|
-
return { value: o && o[i++], done: !o };
|
|
60
|
-
}
|
|
61
|
-
};
|
|
62
|
-
throw new TypeError(s ? "Object is not iterable." : "Symbol.iterator is not defined.");
|
|
63
|
-
};
|
|
64
|
-
var __read = (this && this.__read) || function (o, n) {
|
|
65
|
-
var m = typeof Symbol === "function" && o[Symbol.iterator];
|
|
66
|
-
if (!m) return o;
|
|
67
|
-
var i = m.call(o), r, ar = [], e;
|
|
68
|
-
try {
|
|
69
|
-
while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value);
|
|
70
|
-
}
|
|
71
|
-
catch (error) { e = { error: error }; }
|
|
72
|
-
finally {
|
|
73
|
-
try {
|
|
74
|
-
if (r && !r.done && (m = i["return"])) m.call(i);
|
|
75
|
-
}
|
|
76
|
-
finally { if (e) throw e.error; }
|
|
77
|
-
}
|
|
78
|
-
return ar;
|
|
79
|
-
};
|
|
80
|
-
var __spreadArray = (this && this.__spreadArray) || function (to, from) {
|
|
81
|
-
for (var i = 0, il = from.length, j = to.length; i < il; i++, j++)
|
|
82
|
-
to[j] = from[i];
|
|
83
|
-
return to;
|
|
84
|
-
};
|
|
85
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
86
3
|
exports.WebUSB = exports.getWebUsb = void 0;
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
4
|
+
const usb = require("../usb");
|
|
5
|
+
const events_1 = require("events");
|
|
6
|
+
const webusb_device_1 = require("./webusb-device");
|
|
90
7
|
/**
|
|
91
8
|
* Convenience method to get the WebUSB interface available
|
|
92
9
|
*/
|
|
93
|
-
|
|
10
|
+
const getWebUsb = () => {
|
|
94
11
|
if (navigator && navigator.usb) {
|
|
95
12
|
return navigator.usb;
|
|
96
13
|
}
|
|
97
14
|
return new WebUSB();
|
|
98
15
|
};
|
|
99
16
|
exports.getWebUsb = getWebUsb;
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
_this.name = name;
|
|
105
|
-
return _this;
|
|
17
|
+
class NamedError extends Error {
|
|
18
|
+
constructor(message, name) {
|
|
19
|
+
super(message);
|
|
20
|
+
this.name = name;
|
|
106
21
|
}
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
function WebUSB(options) {
|
|
111
|
-
var _this = this;
|
|
112
|
-
if (options === void 0) { options = {}; }
|
|
22
|
+
}
|
|
23
|
+
class WebUSB {
|
|
24
|
+
constructor(options = {}) {
|
|
113
25
|
this.options = options;
|
|
114
26
|
this.emitter = new events_1.EventEmitter();
|
|
115
27
|
this.knownDevices = new Map();
|
|
116
28
|
this.authorisedDevices = new Set();
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
return __generator(this, function (_a) {
|
|
139
|
-
// When disconnected, emit an event if the device was a known allowed device
|
|
140
|
-
if (this.knownDevices.has(device)) {
|
|
141
|
-
webDevice = this.knownDevices.get(device);
|
|
142
|
-
if (webDevice && this.isAuthorisedDevice(webDevice)) {
|
|
143
|
-
event_2 = {
|
|
144
|
-
type: 'disconnect',
|
|
145
|
-
device: webDevice
|
|
146
|
-
};
|
|
147
|
-
this.emitter.emit('disconnect', event_2);
|
|
148
|
-
}
|
|
29
|
+
const deviceConnectCallback = async (device) => {
|
|
30
|
+
const webDevice = await this.getWebDevice(device);
|
|
31
|
+
// When connected, emit an event if it is an allowed device
|
|
32
|
+
if (webDevice && this.isAuthorisedDevice(webDevice)) {
|
|
33
|
+
const event = {
|
|
34
|
+
type: 'connect',
|
|
35
|
+
device: webDevice
|
|
36
|
+
};
|
|
37
|
+
this.emitter.emit('connect', event);
|
|
38
|
+
}
|
|
39
|
+
};
|
|
40
|
+
const deviceDisconnectCallback = async (device) => {
|
|
41
|
+
// When disconnected, emit an event if the device was a known allowed device
|
|
42
|
+
if (this.knownDevices.has(device)) {
|
|
43
|
+
const webDevice = this.knownDevices.get(device);
|
|
44
|
+
if (webDevice && this.isAuthorisedDevice(webDevice)) {
|
|
45
|
+
const event = {
|
|
46
|
+
type: 'disconnect',
|
|
47
|
+
device: webDevice
|
|
48
|
+
};
|
|
49
|
+
this.emitter.emit('disconnect', event);
|
|
149
50
|
}
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
var listenerCount = _this.emitter.listenerCount(event);
|
|
51
|
+
}
|
|
52
|
+
};
|
|
53
|
+
this.emitter.on('newListener', event => {
|
|
54
|
+
const listenerCount = this.emitter.listenerCount(event);
|
|
155
55
|
if (listenerCount !== 0) {
|
|
156
56
|
return;
|
|
157
57
|
}
|
|
@@ -162,8 +62,8 @@ var WebUSB = /** @class */ (function () {
|
|
|
162
62
|
usb.addListener('detach', deviceDisconnectCallback);
|
|
163
63
|
}
|
|
164
64
|
});
|
|
165
|
-
this.emitter.on('removeListener',
|
|
166
|
-
|
|
65
|
+
this.emitter.on('removeListener', event => {
|
|
66
|
+
const listenerCount = this.emitter.listenerCount(event);
|
|
167
67
|
if (listenerCount !== 0) {
|
|
168
68
|
return;
|
|
169
69
|
}
|
|
@@ -175,226 +75,143 @@ var WebUSB = /** @class */ (function () {
|
|
|
175
75
|
}
|
|
176
76
|
});
|
|
177
77
|
}
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
this._ondisconnect = fn;
|
|
200
|
-
this.addEventListener('disconnect', this._ondisconnect);
|
|
201
|
-
}
|
|
202
|
-
},
|
|
203
|
-
enumerable: false,
|
|
204
|
-
configurable: true
|
|
205
|
-
});
|
|
206
|
-
WebUSB.prototype.addEventListener = function (type, listener) {
|
|
78
|
+
set onconnect(fn) {
|
|
79
|
+
if (this._onconnect) {
|
|
80
|
+
this.removeEventListener('connect', this._onconnect);
|
|
81
|
+
this._onconnect = undefined;
|
|
82
|
+
}
|
|
83
|
+
if (fn) {
|
|
84
|
+
this._onconnect = fn;
|
|
85
|
+
this.addEventListener('connect', this._onconnect);
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
set ondisconnect(fn) {
|
|
89
|
+
if (this._ondisconnect) {
|
|
90
|
+
this.removeEventListener('disconnect', this._ondisconnect);
|
|
91
|
+
this._ondisconnect = undefined;
|
|
92
|
+
}
|
|
93
|
+
if (fn) {
|
|
94
|
+
this._ondisconnect = fn;
|
|
95
|
+
this.addEventListener('disconnect', this._ondisconnect);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
addEventListener(type, listener) {
|
|
207
99
|
this.emitter.addListener(type, listener);
|
|
208
|
-
}
|
|
209
|
-
|
|
100
|
+
}
|
|
101
|
+
removeEventListener(type, callback) {
|
|
210
102
|
this.emitter.removeListener(type, callback);
|
|
211
|
-
}
|
|
212
|
-
|
|
103
|
+
}
|
|
104
|
+
dispatchEvent(_event) {
|
|
213
105
|
// Don't dispatch from here
|
|
214
106
|
return false;
|
|
215
|
-
}
|
|
107
|
+
}
|
|
216
108
|
/**
|
|
217
109
|
* Requests a single Web USB device
|
|
218
110
|
* @param options The options to use when scanning
|
|
219
111
|
* @returns Promise containing the selected device
|
|
220
112
|
*/
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
throw new TypeError('requestDevice error: subclass code is required');
|
|
249
|
-
}
|
|
250
|
-
// Subclass & Class
|
|
251
|
-
if (filter.subclassCode && !filter.classCode) {
|
|
252
|
-
throw new TypeError('requestDevice error: class code is required');
|
|
253
|
-
}
|
|
254
|
-
});
|
|
255
|
-
return [4 /*yield*/, this.loadDevices(options.filters)];
|
|
256
|
-
case 1:
|
|
257
|
-
devices = _b.sent();
|
|
258
|
-
devices = devices.filter(function (device) { return _this.filterDevice(device, options.filters); });
|
|
259
|
-
if (devices.length === 0) {
|
|
260
|
-
throw new NamedError('Failed to execute \'requestDevice\' on \'USB\': No device selected.', 'NotFoundError');
|
|
261
|
-
}
|
|
262
|
-
_b.label = 2;
|
|
263
|
-
case 2:
|
|
264
|
-
_b.trys.push([2, 6, , 7]);
|
|
265
|
-
if (!this.options.devicesFound) return [3 /*break*/, 4];
|
|
266
|
-
return [4 /*yield*/, this.options.devicesFound(devices)];
|
|
267
|
-
case 3:
|
|
268
|
-
_a = _b.sent();
|
|
269
|
-
return [3 /*break*/, 5];
|
|
270
|
-
case 4:
|
|
271
|
-
_a = devices[0];
|
|
272
|
-
_b.label = 5;
|
|
273
|
-
case 5:
|
|
274
|
-
device = _a;
|
|
275
|
-
if (!device) {
|
|
276
|
-
throw new NamedError('Failed to execute \'requestDevice\' on \'USB\': No device selected.', 'NotFoundError');
|
|
277
|
-
}
|
|
278
|
-
this.authorisedDevices.add({
|
|
279
|
-
vendorId: device.vendorId,
|
|
280
|
-
productId: device.productId,
|
|
281
|
-
classCode: device.deviceClass,
|
|
282
|
-
subclassCode: device.deviceSubclass,
|
|
283
|
-
protocolCode: device.deviceProtocol,
|
|
284
|
-
serialNumber: device.serialNumber
|
|
285
|
-
});
|
|
286
|
-
return [2 /*return*/, device];
|
|
287
|
-
case 6:
|
|
288
|
-
error_1 = _b.sent();
|
|
289
|
-
throw new NamedError('Failed to execute \'requestDevice\' on \'USB\': No device selected.', 'NotFoundError');
|
|
290
|
-
case 7: return [2 /*return*/];
|
|
291
|
-
}
|
|
292
|
-
});
|
|
113
|
+
async requestDevice(options) {
|
|
114
|
+
// Must have options
|
|
115
|
+
if (!options) {
|
|
116
|
+
throw new TypeError('requestDevice error: 1 argument required, but only 0 present');
|
|
117
|
+
}
|
|
118
|
+
// Options must be an object
|
|
119
|
+
if (options.constructor !== {}.constructor) {
|
|
120
|
+
throw new TypeError('requestDevice error: parameter 1 (options) is not an object');
|
|
121
|
+
}
|
|
122
|
+
// Must have a filter
|
|
123
|
+
if (!options.filters) {
|
|
124
|
+
throw new TypeError('requestDevice error: required member filters is undefined');
|
|
125
|
+
}
|
|
126
|
+
// Filter must be an array
|
|
127
|
+
if (options.filters.constructor !== [].constructor) {
|
|
128
|
+
throw new TypeError('requestDevice error: the provided value cannot be converted to a sequence');
|
|
129
|
+
}
|
|
130
|
+
// Check filters
|
|
131
|
+
options.filters.forEach(filter => {
|
|
132
|
+
// Protocol & Subclass
|
|
133
|
+
if (filter.protocolCode && !filter.subclassCode) {
|
|
134
|
+
throw new TypeError('requestDevice error: subclass code is required');
|
|
135
|
+
}
|
|
136
|
+
// Subclass & Class
|
|
137
|
+
if (filter.subclassCode && !filter.classCode) {
|
|
138
|
+
throw new TypeError('requestDevice error: class code is required');
|
|
139
|
+
}
|
|
293
140
|
});
|
|
294
|
-
|
|
141
|
+
let devices = await this.loadDevices(options.filters);
|
|
142
|
+
devices = devices.filter(device => this.filterDevice(device, options.filters));
|
|
143
|
+
if (devices.length === 0) {
|
|
144
|
+
throw new NamedError('Failed to execute \'requestDevice\' on \'USB\': No device selected.', 'NotFoundError');
|
|
145
|
+
}
|
|
146
|
+
try {
|
|
147
|
+
// If no devicesFound function, select the first device found
|
|
148
|
+
const device = this.options.devicesFound ? await this.options.devicesFound(devices) : devices[0];
|
|
149
|
+
if (!device) {
|
|
150
|
+
throw new NamedError('Failed to execute \'requestDevice\' on \'USB\': No device selected.', 'NotFoundError');
|
|
151
|
+
}
|
|
152
|
+
this.authorisedDevices.add({
|
|
153
|
+
vendorId: device.vendorId,
|
|
154
|
+
productId: device.productId,
|
|
155
|
+
classCode: device.deviceClass,
|
|
156
|
+
subclassCode: device.deviceSubclass,
|
|
157
|
+
protocolCode: device.deviceProtocol,
|
|
158
|
+
serialNumber: device.serialNumber
|
|
159
|
+
});
|
|
160
|
+
return device;
|
|
161
|
+
}
|
|
162
|
+
catch (error) {
|
|
163
|
+
throw new NamedError('Failed to execute \'requestDevice\' on \'USB\': No device selected.', 'NotFoundError');
|
|
164
|
+
}
|
|
165
|
+
}
|
|
295
166
|
/**
|
|
296
167
|
* Gets all allowed Web USB devices which are connected
|
|
297
168
|
* @returns Promise containing an array of devices
|
|
298
169
|
*/
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
switch (_b.label) {
|
|
321
|
-
case 0:
|
|
322
|
-
devices = usb.getDeviceList();
|
|
323
|
-
// Pre-filter devices
|
|
324
|
-
devices = this.quickFilter(devices, preFilters);
|
|
325
|
-
refreshedKnownDevices = new Map();
|
|
326
|
-
_b.label = 1;
|
|
327
|
-
case 1:
|
|
328
|
-
_b.trys.push([1, 6, 7, 8]);
|
|
329
|
-
devices_1 = __values(devices), devices_1_1 = devices_1.next();
|
|
330
|
-
_b.label = 2;
|
|
331
|
-
case 2:
|
|
332
|
-
if (!!devices_1_1.done) return [3 /*break*/, 5];
|
|
333
|
-
device = devices_1_1.value;
|
|
334
|
-
return [4 /*yield*/, this.getWebDevice(device)];
|
|
335
|
-
case 3:
|
|
336
|
-
webDevice = _b.sent();
|
|
337
|
-
if (webDevice) {
|
|
338
|
-
refreshedKnownDevices.set(device, webDevice);
|
|
339
|
-
}
|
|
340
|
-
_b.label = 4;
|
|
341
|
-
case 4:
|
|
342
|
-
devices_1_1 = devices_1.next();
|
|
343
|
-
return [3 /*break*/, 2];
|
|
344
|
-
case 5: return [3 /*break*/, 8];
|
|
345
|
-
case 6:
|
|
346
|
-
e_1_1 = _b.sent();
|
|
347
|
-
e_1 = { error: e_1_1 };
|
|
348
|
-
return [3 /*break*/, 8];
|
|
349
|
-
case 7:
|
|
350
|
-
try {
|
|
351
|
-
if (devices_1_1 && !devices_1_1.done && (_a = devices_1.return)) _a.call(devices_1);
|
|
352
|
-
}
|
|
353
|
-
finally { if (e_1) throw e_1.error; }
|
|
354
|
-
return [7 /*endfinally*/];
|
|
355
|
-
case 8:
|
|
356
|
-
// Refresh knownDevices to remove old devices from the map
|
|
357
|
-
this.knownDevices = refreshedKnownDevices;
|
|
358
|
-
return [2 /*return*/, __spreadArray([], __read(this.knownDevices.values()))];
|
|
359
|
-
}
|
|
360
|
-
});
|
|
361
|
-
});
|
|
362
|
-
};
|
|
170
|
+
async getDevices() {
|
|
171
|
+
const preFilters = this.options.allowAllDevices ? undefined : this.options.allowedDevices;
|
|
172
|
+
// Refresh devices and filter for allowed ones
|
|
173
|
+
const devices = await this.loadDevices(preFilters);
|
|
174
|
+
return devices.filter(device => this.isAuthorisedDevice(device));
|
|
175
|
+
}
|
|
176
|
+
async loadDevices(preFilters) {
|
|
177
|
+
let devices = usb.getDeviceList();
|
|
178
|
+
// Pre-filter devices
|
|
179
|
+
devices = this.quickFilter(devices, preFilters);
|
|
180
|
+
const refreshedKnownDevices = new Map();
|
|
181
|
+
for (const device of devices) {
|
|
182
|
+
const webDevice = await this.getWebDevice(device);
|
|
183
|
+
if (webDevice) {
|
|
184
|
+
refreshedKnownDevices.set(device, webDevice);
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
// Refresh knownDevices to remove old devices from the map
|
|
188
|
+
this.knownDevices = refreshedKnownDevices;
|
|
189
|
+
return [...this.knownDevices.values()];
|
|
190
|
+
}
|
|
363
191
|
// Get a WebUSBDevice corresponding to underlying device.
|
|
364
192
|
// Returns undefined the device was not found and could not be created.
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
webDevice = _b.sent();
|
|
381
|
-
this.knownDevices.set(device, webDevice);
|
|
382
|
-
return [3 /*break*/, 4];
|
|
383
|
-
case 3:
|
|
384
|
-
_a = _b.sent();
|
|
385
|
-
return [3 /*break*/, 4];
|
|
386
|
-
case 4: return [2 /*return*/, this.knownDevices.get(device)];
|
|
387
|
-
}
|
|
388
|
-
});
|
|
389
|
-
});
|
|
390
|
-
};
|
|
193
|
+
async getWebDevice(device) {
|
|
194
|
+
if (!this.knownDevices.has(device)) {
|
|
195
|
+
if (this.options.deviceTimeout) {
|
|
196
|
+
device.timeout = this.options.deviceTimeout;
|
|
197
|
+
}
|
|
198
|
+
try {
|
|
199
|
+
const webDevice = await webusb_device_1.WebUSBDevice.createInstance(device);
|
|
200
|
+
this.knownDevices.set(device, webDevice);
|
|
201
|
+
}
|
|
202
|
+
catch {
|
|
203
|
+
// Ignore creation issues as this may be a system device
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
return this.knownDevices.get(device);
|
|
207
|
+
}
|
|
391
208
|
// Undertake quick filter on devices before creating WebUSB devices if possible
|
|
392
|
-
|
|
209
|
+
quickFilter(devices, preFilters) {
|
|
393
210
|
if (!preFilters || !preFilters.length) {
|
|
394
211
|
return devices;
|
|
395
212
|
}
|
|
396
213
|
// Just pre-filter on vid/pid
|
|
397
|
-
return devices.filter(
|
|
214
|
+
return devices.filter(device => preFilters.some(filter => {
|
|
398
215
|
// Vendor
|
|
399
216
|
if (filter.vendorId && filter.vendorId !== device.deviceDescriptor.idVendor)
|
|
400
217
|
return false;
|
|
@@ -404,14 +221,14 @@ var WebUSB = /** @class */ (function () {
|
|
|
404
221
|
// Ignore Class, Subclass and Protocol as these need to check interfaces, too
|
|
405
222
|
// Ignore serial number for node-usb as it requires device connection
|
|
406
223
|
return true;
|
|
407
|
-
})
|
|
408
|
-
}
|
|
224
|
+
}));
|
|
225
|
+
}
|
|
409
226
|
// Filter WebUSB devices
|
|
410
|
-
|
|
227
|
+
filterDevice(device, filters) {
|
|
411
228
|
if (!filters || !filters.length) {
|
|
412
229
|
return true;
|
|
413
230
|
}
|
|
414
|
-
return filters.some(
|
|
231
|
+
return filters.some(filter => {
|
|
415
232
|
// Vendor
|
|
416
233
|
if (filter.vendorId && filter.vendorId !== device.vendorId)
|
|
417
234
|
return false;
|
|
@@ -424,7 +241,7 @@ var WebUSB = /** @class */ (function () {
|
|
|
424
241
|
return false;
|
|
425
242
|
}
|
|
426
243
|
// Interface Descriptors
|
|
427
|
-
|
|
244
|
+
const match = device.configuration.interfaces.some(iface => {
|
|
428
245
|
// Class
|
|
429
246
|
if (filter.classCode && filter.classCode !== iface.alternate.interfaceClass)
|
|
430
247
|
return false;
|
|
@@ -454,9 +271,9 @@ var WebUSB = /** @class */ (function () {
|
|
|
454
271
|
return false;
|
|
455
272
|
return true;
|
|
456
273
|
});
|
|
457
|
-
}
|
|
274
|
+
}
|
|
458
275
|
// Check whether a device is authorised
|
|
459
|
-
|
|
276
|
+
isAuthorisedDevice(device) {
|
|
460
277
|
// All devices are authorised
|
|
461
278
|
if (this.options.allowAllDevices) {
|
|
462
279
|
return true;
|
|
@@ -466,16 +283,13 @@ var WebUSB = /** @class */ (function () {
|
|
|
466
283
|
return true;
|
|
467
284
|
}
|
|
468
285
|
// Check authorised devices
|
|
469
|
-
return
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
};
|
|
478
|
-
return WebUSB;
|
|
479
|
-
}());
|
|
286
|
+
return [...this.authorisedDevices.values()].some(authorised => authorised.vendorId === device.vendorId
|
|
287
|
+
&& authorised.productId === device.productId
|
|
288
|
+
&& authorised.classCode === device.deviceClass
|
|
289
|
+
&& authorised.subclassCode === device.deviceSubclass
|
|
290
|
+
&& authorised.protocolCode === device.deviceProtocol
|
|
291
|
+
&& authorised.serialNumber === device.serialNumber);
|
|
292
|
+
}
|
|
293
|
+
}
|
|
480
294
|
exports.WebUSB = WebUSB;
|
|
481
295
|
//# sourceMappingURL=index.js.map
|