@phystack/hub-client 4.4.53 → 4.4.55
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/dist/index.d.ts +18 -25
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +252 -188
- package/dist/index.js.map +1 -1
- package/dist/peripheral-twin.d.ts +10 -9
- package/dist/peripheral-twin.d.ts.map +1 -1
- package/dist/peripheral-twin.js +24 -54
- package/dist/peripheral-twin.js.map +1 -1
- package/dist/services/phyhub-connection.service.d.ts +1 -0
- package/dist/services/phyhub-connection.service.d.ts.map +1 -1
- package/dist/services/phyhub-connection.service.js +17 -0
- package/dist/services/phyhub-connection.service.js.map +1 -1
- package/dist/services/phyhub-direct-connection.service.d.ts +21 -0
- package/dist/services/phyhub-direct-connection.service.d.ts.map +1 -0
- package/dist/services/phyhub-direct-connection.service.js +101 -0
- package/dist/services/phyhub-direct-connection.service.js.map +1 -0
- package/dist/services/webrtc/data-channel-handler.d.ts +45 -0
- package/dist/services/webrtc/data-channel-handler.d.ts.map +1 -0
- package/dist/services/webrtc/data-channel-handler.js +260 -0
- package/dist/services/webrtc/data-channel-handler.js.map +1 -0
- package/dist/services/webrtc/index.d.ts +8 -0
- package/dist/services/webrtc/index.d.ts.map +1 -0
- package/dist/services/webrtc/index.js +18 -0
- package/dist/services/webrtc/index.js.map +1 -0
- package/dist/services/webrtc/media-stream-handler.d.ts +57 -0
- package/dist/services/webrtc/media-stream-handler.d.ts.map +1 -0
- package/dist/services/webrtc/media-stream-handler.js +367 -0
- package/dist/services/webrtc/media-stream-handler.js.map +1 -0
- package/dist/services/webrtc/peer-connection-manager.d.ts +40 -0
- package/dist/services/webrtc/peer-connection-manager.d.ts.map +1 -0
- package/dist/services/webrtc/peer-connection-manager.js +335 -0
- package/dist/services/webrtc/peer-connection-manager.js.map +1 -0
- package/dist/services/webrtc/types.d.ts +133 -0
- package/dist/services/webrtc/types.d.ts.map +1 -0
- package/dist/services/webrtc/types.js +12 -0
- package/dist/services/webrtc/types.js.map +1 -0
- package/dist/services/webrtc/webrtc-globals.d.ts +4 -0
- package/dist/services/webrtc/webrtc-globals.d.ts.map +1 -0
- package/dist/services/webrtc/webrtc-globals.js +72 -0
- package/dist/services/webrtc/webrtc-globals.js.map +1 -0
- package/dist/services/webrtc/webrtc-manager.d.ts +35 -0
- package/dist/services/webrtc/webrtc-manager.d.ts.map +1 -0
- package/dist/services/webrtc/webrtc-manager.js +274 -0
- package/dist/services/webrtc/webrtc-manager.js.map +1 -0
- package/dist/test/communication-comprehensive-test.d.ts +8 -0
- package/dist/test/communication-comprehensive-test.d.ts.map +1 -0
- package/dist/test/communication-comprehensive-test.js +356 -0
- package/dist/test/communication-comprehensive-test.js.map +1 -0
- package/dist/test/webrtc-channel-names-test.d.ts +2 -0
- package/dist/test/webrtc-channel-names-test.d.ts.map +1 -0
- package/dist/test/webrtc-channel-names-test.js +177 -0
- package/dist/test/webrtc-channel-names-test.js.map +1 -0
- package/dist/test/webrtc-comprehensive-test.d.ts +2 -0
- package/dist/test/webrtc-comprehensive-test.d.ts.map +1 -0
- package/dist/test/webrtc-comprehensive-test.js +328 -0
- package/dist/test/webrtc-comprehensive-test.js.map +1 -0
- package/dist/test/webrtc-reconnect-test.d.ts +4 -0
- package/dist/test/webrtc-reconnect-test.d.ts.map +1 -0
- package/dist/test/webrtc-reconnect-test.js +244 -0
- package/dist/test/webrtc-reconnect-test.js.map +1 -0
- package/dist/test/webrtc-test-harness.d.ts +4 -0
- package/dist/test/webrtc-test-harness.d.ts.map +1 -0
- package/dist/test/webrtc-test-harness.js +169 -0
- package/dist/test/webrtc-test-harness.js.map +1 -0
- package/dist/twin-messaging.d.ts +23 -0
- package/dist/twin-messaging.d.ts.map +1 -0
- package/dist/twin-messaging.js +96 -0
- package/dist/twin-messaging.js.map +1 -0
- package/dist/types/twin.types.d.ts +36 -20
- package/dist/types/twin.types.d.ts.map +1 -1
- package/dist/types/twin.types.js.map +1 -1
- package/docs/webrtc-howto.md +398 -0
- package/docs/webrtc-test.md +330 -0
- package/package.json +3 -3
- package/scripts/webrtc-test.sh +401 -0
- package/src/index.ts +370 -259
- package/src/peripheral-twin.ts +44 -67
- package/src/services/phyhub-connection.service.ts +24 -0
- package/src/services/phyhub-direct-connection.service.ts +159 -0
- package/src/services/webrtc/data-channel-handler.ts +362 -0
- package/src/services/webrtc/index.ts +36 -0
- package/src/services/webrtc/media-stream-handler.ts +515 -0
- package/src/services/webrtc/peer-connection-manager.ts +463 -0
- package/src/services/webrtc/types.ts +270 -0
- package/src/services/webrtc/webrtc-globals.ts +108 -0
- package/src/services/webrtc/webrtc-manager.ts +490 -0
- package/src/test/communication-comprehensive-test.ts +533 -0
- package/src/test/webrtc-channel-names-test.ts +266 -0
- package/src/test/webrtc-comprehensive-test.ts +494 -0
- package/src/test/webrtc-reconnect-test.ts +345 -0
- package/src/test/webrtc-test-harness.ts +254 -0
- package/src/twin-messaging.ts +193 -0
- package/src/types/twin.types.ts +59 -20
- package/dist/services/webrtc/datachannel.d.ts +0 -10
- package/dist/services/webrtc/datachannel.d.ts.map +0 -1
- package/dist/services/webrtc/datachannel.js +0 -290
- package/dist/services/webrtc/datachannel.js.map +0 -1
- package/dist/services/webrtc/mediastream.d.ts +0 -10
- package/dist/services/webrtc/mediastream.d.ts.map +0 -1
- package/dist/services/webrtc/mediastream.js +0 -396
- package/dist/services/webrtc/mediastream.js.map +0 -1
- package/dist/services/webrtc/peer-connection-ice.d.ts +0 -32
- package/dist/services/webrtc/peer-connection-ice.d.ts.map +0 -1
- package/dist/services/webrtc/peer-connection-ice.js +0 -483
- package/dist/services/webrtc/peer-connection-ice.js.map +0 -1
- package/src/services/webrtc/datachannel.ts +0 -421
- package/src/services/webrtc/mediastream.ts +0 -602
- package/src/services/webrtc/peer-connection-ice.ts +0 -689
package/src/peripheral-twin.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { EventPayload, PhygridDataChannel, PhygridMediaStream, PhyHubClient } from ".";
|
|
2
|
-
import { Instance, TwinResponse, TwinTypeEnum } from "./types/twin.types";
|
|
2
|
+
import { Instance, TwinMessageResult, TwinResponse, TwinTypeEnum } from "./types/twin.types";
|
|
3
|
+
import { createTwinMessaging, TwinMessagingMethods } from "./twin-messaging";
|
|
3
4
|
|
|
4
5
|
export class PeripheralTwinInstance {
|
|
5
6
|
public phyHubClient: PhyHubClient;
|
|
@@ -7,7 +8,7 @@ export class PeripheralTwinInstance {
|
|
|
7
8
|
public edgeInstance: Instance | null = null;
|
|
8
9
|
public peripheralTwinResponse: TwinResponse | null = null;
|
|
9
10
|
|
|
10
|
-
private
|
|
11
|
+
private messaging: TwinMessagingMethods | null = null;
|
|
11
12
|
|
|
12
13
|
constructor(phyHubClient: PhyHubClient, twinId: string) {
|
|
13
14
|
this.phyHubClient = phyHubClient;
|
|
@@ -36,82 +37,58 @@ export class PeripheralTwinInstance {
|
|
|
36
37
|
|
|
37
38
|
this.peripheralTwinResponse = peripheralTwinResponse;
|
|
38
39
|
|
|
39
|
-
|
|
40
|
-
|
|
40
|
+
// Create messaging methods using the shared factory
|
|
41
|
+
this.messaging = createTwinMessaging({
|
|
42
|
+
sendEvent: (targetTwinId, payload) => this.phyHubClient.sendEvent(targetTwinId, payload),
|
|
43
|
+
onTwinMessage: (twinId, callback) => this.phyHubClient.onTwinMessage(twinId, callback),
|
|
44
|
+
twinId: peripheralTwinResponse.id,
|
|
45
|
+
deviceId: edgeInstance.deviceId,
|
|
46
|
+
typePrefix: `peripheralInstance:${peripheralTwinResponse.id}`,
|
|
47
|
+
});
|
|
41
48
|
|
|
42
|
-
|
|
43
|
-
async emit(eventType: string, payload: any) {
|
|
44
|
-
return await this.sendEvent(eventType, payload);
|
|
49
|
+
await this.phyHubClient.subscribeTwin(this.twinId);
|
|
45
50
|
}
|
|
46
51
|
|
|
47
|
-
|
|
48
|
-
|
|
52
|
+
private ensureInitialized(): void {
|
|
53
|
+
if (!this.messaging) {
|
|
54
|
+
throw new Error('[PeripheralTwinInstance] Not initialized. Call initialize() first.');
|
|
55
|
+
}
|
|
49
56
|
}
|
|
50
57
|
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
58
|
+
/**
|
|
59
|
+
* Send a message to the twin.
|
|
60
|
+
* - Without callback: Fire-and-forget (returns void)
|
|
61
|
+
* - With callback: Request-response pattern (returns Promise)
|
|
62
|
+
*/
|
|
63
|
+
emit(eventType: string, payload: any): void;
|
|
64
|
+
emit(eventType: string, payload: any, callback: (response: TwinMessageResult) => void): Promise<TwinMessageResult>;
|
|
65
|
+
emit(
|
|
66
|
+
eventType: string,
|
|
67
|
+
payload: any,
|
|
68
|
+
callback?: (response: TwinMessageResult) => void
|
|
69
|
+
): void | Promise<TwinMessageResult> {
|
|
70
|
+
this.ensureInitialized();
|
|
71
|
+
if (callback) {
|
|
72
|
+
return this.messaging!.emit(eventType, payload, callback);
|
|
73
|
+
} else {
|
|
74
|
+
this.messaging!.emit(eventType, payload);
|
|
54
75
|
}
|
|
55
|
-
|
|
56
|
-
const messagePayload = {
|
|
57
|
-
type: `${this.instanceTypePrefix}:${this.peripheralTwinResponse.id}:${eventType}`,
|
|
58
|
-
sourceTwinId: this.peripheralTwinResponse.id,
|
|
59
|
-
sourceDeviceId: this.edgeInstance.deviceId,
|
|
60
|
-
data: payload,
|
|
61
|
-
};
|
|
62
|
-
|
|
63
|
-
const result = await this.phyHubClient.sendTwinMessage(this.peripheralTwinResponse.id, messagePayload);
|
|
64
|
-
return result;
|
|
65
|
-
};
|
|
66
|
-
|
|
67
|
-
// alias to onEvent()
|
|
68
|
-
on(eventType: string, callback: (message: any) => void) {
|
|
69
|
-
return this.onEvent(eventType, callback);
|
|
70
76
|
}
|
|
71
77
|
|
|
72
|
-
|
|
73
|
-
|
|
78
|
+
/**
|
|
79
|
+
* Listen for events, with optional respond callback for request-response
|
|
80
|
+
*/
|
|
81
|
+
on(
|
|
82
|
+
eventType: string,
|
|
83
|
+
callback: (message: any, respond?: (result: TwinMessageResult) => void) => void
|
|
84
|
+
) {
|
|
85
|
+
this.ensureInitialized();
|
|
86
|
+
this.messaging!.on(eventType, callback);
|
|
74
87
|
}
|
|
75
88
|
|
|
76
|
-
private peripheralTwinOn(eventType: string, callback: (message: any) => void) {
|
|
77
|
-
console.log(`Setting up listener for peripheral ${this.twinId} event: ${eventType}`);
|
|
78
|
-
|
|
79
|
-
if (!this.peripheralTwinResponse) {
|
|
80
|
-
console.error('Object is not initialized correctly');
|
|
81
|
-
return;
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
const onMessage = (payload: any) => {
|
|
85
|
-
// console.log(`Received message for peripheral ${peripheralTwinId}:`, payload);
|
|
86
|
-
const messageType = payload.data?.type || payload.type;
|
|
87
|
-
if (messageType === `${this.instanceTypePrefix}:${this.peripheralTwinResponse!.id}:${eventType}`) {
|
|
88
|
-
// console.log('Processing matching message type');
|
|
89
|
-
callback(payload.data?.data || payload.data);
|
|
90
|
-
} else {
|
|
91
|
-
// console.log('Ignoring non-matching message type:', messageType);
|
|
92
|
-
}
|
|
93
|
-
};
|
|
94
|
-
|
|
95
|
-
this.phyHubClient.onTwinMessage(this.peripheralTwinResponse.id, onMessage);
|
|
96
|
-
};
|
|
97
|
-
|
|
98
89
|
to(targetTwinId: string) {
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
if (!this.edgeInstance || !this.peripheralTwinResponse) {
|
|
102
|
-
throw new Error('Object is not initialized correctly');
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
const messagePayload = {
|
|
106
|
-
type: `${this.instanceTypePrefix}:${this.peripheralTwinResponse.id}:${eventType}`,
|
|
107
|
-
sourceTwinId: this.edgeInstance.id,
|
|
108
|
-
sourceDeviceId: this.edgeInstance.deviceId,
|
|
109
|
-
data: payload,
|
|
110
|
-
};
|
|
111
|
-
|
|
112
|
-
return await this.phyHubClient.sendTwinMessage(targetTwinId, messagePayload);
|
|
113
|
-
}
|
|
114
|
-
}
|
|
90
|
+
this.ensureInitialized();
|
|
91
|
+
return this.messaging!.to(targetTwinId);
|
|
115
92
|
}
|
|
116
93
|
|
|
117
94
|
async getDataChannel() {
|
|
@@ -2,6 +2,8 @@ import { Socket } from 'socket.io-client';
|
|
|
2
2
|
import { get } from 'lodash';
|
|
3
3
|
import { isBrowser } from '../helpers/browser.helper';
|
|
4
4
|
import { getSocketIOWithProxy } from '@phystack/socket.io-proxy';
|
|
5
|
+
import { PhyHubDirectConnection } from './phyhub-direct-connection.service';
|
|
6
|
+
|
|
5
7
|
interface UrlConfig {
|
|
6
8
|
url: string;
|
|
7
9
|
timeout: number;
|
|
@@ -14,12 +16,26 @@ export class PhyHubConnection {
|
|
|
14
16
|
private socketUrls: UrlConfig[] = [];
|
|
15
17
|
private instanceId: string | undefined;
|
|
16
18
|
private moduleName: string | undefined;
|
|
19
|
+
private directConnection: PhyHubDirectConnection | null = null;
|
|
17
20
|
|
|
18
21
|
private constructor(
|
|
19
22
|
params: { instanceId?: string; moduleName?: string; dataResidency?: string } = {}
|
|
20
23
|
) {
|
|
21
24
|
this.instanceId = params.instanceId;
|
|
22
25
|
this.moduleName = params.moduleName;
|
|
26
|
+
|
|
27
|
+
// Check for direct connection mode (for testing)
|
|
28
|
+
if (PhyHubDirectConnection.isEnabled()) {
|
|
29
|
+
this.directConnection = PhyHubDirectConnection.fromEnv();
|
|
30
|
+
if (this.directConnection) {
|
|
31
|
+
console.log('[PhyHubConnection] Direct connection mode enabled');
|
|
32
|
+
// Use device ID as instance ID if not provided
|
|
33
|
+
if (!this.instanceId) {
|
|
34
|
+
this.instanceId = this.directConnection.getInstanceId();
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
|
23
39
|
this.setSocketUrls(params.dataResidency);
|
|
24
40
|
this.fetchPhygridSocketInstance();
|
|
25
41
|
}
|
|
@@ -137,6 +153,14 @@ export class PhyHubConnection {
|
|
|
137
153
|
public async getPhyHubSocket(): Promise<Socket> {
|
|
138
154
|
console.info(`getPhyHubSocket(): Getting phyhub socket`);
|
|
139
155
|
|
|
156
|
+
// Use direct connection if enabled (for testing)
|
|
157
|
+
if (this.directConnection) {
|
|
158
|
+
console.log('[PhyHubConnection] Using direct connection');
|
|
159
|
+
const socket = await this.directConnection.connect();
|
|
160
|
+
this.phygridSocketSingleton = socket;
|
|
161
|
+
return socket;
|
|
162
|
+
}
|
|
163
|
+
|
|
140
164
|
// Always check top window first
|
|
141
165
|
if (isBrowser) {
|
|
142
166
|
const topWindow = this.getTopWindow();
|
|
@@ -0,0 +1,159 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* PhyHub Direct Connection Service
|
|
3
|
+
*
|
|
4
|
+
* Allows direct connection to PhyHub for testing purposes,
|
|
5
|
+
* bypassing the phyos layer that normally runs on devices.
|
|
6
|
+
*
|
|
7
|
+
* Usage:
|
|
8
|
+
* - Set PHYHUB_DIRECT=true to enable direct connection
|
|
9
|
+
* - Provide DEVICE_ID and ACCESS_KEY environment variables
|
|
10
|
+
* - Optionally set PHYHUB_URL (defaults to EU region)
|
|
11
|
+
*/
|
|
12
|
+
|
|
13
|
+
import { Socket } from 'socket.io-client';
|
|
14
|
+
import { getSocketIOWithProxy } from '@phystack/socket.io-proxy';
|
|
15
|
+
|
|
16
|
+
export interface DirectConnectionConfig {
|
|
17
|
+
deviceId: string;
|
|
18
|
+
accessKey: string;
|
|
19
|
+
phyhubUrl?: string;
|
|
20
|
+
instanceId?: string; // Optional: override the twin ID to use
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const DEFAULT_PHYHUB_URLS: Record<string, string> = {
|
|
24
|
+
eu: 'https://phyhub.eu.omborigrid.net',
|
|
25
|
+
us: 'https://phyhub.us.omborigrid.net',
|
|
26
|
+
uae: 'https://phyhub.uae.omborigrid.net',
|
|
27
|
+
au: 'https://phyhub.au.omborigrid.net',
|
|
28
|
+
in: 'https://phyhub.in.omborigrid.net',
|
|
29
|
+
qa: 'https://phyhub.qa.omborigrid.net',
|
|
30
|
+
dev: 'https://phyhub.dev.omborigrid.net',
|
|
31
|
+
local: 'http://localhost:3000',
|
|
32
|
+
};
|
|
33
|
+
|
|
34
|
+
export class PhyHubDirectConnection {
|
|
35
|
+
private socket: Socket | null = null;
|
|
36
|
+
private config: DirectConnectionConfig;
|
|
37
|
+
|
|
38
|
+
constructor(config: DirectConnectionConfig) {
|
|
39
|
+
this.config = {
|
|
40
|
+
...config,
|
|
41
|
+
phyhubUrl: config.phyhubUrl || DEFAULT_PHYHUB_URLS.eu,
|
|
42
|
+
};
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Create a direct connection from environment variables
|
|
47
|
+
* @throws Error if required environment variables are missing
|
|
48
|
+
*/
|
|
49
|
+
static fromEnv(): PhyHubDirectConnection {
|
|
50
|
+
const deviceId = process.env.DEVICE_ID || process.env.PHYGRID_DEVICE_ID;
|
|
51
|
+
const accessKey = process.env.ACCESS_KEY || process.env.PHYGRID_DEVICE_KEY;
|
|
52
|
+
|
|
53
|
+
if (!deviceId) {
|
|
54
|
+
throw new Error('[PhyHubDirectConnection] DEVICE_ID or PHYGRID_DEVICE_ID env var required');
|
|
55
|
+
}
|
|
56
|
+
if (!accessKey) {
|
|
57
|
+
throw new Error('[PhyHubDirectConnection] ACCESS_KEY or PHYGRID_DEVICE_KEY env var required');
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
const region = process.env.PHYHUB_REGION?.toLowerCase();
|
|
61
|
+
const phyhubUrl = process.env.PHYHUB_URL || (region ? DEFAULT_PHYHUB_URLS[region] : undefined);
|
|
62
|
+
|
|
63
|
+
if (!phyhubUrl) {
|
|
64
|
+
throw new Error(`[PhyHubDirectConnection] PHYHUB_URL or valid PHYHUB_REGION required. Valid regions: ${Object.keys(DEFAULT_PHYHUB_URLS).join(', ')}`);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
return new PhyHubDirectConnection({
|
|
68
|
+
deviceId,
|
|
69
|
+
accessKey,
|
|
70
|
+
phyhubUrl,
|
|
71
|
+
instanceId: process.env.TWIN_ID || process.env.INSTANCE_ID,
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
/**
|
|
76
|
+
* Check if direct connection mode is enabled
|
|
77
|
+
*/
|
|
78
|
+
static isEnabled(): boolean {
|
|
79
|
+
return process.env.PHYHUB_DIRECT === 'true' || process.env.PHYHUB_DIRECT === '1';
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
/**
|
|
83
|
+
* Get the device ID (also used as the primary twin ID)
|
|
84
|
+
*/
|
|
85
|
+
getDeviceId(): string {
|
|
86
|
+
return this.config.deviceId;
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
/**
|
|
90
|
+
* Get the instance/twin ID to use
|
|
91
|
+
*/
|
|
92
|
+
getInstanceId(): string {
|
|
93
|
+
return this.config.instanceId || this.config.deviceId;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
/**
|
|
97
|
+
* Connect directly to PhyHub
|
|
98
|
+
*/
|
|
99
|
+
async connect(): Promise<Socket> {
|
|
100
|
+
if (this.socket?.connected) {
|
|
101
|
+
return this.socket;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const { deviceId, accessKey, phyhubUrl } = this.config;
|
|
105
|
+
|
|
106
|
+
console.log(`[PhyHubDirectConnection] Connecting to ${phyhubUrl}`);
|
|
107
|
+
console.log(`[PhyHubDirectConnection] Device ID: ${deviceId}`);
|
|
108
|
+
|
|
109
|
+
this.socket = await getSocketIOWithProxy(phyhubUrl!, {
|
|
110
|
+
auth: {
|
|
111
|
+
deviceId,
|
|
112
|
+
accessKey,
|
|
113
|
+
},
|
|
114
|
+
reconnection: true,
|
|
115
|
+
reconnectionAttempts: 5,
|
|
116
|
+
reconnectionDelay: 1000,
|
|
117
|
+
timeout: 10000,
|
|
118
|
+
});
|
|
119
|
+
|
|
120
|
+
await new Promise<void>((resolve, reject) => {
|
|
121
|
+
const timeout = setTimeout(() => {
|
|
122
|
+
reject(new Error('Connection timeout'));
|
|
123
|
+
}, 15000);
|
|
124
|
+
|
|
125
|
+
this.socket!.on('connect', () => {
|
|
126
|
+
clearTimeout(timeout);
|
|
127
|
+
console.log(`[PhyHubDirectConnection] Connected successfully`);
|
|
128
|
+
resolve();
|
|
129
|
+
});
|
|
130
|
+
|
|
131
|
+
this.socket!.on('connect_error', (error) => {
|
|
132
|
+
clearTimeout(timeout);
|
|
133
|
+
console.error(`[PhyHubDirectConnection] Connection error:`, error.message);
|
|
134
|
+
reject(error);
|
|
135
|
+
});
|
|
136
|
+
});
|
|
137
|
+
|
|
138
|
+
return this.socket;
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
/**
|
|
142
|
+
* Disconnect from PhyHub
|
|
143
|
+
*/
|
|
144
|
+
disconnect(): void {
|
|
145
|
+
if (this.socket) {
|
|
146
|
+
this.socket.disconnect();
|
|
147
|
+
this.socket = null;
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
/**
|
|
152
|
+
* Get the socket instance
|
|
153
|
+
*/
|
|
154
|
+
getSocket(): Socket | null {
|
|
155
|
+
return this.socket;
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
export default PhyHubDirectConnection;
|