@nurama/sdk 0.0.0-stage → 1.4.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/LICENSE +202 -0
- package/NOTICE +5 -0
- package/README.md +1080 -2
- package/dist/BotClient.d.ts +66 -0
- package/dist/BotClient.d.ts.map +1 -0
- package/dist/BotClient.js +68 -0
- package/dist/BotClient.js.map +1 -0
- package/dist/NuramaClient.d.ts +448 -0
- package/dist/NuramaClient.d.ts.map +1 -0
- package/dist/NuramaClient.js +864 -0
- package/dist/NuramaClient.js.map +1 -0
- package/dist/browser/nurama-bot-sdk.js +11780 -0
- package/dist/browser/nurama-bot-sdk.min.js +1 -0
- package/dist/browser/nurama-sdk.js +11732 -0
- package/dist/browser/nurama-sdk.min.js +1 -0
- package/dist/routes/ai.d.ts +280 -0
- package/dist/routes/ai.d.ts.map +1 -0
- package/dist/routes/ai.js +173 -0
- package/dist/routes/ai.js.map +1 -0
- package/dist/routes/asset.d.ts +493 -0
- package/dist/routes/asset.d.ts.map +1 -0
- package/dist/routes/asset.js +848 -0
- package/dist/routes/asset.js.map +1 -0
- package/dist/routes/auth.d.ts +218 -0
- package/dist/routes/auth.d.ts.map +1 -0
- package/dist/routes/auth.js +454 -0
- package/dist/routes/auth.js.map +1 -0
- package/dist/routes/blogPosts.d.ts +17 -0
- package/dist/routes/blogPosts.d.ts.map +1 -0
- package/dist/routes/blogPosts.js +29 -0
- package/dist/routes/blogPosts.js.map +1 -0
- package/dist/routes/board.d.ts +187 -0
- package/dist/routes/board.d.ts.map +1 -0
- package/dist/routes/board.js +270 -0
- package/dist/routes/board.js.map +1 -0
- package/dist/routes/bot.d.ts +147 -0
- package/dist/routes/bot.d.ts.map +1 -0
- package/dist/routes/bot.js +157 -0
- package/dist/routes/bot.js.map +1 -0
- package/dist/routes/chat.d.ts +842 -0
- package/dist/routes/chat.d.ts.map +1 -0
- package/dist/routes/chat.js +863 -0
- package/dist/routes/chat.js.map +1 -0
- package/dist/routes/chatAi.d.ts +51 -0
- package/dist/routes/chatAi.d.ts.map +1 -0
- package/dist/routes/chatAi.js +109 -0
- package/dist/routes/chatAi.js.map +1 -0
- package/dist/routes/config.d.ts +11 -0
- package/dist/routes/config.d.ts.map +1 -0
- package/dist/routes/config.js +24 -0
- package/dist/routes/config.js.map +1 -0
- package/dist/routes/convo.d.ts +169 -0
- package/dist/routes/convo.d.ts.map +1 -0
- package/dist/routes/convo.js +284 -0
- package/dist/routes/convo.js.map +1 -0
- package/dist/routes/credits.d.ts +82 -0
- package/dist/routes/credits.d.ts.map +1 -0
- package/dist/routes/credits.js +49 -0
- package/dist/routes/credits.js.map +1 -0
- package/dist/routes/device.d.ts +74 -0
- package/dist/routes/device.d.ts.map +1 -0
- package/dist/routes/device.js +122 -0
- package/dist/routes/device.js.map +1 -0
- package/dist/routes/folder.d.ts +75 -0
- package/dist/routes/folder.d.ts.map +1 -0
- package/dist/routes/folder.js +99 -0
- package/dist/routes/folder.js.map +1 -0
- package/dist/routes/invite.d.ts +61 -0
- package/dist/routes/invite.d.ts.map +1 -0
- package/dist/routes/invite.js +86 -0
- package/dist/routes/invite.js.map +1 -0
- package/dist/routes/joinLink.d.ts +38 -0
- package/dist/routes/joinLink.d.ts.map +1 -0
- package/dist/routes/joinLink.js +81 -0
- package/dist/routes/joinLink.js.map +1 -0
- package/dist/routes/membership.d.ts +116 -0
- package/dist/routes/membership.d.ts.map +1 -0
- package/dist/routes/membership.js +183 -0
- package/dist/routes/membership.js.map +1 -0
- package/dist/routes/notification.d.ts +103 -0
- package/dist/routes/notification.d.ts.map +1 -0
- package/dist/routes/notification.js +89 -0
- package/dist/routes/notification.js.map +1 -0
- package/dist/routes/payment.d.ts +56 -0
- package/dist/routes/payment.d.ts.map +1 -0
- package/dist/routes/payment.js +78 -0
- package/dist/routes/payment.js.map +1 -0
- package/dist/routes/product.d.ts +43 -0
- package/dist/routes/product.d.ts.map +1 -0
- package/dist/routes/product.js +53 -0
- package/dist/routes/product.js.map +1 -0
- package/dist/routes/project.d.ts +821 -0
- package/dist/routes/project.d.ts.map +1 -0
- package/dist/routes/project.js +1153 -0
- package/dist/routes/project.js.map +1 -0
- package/dist/routes/public.d.ts +269 -0
- package/dist/routes/public.d.ts.map +1 -0
- package/dist/routes/public.js +412 -0
- package/dist/routes/public.js.map +1 -0
- package/dist/routes/scratch.d.ts +70 -0
- package/dist/routes/scratch.d.ts.map +1 -0
- package/dist/routes/scratch.js +67 -0
- package/dist/routes/scratch.js.map +1 -0
- package/dist/routes/settings.d.ts +102 -0
- package/dist/routes/settings.d.ts.map +1 -0
- package/dist/routes/settings.js +94 -0
- package/dist/routes/settings.js.map +1 -0
- package/dist/routes/shortlink.d.ts +79 -0
- package/dist/routes/shortlink.d.ts.map +1 -0
- package/dist/routes/shortlink.js +25 -0
- package/dist/routes/shortlink.js.map +1 -0
- package/dist/routes/socket.d.ts +108 -0
- package/dist/routes/socket.d.ts.map +1 -0
- package/dist/routes/socket.js +555 -0
- package/dist/routes/socket.js.map +1 -0
- package/dist/routes/storage.d.ts +44 -0
- package/dist/routes/storage.d.ts.map +1 -0
- package/dist/routes/storage.js +49 -0
- package/dist/routes/storage.js.map +1 -0
- package/dist/routes/subscription.d.ts +184 -0
- package/dist/routes/subscription.d.ts.map +1 -0
- package/dist/routes/subscription.js +219 -0
- package/dist/routes/subscription.js.map +1 -0
- package/dist/routes/supportChat.d.ts +40 -0
- package/dist/routes/supportChat.d.ts.map +1 -0
- package/dist/routes/supportChat.js +53 -0
- package/dist/routes/supportChat.js.map +1 -0
- package/dist/routes/supportTicket.d.ts +89 -0
- package/dist/routes/supportTicket.d.ts.map +1 -0
- package/dist/routes/supportTicket.js +54 -0
- package/dist/routes/supportTicket.js.map +1 -0
- package/dist/routes/tag.d.ts +72 -0
- package/dist/routes/tag.d.ts.map +1 -0
- package/dist/routes/tag.js +81 -0
- package/dist/routes/tag.js.map +1 -0
- package/dist/routes/task.d.ts +252 -0
- package/dist/routes/task.d.ts.map +1 -0
- package/dist/routes/task.js +284 -0
- package/dist/routes/task.js.map +1 -0
- package/dist/routes/taskRelation.d.ts +80 -0
- package/dist/routes/taskRelation.d.ts.map +1 -0
- package/dist/routes/taskRelation.js +71 -0
- package/dist/routes/taskRelation.js.map +1 -0
- package/dist/routes/token.d.ts +75 -0
- package/dist/routes/token.d.ts.map +1 -0
- package/dist/routes/token.js +51 -0
- package/dist/routes/token.js.map +1 -0
- package/dist/routes/user.d.ts +112 -0
- package/dist/routes/user.d.ts.map +1 -0
- package/dist/routes/user.js +151 -0
- package/dist/routes/user.js.map +1 -0
- package/dist/routes/version.d.ts +42 -0
- package/dist/routes/version.d.ts.map +1 -0
- package/dist/routes/version.js +38 -0
- package/dist/routes/version.js.map +1 -0
- package/dist/routes/webhook.d.ts +170 -0
- package/dist/routes/webhook.d.ts.map +1 -0
- package/dist/routes/webhook.js +173 -0
- package/dist/routes/webhook.js.map +1 -0
- package/dist/routes/workspace.d.ts +120 -0
- package/dist/routes/workspace.d.ts.map +1 -0
- package/dist/routes/workspace.js +199 -0
- package/dist/routes/workspace.js.map +1 -0
- package/dist/utils/uploadSessionManager.d.ts +133 -0
- package/dist/utils/uploadSessionManager.d.ts.map +1 -0
- package/dist/utils/uploadSessionManager.js +321 -0
- package/dist/utils/uploadSessionManager.js.map +1 -0
- package/dist/utils/urlParams.d.ts +35 -0
- package/dist/utils/urlParams.d.ts.map +1 -0
- package/dist/utils/urlParams.js +146 -0
- package/dist/utils/urlParams.js.map +1 -0
- package/dist/version.d.ts +15 -0
- package/dist/version.d.ts.map +1 -0
- package/dist/version.js +12 -0
- package/dist/version.js.map +1 -0
- package/package.json +87 -3
- package/src/BotClient.ts +113 -0
- package/src/NuramaClient.ts +1193 -0
- package/src/bot-browser-entry.js +15 -0
- package/src/browser-entry.js +20 -0
- package/src/routes/ai.ts +378 -0
- package/src/routes/asset.ts +1104 -0
- package/src/routes/auth.ts +587 -0
- package/src/routes/blogPosts.ts +29 -0
- package/src/routes/board.ts +403 -0
- package/src/routes/bot.ts +257 -0
- package/src/routes/chat.ts +1292 -0
- package/src/routes/chatAi.ts +125 -0
- package/src/routes/config.ts +31 -0
- package/src/routes/convo.ts +321 -0
- package/src/routes/credits.ts +112 -0
- package/src/routes/device.ts +133 -0
- package/src/routes/folder.ts +154 -0
- package/src/routes/invite.ts +133 -0
- package/src/routes/joinLink.ts +100 -0
- package/src/routes/membership.ts +237 -0
- package/src/routes/notification.ts +166 -0
- package/src/routes/payment.ts +104 -0
- package/src/routes/product.ts +67 -0
- package/src/routes/project.ts +1528 -0
- package/src/routes/public.ts +496 -0
- package/src/routes/scratch.ts +94 -0
- package/src/routes/settings.ts +152 -0
- package/src/routes/shortlink.ts +90 -0
- package/src/routes/socket.ts +739 -0
- package/src/routes/storage.ts +83 -0
- package/src/routes/subscription.ts +307 -0
- package/src/routes/supportChat.ts +62 -0
- package/src/routes/supportTicket.ts +114 -0
- package/src/routes/tag.ts +131 -0
- package/src/routes/task.ts +431 -0
- package/src/routes/taskRelation.ts +125 -0
- package/src/routes/token.ts +113 -0
- package/src/routes/user.ts +214 -0
- package/src/routes/version.ts +62 -0
- package/src/routes/webhook.ts +295 -0
- package/src/routes/workspace.ts +223 -0
- package/src/utils/uploadSessionManager.ts +407 -0
- package/src/utils/urlParams.ts +181 -0
- package/src/version.ts +22 -0
|
@@ -0,0 +1,214 @@
|
|
|
1
|
+
import NuramaClient from '../NuramaClient.js';
|
|
2
|
+
import { type User, type PublicUser } from '@nurama/types';
|
|
3
|
+
|
|
4
|
+
export interface FileData {
|
|
5
|
+
name: string;
|
|
6
|
+
checksum: string;
|
|
7
|
+
sizeInMB: number;
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
// Define the type for the update data based on backend validation
|
|
11
|
+
export interface UpdateUserData {
|
|
12
|
+
email?: string;
|
|
13
|
+
userName?: string;
|
|
14
|
+
password?: string;
|
|
15
|
+
firstName?: string;
|
|
16
|
+
middleName?: string;
|
|
17
|
+
lastName?: string;
|
|
18
|
+
company?: string;
|
|
19
|
+
displayName?: string;
|
|
20
|
+
color?: string;
|
|
21
|
+
allowOauthAutolink?: boolean;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export interface PreferencesData {
|
|
25
|
+
hide?: string[];
|
|
26
|
+
// Per-user UX dismissals — anything the user has explicitly opted
|
|
27
|
+
// out of seeing again. The BE merges this object one level deep, so a
|
|
28
|
+
// write to one `dismissed.*` key preserves its siblings. For each
|
|
29
|
+
// inner array the server treats the value as the full list — callers
|
|
30
|
+
// should merge the new id into the existing array before sending.
|
|
31
|
+
dismissed?: {
|
|
32
|
+
todos?: string[];
|
|
33
|
+
};
|
|
34
|
+
// Daily-tips carousel state. `disabled` opts out entirely; `lastShownDate`
|
|
35
|
+
// (local `YYYY-MM-DD`) gates the once-per-day rule cumulatively across
|
|
36
|
+
// workspaces and devices. Merged one level deep by the BE.
|
|
37
|
+
dailyTips?: {
|
|
38
|
+
disabled?: boolean;
|
|
39
|
+
lastShownDate?: string;
|
|
40
|
+
};
|
|
41
|
+
// Per-project feature-intro tutorials the user has seen, keyed by project
|
|
42
|
+
// id. Merged one level deep by the BE.
|
|
43
|
+
featureIntros?: Record<string, string[]>;
|
|
44
|
+
// Preferred date display format. Seeded at registration from the
|
|
45
|
+
// registrant's country (European unless month-first, e.g. the US → american);
|
|
46
|
+
// European is the fallback when unset. User-overridable, incl. ISO (YYYY-MM-DD).
|
|
47
|
+
dateFormat?: 'european' | 'american' | 'iso';
|
|
48
|
+
// Add other preferences
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
// Structural shape only — visible strings are looked up on the FE by
|
|
52
|
+
// `id` against the `auth.todos.<id>.{title,description,actionLabel}`
|
|
53
|
+
// i18n keys. Keeps the backend response language-agnostic.
|
|
54
|
+
export interface UserTodo {
|
|
55
|
+
id: string;
|
|
56
|
+
dismissible: boolean;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
/**
|
|
60
|
+
* Defines user-related methods for the NuramaClient.
|
|
61
|
+
* @param {NuramaClient} client - The NuramaClient instance.
|
|
62
|
+
* @returns {object} An object containing the user-related methods.
|
|
63
|
+
*/
|
|
64
|
+
export default function createUserMethods(client: NuramaClient) {
|
|
65
|
+
// Specify return type more accurately if possible, using UserMethods interface
|
|
66
|
+
return {
|
|
67
|
+
/**
|
|
68
|
+
* Retrieves the public profile of a specific user.
|
|
69
|
+
* Requires authentication.
|
|
70
|
+
* @param {string} userId - The ID of the user to retrieve.
|
|
71
|
+
* @returns {Promise<object>} Public user object.
|
|
72
|
+
*/
|
|
73
|
+
async getUser(userId: string): Promise<PublicUser> {
|
|
74
|
+
if (!userId) {
|
|
75
|
+
throw new Error('userId is required.');
|
|
76
|
+
}
|
|
77
|
+
return client._request({
|
|
78
|
+
method: 'GET',
|
|
79
|
+
endpoint: `/v1/users/${userId}`,
|
|
80
|
+
sendJWT: true,
|
|
81
|
+
});
|
|
82
|
+
},
|
|
83
|
+
|
|
84
|
+
/**
|
|
85
|
+
* Retrieves the current user's profile.
|
|
86
|
+
* Requires authentication.
|
|
87
|
+
* @returns {Promise<PublicUser>} The current user's profile.
|
|
88
|
+
* @throws {Error} If no user ID is found in the token.
|
|
89
|
+
*/
|
|
90
|
+
async getSelf(): Promise<PublicUser> {
|
|
91
|
+
return client._request({
|
|
92
|
+
method: 'GET',
|
|
93
|
+
endpoint: '/v1/users',
|
|
94
|
+
sendJWT: true,
|
|
95
|
+
});
|
|
96
|
+
},
|
|
97
|
+
|
|
98
|
+
/**
|
|
99
|
+
* Deletes the current user.
|
|
100
|
+
* Requires authentication.
|
|
101
|
+
* @returns {Promise<void>}
|
|
102
|
+
*/
|
|
103
|
+
async deleteCurrentUser(): Promise<void> {
|
|
104
|
+
return client._request({
|
|
105
|
+
method: 'DELETE',
|
|
106
|
+
endpoint: '/v1/users',
|
|
107
|
+
sendJWT: true,
|
|
108
|
+
});
|
|
109
|
+
},
|
|
110
|
+
/**
|
|
111
|
+
* Updates the user's avatar.
|
|
112
|
+
* @param {object} fileData - File metadata (e.g., { name, checksum, sizeInMB }).
|
|
113
|
+
* @returns {Promise<object>} Object containing signed URL data and updated user info.
|
|
114
|
+
*/
|
|
115
|
+
async updateAvatar(fileData: FileData): Promise<any> {
|
|
116
|
+
return client._request({
|
|
117
|
+
method: 'PUT',
|
|
118
|
+
endpoint: '/v1/users/avatar',
|
|
119
|
+
body: fileData,
|
|
120
|
+
sendJWT: true,
|
|
121
|
+
});
|
|
122
|
+
},
|
|
123
|
+
/**
|
|
124
|
+
* Creates a new avatar for the user.
|
|
125
|
+
* @param {object} fileData - File metadata (e.g., { name, checksum, sizeInMB }).
|
|
126
|
+
* @returns {Promise<object>} Object containing signed URL data and updated user info.
|
|
127
|
+
*/
|
|
128
|
+
async createAvatar(fileData: FileData): Promise<any> {
|
|
129
|
+
return client._request({
|
|
130
|
+
method: 'POST',
|
|
131
|
+
endpoint: '/v1/users/avatar',
|
|
132
|
+
body: fileData,
|
|
133
|
+
sendJWT: true,
|
|
134
|
+
});
|
|
135
|
+
},
|
|
136
|
+
/**
|
|
137
|
+
* Updates the user's preferences.
|
|
138
|
+
* @param {object} preferenceData - Preference data to update (e.g., { hide: ['feedHint'] }).
|
|
139
|
+
* @returns {Promise<object>} Updated user object.
|
|
140
|
+
*/
|
|
141
|
+
async updatePreferences(preferenceData: PreferencesData): Promise<User> {
|
|
142
|
+
return client._request({
|
|
143
|
+
method: 'PATCH',
|
|
144
|
+
endpoint: '/v1/users/preferences',
|
|
145
|
+
body: preferenceData,
|
|
146
|
+
sendJWT: true,
|
|
147
|
+
});
|
|
148
|
+
},
|
|
149
|
+
|
|
150
|
+
/**
|
|
151
|
+
* Record that the current user has seen a one-time UI element (welcome
|
|
152
|
+
* video, tutorial coachmark). Idempotent. Returns the updated user.
|
|
153
|
+
* @param {string} element - one-time element key (see backend oneTimeElements).
|
|
154
|
+
*/
|
|
155
|
+
async markSeen(element: string): Promise<User> {
|
|
156
|
+
return client._request({
|
|
157
|
+
method: 'POST',
|
|
158
|
+
endpoint: '/v1/users/has-seen',
|
|
159
|
+
body: { element },
|
|
160
|
+
sendJWT: true,
|
|
161
|
+
});
|
|
162
|
+
},
|
|
163
|
+
|
|
164
|
+
/**
|
|
165
|
+
* Remove one-time UI elements from the current user's `hasSeen` so they
|
|
166
|
+
* display again. Pass specific element keys, or omit to clear ALL.
|
|
167
|
+
* Returns the updated user.
|
|
168
|
+
* @param {string[]} [elements] - elements to remove; omit to clear all.
|
|
169
|
+
*/
|
|
170
|
+
async unmarkSeen(elements?: string[]): Promise<User> {
|
|
171
|
+
return client._request({
|
|
172
|
+
method: 'DELETE',
|
|
173
|
+
endpoint: '/v1/users/has-seen',
|
|
174
|
+
body: elements ? { elements } : {},
|
|
175
|
+
sendJWT: true,
|
|
176
|
+
});
|
|
177
|
+
},
|
|
178
|
+
|
|
179
|
+
/**
|
|
180
|
+
* Updates the logged-in user's profile.
|
|
181
|
+
* Requires authentication.
|
|
182
|
+
* At least one field must be provided.
|
|
183
|
+
* @param {UpdateUserData} updateData - The user data fields to update.
|
|
184
|
+
* @returns {Promise<User>} The updated user object.
|
|
185
|
+
*/
|
|
186
|
+
async updateSelf(updateData: UpdateUserData): Promise<User> {
|
|
187
|
+
// Ensure at least one key is present, matching backend validation .min(1)
|
|
188
|
+
if (Object.keys(updateData).length === 0) {
|
|
189
|
+
throw new Error('At least one field must be provided to update the user.');
|
|
190
|
+
}
|
|
191
|
+
return client._request<User>({
|
|
192
|
+
method: 'PATCH',
|
|
193
|
+
endpoint: '/v1/users', // Endpoint for updating the logged-in user
|
|
194
|
+
body: updateData,
|
|
195
|
+
sendJWT: true,
|
|
196
|
+
});
|
|
197
|
+
},
|
|
198
|
+
|
|
199
|
+
/**
|
|
200
|
+
* Get the current user's active site-level Todos for the onboarding
|
|
201
|
+
* drawer. Returns only todos whose completion condition isn't met and
|
|
202
|
+
* (for dismissibles) that the user hasn't opted out of. Server
|
|
203
|
+
* computes from live state — no caching on the server side, so a
|
|
204
|
+
* fresh call always reflects ground truth.
|
|
205
|
+
*/
|
|
206
|
+
async getTodos(): Promise<{ todos: UserTodo[] }> {
|
|
207
|
+
return client._request<{ todos: UserTodo[] }>({
|
|
208
|
+
method: 'GET',
|
|
209
|
+
endpoint: '/v1/users/todos',
|
|
210
|
+
sendJWT: true,
|
|
211
|
+
});
|
|
212
|
+
},
|
|
213
|
+
};
|
|
214
|
+
}
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import NuramaClient from '../NuramaClient.js';
|
|
2
|
+
|
|
3
|
+
// --- Response Interfaces ---
|
|
4
|
+
export interface CommitResponse {
|
|
5
|
+
buildCommit: string;
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
export interface HealthStatus {
|
|
9
|
+
status: 'healthy' | 'degraded' | 'unhealthy';
|
|
10
|
+
/** Epoch milliseconds when the check ran. */
|
|
11
|
+
timestamp: number;
|
|
12
|
+
/** Process uptime in seconds. */
|
|
13
|
+
uptime: number;
|
|
14
|
+
/** Present when status is `degraded` or `unhealthy`. */
|
|
15
|
+
reason?: string;
|
|
16
|
+
postgres: { status: 'connected' | 'disconnected'; [key: string]: unknown };
|
|
17
|
+
memory: Record<string, unknown>;
|
|
18
|
+
[key: string]: unknown;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
// --- Method Definitions ---
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* Defines version-related methods for the NuramaClient.
|
|
25
|
+
* @param {NuramaClient} client - The NuramaClient instance.
|
|
26
|
+
* @returns {object} An object containing the version-related methods.
|
|
27
|
+
*/
|
|
28
|
+
export default function createVersionMethods(client: NuramaClient) {
|
|
29
|
+
return {
|
|
30
|
+
/**
|
|
31
|
+
* Retrieves the latest git commit hash of the deployed application.
|
|
32
|
+
* This is a public endpoint and does not require authentication.
|
|
33
|
+
* @returns {Promise<CommitResponse>} An object containing the buildCommit hash.
|
|
34
|
+
*/
|
|
35
|
+
async getCommitHash(): Promise<CommitResponse> {
|
|
36
|
+
return client._request<CommitResponse>({
|
|
37
|
+
method: 'GET',
|
|
38
|
+
endpoint: '/v1/version/commit',
|
|
39
|
+
sendJWT: false,
|
|
40
|
+
});
|
|
41
|
+
},
|
|
42
|
+
|
|
43
|
+
/**
|
|
44
|
+
* Retrieves the API health report (database connectivity, memory, uptime).
|
|
45
|
+
* Public endpoint. Resolves normally for `healthy` and `degraded`; the API
|
|
46
|
+
* responds 503 for `unhealthy`, which surfaces as a thrown error with `status: 503`
|
|
47
|
+
* and the report on `data`.
|
|
48
|
+
* @returns {Promise<HealthStatus>} The health report.
|
|
49
|
+
*/
|
|
50
|
+
async getHealth(): Promise<HealthStatus> {
|
|
51
|
+
return client._request<HealthStatus>({
|
|
52
|
+
method: 'GET',
|
|
53
|
+
endpoint: '/v1/version/health',
|
|
54
|
+
sendJWT: false,
|
|
55
|
+
bypassCache: true,
|
|
56
|
+
});
|
|
57
|
+
},
|
|
58
|
+
};
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
// --- Export Method Type ---
|
|
62
|
+
export type VersionMethods = ReturnType<typeof createVersionMethods>;
|
|
@@ -0,0 +1,295 @@
|
|
|
1
|
+
import NuramaClient from '../NuramaClient.js';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Wire-format webhook event names. Mirrors the backend's
|
|
5
|
+
* `@config/webhookEvents` registry. New events land here and on the
|
|
6
|
+
* backend together; the additive-only payload contract means receivers
|
|
7
|
+
* pinned to a specific event name keep working as fields are added.
|
|
8
|
+
*/
|
|
9
|
+
export type WebhookEvent =
|
|
10
|
+
| 'task.created'
|
|
11
|
+
| 'task.updated'
|
|
12
|
+
| 'task.deleted'
|
|
13
|
+
| 'chat.message.created'
|
|
14
|
+
| 'asset.published'
|
|
15
|
+
| 'webhook.test';
|
|
16
|
+
|
|
17
|
+
export type WebhookSubscriptionStatus = 'active' | 'paused' | 'failedOut';
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Public shape of a webhook subscription. Never includes the signing
|
|
21
|
+
* secret or the encrypted ciphertext — those are server-only fields.
|
|
22
|
+
*/
|
|
23
|
+
export interface WebhookSubscription {
|
|
24
|
+
id: string;
|
|
25
|
+
workspaceId: string;
|
|
26
|
+
appId?: string | null;
|
|
27
|
+
name: string;
|
|
28
|
+
url: string;
|
|
29
|
+
events: WebhookEvent[];
|
|
30
|
+
status: WebhookSubscriptionStatus;
|
|
31
|
+
failedOutAt?: string | null;
|
|
32
|
+
failedOutReason?: string | null;
|
|
33
|
+
/**
|
|
34
|
+
* Optional expiration. When set and in the past, the worker stops
|
|
35
|
+
* fanning new attempts to this subscription, and any in-flight
|
|
36
|
+
* attempts DLQ with a clear reason rather than retrying. Null = no
|
|
37
|
+
* expiry; the subscription delivers indefinitely until manually
|
|
38
|
+
* paused or deleted.
|
|
39
|
+
*/
|
|
40
|
+
expiresAt?: string | null;
|
|
41
|
+
createdAt: string;
|
|
42
|
+
updatedAt: string;
|
|
43
|
+
createdById: string;
|
|
44
|
+
lastDeliveryAt?: string | null;
|
|
45
|
+
lastSuccessAt?: string | null;
|
|
46
|
+
lastFailureAt?: string | null;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
export interface CreateWebhookData {
|
|
50
|
+
name: string;
|
|
51
|
+
url: string;
|
|
52
|
+
events: WebhookEvent[];
|
|
53
|
+
/** Optional ISO timestamp. Must be in the future when set. */
|
|
54
|
+
expiresAt?: string | null;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
export interface UpdateWebhookData {
|
|
58
|
+
name?: string;
|
|
59
|
+
url?: string;
|
|
60
|
+
events?: WebhookEvent[];
|
|
61
|
+
status?: 'active' | 'paused';
|
|
62
|
+
/** Pass null to clear an existing expiry; pass a future ISO date to set / extend. */
|
|
63
|
+
expiresAt?: string | null;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
export interface CreateWebhookResponse {
|
|
67
|
+
subscription: WebhookSubscription;
|
|
68
|
+
/**
|
|
69
|
+
* The HMAC signing secret. Returned ONLY here (and from
|
|
70
|
+
* `rotateWebhookSecret`). The server keeps the ciphertext on the row
|
|
71
|
+
* and cannot recover the plaintext later — the customer must capture
|
|
72
|
+
* it now or rotate.
|
|
73
|
+
*/
|
|
74
|
+
signingSecret: string;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
export interface RotateWebhookSecretResponse extends CreateWebhookResponse {}
|
|
78
|
+
|
|
79
|
+
export type WebhookAttemptStatus = 'pending' | 'inflight' | 'succeeded' | 'failed' | 'dlq';
|
|
80
|
+
|
|
81
|
+
export interface WebhookAttempt {
|
|
82
|
+
id: string;
|
|
83
|
+
notificationId: string;
|
|
84
|
+
subscriptionId: string;
|
|
85
|
+
attempt: number;
|
|
86
|
+
maxAttempts: number;
|
|
87
|
+
status: WebhookAttemptStatus;
|
|
88
|
+
signatureV1: string;
|
|
89
|
+
scheduledAt: string;
|
|
90
|
+
startedAt?: string | null;
|
|
91
|
+
deliveredAt?: string | null;
|
|
92
|
+
nextRetryAt?: string | null;
|
|
93
|
+
responseCode?: number | null;
|
|
94
|
+
responseBody?: string | null;
|
|
95
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
96
|
+
responseHeaders?: Record<string, any> | null;
|
|
97
|
+
errorMessage?: string | null;
|
|
98
|
+
createdAt: string;
|
|
99
|
+
updatedAt: string;
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
export interface ListDeliveriesParams {
|
|
103
|
+
limit?: number;
|
|
104
|
+
cursor?: string;
|
|
105
|
+
status?: WebhookAttemptStatus;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
export interface ListDeliveriesResponse {
|
|
109
|
+
items: WebhookAttempt[];
|
|
110
|
+
nextCursor: string | null;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
export interface TestWebhookResponse {
|
|
114
|
+
queued: true;
|
|
115
|
+
message: string;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
/**
|
|
119
|
+
* Outbound webhook subscription management. Admin-gated server-side
|
|
120
|
+
* by `canManageWebhooks`. All operations are workspace-scoped — there
|
|
121
|
+
* is no app-owned surface here yet (Phase 3 / OAuth).
|
|
122
|
+
*/
|
|
123
|
+
export default function createWebhookMethods(client: NuramaClient) {
|
|
124
|
+
return {
|
|
125
|
+
/**
|
|
126
|
+
* Create a webhook subscription. The signing secret is in the
|
|
127
|
+
* response's `secret` field — store it immediately, it cannot be
|
|
128
|
+
* retrieved again.
|
|
129
|
+
*
|
|
130
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
131
|
+
*/
|
|
132
|
+
async createWebhook(
|
|
133
|
+
workspaceId: string,
|
|
134
|
+
data: CreateWebhookData,
|
|
135
|
+
): Promise<CreateWebhookResponse> {
|
|
136
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
137
|
+
return client._request<CreateWebhookResponse>({
|
|
138
|
+
method: 'POST',
|
|
139
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks`,
|
|
140
|
+
body: data,
|
|
141
|
+
sendJWT: true,
|
|
142
|
+
});
|
|
143
|
+
},
|
|
144
|
+
|
|
145
|
+
/**
|
|
146
|
+
* List webhook subscriptions in a workspace. Secrets are never returned.
|
|
147
|
+
*
|
|
148
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
149
|
+
*/
|
|
150
|
+
async listWebhooks(workspaceId: string): Promise<WebhookSubscription[]> {
|
|
151
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
152
|
+
return client._request<WebhookSubscription[]>({
|
|
153
|
+
method: 'GET',
|
|
154
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks`,
|
|
155
|
+
sendJWT: true,
|
|
156
|
+
bypassCache: true,
|
|
157
|
+
});
|
|
158
|
+
},
|
|
159
|
+
|
|
160
|
+
/**
|
|
161
|
+
* Fetch a single webhook subscription by id.
|
|
162
|
+
*
|
|
163
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
164
|
+
*/
|
|
165
|
+
async getWebhook(workspaceId: string, webhookId: string): Promise<WebhookSubscription> {
|
|
166
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
167
|
+
if (!webhookId) throw new Error('webhookId is required.');
|
|
168
|
+
return client._request<WebhookSubscription>({
|
|
169
|
+
method: 'GET',
|
|
170
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks/${webhookId}`,
|
|
171
|
+
sendJWT: true,
|
|
172
|
+
bypassCache: true,
|
|
173
|
+
});
|
|
174
|
+
},
|
|
175
|
+
|
|
176
|
+
/**
|
|
177
|
+
* Update a webhook subscription's url, event filter, or active state.
|
|
178
|
+
*
|
|
179
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
180
|
+
*/
|
|
181
|
+
async updateWebhook(
|
|
182
|
+
workspaceId: string,
|
|
183
|
+
webhookId: string,
|
|
184
|
+
data: UpdateWebhookData,
|
|
185
|
+
): Promise<WebhookSubscription> {
|
|
186
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
187
|
+
if (!webhookId) throw new Error('webhookId is required.');
|
|
188
|
+
return client._request<WebhookSubscription>({
|
|
189
|
+
method: 'PATCH',
|
|
190
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks/${webhookId}`,
|
|
191
|
+
body: data,
|
|
192
|
+
sendJWT: true,
|
|
193
|
+
});
|
|
194
|
+
},
|
|
195
|
+
|
|
196
|
+
/**
|
|
197
|
+
* Delete a webhook subscription. In-flight deliveries continue to
|
|
198
|
+
* the receiver until they exhaust retries; no new deliveries fire.
|
|
199
|
+
*
|
|
200
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
201
|
+
*/
|
|
202
|
+
async deleteWebhook(workspaceId: string, webhookId: string): Promise<void> {
|
|
203
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
204
|
+
if (!webhookId) throw new Error('webhookId is required.');
|
|
205
|
+
return client._request<void>({
|
|
206
|
+
method: 'DELETE',
|
|
207
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks/${webhookId}`,
|
|
208
|
+
sendJWT: true,
|
|
209
|
+
});
|
|
210
|
+
},
|
|
211
|
+
|
|
212
|
+
/**
|
|
213
|
+
* Generate a new HMAC signing secret for a subscription and return
|
|
214
|
+
* it once. The old secret is invalidated immediately.
|
|
215
|
+
*
|
|
216
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
217
|
+
*/
|
|
218
|
+
async rotateWebhookSecret(
|
|
219
|
+
workspaceId: string,
|
|
220
|
+
webhookId: string,
|
|
221
|
+
): Promise<RotateWebhookSecretResponse> {
|
|
222
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
223
|
+
if (!webhookId) throw new Error('webhookId is required.');
|
|
224
|
+
return client._request<RotateWebhookSecretResponse>({
|
|
225
|
+
method: 'POST',
|
|
226
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks/${webhookId}/rotate-secret`,
|
|
227
|
+
sendJWT: true,
|
|
228
|
+
});
|
|
229
|
+
},
|
|
230
|
+
|
|
231
|
+
/**
|
|
232
|
+
* Fire a synthetic `webhook.test` delivery to the subscription's
|
|
233
|
+
* URL. The receiver gets a small payload they can use to verify
|
|
234
|
+
* their HMAC + parsing setup. Returns immediately; check the
|
|
235
|
+
* delivery log for the outcome.
|
|
236
|
+
*/
|
|
237
|
+
async testWebhook(workspaceId: string, webhookId: string): Promise<TestWebhookResponse> {
|
|
238
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
239
|
+
if (!webhookId) throw new Error('webhookId is required.');
|
|
240
|
+
return client._request<TestWebhookResponse>({
|
|
241
|
+
method: 'POST',
|
|
242
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks/${webhookId}/test`,
|
|
243
|
+
sendJWT: true,
|
|
244
|
+
});
|
|
245
|
+
},
|
|
246
|
+
|
|
247
|
+
/**
|
|
248
|
+
* Paginated list of delivery attempts for a webhook subscription.
|
|
249
|
+
* Useful for diagnosing failures (HTTP status, response body snippet,
|
|
250
|
+
* retry timing).
|
|
251
|
+
*
|
|
252
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
253
|
+
*/
|
|
254
|
+
async listWebhookDeliveries(
|
|
255
|
+
workspaceId: string,
|
|
256
|
+
webhookId: string,
|
|
257
|
+
params: ListDeliveriesParams = {},
|
|
258
|
+
): Promise<ListDeliveriesResponse> {
|
|
259
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
260
|
+
if (!webhookId) throw new Error('webhookId is required.');
|
|
261
|
+
const search = new URLSearchParams();
|
|
262
|
+
if (params.limit !== undefined) search.set('limit', String(params.limit));
|
|
263
|
+
if (params.cursor !== undefined) search.set('cursor', params.cursor);
|
|
264
|
+
if (params.status !== undefined) search.set('status', params.status);
|
|
265
|
+
const qs = search.toString();
|
|
266
|
+
return client._request<ListDeliveriesResponse>({
|
|
267
|
+
method: 'GET',
|
|
268
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks/${webhookId}/deliveries${qs ? `?${qs}` : ''}`,
|
|
269
|
+
sendJWT: true,
|
|
270
|
+
bypassCache: true,
|
|
271
|
+
});
|
|
272
|
+
},
|
|
273
|
+
|
|
274
|
+
/**
|
|
275
|
+
* Re-fire a specific past delivery attempt. Useful for confirming a
|
|
276
|
+
* receiver fix without waiting for the next real event.
|
|
277
|
+
*
|
|
278
|
+
* @requires `canManageWebhooks` on the workspace.
|
|
279
|
+
*/
|
|
280
|
+
async replayWebhookDelivery(
|
|
281
|
+
workspaceId: string,
|
|
282
|
+
webhookId: string,
|
|
283
|
+
attemptId: string,
|
|
284
|
+
): Promise<{ attempt: WebhookAttempt }> {
|
|
285
|
+
if (!workspaceId) throw new Error('workspaceId is required.');
|
|
286
|
+
if (!webhookId) throw new Error('webhookId is required.');
|
|
287
|
+
if (!attemptId) throw new Error('attemptId is required.');
|
|
288
|
+
return client._request<{ attempt: WebhookAttempt }>({
|
|
289
|
+
method: 'POST',
|
|
290
|
+
endpoint: `/v1/workspaces/${workspaceId}/webhooks/${webhookId}/deliveries/${attemptId}/replay`,
|
|
291
|
+
sendJWT: true,
|
|
292
|
+
});
|
|
293
|
+
},
|
|
294
|
+
};
|
|
295
|
+
}
|