stagelinq 3.0.4 → 3.1.2
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/README.md +2 -1
- package/dist/Databases/Databases.d.ts +3 -1
- package/dist/Databases/Databases.js +9 -8
- package/dist/Databases/Databases.js.map +1 -1
- package/dist/Databases/DbConnection.d.ts +3 -1
- package/dist/Databases/DbConnection.js +6 -4
- package/dist/Databases/DbConnection.js.map +1 -1
- package/dist/StageLinq/index.d.ts +1 -1
- package/dist/StageLinq/index.js +8 -8
- package/dist/StageLinq/index.js.map +1 -1
- package/dist/devices/Player.d.ts +3 -0
- package/dist/devices/Player.js +15 -6
- package/dist/devices/Player.js.map +1 -1
- package/dist/eaas/beacon.d.ts +3 -1
- package/dist/eaas/beacon.js +10 -9
- package/dist/eaas/beacon.js.map +1 -1
- package/dist/eaas/discoverer.d.ts +3 -1
- package/dist/eaas/discoverer.js +16 -12
- package/dist/eaas/discoverer.js.map +1 -1
- package/dist/eaas/engine-library-client.d.ts +3 -1
- package/dist/eaas/engine-library-client.js +7 -6
- package/dist/eaas/engine-library-client.js.map +1 -1
- package/dist/eaas/http-client.d.ts +3 -1
- package/dist/eaas/http-client.js +5 -4
- package/dist/eaas/http-client.js.map +1 -1
- package/dist/index.d.ts +2 -0
- package/dist/index.js +4 -1
- package/dist/index.js.map +1 -1
- package/dist/metadata/index.d.ts +26 -0
- package/dist/metadata/index.js +53 -0
- package/dist/metadata/index.js.map +1 -0
- package/dist/metadata/reader.d.ts +11 -0
- package/dist/metadata/reader.js +20 -0
- package/dist/metadata/reader.js.map +1 -0
- package/dist/network/ConnectionHealth.d.ts +3 -1
- package/dist/network/ConnectionHealth.js +13 -12
- package/dist/network/ConnectionHealth.js.map +1 -1
- package/dist/network/NetworkDevice.d.ts +4 -2
- package/dist/network/NetworkDevice.js +9 -8
- package/dist/network/NetworkDevice.js.map +1 -1
- package/dist/network/StageLinqDevices.d.ts +12 -2
- package/dist/network/StageLinqDevices.js +59 -25
- package/dist/network/StageLinqDevices.js.map +1 -1
- package/dist/network/announce.d.ts +3 -2
- package/dist/network/announce.js +40 -15
- package/dist/network/announce.js.map +1 -1
- package/dist/services/FileTransfer.d.ts +14 -0
- package/dist/services/FileTransfer.js +86 -6
- package/dist/services/FileTransfer.js.map +1 -1
- package/dist/services/Service.d.ts +3 -1
- package/dist/services/Service.js +7 -6
- package/dist/services/Service.js.map +1 -1
- package/dist/services/StateMap.js +0 -1
- package/dist/services/StateMap.js.map +1 -1
- package/dist/services/TimeSync.js +2 -3
- package/dist/services/TimeSync.js.map +1 -1
- package/dist/types/index.d.ts +4 -0
- package/dist/types/index.js +1 -0
- package/dist/types/index.js.map +1 -1
- package/dist/types/logger.d.ts +13 -0
- package/dist/types/logger.js +11 -0
- package/dist/types/logger.js.map +1 -0
- package/dist/utils/tcp.d.ts +2 -1
- package/dist/utils/tcp.js +3 -3
- package/dist/utils/tcp.js.map +1 -1
- package/package.json +5 -1
- package/dist/LogEmitter/index.d.ts +0 -20
- package/dist/LogEmitter/index.js +0 -35
- package/dist/LogEmitter/index.js.map +0 -1
package/dist/eaas/discoverer.js
CHANGED
|
@@ -15,7 +15,7 @@ const dgram_1 = require("dgram");
|
|
|
15
15
|
const events_1 = require("events");
|
|
16
16
|
const os_1 = require("os");
|
|
17
17
|
const ip_1 = require("ip");
|
|
18
|
-
const
|
|
18
|
+
const logger_1 = require("../types/logger");
|
|
19
19
|
const types_1 = require("./types");
|
|
20
20
|
const messages_1 = require("./messages");
|
|
21
21
|
const DEFAULT_TIMEOUT = 5000;
|
|
@@ -44,11 +44,12 @@ const DEFAULT_SCAN_INTERVAL = 10000;
|
|
|
44
44
|
* ```
|
|
45
45
|
*/
|
|
46
46
|
class EAASDiscoverer extends events_1.EventEmitter {
|
|
47
|
-
constructor(options = {}) {
|
|
47
|
+
constructor(options = {}, logger = logger_1.noopLogger) {
|
|
48
48
|
super();
|
|
49
49
|
this.socket = null;
|
|
50
50
|
this.scanTimer = null;
|
|
51
51
|
this.discoveredDevices = new Map();
|
|
52
|
+
this.logger = logger;
|
|
52
53
|
this.options = {
|
|
53
54
|
timeout: options.timeout ?? DEFAULT_TIMEOUT,
|
|
54
55
|
scanInterval: options.scanInterval ?? DEFAULT_SCAN_INTERVAL,
|
|
@@ -74,7 +75,7 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
74
75
|
*/
|
|
75
76
|
async startScanning() {
|
|
76
77
|
if (this.scanTimer) {
|
|
77
|
-
|
|
78
|
+
this.logger.warn('EAAS: Already scanning');
|
|
78
79
|
return;
|
|
79
80
|
}
|
|
80
81
|
await this.initSocket();
|
|
@@ -89,7 +90,7 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
89
90
|
this.emit('error', err);
|
|
90
91
|
}
|
|
91
92
|
}, this.options.scanInterval);
|
|
92
|
-
|
|
93
|
+
this.logger.info('EAAS: Started scanning for devices');
|
|
93
94
|
}
|
|
94
95
|
/**
|
|
95
96
|
* Stop continuous scanning.
|
|
@@ -100,7 +101,7 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
100
101
|
this.scanTimer = null;
|
|
101
102
|
}
|
|
102
103
|
this.closeSocket();
|
|
103
|
-
|
|
104
|
+
this.logger.info('EAAS: Stopped scanning for devices');
|
|
104
105
|
}
|
|
105
106
|
/**
|
|
106
107
|
* Get all discovered devices.
|
|
@@ -119,7 +120,7 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
119
120
|
try {
|
|
120
121
|
this.socket = (0, dgram_1.createSocket)({ type: 'udp4', reuseAddr: true });
|
|
121
122
|
this.socket.on('error', (err) => {
|
|
122
|
-
|
|
123
|
+
this.logger.error(`EAAS discovery socket error: ${err}`);
|
|
123
124
|
this.emit('error', err);
|
|
124
125
|
});
|
|
125
126
|
this.socket.on('message', (msg, rinfo) => {
|
|
@@ -145,7 +146,7 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
145
146
|
this.socket.close();
|
|
146
147
|
}
|
|
147
148
|
catch (err) {
|
|
148
|
-
|
|
149
|
+
this.logger.warn(`EAAS: Error closing socket: ${err}`);
|
|
149
150
|
}
|
|
150
151
|
this.socket = null;
|
|
151
152
|
}
|
|
@@ -157,12 +158,12 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
157
158
|
const request = (0, messages_1.createDiscoveryRequest)();
|
|
158
159
|
const targets = this.getBroadcastTargets();
|
|
159
160
|
if (targets.length === 0) {
|
|
160
|
-
|
|
161
|
+
this.logger.warn('EAAS: No broadcast targets found');
|
|
161
162
|
return;
|
|
162
163
|
}
|
|
163
164
|
const promises = targets.map((target) => this.sendTo(request, target));
|
|
164
165
|
await Promise.all(promises);
|
|
165
|
-
|
|
166
|
+
this.logger.debug(`EAAS: Broadcast discovery request to ${targets.length} interfaces`);
|
|
166
167
|
}
|
|
167
168
|
/**
|
|
168
169
|
* Send data to a specific broadcast address.
|
|
@@ -175,7 +176,7 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
175
176
|
}
|
|
176
177
|
this.socket.send(data, types_1.EAAS_DISCOVERY_PORT, address, (err) => {
|
|
177
178
|
if (err) {
|
|
178
|
-
|
|
179
|
+
this.logger.warn(`EAAS: Failed to send to ${address}: ${err}`);
|
|
179
180
|
}
|
|
180
181
|
resolve();
|
|
181
182
|
});
|
|
@@ -193,7 +194,7 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
193
194
|
const key = `${device.address}:${device.grpcPort}`;
|
|
194
195
|
if (!this.discoveredDevices.has(key)) {
|
|
195
196
|
this.discoveredDevices.set(key, device);
|
|
196
|
-
|
|
197
|
+
this.logger.info(`EAAS: Discovered device: ${device.hostname} at ${device.address}:${device.grpcPort}`);
|
|
197
198
|
this.emit('discovered', device);
|
|
198
199
|
}
|
|
199
200
|
}
|
|
@@ -208,12 +209,15 @@ class EAASDiscoverer extends events_1.EventEmitter {
|
|
|
208
209
|
continue;
|
|
209
210
|
for (const entry of iface) {
|
|
210
211
|
if (entry.family === 'IPv4' && !entry.internal) {
|
|
212
|
+
// Skip link-local addresses (169.254.x.x)
|
|
213
|
+
if (entry.address.startsWith('169.254.'))
|
|
214
|
+
continue;
|
|
211
215
|
try {
|
|
212
216
|
const info = (0, ip_1.subnet)(entry.address, entry.netmask);
|
|
213
217
|
targets.push(info.broadcastAddress);
|
|
214
218
|
}
|
|
215
219
|
catch (err) {
|
|
216
|
-
|
|
220
|
+
this.logger.warn(`EAAS: Failed to get broadcast for ${entry.address}: ${err}`);
|
|
217
221
|
}
|
|
218
222
|
}
|
|
219
223
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"discoverer.js","sourceRoot":"","sources":["../../eaas/discoverer.ts"],"names":[],"mappings":";AAAA;;;;;;;;;GASG;;;AAEH,iCAAsE;AACtE,mCAAsC;AACtC,2BAAuC;AACvC,2BAA4B;
|
|
1
|
+
{"version":3,"file":"discoverer.js","sourceRoot":"","sources":["../../eaas/discoverer.ts"],"names":[],"mappings":"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"}
|
|
@@ -15,6 +15,7 @@
|
|
|
15
15
|
* License: MIT
|
|
16
16
|
*/
|
|
17
17
|
import { EventEmitter } from 'events';
|
|
18
|
+
import type { Logger } from '../types/logger';
|
|
18
19
|
import { EAASDevice } from './types';
|
|
19
20
|
import { GetLibrariesRequest, GetLibrariesResponse, GetLibraryRequest, GetLibraryResponse, GetTracksRequest, GetTracksResponse, GetTrackRequest, GetTrackResponse, SearchTracksRequest, SearchTracksResponse, GetSearchFiltersRequest, GetSearchFiltersResponse, GetHistorySessionsRequest, GetHistorySessionsResponse, GetHistoryPlayedTracksRequest, GetHistoryPlayedTracksResponse, EventStreamRequest, LibraryEvent } from './grpc-types';
|
|
20
21
|
export interface EngineLibraryClientOptions {
|
|
@@ -53,7 +54,8 @@ export declare class EngineLibraryClient extends EventEmitter {
|
|
|
53
54
|
private device;
|
|
54
55
|
private _options;
|
|
55
56
|
private connected;
|
|
56
|
-
|
|
57
|
+
private logger;
|
|
58
|
+
constructor(device: EAASDevice, options?: EngineLibraryClientOptions, logger?: Logger);
|
|
57
59
|
/**
|
|
58
60
|
* Get the client options.
|
|
59
61
|
*/
|
|
@@ -18,7 +18,7 @@
|
|
|
18
18
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
19
19
|
exports.EngineLibraryClient = void 0;
|
|
20
20
|
const events_1 = require("events");
|
|
21
|
-
const
|
|
21
|
+
const logger_1 = require("../types/logger");
|
|
22
22
|
/**
|
|
23
23
|
* Engine Library gRPC Client
|
|
24
24
|
*
|
|
@@ -43,13 +43,14 @@ const LogEmitter_1 = require("../LogEmitter");
|
|
|
43
43
|
*/
|
|
44
44
|
class EngineLibraryClient extends events_1.EventEmitter {
|
|
45
45
|
// private grpcClient: any = null; // Placeholder for actual gRPC client
|
|
46
|
-
constructor(device, options = {}) {
|
|
46
|
+
constructor(device, options = {}, logger = logger_1.noopLogger) {
|
|
47
47
|
super();
|
|
48
48
|
this.connected = false;
|
|
49
49
|
this.device = device;
|
|
50
50
|
this._options = {
|
|
51
51
|
timeout: options.timeout ?? 10000,
|
|
52
52
|
};
|
|
53
|
+
this.logger = logger;
|
|
53
54
|
}
|
|
54
55
|
/**
|
|
55
56
|
* Get the client options.
|
|
@@ -76,11 +77,11 @@ class EngineLibraryClient extends events_1.EventEmitter {
|
|
|
76
77
|
*/
|
|
77
78
|
async connect() {
|
|
78
79
|
if (this.connected) {
|
|
79
|
-
|
|
80
|
+
this.logger.warn('EAAS: Already connected');
|
|
80
81
|
return;
|
|
81
82
|
}
|
|
82
83
|
const endpoint = `${this.device.address}:${this.device.grpcPort}`;
|
|
83
|
-
|
|
84
|
+
this.logger.info(`EAAS: Connecting to ${endpoint}`);
|
|
84
85
|
// TODO: Implement actual gRPC connection
|
|
85
86
|
// This requires @grpc/grpc-js and generated proto bindings
|
|
86
87
|
//
|
|
@@ -109,7 +110,7 @@ class EngineLibraryClient extends events_1.EventEmitter {
|
|
|
109
110
|
// this.grpcClient = null;
|
|
110
111
|
this.connected = false;
|
|
111
112
|
this.emit('disconnected');
|
|
112
|
-
|
|
113
|
+
this.logger.info('EAAS: Disconnected');
|
|
113
114
|
}
|
|
114
115
|
/**
|
|
115
116
|
* Get all available music libraries.
|
|
@@ -188,7 +189,7 @@ class EngineLibraryClient extends events_1.EventEmitter {
|
|
|
188
189
|
// }
|
|
189
190
|
// });
|
|
190
191
|
// stream.on('error', (err) => this.emit('error', err));
|
|
191
|
-
// stream.on('end', () =>
|
|
192
|
+
// stream.on('end', () => this.logger.info('EAAS: Event stream ended'));
|
|
192
193
|
throw new Error('gRPC not implemented');
|
|
193
194
|
}
|
|
194
195
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"engine-library-client.js","sourceRoot":"","sources":["../../eaas/engine-library-client.ts"],"names":[],"mappings":";AAAA;;;;;;;;;;;;;;;GAeG;;;AAEH,mCAAsC;
|
|
1
|
+
{"version":3,"file":"engine-library-client.js","sourceRoot":"","sources":["../../eaas/engine-library-client.ts"],"names":[],"mappings":"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"}
|
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
* Original: https://github.com/icedream/go-stagelinq
|
|
9
9
|
* License: MIT
|
|
10
10
|
*/
|
|
11
|
+
import type { Logger } from '../types/logger';
|
|
11
12
|
import { EAASDevice } from './types';
|
|
12
13
|
export interface EAASHttpClientOptions {
|
|
13
14
|
/** Request timeout in milliseconds */
|
|
@@ -36,7 +37,8 @@ export declare class EAASHttpClient {
|
|
|
36
37
|
private device;
|
|
37
38
|
private options;
|
|
38
39
|
private baseUrl;
|
|
39
|
-
|
|
40
|
+
private logger;
|
|
41
|
+
constructor(device: EAASDevice, options?: EAASHttpClientOptions, logger?: Logger);
|
|
40
42
|
/**
|
|
41
43
|
* Get the device this client is connected to.
|
|
42
44
|
*/
|
package/dist/eaas/http-client.js
CHANGED
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
*/
|
|
12
12
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
13
13
|
exports.EAASHttpClient = void 0;
|
|
14
|
-
const
|
|
14
|
+
const logger_1 = require("../types/logger");
|
|
15
15
|
/**
|
|
16
16
|
* EAAS HTTP Client
|
|
17
17
|
*
|
|
@@ -32,12 +32,13 @@ const LogEmitter_1 = require("../LogEmitter");
|
|
|
32
32
|
* ```
|
|
33
33
|
*/
|
|
34
34
|
class EAASHttpClient {
|
|
35
|
-
constructor(device, options = {}) {
|
|
35
|
+
constructor(device, options = {}, logger = logger_1.noopLogger) {
|
|
36
36
|
this.device = device;
|
|
37
37
|
this.options = {
|
|
38
38
|
timeout: options.timeout ?? 30000,
|
|
39
39
|
};
|
|
40
40
|
this.baseUrl = `http://${device.address}:${device.httpPort}`;
|
|
41
|
+
this.logger = logger;
|
|
41
42
|
}
|
|
42
43
|
/**
|
|
43
44
|
* Get the device this client is connected to.
|
|
@@ -64,7 +65,7 @@ class EAASHttpClient {
|
|
|
64
65
|
return response.ok;
|
|
65
66
|
}
|
|
66
67
|
catch (err) {
|
|
67
|
-
|
|
68
|
+
this.logger.debug(`EAAS HTTP: Ping failed: ${err}`);
|
|
68
69
|
return false;
|
|
69
70
|
}
|
|
70
71
|
}
|
|
@@ -112,7 +113,7 @@ class EAASHttpClient {
|
|
|
112
113
|
return { size, contentType };
|
|
113
114
|
}
|
|
114
115
|
catch (err) {
|
|
115
|
-
|
|
116
|
+
this.logger.debug(`EAAS HTTP: Failed to get file info: ${err}`);
|
|
116
117
|
return null;
|
|
117
118
|
}
|
|
118
119
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"http-client.js","sourceRoot":"","sources":["../../eaas/http-client.ts"],"names":[],"mappings":";AAAA;;;;;;;;;GASG;;;
|
|
1
|
+
{"version":3,"file":"http-client.js","sourceRoot":"","sources":["../../eaas/http-client.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -36,7 +36,7 @@ var __importStar = (this && this.__importStar) || (function () {
|
|
|
36
36
|
};
|
|
37
37
|
})();
|
|
38
38
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
39
|
-
exports.EAAS = void 0;
|
|
39
|
+
exports.extractMetadataFromDevice = exports.EAAS = void 0;
|
|
40
40
|
__exportStar(require("./config"), exports);
|
|
41
41
|
__exportStar(require("./network"), exports);
|
|
42
42
|
__exportStar(require("./services"), exports);
|
|
@@ -45,4 +45,7 @@ __exportStar(require("./types"), exports);
|
|
|
45
45
|
__exportStar(require("./utils"), exports);
|
|
46
46
|
// Export EAAS as a namespace to avoid name conflicts
|
|
47
47
|
exports.EAAS = __importStar(require("./eaas"));
|
|
48
|
+
// Export metadata extraction
|
|
49
|
+
var metadata_1 = require("./metadata");
|
|
50
|
+
Object.defineProperty(exports, "extractMetadataFromDevice", { enumerable: true, get: function () { return metadata_1.extractMetadataFromDevice; } });
|
|
48
51
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,2CAAyB;AACzB,4CAA0B;AAC1B,6CAA2B;AAC3B,8CAA4B;AAC5B,0CAAwB;AACxB,0CAAwB;AAExB,qDAAqD;AACrD,+CAA+B"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,2CAAyB;AACzB,4CAA0B;AAC1B,6CAA2B;AAC3B,8CAA4B;AAC5B,0CAAwB;AACxB,0CAAwB;AAExB,qDAAqD;AACrD,+CAA+B;AAE/B,6BAA6B;AAC7B,uCAAuD;AAA9C,qHAAA,yBAAyB,OAAA"}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import type { ExtractedMetadata } from 'metadata-connect';
|
|
2
|
+
import type { FileTransfer } from '../services/FileTransfer';
|
|
3
|
+
export type { ExtractedMetadata } from 'metadata-connect';
|
|
4
|
+
/**
|
|
5
|
+
* Extract metadata from an audio file on a StageLinQ device
|
|
6
|
+
*
|
|
7
|
+
* This function reads only the necessary bytes from the file header,
|
|
8
|
+
* avoiding the need to transfer entire audio files over the network.
|
|
9
|
+
*
|
|
10
|
+
* @param fileTransfer - The FileTransfer service connected to the device
|
|
11
|
+
* @param networkPath - The file path on the device (from TrackNetworkPath signal)
|
|
12
|
+
* @returns Extracted metadata, or null if extraction fails
|
|
13
|
+
*
|
|
14
|
+
* @example
|
|
15
|
+
* ```typescript
|
|
16
|
+
* // When a track is loaded, extract its metadata
|
|
17
|
+
* const metadata = await extractMetadataFromDevice(fileTransfer, trackNetworkPath);
|
|
18
|
+
* if (metadata) {
|
|
19
|
+
* console.log(metadata.title, metadata.artist);
|
|
20
|
+
* if (metadata.artwork) {
|
|
21
|
+
* // Display artwork
|
|
22
|
+
* }
|
|
23
|
+
* }
|
|
24
|
+
* ```
|
|
25
|
+
*/
|
|
26
|
+
export declare function extractMetadataFromDevice(fileTransfer: FileTransfer, networkPath: string): Promise<ExtractedMetadata | null>;
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.extractMetadataFromDevice = extractMetadataFromDevice;
|
|
4
|
+
const metadata_connect_1 = require("metadata-connect");
|
|
5
|
+
const reader_1 = require("./reader");
|
|
6
|
+
/**
|
|
7
|
+
* Extract metadata from an audio file on a StageLinQ device
|
|
8
|
+
*
|
|
9
|
+
* This function reads only the necessary bytes from the file header,
|
|
10
|
+
* avoiding the need to transfer entire audio files over the network.
|
|
11
|
+
*
|
|
12
|
+
* @param fileTransfer - The FileTransfer service connected to the device
|
|
13
|
+
* @param networkPath - The file path on the device (from TrackNetworkPath signal)
|
|
14
|
+
* @returns Extracted metadata, or null if extraction fails
|
|
15
|
+
*
|
|
16
|
+
* @example
|
|
17
|
+
* ```typescript
|
|
18
|
+
* // When a track is loaded, extract its metadata
|
|
19
|
+
* const metadata = await extractMetadataFromDevice(fileTransfer, trackNetworkPath);
|
|
20
|
+
* if (metadata) {
|
|
21
|
+
* console.log(metadata.title, metadata.artist);
|
|
22
|
+
* if (metadata.artwork) {
|
|
23
|
+
* // Display artwork
|
|
24
|
+
* }
|
|
25
|
+
* }
|
|
26
|
+
* ```
|
|
27
|
+
*/
|
|
28
|
+
async function extractMetadataFromDevice(fileTransfer, networkPath) {
|
|
29
|
+
// Skip streaming tracks (they don't have a file path)
|
|
30
|
+
if (networkPath.includes('streaming://')) {
|
|
31
|
+
return null;
|
|
32
|
+
}
|
|
33
|
+
// Get file extension and check if supported
|
|
34
|
+
const extension = networkPath.split('.').pop()?.toLowerCase() ?? '';
|
|
35
|
+
if (!(0, metadata_connect_1.isExtensionSupported)(extension)) {
|
|
36
|
+
return null;
|
|
37
|
+
}
|
|
38
|
+
try {
|
|
39
|
+
// Get file size
|
|
40
|
+
const size = await fileTransfer.getFileSize(networkPath);
|
|
41
|
+
if (size === 0) {
|
|
42
|
+
return null;
|
|
43
|
+
}
|
|
44
|
+
// Create reader and extract metadata
|
|
45
|
+
const reader = (0, reader_1.createFileTransferReader)(fileTransfer, networkPath, size);
|
|
46
|
+
return await (0, metadata_connect_1.extractMetadata)(reader);
|
|
47
|
+
}
|
|
48
|
+
catch {
|
|
49
|
+
// Return null on any error (file not found, network issues, etc.)
|
|
50
|
+
return null;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../metadata/index.ts"],"names":[],"mappings":";;AA6BA,8DA6BC;AA1DD,uDAAyE;AAGzE,qCAAoD;AAIpD;;;;;;;;;;;;;;;;;;;;;GAqBG;AACI,KAAK,UAAU,yBAAyB,CAC7C,YAA0B,EAC1B,WAAmB;IAEnB,sDAAsD;IACtD,IAAI,WAAW,CAAC,QAAQ,CAAC,cAAc,CAAC,EAAE,CAAC;QACzC,OAAO,IAAI,CAAC;IACd,CAAC;IAED,4CAA4C;IAC5C,MAAM,SAAS,GAAG,WAAW,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,WAAW,EAAE,IAAI,EAAE,CAAC;IACpE,IAAI,CAAC,IAAA,uCAAoB,EAAC,SAAS,CAAC,EAAE,CAAC;QACrC,OAAO,IAAI,CAAC;IACd,CAAC;IAED,IAAI,CAAC;QACH,gBAAgB;QAChB,MAAM,IAAI,GAAG,MAAM,YAAY,CAAC,WAAW,CAAC,WAAW,CAAC,CAAC;QACzD,IAAI,IAAI,KAAK,CAAC,EAAE,CAAC;YACf,OAAO,IAAI,CAAC;QACd,CAAC;QAED,qCAAqC;QACrC,MAAM,MAAM,GAAG,IAAA,iCAAwB,EAAC,YAAY,EAAE,WAAW,EAAE,IAAI,CAAC,CAAC;QACzE,OAAO,MAAM,IAAA,kCAAe,EAAC,MAAM,CAAC,CAAC;IACvC,CAAC;IAAC,MAAM,CAAC;QACP,kEAAkE;QAClE,OAAO,IAAI,CAAC;IACd,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { FileReader } from 'metadata-connect';
|
|
2
|
+
import type { FileTransfer } from '../services/FileTransfer';
|
|
3
|
+
/**
|
|
4
|
+
* Create a FileReader that reads from a StageLinQ device via FileTransfer
|
|
5
|
+
*
|
|
6
|
+
* @param fileTransfer - The FileTransfer service connected to the device
|
|
7
|
+
* @param path - The file path on the device
|
|
8
|
+
* @param size - The file size in bytes
|
|
9
|
+
* @returns FileReader interface for metadata extraction
|
|
10
|
+
*/
|
|
11
|
+
export declare function createFileTransferReader(fileTransfer: FileTransfer, path: string, size: number): FileReader;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.createFileTransferReader = createFileTransferReader;
|
|
4
|
+
/**
|
|
5
|
+
* Create a FileReader that reads from a StageLinQ device via FileTransfer
|
|
6
|
+
*
|
|
7
|
+
* @param fileTransfer - The FileTransfer service connected to the device
|
|
8
|
+
* @param path - The file path on the device
|
|
9
|
+
* @param size - The file size in bytes
|
|
10
|
+
* @returns FileReader interface for metadata extraction
|
|
11
|
+
*/
|
|
12
|
+
function createFileTransferReader(fileTransfer, path, size) {
|
|
13
|
+
const extension = path.split('.').pop()?.toLowerCase() ?? '';
|
|
14
|
+
return {
|
|
15
|
+
size,
|
|
16
|
+
extension,
|
|
17
|
+
read: (offset, length) => fileTransfer.getFileRange(path, offset, length),
|
|
18
|
+
};
|
|
19
|
+
}
|
|
20
|
+
//# sourceMappingURL=reader.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"reader.js","sourceRoot":"","sources":["../../metadata/reader.ts"],"names":[],"mappings":";;AAWA,4DAaC;AArBD;;;;;;;GAOG;AACH,SAAgB,wBAAwB,CACtC,YAA0B,EAC1B,IAAY,EACZ,IAAY;IAEZ,MAAM,SAAS,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,WAAW,EAAE,IAAI,EAAE,CAAC;IAE7D,OAAO;QACL,IAAI;QACJ,SAAS;QACT,IAAI,EAAE,CAAC,MAAc,EAAE,MAAc,EAAmB,EAAE,CACxD,YAAY,CAAC,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC;KAClD,CAAC;AACJ,CAAC"}
|
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
* automatic reconnection on connection loss.
|
|
7
7
|
*/
|
|
8
8
|
import { EventEmitter } from 'events';
|
|
9
|
+
import type { Logger } from '../types/logger';
|
|
9
10
|
export interface ConnectionHealthOptions {
|
|
10
11
|
/** Interval between heartbeat checks in milliseconds (default: 5000) */
|
|
11
12
|
heartbeatInterval?: number;
|
|
@@ -73,7 +74,8 @@ export declare class ConnectionHealth extends EventEmitter {
|
|
|
73
74
|
private isRunning;
|
|
74
75
|
private _isHealthy;
|
|
75
76
|
private reconnectCallback;
|
|
76
|
-
|
|
77
|
+
private logger;
|
|
78
|
+
constructor(options?: ConnectionHealthOptions, logger?: Logger);
|
|
77
79
|
/**
|
|
78
80
|
* Get current connection status.
|
|
79
81
|
*/
|
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
10
10
|
exports.ConnectionHealth = void 0;
|
|
11
11
|
const events_1 = require("events");
|
|
12
|
-
const
|
|
12
|
+
const logger_1 = require("../types/logger");
|
|
13
13
|
/**
|
|
14
14
|
* Connection Health Monitor
|
|
15
15
|
*
|
|
@@ -41,7 +41,7 @@ const LogEmitter_1 = require("../LogEmitter");
|
|
|
41
41
|
* ```
|
|
42
42
|
*/
|
|
43
43
|
class ConnectionHealth extends events_1.EventEmitter {
|
|
44
|
-
constructor(options = {}) {
|
|
44
|
+
constructor(options = {}, logger = logger_1.noopLogger) {
|
|
45
45
|
super();
|
|
46
46
|
this.heartbeatTimer = null;
|
|
47
47
|
this.lastActivityTime = Date.now();
|
|
@@ -50,6 +50,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
50
50
|
this.isRunning = false;
|
|
51
51
|
this._isHealthy = true;
|
|
52
52
|
this.reconnectCallback = null;
|
|
53
|
+
this.logger = logger;
|
|
53
54
|
this.options = {
|
|
54
55
|
heartbeatInterval: options.heartbeatInterval ?? 5000,
|
|
55
56
|
staleTimeout: options.staleTimeout ?? 15000,
|
|
@@ -88,7 +89,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
88
89
|
*/
|
|
89
90
|
start() {
|
|
90
91
|
if (this.isRunning) {
|
|
91
|
-
|
|
92
|
+
this.logger.warn('ConnectionHealth: Already running');
|
|
92
93
|
return;
|
|
93
94
|
}
|
|
94
95
|
this.isRunning = true;
|
|
@@ -98,7 +99,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
98
99
|
this.heartbeatTimer = setInterval(() => {
|
|
99
100
|
this.checkHealth();
|
|
100
101
|
}, this.options.heartbeatInterval);
|
|
101
|
-
|
|
102
|
+
this.logger.debug('ConnectionHealth: Started monitoring');
|
|
102
103
|
}
|
|
103
104
|
/**
|
|
104
105
|
* Stop the health monitor.
|
|
@@ -109,7 +110,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
109
110
|
this.heartbeatTimer = null;
|
|
110
111
|
}
|
|
111
112
|
this.isRunning = false;
|
|
112
|
-
|
|
113
|
+
this.logger.debug('ConnectionHealth: Stopped monitoring');
|
|
113
114
|
}
|
|
114
115
|
/**
|
|
115
116
|
* Record activity to indicate the connection is alive.
|
|
@@ -118,7 +119,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
118
119
|
recordActivity() {
|
|
119
120
|
this.lastActivityTime = Date.now();
|
|
120
121
|
if (this.missedHeartbeats > 0) {
|
|
121
|
-
|
|
122
|
+
this.logger.debug(`ConnectionHealth: Activity restored after ${this.missedHeartbeats} missed heartbeats`);
|
|
122
123
|
this.missedHeartbeats = 0;
|
|
123
124
|
}
|
|
124
125
|
if (!this._isHealthy) {
|
|
@@ -144,7 +145,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
144
145
|
}
|
|
145
146
|
// Missed a heartbeat
|
|
146
147
|
this.missedHeartbeats++;
|
|
147
|
-
|
|
148
|
+
this.logger.debug(`ConnectionHealth: Missed heartbeat (${this.missedHeartbeats})`);
|
|
148
149
|
if (timeSinceActivity >= this.options.staleTimeout) {
|
|
149
150
|
// Connection is stale
|
|
150
151
|
if (this._isHealthy) {
|
|
@@ -165,11 +166,11 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
165
166
|
while (this.reconnectAttempt < this.options.maxReconnectAttempts) {
|
|
166
167
|
this.reconnectAttempt++;
|
|
167
168
|
this.emit('reconnecting', this.reconnectAttempt);
|
|
168
|
-
|
|
169
|
+
this.logger.info(`ConnectionHealth: Reconnect attempt ${this.reconnectAttempt}/${this.options.maxReconnectAttempts}`);
|
|
169
170
|
try {
|
|
170
171
|
const success = await this.reconnectCallback();
|
|
171
172
|
if (success) {
|
|
172
|
-
|
|
173
|
+
this.logger.info('ConnectionHealth: Reconnected successfully');
|
|
173
174
|
this._isHealthy = true;
|
|
174
175
|
this.reconnectAttempt = 0;
|
|
175
176
|
this.lastActivityTime = Date.now();
|
|
@@ -179,7 +180,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
179
180
|
}
|
|
180
181
|
}
|
|
181
182
|
catch (err) {
|
|
182
|
-
|
|
183
|
+
this.logger.warn(`ConnectionHealth: Reconnect failed: ${err}`);
|
|
183
184
|
}
|
|
184
185
|
// Wait before next attempt
|
|
185
186
|
if (this.reconnectAttempt < this.options.maxReconnectAttempts) {
|
|
@@ -187,7 +188,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
187
188
|
}
|
|
188
189
|
}
|
|
189
190
|
// All attempts failed
|
|
190
|
-
|
|
191
|
+
this.logger.error('ConnectionHealth: All reconnect attempts failed');
|
|
191
192
|
this.emit('reconnectFailed');
|
|
192
193
|
}
|
|
193
194
|
/**
|
|
@@ -195,7 +196,7 @@ class ConnectionHealth extends events_1.EventEmitter {
|
|
|
195
196
|
*/
|
|
196
197
|
async forceReconnect() {
|
|
197
198
|
if (!this.reconnectCallback) {
|
|
198
|
-
|
|
199
|
+
this.logger.warn('ConnectionHealth: No reconnect callback set');
|
|
199
200
|
return false;
|
|
200
201
|
}
|
|
201
202
|
this.reconnectAttempt = 0;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ConnectionHealth.js","sourceRoot":"","sources":["../../network/ConnectionHealth.ts"],"names":[],"mappings":";AAAA;;;;;;GAMG;;;AAEH,mCAAsC;
|
|
1
|
+
{"version":3,"file":"ConnectionHealth.js","sourceRoot":"","sources":["../../network/ConnectionHealth.ts"],"names":[],"mappings":"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"}
|