@oxyhq/services 5.16.35 → 5.16.37
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 +8 -26
- package/lib/commonjs/core/OxyServices.base.js.map +1 -1
- package/lib/commonjs/core/mixins/OxyServices.user.js.map +1 -1
- package/lib/commonjs/core/mixins/OxyServices.utility.js.map +1 -1
- package/lib/commonjs/crypto/README.md +142 -0
- package/lib/commonjs/crypto/core.js +147 -0
- package/lib/commonjs/crypto/core.js.map +1 -0
- package/lib/commonjs/crypto/index.js +16 -0
- package/lib/commonjs/crypto/index.js.map +1 -1
- package/lib/commonjs/crypto/keyManager.js +19 -22
- package/lib/commonjs/crypto/keyManager.js.map +1 -1
- package/lib/commonjs/crypto/signatureService.js +116 -28
- package/lib/commonjs/crypto/signatureService.js.map +1 -1
- package/lib/commonjs/index.js +0 -12
- package/lib/commonjs/index.js.map +1 -1
- package/lib/commonjs/models/interfaces.js +10 -11
- package/lib/commonjs/models/interfaces.js.map +1 -1
- package/lib/commonjs/node/index.js +10 -1
- package/lib/commonjs/node/index.js.map +1 -1
- package/lib/commonjs/node/signatureService.js +107 -0
- package/lib/commonjs/node/signatureService.js.map +1 -0
- package/lib/commonjs/ui/context/OxyContext.js +23 -0
- package/lib/commonjs/ui/context/OxyContext.js.map +1 -1
- package/lib/commonjs/ui/context/hooks/useAuthOperations.js +29 -2
- package/lib/commonjs/ui/context/hooks/useAuthOperations.js.map +1 -1
- package/lib/commonjs/ui/context/hooks/useLanguageManagement.js.map +1 -1
- package/lib/commonjs/ui/hooks/useLanguageManagement.js.map +1 -1
- package/lib/commonjs/ui/hooks/useSessionManagement.js.map +1 -1
- package/lib/commonjs/ui/index.js +0 -2
- package/lib/commonjs/ui/index.js.map +1 -1
- package/lib/commonjs/ui/screens/AccountSettingsScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/OxyAuthScreen.js +11 -2
- package/lib/commonjs/ui/screens/OxyAuthScreen.js.map +1 -1
- package/lib/module/core/OxyServices.base.js.map +1 -1
- package/lib/module/core/mixins/OxyServices.user.js.map +1 -1
- package/lib/module/core/mixins/OxyServices.utility.js.map +1 -1
- package/lib/module/crypto/README.md +142 -0
- package/lib/module/crypto/core.js +133 -0
- package/lib/module/crypto/core.js.map +1 -0
- package/lib/module/crypto/index.js +3 -9
- package/lib/module/crypto/index.js.map +1 -1
- package/lib/module/crypto/keyManager.js +19 -22
- package/lib/module/crypto/keyManager.js.map +1 -1
- package/lib/module/crypto/signatureService.js +113 -23
- package/lib/module/crypto/signatureService.js.map +1 -1
- package/lib/module/index.js +0 -2
- package/lib/module/index.js.map +1 -1
- package/lib/module/models/interfaces.js +10 -11
- package/lib/module/models/interfaces.js.map +1 -1
- package/lib/module/node/index.js +3 -0
- package/lib/module/node/index.js.map +1 -1
- package/lib/module/node/signatureService.js +101 -0
- package/lib/module/node/signatureService.js.map +1 -0
- package/lib/module/ui/context/OxyContext.js +23 -0
- package/lib/module/ui/context/OxyContext.js.map +1 -1
- package/lib/module/ui/context/hooks/useAuthOperations.js +29 -2
- package/lib/module/ui/context/hooks/useAuthOperations.js.map +1 -1
- package/lib/module/ui/context/hooks/useLanguageManagement.js.map +1 -1
- package/lib/module/ui/hooks/useLanguageManagement.js.map +1 -1
- package/lib/module/ui/hooks/useSessionManagement.js.map +1 -1
- package/lib/module/ui/index.js +0 -1
- package/lib/module/ui/index.js.map +1 -1
- package/lib/module/ui/screens/AccountSettingsScreen.js.map +1 -1
- package/lib/module/ui/screens/OxyAuthScreen.js +11 -2
- package/lib/module/ui/screens/OxyAuthScreen.js.map +1 -1
- package/lib/typescript/core/OxyServices.base.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.analytics.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.assets.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.auth.d.ts +1 -1
- package/lib/typescript/core/mixins/OxyServices.auth.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.developer.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.devices.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.karma.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.language.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.location.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.payment.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.privacy.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.security.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.user.d.ts +1 -2
- package/lib/typescript/core/mixins/OxyServices.user.d.ts.map +1 -1
- package/lib/typescript/core/mixins/OxyServices.utility.d.ts.map +1 -1
- package/lib/typescript/core/mixins/index.d.ts +13 -13
- package/lib/typescript/core/mixins/index.d.ts.map +1 -1
- package/lib/typescript/core/services/SessionService.d.ts +1 -1
- package/lib/typescript/core/services/SessionService.d.ts.map +1 -1
- package/lib/typescript/crypto/core.d.ts +56 -0
- package/lib/typescript/crypto/core.d.ts.map +1 -0
- package/lib/typescript/crypto/index.d.ts +1 -9
- package/lib/typescript/crypto/index.d.ts.map +1 -1
- package/lib/typescript/crypto/keyManager.d.ts +13 -1
- package/lib/typescript/crypto/keyManager.d.ts.map +1 -1
- package/lib/typescript/crypto/signatureService.d.ts +15 -9
- package/lib/typescript/crypto/signatureService.d.ts.map +1 -1
- package/lib/typescript/index.d.ts +1 -2
- package/lib/typescript/index.d.ts.map +1 -1
- package/lib/typescript/models/interfaces.d.ts +68 -15
- package/lib/typescript/models/interfaces.d.ts.map +1 -1
- package/lib/typescript/node/index.d.ts +1 -0
- package/lib/typescript/node/index.d.ts.map +1 -1
- package/lib/typescript/node/signatureService.d.ts +55 -0
- package/lib/typescript/node/signatureService.d.ts.map +1 -0
- package/lib/typescript/ui/context/OxyContext.d.ts +1 -2
- package/lib/typescript/ui/context/OxyContext.d.ts.map +1 -1
- package/lib/typescript/ui/context/hooks/useAuthOperations.d.ts +1 -2
- package/lib/typescript/ui/context/hooks/useAuthOperations.d.ts.map +1 -1
- package/lib/typescript/ui/context/hooks/useLanguageManagement.d.ts +1 -2
- package/lib/typescript/ui/context/hooks/useLanguageManagement.d.ts.map +1 -1
- package/lib/typescript/ui/hooks/mutations/useAccountMutations.d.ts +1 -1
- package/lib/typescript/ui/hooks/mutations/useAccountMutations.d.ts.map +1 -1
- package/lib/typescript/ui/hooks/queries/useAccountQueries.d.ts +1 -1
- package/lib/typescript/ui/hooks/queries/useAccountQueries.d.ts.map +1 -1
- package/lib/typescript/ui/hooks/useLanguageManagement.d.ts +1 -2
- package/lib/typescript/ui/hooks/useLanguageManagement.d.ts.map +1 -1
- package/lib/typescript/ui/hooks/useSessionManagement.d.ts +1 -2
- package/lib/typescript/ui/hooks/useSessionManagement.d.ts.map +1 -1
- package/lib/typescript/ui/index.d.ts +1 -1
- package/lib/typescript/ui/index.d.ts.map +1 -1
- package/lib/typescript/ui/screens/OxyAuthScreen.d.ts.map +1 -1
- package/lib/typescript/ui/stores/authStore.d.ts +1 -1
- package/lib/typescript/ui/stores/authStore.d.ts.map +1 -1
- package/lib/typescript/ui/utils/avatarUtils.d.ts +1 -1
- package/lib/typescript/ui/utils/avatarUtils.d.ts.map +1 -1
- package/package.json +6 -1
- package/src/core/OxyServices.base.ts +1 -2
- package/src/core/mixins/OxyServices.auth.ts +1 -1
- package/src/core/mixins/OxyServices.user.ts +1 -2
- package/src/core/mixins/OxyServices.utility.ts +1 -2
- package/src/core/services/SessionService.ts +1 -1
- package/src/crypto/README.md +142 -0
- package/src/crypto/__tests__/core.test.ts +203 -0
- package/src/crypto/core.ts +142 -0
- package/src/crypto/index.ts +3 -10
- package/src/crypto/keyManager.ts +25 -21
- package/src/crypto/signatureService.ts +137 -36
- package/src/index.ts +2 -3
- package/src/models/interfaces.ts +73 -21
- package/src/node/index.ts +3 -0
- package/src/node/signatureService.ts +126 -0
- package/src/ui/context/OxyContext.tsx +26 -2
- package/src/ui/context/hooks/useAuthOperations.ts +33 -4
- package/src/ui/context/hooks/useLanguageManagement.ts +1 -2
- package/src/ui/hooks/auth/index.ts +2 -0
- package/src/ui/hooks/mutations/useAccountMutations.ts +1 -1
- package/src/ui/hooks/mutations/useServicesMutations.ts +1 -1
- package/src/ui/hooks/queries/useAccountQueries.ts +1 -1
- package/src/ui/hooks/useLanguageManagement.ts +1 -2
- package/src/ui/hooks/useSessionManagement.ts +1 -2
- package/src/ui/index.ts +1 -2
- package/src/ui/screens/AccountSettingsScreen.tsx +6 -6
- package/src/ui/screens/AccountSwitcherScreen.tsx +1 -1
- package/src/ui/screens/OxyAuthScreen.tsx +11 -2
- package/src/ui/screens/ProfileScreen.tsx +1 -1
- package/src/ui/stores/authStore.ts +1 -1
- package/src/ui/types/navigation.ts +1 -1
- package/src/ui/utils/avatarUtils.ts +1 -1
- package/lib/commonjs/core/services/AuthService.js +0 -156
- package/lib/commonjs/core/services/AuthService.js.map +0 -1
- package/lib/commonjs/core/services/SessionTransportService.js +0 -64
- package/lib/commonjs/core/services/SessionTransportService.js.map +0 -1
- package/lib/commonjs/core/services/UserService.js +0 -123
- package/lib/commonjs/core/services/UserService.js.map +0 -1
- package/lib/commonjs/core/services/index.js +0 -34
- package/lib/commonjs/core/services/index.js.map +0 -1
- package/lib/commonjs/shared/crypto/messageBuilders.js +0 -79
- package/lib/commonjs/shared/crypto/messageBuilders.js.map +0 -1
- package/lib/commonjs/shared/crypto/platform.js +0 -118
- package/lib/commonjs/shared/crypto/platform.js.map +0 -1
- package/lib/commonjs/shared/crypto/signature.js +0 -191
- package/lib/commonjs/shared/crypto/signature.js.map +0 -1
- package/lib/commonjs/shared/index.js +0 -94
- package/lib/commonjs/shared/index.js.map +0 -1
- package/lib/commonjs/shared/models/index.js +0 -2
- package/lib/commonjs/shared/models/index.js.map +0 -1
- package/lib/commonjs/shared/transport/index.js +0 -260
- package/lib/commonjs/shared/transport/index.js.map +0 -1
- package/lib/commonjs/shared/utils/index.js +0 -82
- package/lib/commonjs/shared/utils/index.js.map +0 -1
- package/lib/module/core/services/AuthService.js +0 -151
- package/lib/module/core/services/AuthService.js.map +0 -1
- package/lib/module/core/services/SessionTransportService.js +0 -59
- package/lib/module/core/services/SessionTransportService.js.map +0 -1
- package/lib/module/core/services/UserService.js +0 -118
- package/lib/module/core/services/UserService.js.map +0 -1
- package/lib/module/core/services/index.js +0 -16
- package/lib/module/core/services/index.js.map +0 -1
- package/lib/module/shared/crypto/messageBuilders.js +0 -70
- package/lib/module/shared/crypto/messageBuilders.js.map +0 -1
- package/lib/module/shared/crypto/platform.js +0 -112
- package/lib/module/shared/crypto/platform.js.map +0 -1
- package/lib/module/shared/crypto/signature.js +0 -186
- package/lib/module/shared/crypto/signature.js.map +0 -1
- package/lib/module/shared/index.js +0 -30
- package/lib/module/shared/index.js.map +0 -1
- package/lib/module/shared/models/index.js +0 -2
- package/lib/module/shared/models/index.js.map +0 -1
- package/lib/module/shared/transport/index.js +0 -254
- package/lib/module/shared/transport/index.js.map +0 -1
- package/lib/module/shared/utils/index.js +0 -74
- package/lib/module/shared/utils/index.js.map +0 -1
- package/lib/typescript/core/services/AuthService.d.ts +0 -50
- package/lib/typescript/core/services/AuthService.d.ts.map +0 -1
- package/lib/typescript/core/services/SessionTransportService.d.ts +0 -31
- package/lib/typescript/core/services/SessionTransportService.d.ts.map +0 -1
- package/lib/typescript/core/services/UserService.d.ts +0 -39
- package/lib/typescript/core/services/UserService.d.ts.map +0 -1
- package/lib/typescript/core/services/index.d.ts +0 -13
- package/lib/typescript/core/services/index.d.ts.map +0 -1
- package/lib/typescript/shared/crypto/messageBuilders.d.ts +0 -38
- package/lib/typescript/shared/crypto/messageBuilders.d.ts.map +0 -1
- package/lib/typescript/shared/crypto/platform.d.ts +0 -54
- package/lib/typescript/shared/crypto/platform.d.ts.map +0 -1
- package/lib/typescript/shared/crypto/signature.d.ts +0 -72
- package/lib/typescript/shared/crypto/signature.d.ts.map +0 -1
- package/lib/typescript/shared/index.d.ts +0 -20
- package/lib/typescript/shared/index.d.ts.map +0 -1
- package/lib/typescript/shared/models/index.d.ts +0 -163
- package/lib/typescript/shared/models/index.d.ts.map +0 -1
- package/lib/typescript/shared/transport/index.d.ts +0 -73
- package/lib/typescript/shared/transport/index.d.ts.map +0 -1
- package/lib/typescript/shared/utils/index.d.ts +0 -28
- package/lib/typescript/shared/utils/index.d.ts.map +0 -1
- package/src/core/services/AuthService.ts +0 -153
- package/src/core/services/SessionTransportService.ts +0 -69
- package/src/core/services/UserService.ts +0 -125
- package/src/core/services/index.ts +0 -14
- package/src/shared/crypto/messageBuilders.ts +0 -89
- package/src/shared/crypto/platform.ts +0 -140
- package/src/shared/crypto/signature.ts +0 -235
- package/src/shared/index.ts +0 -28
- package/src/shared/models/index.ts +0 -173
- package/src/shared/transport/index.ts +0 -349
- package/src/shared/utils/index.ts +0 -73
|
@@ -1,173 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Shared Data Models
|
|
3
|
-
*
|
|
4
|
-
* Canonical TypeScript interfaces used across Accounts, Services SDK, and API packages.
|
|
5
|
-
* These models eliminate type drift and ensure consistency across the monorepo.
|
|
6
|
-
*/
|
|
7
|
-
|
|
8
|
-
/**
|
|
9
|
-
* User Model
|
|
10
|
-
*
|
|
11
|
-
* IMPORTANT:
|
|
12
|
-
* - id: MongoDB ObjectId (24 hex characters) - PRIMARY IDENTIFIER for all internal operations
|
|
13
|
-
* - publicKey: Cryptographic public key (130 hex characters) - LOOKUP KEY for authentication and identity operations
|
|
14
|
-
*
|
|
15
|
-
* Never use publicKey as an ID. Always use id (ObjectId) for:
|
|
16
|
-
* - Database queries
|
|
17
|
-
* - Session userId
|
|
18
|
-
* - Token userId
|
|
19
|
-
* - Socket room names
|
|
20
|
-
* - API route parameters (unless explicitly doing publicKey lookup)
|
|
21
|
-
*/
|
|
22
|
-
export interface User {
|
|
23
|
-
id: string; // MongoDB ObjectId - PRIMARY IDENTIFIER (always 24 hex chars)
|
|
24
|
-
publicKey: string; // Cryptographic public key - LOOKUP KEY (130 hex chars for secp256k1)
|
|
25
|
-
username: string;
|
|
26
|
-
email?: string;
|
|
27
|
-
avatar?: string; // Avatar file id (asset id)
|
|
28
|
-
privacySettings?: {
|
|
29
|
-
[key: string]: unknown;
|
|
30
|
-
};
|
|
31
|
-
name?: {
|
|
32
|
-
first?: string;
|
|
33
|
-
last?: string;
|
|
34
|
-
full?: string; // virtual, not stored in DB, returned by API
|
|
35
|
-
[key: string]: unknown;
|
|
36
|
-
};
|
|
37
|
-
bio?: string;
|
|
38
|
-
karma?: number;
|
|
39
|
-
location?: string;
|
|
40
|
-
website?: string;
|
|
41
|
-
createdAt?: string;
|
|
42
|
-
updatedAt?: string;
|
|
43
|
-
links?: Array<{
|
|
44
|
-
title?: string;
|
|
45
|
-
description?: string;
|
|
46
|
-
image?: string;
|
|
47
|
-
link: string;
|
|
48
|
-
}>;
|
|
49
|
-
_count?: {
|
|
50
|
-
followers?: number;
|
|
51
|
-
following?: number;
|
|
52
|
-
};
|
|
53
|
-
accountExpiresAfterInactivityDays?: number | null;
|
|
54
|
-
[key: string]: unknown;
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
/**
|
|
58
|
-
* Session Model
|
|
59
|
-
* Represents an authenticated session on a device
|
|
60
|
-
*/
|
|
61
|
-
export interface Session {
|
|
62
|
-
sessionId: string;
|
|
63
|
-
userId: string; // MongoDB ObjectId - PRIMARY IDENTIFIER
|
|
64
|
-
deviceId: string;
|
|
65
|
-
deviceInfo?: {
|
|
66
|
-
deviceName?: string;
|
|
67
|
-
deviceType?: string;
|
|
68
|
-
platform?: string;
|
|
69
|
-
browser?: string;
|
|
70
|
-
os?: string;
|
|
71
|
-
ipAddress?: string;
|
|
72
|
-
userAgent?: string;
|
|
73
|
-
location?: string;
|
|
74
|
-
fingerprint?: string;
|
|
75
|
-
lastActive?: string | Date;
|
|
76
|
-
};
|
|
77
|
-
isActive: boolean;
|
|
78
|
-
expiresAt: string | Date;
|
|
79
|
-
lastActive?: string | Date;
|
|
80
|
-
createdAt?: string | Date;
|
|
81
|
-
updatedAt?: string | Date;
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
/**
|
|
85
|
-
* Challenge Payload
|
|
86
|
-
* Used in challenge-response authentication
|
|
87
|
-
*/
|
|
88
|
-
export interface ChallengePayload {
|
|
89
|
-
challenge: string;
|
|
90
|
-
publicKey: string;
|
|
91
|
-
expiresAt: string | Date;
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
/**
|
|
95
|
-
* Signed Message
|
|
96
|
-
* Represents a message with cryptographic signature
|
|
97
|
-
*/
|
|
98
|
-
export interface SignedMessage {
|
|
99
|
-
message: string;
|
|
100
|
-
signature: string;
|
|
101
|
-
publicKey: string;
|
|
102
|
-
timestamp: number;
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
/**
|
|
106
|
-
* Auth Challenge Response
|
|
107
|
-
* Response to an authentication challenge
|
|
108
|
-
*/
|
|
109
|
-
export interface AuthChallengeResponse {
|
|
110
|
-
challenge: string;
|
|
111
|
-
publicKey: string;
|
|
112
|
-
signature: string;
|
|
113
|
-
timestamp: number;
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
/**
|
|
117
|
-
* Session Auth Response
|
|
118
|
-
* Response from session authorization (SSO flow)
|
|
119
|
-
*/
|
|
120
|
-
export interface SessionAuthResponse {
|
|
121
|
-
sessionToken: string;
|
|
122
|
-
status: 'pending' | 'authorized' | 'expired' | 'cancelled';
|
|
123
|
-
accessToken?: string;
|
|
124
|
-
refreshToken?: string;
|
|
125
|
-
user?: User;
|
|
126
|
-
expiresAt: string | Date;
|
|
127
|
-
createdAt?: string | Date;
|
|
128
|
-
}
|
|
129
|
-
|
|
130
|
-
/**
|
|
131
|
-
* Registration Request
|
|
132
|
-
* Used when registering a new identity
|
|
133
|
-
*/
|
|
134
|
-
export interface RegistrationRequest {
|
|
135
|
-
publicKey: string;
|
|
136
|
-
signature: string;
|
|
137
|
-
timestamp: number;
|
|
138
|
-
username?: string;
|
|
139
|
-
email?: string;
|
|
140
|
-
}
|
|
141
|
-
|
|
142
|
-
/**
|
|
143
|
-
* Login Response
|
|
144
|
-
* Response from successful authentication
|
|
145
|
-
*/
|
|
146
|
-
export interface LoginResponse {
|
|
147
|
-
accessToken?: string;
|
|
148
|
-
refreshToken?: string;
|
|
149
|
-
token?: string; // For backwards compatibility
|
|
150
|
-
user: User;
|
|
151
|
-
message?: string;
|
|
152
|
-
}
|
|
153
|
-
|
|
154
|
-
/**
|
|
155
|
-
* Pagination Info
|
|
156
|
-
* Standard pagination metadata
|
|
157
|
-
*/
|
|
158
|
-
export interface PaginationInfo {
|
|
159
|
-
total: number;
|
|
160
|
-
limit: number;
|
|
161
|
-
offset: number;
|
|
162
|
-
hasMore: boolean;
|
|
163
|
-
}
|
|
164
|
-
|
|
165
|
-
/**
|
|
166
|
-
* Search Profiles Response
|
|
167
|
-
* Response from profile search with pagination
|
|
168
|
-
*/
|
|
169
|
-
export interface SearchProfilesResponse {
|
|
170
|
-
data: User[];
|
|
171
|
-
pagination: PaginationInfo;
|
|
172
|
-
}
|
|
173
|
-
|
|
@@ -1,349 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Transport Abstraction
|
|
3
|
-
*
|
|
4
|
-
* Unified transport layer for WebSocket, SSE, and polling.
|
|
5
|
-
* Provides automatic fallback and unified configuration.
|
|
6
|
-
*/
|
|
7
|
-
|
|
8
|
-
export type TransportType = 'websocket' | 'sse' | 'polling';
|
|
9
|
-
|
|
10
|
-
export interface TransportConfig {
|
|
11
|
-
baseURL: string;
|
|
12
|
-
namespace?: string;
|
|
13
|
-
sessionToken?: string;
|
|
14
|
-
accessToken?: string;
|
|
15
|
-
pollingInterval?: number; // milliseconds
|
|
16
|
-
reconnectAttempts?: number;
|
|
17
|
-
reconnectDelay?: number; // milliseconds
|
|
18
|
-
timeout?: number; // milliseconds
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
export interface TransportUpdate {
|
|
22
|
-
status: 'authorized' | 'cancelled' | 'expired' | 'pending';
|
|
23
|
-
sessionId?: string;
|
|
24
|
-
publicKey?: string;
|
|
25
|
-
userId?: string;
|
|
26
|
-
username?: string;
|
|
27
|
-
[key: string]: unknown;
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
export interface TransportCallbacks {
|
|
31
|
-
onUpdate?: (update: TransportUpdate) => void;
|
|
32
|
-
onConnect?: () => void;
|
|
33
|
-
onDisconnect?: () => void;
|
|
34
|
-
onError?: (error: Error) => void;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
/**
|
|
38
|
-
* Transport Interface
|
|
39
|
-
* All transport implementations must implement this
|
|
40
|
-
*/
|
|
41
|
-
export interface Transport {
|
|
42
|
-
/**
|
|
43
|
-
* Connect to the transport
|
|
44
|
-
*/
|
|
45
|
-
connect(): Promise<void>;
|
|
46
|
-
|
|
47
|
-
/**
|
|
48
|
-
* Disconnect from the transport
|
|
49
|
-
*/
|
|
50
|
-
disconnect(): void;
|
|
51
|
-
|
|
52
|
-
/**
|
|
53
|
-
* Check if currently connected
|
|
54
|
-
*/
|
|
55
|
-
isConnected(): boolean;
|
|
56
|
-
|
|
57
|
-
/**
|
|
58
|
-
* Get the transport type
|
|
59
|
-
*/
|
|
60
|
-
getType(): TransportType;
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
/**
|
|
64
|
-
* Transport Factory
|
|
65
|
-
* Creates the appropriate transport based on availability and configuration
|
|
66
|
-
*/
|
|
67
|
-
export class TransportFactory {
|
|
68
|
-
/**
|
|
69
|
-
* Create a transport with automatic fallback
|
|
70
|
-
* Tries WebSocket first, then SSE, then polling
|
|
71
|
-
*/
|
|
72
|
-
static async create(
|
|
73
|
-
config: TransportConfig,
|
|
74
|
-
callbacks: TransportCallbacks
|
|
75
|
-
): Promise<Transport> {
|
|
76
|
-
// Try WebSocket first (best for real-time)
|
|
77
|
-
if (await this.isWebSocketAvailable()) {
|
|
78
|
-
try {
|
|
79
|
-
return new WebSocketTransport(config, callbacks);
|
|
80
|
-
} catch (error) {
|
|
81
|
-
// Fall through to SSE
|
|
82
|
-
}
|
|
83
|
-
}
|
|
84
|
-
|
|
85
|
-
// Try SSE second (good for one-way updates)
|
|
86
|
-
if (await this.isSSEAvailable()) {
|
|
87
|
-
try {
|
|
88
|
-
return new SSETransport(config, callbacks);
|
|
89
|
-
} catch (error) {
|
|
90
|
-
// Fall through to polling
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
// Fall back to polling (always available)
|
|
95
|
-
return new PollingTransport(config, callbacks);
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
/**
|
|
99
|
-
* Check if WebSocket is available
|
|
100
|
-
*/
|
|
101
|
-
private static async isWebSocketAvailable(): Promise<boolean> {
|
|
102
|
-
// WebSocket is available in browsers and Node.js with socket.io-client
|
|
103
|
-
return typeof window !== 'undefined' || typeof process !== 'undefined';
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
/**
|
|
107
|
-
* Check if SSE is available
|
|
108
|
-
*/
|
|
109
|
-
private static async isSSEAvailable(): Promise<boolean> {
|
|
110
|
-
// SSE is available in browsers via EventSource
|
|
111
|
-
// In Node.js, would need a polyfill or library
|
|
112
|
-
return typeof EventSource !== 'undefined' ||
|
|
113
|
-
(typeof window !== 'undefined' && 'EventSource' in window);
|
|
114
|
-
}
|
|
115
|
-
}
|
|
116
|
-
|
|
117
|
-
/**
|
|
118
|
-
* WebSocket Transport Implementation
|
|
119
|
-
* Uses socket.io-client for WebSocket connections
|
|
120
|
-
*/
|
|
121
|
-
class WebSocketTransport implements Transport {
|
|
122
|
-
private socket: any = null;
|
|
123
|
-
private config: TransportConfig;
|
|
124
|
-
private callbacks: TransportCallbacks;
|
|
125
|
-
private connected = false;
|
|
126
|
-
|
|
127
|
-
constructor(config: TransportConfig, callbacks: TransportCallbacks) {
|
|
128
|
-
this.config = config;
|
|
129
|
-
this.callbacks = callbacks;
|
|
130
|
-
}
|
|
131
|
-
|
|
132
|
-
async connect(): Promise<void> {
|
|
133
|
-
// Dynamic import to avoid bundling socket.io-client if not needed
|
|
134
|
-
let io: any;
|
|
135
|
-
try {
|
|
136
|
-
io = (await import('socket.io-client')).default;
|
|
137
|
-
} catch (error) {
|
|
138
|
-
throw new Error('socket.io-client is required for WebSocket transport. Install it as a dependency.');
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
const url = this.config.namespace
|
|
142
|
-
? `${this.config.baseURL}/${this.config.namespace}`
|
|
143
|
-
: this.config.baseURL;
|
|
144
|
-
|
|
145
|
-
const socketOptions: any = {
|
|
146
|
-
transports: ['websocket', 'polling'],
|
|
147
|
-
reconnection: true,
|
|
148
|
-
reconnectionAttempts: this.config.reconnectAttempts ?? 3,
|
|
149
|
-
reconnectionDelay: this.config.reconnectDelay ?? 1000,
|
|
150
|
-
};
|
|
151
|
-
|
|
152
|
-
if (this.config.accessToken) {
|
|
153
|
-
socketOptions.auth = { token: this.config.accessToken };
|
|
154
|
-
}
|
|
155
|
-
|
|
156
|
-
this.socket = io(url, socketOptions);
|
|
157
|
-
|
|
158
|
-
this.socket.on('connect', () => {
|
|
159
|
-
this.connected = true;
|
|
160
|
-
if (this.config.sessionToken) {
|
|
161
|
-
this.socket.emit('join', this.config.sessionToken);
|
|
162
|
-
}
|
|
163
|
-
this.callbacks.onConnect?.();
|
|
164
|
-
});
|
|
165
|
-
|
|
166
|
-
this.socket.on('auth_update', (payload: TransportUpdate) => {
|
|
167
|
-
this.callbacks.onUpdate?.(payload);
|
|
168
|
-
});
|
|
169
|
-
|
|
170
|
-
this.socket.on('connect_error', (error: Error) => {
|
|
171
|
-
this.callbacks.onError?.(error);
|
|
172
|
-
});
|
|
173
|
-
|
|
174
|
-
this.socket.on('disconnect', () => {
|
|
175
|
-
this.connected = false;
|
|
176
|
-
this.callbacks.onDisconnect?.();
|
|
177
|
-
});
|
|
178
|
-
}
|
|
179
|
-
|
|
180
|
-
disconnect(): void {
|
|
181
|
-
if (this.socket) {
|
|
182
|
-
this.socket.disconnect();
|
|
183
|
-
this.socket = null;
|
|
184
|
-
this.connected = false;
|
|
185
|
-
}
|
|
186
|
-
}
|
|
187
|
-
|
|
188
|
-
isConnected(): boolean {
|
|
189
|
-
return this.connected && this.socket?.connected === true;
|
|
190
|
-
}
|
|
191
|
-
|
|
192
|
-
getType(): TransportType {
|
|
193
|
-
return 'websocket';
|
|
194
|
-
}
|
|
195
|
-
}
|
|
196
|
-
|
|
197
|
-
/**
|
|
198
|
-
* SSE Transport Implementation
|
|
199
|
-
* Uses EventSource for Server-Sent Events
|
|
200
|
-
*/
|
|
201
|
-
class SSETransport implements Transport {
|
|
202
|
-
private eventSource: EventSource | null = null;
|
|
203
|
-
private config: TransportConfig;
|
|
204
|
-
private callbacks: TransportCallbacks;
|
|
205
|
-
private connected = false;
|
|
206
|
-
|
|
207
|
-
constructor(config: TransportConfig, callbacks: TransportCallbacks) {
|
|
208
|
-
this.config = config;
|
|
209
|
-
this.callbacks = callbacks;
|
|
210
|
-
}
|
|
211
|
-
|
|
212
|
-
async connect(): Promise<void> {
|
|
213
|
-
if (typeof EventSource === 'undefined') {
|
|
214
|
-
throw new Error('EventSource is not available in this environment');
|
|
215
|
-
}
|
|
216
|
-
|
|
217
|
-
const url = this.config.sessionToken
|
|
218
|
-
? `${this.config.baseURL}/auth/session/stream/${this.config.sessionToken}`
|
|
219
|
-
: `${this.config.baseURL}/auth/session/stream`;
|
|
220
|
-
|
|
221
|
-
this.eventSource = new EventSource(url);
|
|
222
|
-
|
|
223
|
-
this.eventSource.onopen = () => {
|
|
224
|
-
this.connected = true;
|
|
225
|
-
this.callbacks.onConnect?.();
|
|
226
|
-
};
|
|
227
|
-
|
|
228
|
-
this.eventSource.onmessage = (event) => {
|
|
229
|
-
try {
|
|
230
|
-
const update = JSON.parse(event.data) as TransportUpdate;
|
|
231
|
-
this.callbacks.onUpdate?.(update);
|
|
232
|
-
} catch (error) {
|
|
233
|
-
this.callbacks.onError?.(error as Error);
|
|
234
|
-
}
|
|
235
|
-
};
|
|
236
|
-
|
|
237
|
-
this.eventSource.onerror = (error) => {
|
|
238
|
-
this.callbacks.onError?.(new Error('SSE connection error'));
|
|
239
|
-
};
|
|
240
|
-
}
|
|
241
|
-
|
|
242
|
-
disconnect(): void {
|
|
243
|
-
if (this.eventSource) {
|
|
244
|
-
this.eventSource.close();
|
|
245
|
-
this.eventSource = null;
|
|
246
|
-
this.connected = false;
|
|
247
|
-
}
|
|
248
|
-
}
|
|
249
|
-
|
|
250
|
-
isConnected(): boolean {
|
|
251
|
-
return this.connected && this.eventSource?.readyState === EventSource.OPEN;
|
|
252
|
-
}
|
|
253
|
-
|
|
254
|
-
getType(): TransportType {
|
|
255
|
-
return 'sse';
|
|
256
|
-
}
|
|
257
|
-
}
|
|
258
|
-
|
|
259
|
-
/**
|
|
260
|
-
* Polling Transport Implementation
|
|
261
|
-
* Uses HTTP polling as fallback
|
|
262
|
-
*/
|
|
263
|
-
class PollingTransport implements Transport {
|
|
264
|
-
private intervalId: ReturnType<typeof setInterval> | null = null;
|
|
265
|
-
private config: TransportConfig;
|
|
266
|
-
private callbacks: TransportCallbacks;
|
|
267
|
-
private connected = false;
|
|
268
|
-
private abortController: AbortController | null = null;
|
|
269
|
-
|
|
270
|
-
constructor(config: TransportConfig, callbacks: TransportCallbacks) {
|
|
271
|
-
this.config = config;
|
|
272
|
-
this.callbacks = callbacks;
|
|
273
|
-
}
|
|
274
|
-
|
|
275
|
-
async connect(): Promise<void> {
|
|
276
|
-
this.connected = true;
|
|
277
|
-
this.callbacks.onConnect?.();
|
|
278
|
-
|
|
279
|
-
const poll = async () => {
|
|
280
|
-
if (!this.config.sessionToken) {
|
|
281
|
-
return;
|
|
282
|
-
}
|
|
283
|
-
|
|
284
|
-
try {
|
|
285
|
-
this.abortController = new AbortController();
|
|
286
|
-
const response = await fetch(
|
|
287
|
-
`${this.config.baseURL}/api/auth/session/status/${this.config.sessionToken}`,
|
|
288
|
-
{
|
|
289
|
-
signal: this.abortController.signal,
|
|
290
|
-
headers: this.config.accessToken
|
|
291
|
-
? { Authorization: `Bearer ${this.config.accessToken}` }
|
|
292
|
-
: {},
|
|
293
|
-
}
|
|
294
|
-
);
|
|
295
|
-
|
|
296
|
-
if (!response.ok) {
|
|
297
|
-
throw new Error(`Polling failed: ${response.statusText}`);
|
|
298
|
-
}
|
|
299
|
-
|
|
300
|
-
const data = await response.json();
|
|
301
|
-
|
|
302
|
-
if (data.authorized && data.sessionId) {
|
|
303
|
-
this.callbacks.onUpdate?.({
|
|
304
|
-
status: 'authorized',
|
|
305
|
-
sessionId: data.sessionId,
|
|
306
|
-
publicKey: data.publicKey,
|
|
307
|
-
});
|
|
308
|
-
} else if (data.status === 'expired') {
|
|
309
|
-
this.callbacks.onUpdate?.({ status: 'expired' });
|
|
310
|
-
} else if (data.status === 'cancelled') {
|
|
311
|
-
this.callbacks.onUpdate?.({ status: 'cancelled' });
|
|
312
|
-
}
|
|
313
|
-
} catch (error) {
|
|
314
|
-
if (error instanceof Error && error.name !== 'AbortError') {
|
|
315
|
-
this.callbacks.onError?.(error);
|
|
316
|
-
}
|
|
317
|
-
}
|
|
318
|
-
};
|
|
319
|
-
|
|
320
|
-
// Poll immediately, then at intervals
|
|
321
|
-
await poll();
|
|
322
|
-
this.intervalId = setInterval(
|
|
323
|
-
poll,
|
|
324
|
-
this.config.pollingInterval ?? 3000
|
|
325
|
-
);
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
disconnect(): void {
|
|
329
|
-
if (this.intervalId) {
|
|
330
|
-
clearInterval(this.intervalId);
|
|
331
|
-
this.intervalId = null;
|
|
332
|
-
}
|
|
333
|
-
if (this.abortController) {
|
|
334
|
-
this.abortController.abort();
|
|
335
|
-
this.abortController = null;
|
|
336
|
-
}
|
|
337
|
-
this.connected = false;
|
|
338
|
-
this.callbacks.onDisconnect?.();
|
|
339
|
-
}
|
|
340
|
-
|
|
341
|
-
isConnected(): boolean {
|
|
342
|
-
return this.connected && this.intervalId !== null;
|
|
343
|
-
}
|
|
344
|
-
|
|
345
|
-
getType(): TransportType {
|
|
346
|
-
return 'polling';
|
|
347
|
-
}
|
|
348
|
-
}
|
|
349
|
-
|
|
@@ -1,73 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Shared Utilities
|
|
3
|
-
*
|
|
4
|
-
* Common utility functions used across Accounts, Services SDK, and API packages.
|
|
5
|
-
*/
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* Get a shortened display version of a public key
|
|
9
|
-
* Format: first 8 chars ... last 8 chars
|
|
10
|
-
*/
|
|
11
|
-
export function shortenPublicKey(publicKey: string): string {
|
|
12
|
-
if (publicKey.length <= 16) return publicKey;
|
|
13
|
-
return `${publicKey.slice(0, 8)}...${publicKey.slice(-8)}`;
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
/**
|
|
17
|
-
* Generate a secure random session token
|
|
18
|
-
* Uses crypto.randomBytes (Node) or Web Crypto API (Browser/RN)
|
|
19
|
-
*/
|
|
20
|
-
export async function generateSessionToken(size: number = 32): Promise<string> {
|
|
21
|
-
// Use platform-appropriate random bytes
|
|
22
|
-
if (typeof window !== 'undefined' && window.crypto) {
|
|
23
|
-
// Web platform
|
|
24
|
-
const array = new Uint8Array(size);
|
|
25
|
-
window.crypto.getRandomValues(array);
|
|
26
|
-
return Array.from(array, byte => byte.toString(16).padStart(2, '0')).join('');
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
if (typeof process !== 'undefined' && process.versions?.node) {
|
|
30
|
-
// Node.js platform
|
|
31
|
-
// eslint-disable-next-line @typescript-eslint/no-implied-eval
|
|
32
|
-
const getCrypto = new Function('return require("crypto")');
|
|
33
|
-
const crypto = getCrypto();
|
|
34
|
-
return crypto.randomBytes(size).toString('hex');
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
// React Native - will be handled by platform adapter
|
|
38
|
-
// For now, throw an error if we can't determine platform
|
|
39
|
-
throw new Error('Unable to generate session token: no crypto implementation available');
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
/**
|
|
43
|
-
* Generate a session token synchronously (Node.js only)
|
|
44
|
-
*/
|
|
45
|
-
export function generateSessionTokenSync(size: number = 32): string {
|
|
46
|
-
if (typeof process === 'undefined' || !process.versions?.node) {
|
|
47
|
-
throw new Error('generateSessionTokenSync can only be used in Node.js');
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
// eslint-disable-next-line @typescript-eslint/no-implied-eval
|
|
51
|
-
const getCrypto = new Function('return require("crypto")');
|
|
52
|
-
const crypto = getCrypto();
|
|
53
|
-
return crypto.randomBytes(size).toString('hex');
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
/**
|
|
57
|
-
* Convert bytes to hex string
|
|
58
|
-
*/
|
|
59
|
-
export function bytesToHex(bytes: Uint8Array): string {
|
|
60
|
-
return Array.from(bytes, byte => byte.toString(16).padStart(2, '0')).join('');
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
/**
|
|
64
|
-
* Convert hex string to bytes
|
|
65
|
-
*/
|
|
66
|
-
export function hexToBytes(hex: string): Uint8Array {
|
|
67
|
-
const bytes = new Uint8Array(hex.length / 2);
|
|
68
|
-
for (let i = 0; i < hex.length; i += 2) {
|
|
69
|
-
bytes[i / 2] = parseInt(hex.substr(i, 2), 16);
|
|
70
|
-
}
|
|
71
|
-
return bytes;
|
|
72
|
-
}
|
|
73
|
-
|