@meistrari/vault-sdk 1.6.2 → 1.6.3

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 CHANGED
@@ -8,159 +8,456 @@ This is the SDK for Vault V2.
8
8
  ni @meistrari/vault-sdk-sdk
9
9
  ```
10
10
 
11
- ## Usage
11
+ ## Table of Contents
12
12
 
13
- The main component of the SDK is the `VaultFile` class.
14
- It provides methods to upload, download, and reference files in the vault.
13
+ - [Core Concepts](#core-concepts)
14
+ - [Quick Start](#quick-start)
15
+ - [Authentication Strategies](#authentication-strategies)
16
+ - [API Reference](#api-reference)
17
+ - [VaultFile](#vaultfile)
18
+ - [Vault Client](#vault-client)
19
+ - [Permalinks](#permalinks)
20
+ - [Advanced Usage](#advanced-usage)
15
21
 
16
- ### Creating Files
22
+ ## Core Concepts
17
23
 
18
- To create a new file in the vault, use `VaultFile.fromContent`:
24
+ The SDK revolves around two main components:
25
+
26
+ 1. **VaultFile** - The primary class for interacting with files in the vault
27
+ 2. **Vault Client** - A helper function (`vaultClient`) that simplifies creating VaultFile instances with shared configuration
28
+
29
+ Files in the vault are identified by vault references in the format `vault://{fileId}`.
30
+
31
+ ## Quick Start
19
32
 
20
33
  ```ts
34
+ import { VaultFile, DataTokenAuthStrategy } from '@meistrari/vault-sdk'
35
+
36
+ const config = {
37
+ vaultUrl: 'https://vault.tela.com',
38
+ authStrategy: new DataTokenAuthStrategy('[your-data-token]')
39
+ }
40
+
41
+ // Upload a new file
42
+ const file = new File(['Hello World'], 'hello.txt')
21
43
  const vaultFile = await VaultFile.fromContent({
22
- content: new File(['content'], 'document.txt'), // File content
23
- name: 'document.txt', // Optional: original filename
24
- config: {
25
- vaultUrl,
26
- authStrategy: new DataTokenAuthStrategy(dataToken)
27
- },
28
- upload: true // Optional: upload immediately
44
+ name: 'hello.txt',
45
+ content: file,
46
+ config,
47
+ upload: true
29
48
  })
49
+
50
+ // Get the vault reference to store in your database
51
+ const reference = vaultFile.getVaultReference() // 'vault://abc123...'
52
+
53
+ // Later, retrieve and download the file
54
+ const retrieved = await VaultFile.fromVaultReference({
55
+ reference,
56
+ config
57
+ })
58
+ const content = await retrieved.download() // Returns a Blob
30
59
  ```
31
60
 
32
- ### Retrieving Files
61
+ ## Authentication Strategies
62
+
63
+ The SDK provides two authentication strategies:
33
64
 
34
- To retrieve a file using a vault reference, use `VaultFile.fromVaultReference`:
65
+ ### DataTokenAuthStrategy
66
+
67
+ Used for internal calls to the vault service. Passes the data token as the `x-data-token` header.
35
68
 
36
69
  ```ts
37
- const vaultFile = await VaultFile.fromVaultReference({
38
- reference: 'vault://1234567890', // The vault reference
39
- config: {
40
- vaultUrl,
41
- authStrategy: new DataTokenAuthStrategy(dataToken)
42
- },
43
- download: false // Optional: download immediately if true
44
- })
45
- ```
70
+ import { DataTokenAuthStrategy } from '@meistrari/vault-sdk'
46
71
 
47
- ## Basic Usage Flow
72
+ const authStrategy = new DataTokenAuthStrategy('[your-data-token]')
73
+ ```
48
74
 
49
- The typical workflow with the SDK involves:
75
+ ### APIKeyAuthStrategy
50
76
 
51
- 1. Creating a file in the vault using `VaultFile.fromContent`
52
- 2. Getting a reference to that file with `getVaultReference()`
53
- 3. Later, retrieving the file using `VaultFile.fromVaultReference`
77
+ Used for external calls **through the API Gateway**. Passes the API key as the `Authorization` header.
54
78
 
55
- Here's an example showing the complete flow:
79
+ > [!WARNING]
80
+ > The vault service itself does not support API Keys directly. When using this strategy, requests **must** go through the API Gateway.
81
+ >
82
+ > ✅ Use: `https://staging.api.tela.com/_services/vault`
83
+ > ❌ Not: `https://staging.vault.tela.com`
56
84
 
57
85
  ```ts
58
- import { VaultFile, DataTokenAuthStrategy } from '@meistrari/vault-sdk'
86
+ import { APIKeyAuthStrategy } from '@meistrari/vault-sdk'
87
+
88
+ const authStrategy = new APIKeyAuthStrategy('[your-api-key]')
89
+ ```
59
90
 
60
- const dataToken = '[some-data-token]'
61
- const vaultUrl = Bun.env.VAULT_URL ?? 'https://vault.tela.com'
91
+ ## API Reference
62
92
 
63
- // Step 1: Create and upload a new file
64
- const fileContent = Bun.file('path/to/local/file.txt')
93
+ ### VaultFile
94
+
95
+ The main class for interacting with vault files.
96
+
97
+ #### Static Methods
98
+
99
+ ##### `VaultFile.fromContent(params, options?)`
100
+
101
+ Creates a new VaultFile from content (File or Blob).
102
+
103
+ ```ts
65
104
  const vaultFile = await VaultFile.fromContent({
66
- content: fileContent,
67
- name: 'file.txt', // Optional: original filename
105
+ name: 'document.txt',
106
+ content: new File(['content'], 'document.txt'),
68
107
  config: {
69
108
  vaultUrl,
70
- authStrategy: new DataTokenAuthStrategy(dataToken)
109
+ authStrategy
71
110
  },
72
- upload: true // Upload immediately
73
- })
111
+ upload: false // Set to true to upload immediately
112
+ }, { signal: abortSignal }) // Optional abort signal
113
+ ```
74
114
 
75
- // Step 2: Get a reference to store in your database or application
76
- const vaultReference = vaultFile.getVaultReference() // e.g. 'vault://1234567890'
77
- console.log(`Store this reference: ${vaultReference}`)
115
+ ##### `VaultFile.fromVaultReference(params, options?)`
78
116
 
79
- // ... Later, in another part of your application ...
117
+ Creates a VaultFile instance from an existing vault reference.
80
118
 
81
- // Step 3: Retrieve the file using the reference
82
- const retrievedFile = await VaultFile.fromVaultReference({
83
- reference: vaultReference,
119
+ ```ts
120
+ const vaultFile = await VaultFile.fromVaultReference({
121
+ reference: 'vault://abc123...',
84
122
  config: {
85
123
  vaultUrl,
86
- authStrategy: new DataTokenAuthStrategy(dataToken)
124
+ authStrategy
87
125
  },
88
126
  download: false // Set to true to download immediately
127
+ }, { signal: abortSignal }) // Optional abort signal
128
+ ```
129
+
130
+ ##### `VaultFile.fromStream(params, options?)`
131
+
132
+ Creates a VaultFile for streaming upload workflows. Useful for large files to avoid loading the entire file into memory.
133
+
134
+ ```ts
135
+ const vaultFile = await VaultFile.fromStream({
136
+ name: 'large-video.mp4',
137
+ contentLength: 100 * 1024 * 1024, // 100MB
138
+ contentType: 'video/mp4',
139
+ config: { vaultUrl, authStrategy }
140
+ }, { signal: abortSignal })
141
+
142
+ // Upload using a stream
143
+ const stream = file.stream()
144
+ await vaultFile.uploadStream(stream, {
145
+ contentLength: file.size,
146
+ contentType: file.type
89
147
  })
148
+ ```
149
+
150
+ #### Instance Methods
151
+
152
+ ##### `upload(file?, url?, options?)`
153
+
154
+ Uploads the file to the vault. If no file is provided, uses the content from the VaultFile instance.
155
+
156
+ ```ts
157
+ await vaultFile.upload() // Uses vaultFile.content
158
+ // or
159
+ await vaultFile.upload(someBlob) // Upload specific blob
160
+ ```
161
+
162
+ ##### `uploadStream(stream, options)`
163
+
164
+ Uploads a file using a ReadableStream for memory-efficient processing of large files.
165
+
166
+ ```ts
167
+ const stream = file.stream()
168
+ await vaultFile.uploadStream(stream, {
169
+ contentLength: file.size,
170
+ contentType: 'video/mp4'
171
+ })
172
+ ```
173
+
174
+ ##### `download(responseType?, options?)`
175
+
176
+ Downloads the file content from the vault.
177
+
178
+ ```ts
179
+ const blob = await vaultFile.download() // Returns Blob
180
+ const base64 = await vaultFile.download('base64') // Returns base64 string
181
+ ```
182
+
183
+ ##### `downloadStream(options?)`
184
+
185
+ Downloads the file as a ReadableStream for memory-efficient processing.
186
+
187
+ ```ts
188
+ const stream = await vaultFile.downloadStream()
189
+ const reader = stream.getReader()
190
+
191
+ while (true) {
192
+ const { done, value } = await reader.read()
193
+ if (done)
194
+ break
195
+ console.log('Chunk size:', value.length)
196
+ }
197
+ ```
198
+
199
+ ##### `getVaultReference()`
200
+
201
+ Returns the vault reference string for this file.
202
+
203
+ ```ts
204
+ const reference = vaultFile.getVaultReference() // 'vault://abc123...'
205
+ ```
206
+
207
+ ##### `getFileMetadata(options?)`
208
+
209
+ Fetches the file's metadata from the vault.
210
+
211
+ ```ts
212
+ const metadata = await vaultFile.getFileMetadata()
213
+ // Returns FileMetadata with properties like originalFileName, mimeType, size, etc.
214
+ ```
215
+
216
+ ##### `populateMetadata(options?)`
90
217
 
91
- // Step 4: Download the content when needed
92
- const fileContent = await retrievedFile.download()
93
- console.log(fileContent)
218
+ Populates the file instance's metadata by fetching it from the vault.
219
+
220
+ ```ts
221
+ await vaultFile.populateMetadata()
222
+ console.log(vaultFile.metadata)
94
223
  ```
95
224
 
96
- ### Using the useVault helper
225
+ ##### `getUploadUrl(options?)`
97
226
 
98
- The SDK provides a convenient `useVault` helper function that simplifies creating vault files:
227
+ Gets a pre-signed upload URL for the file.
99
228
 
100
229
  ```ts
101
- import { useVault, DataTokenAuthStrategy } from '@meistrari/vault-sdk'
230
+ const uploadUrl = await vaultFile.getUploadUrl({ expiresIn: 3600 }) // 1 hour
231
+ ```
232
+
233
+ ##### `getDownloadUrl(options?)`
234
+
235
+ Gets a pre-signed download URL for the file.
102
236
 
103
- const dataToken = '[some-data-token]'
104
- const vaultUrl = Bun.env.VAULT_URL ?? 'https://vault.tela.com'
237
+ ```ts
238
+ const downloadUrl = await vaultFile.getDownloadUrl({ expiresIn: 3600 }) // 1 hour
239
+ ```
105
240
 
106
- // Create a vault instance
107
- const vault = useVault({
108
- vaultUrl,
109
- authStrategy: new DataTokenAuthStrategy(dataToken)
241
+ ##### `delete(options?)`
242
+
243
+ Deletes the file from the vault.
244
+
245
+ ```ts
246
+ await vaultFile.delete()
247
+ ```
248
+
249
+ ##### `createPermalink(params?, options?)`
250
+
251
+ Creates a permalink for the file. Requires workspace ID to be set in metadata.
252
+
253
+ ```ts
254
+ await vaultFile.populateMetadata() // Ensure metadata is loaded
255
+ const permalink = await vaultFile.createPermalink({ expiresIn: 86400 }) // 24 hours
256
+ console.log(permalink.url) // Public URL
257
+ ```
258
+
259
+ ##### `getPermalinks(options?)`
260
+
261
+ Gets all valid permalinks for the file.
262
+
263
+ ```ts
264
+ const permalinks = await vaultFile.getPermalinks()
265
+ for (const permalink of permalinks) {
266
+ console.log(permalink.url, permalink.expiresAt)
267
+ }
268
+ ```
269
+
270
+ ### Vault Client
271
+
272
+ The `vaultClient` helper simplifies working with multiple files using shared configuration.
273
+
274
+ ```ts
275
+ import { vaultClient, DataTokenAuthStrategy } from '@meistrari/vault-sdk'
276
+
277
+ const client = vaultClient({
278
+ vaultUrl: 'https://vault.tela.com',
279
+ authStrategy: new DataTokenAuthStrategy('[your-data-token]')
110
280
  })
111
281
 
112
- // Create a file from content
113
- const fileFromContent = vault.createFromContent(
282
+ // Create from content
283
+ const vaultFile = await client.createFromContent(
114
284
  'document.txt',
115
285
  new File(['content'], 'document.txt')
116
286
  )
117
287
 
118
- // Create a file from a vault reference
119
- const fileFromReference = vault.createFromReference('vault://1234567890')
288
+ // Create from reference
289
+ const retrieved = await client.createFromReference('vault://abc123...')
290
+
291
+ // Create from stream
292
+ const streamFile = await client.createFromStream(
293
+ 'video.mp4',
294
+ 100 * 1024 * 1024, // 100MB
295
+ { contentType: 'video/mp4' }
296
+ )
120
297
  ```
121
298
 
122
- The `useVault` helper provides two methods:
299
+ ### Permalinks
123
300
 
124
- - `createFromContent(content, name?)`: Creates a new `VaultFile` instance from content (Blob or File) and an optional name
125
- - `createFromReference(reference)`: Creates a new `VaultFile` instance from a vault reference string
301
+ Permalinks are public, optionally time-limited URLs for files.
126
302
 
127
- This helper makes it more convenient to work with multiple vault files using the same configuration.
303
+ #### `Permalink.create(config, params, options?)`
128
304
 
129
- ### Auth strategies
305
+ Creates a new permalink.
130
306
 
131
- The SDK provides two auth strategies: `DataTokenAuthStrategy` and `APIKeyAuthStrategy`.
307
+ ```ts
308
+ import { Permalink } from '@meistrari/vault-sdk'
132
309
 
133
- #### DataTokenAuthStrategy
310
+ const permalink = await Permalink.create(config, {
311
+ fileId: 'abc123...',
312
+ workspaceId: 'workspace-id',
313
+ expiresIn: 86400 // 24 hours (optional)
314
+ })
134
315
 
135
- It takes a data token, and passes it as the `x-data-token` header in requests to the vault.
136
- Use this when performing internal calls to the vault, such as from `tela-api`.
316
+ console.log(permalink.url)
317
+ ```
318
+
319
+ #### `Permalink.fromId(config, id)`
320
+
321
+ Retrieves a permalink by its ID.
137
322
 
138
323
  ```ts
139
- import { DataTokenAuthStrategy } from '@meistrari/vault-sdk'
324
+ const permalink = await Permalink.fromId(config, 'permalink-id')
325
+ ```
326
+
327
+ #### `permalink.delete(options?)`
140
328
 
141
- const dataToken = '[some-data-token]'
329
+ Deletes the permalink.
142
330
 
143
- const authStrategy = new DataTokenAuthStrategy(dataToken)
331
+ ```ts
332
+ await permalink.delete()
144
333
  ```
145
334
 
146
- #### APIKeyAuthStrategy
335
+ ## Advanced Usage
147
336
 
148
- It takes an API key, and passes it as the `Authorization` header in requests to the vault.
149
- Use this when performing external calls **through the API Gateway**, such as from the frontend.
150
- Since the clerk token is also passed as the `Authorization` header, this strategy can also be used with the value of the `__session` cookie instead of an API key.
337
+ ### Complete Workflow Example
151
338
 
152
- > [!WARNING]
153
- > The vault service itself does not support API Keys, it only understands data tokens.
154
- > To use this strategy, the request **must** go through the API Gateway.
155
- > For that, the gateway URL should be used instead of the vault service URL.
156
- >
157
- > Use this: `https://staging.api.tela.com/_services/vault`.<br>
158
- > Instead of this: `https://vault.tela.com`
339
+ ```ts
340
+ import { VaultFile, DataTokenAuthStrategy } from '@meistrari/vault-sdk'
341
+
342
+ const config = {
343
+ vaultUrl: 'https://vault.tela.com',
344
+ authStrategy: new DataTokenAuthStrategy('[your-data-token]')
345
+ }
346
+
347
+ // 1. Create and upload a file
348
+ const file = new File(['content'], 'document.txt')
349
+ const vaultFile = await VaultFile.fromContent({
350
+ name: 'document.txt',
351
+ content: file,
352
+ config,
353
+ upload: true
354
+ })
355
+
356
+ // 2. Store the reference in your database
357
+ const reference = vaultFile.getVaultReference()
358
+ await db.saveDocument({ vaultReference: reference })
359
+
360
+ // 3. Later, retrieve the file
361
+ const doc = await db.getDocument()
362
+ const retrieved = await VaultFile.fromVaultReference({
363
+ reference: doc.vaultReference,
364
+ config,
365
+ download: true
366
+ })
367
+
368
+ // 4. Use the content
369
+ const blob = retrieved.content // Already downloaded
370
+ console.log('File size:', blob.size)
371
+ ```
372
+
373
+ ### Streaming Large Files
159
374
 
160
375
  ```ts
161
- import { APIKeyAuthStrategy } from '@meistrari/vault-sdk'
376
+ // Upload a large file efficiently
377
+ const vaultFile = await VaultFile.fromStream({
378
+ name: 'large-file.bin',
379
+ contentLength: largeFile.size,
380
+ contentType: largeFile.type,
381
+ config
382
+ })
383
+
384
+ await vaultFile.uploadStream(largeFile.stream(), {
385
+ contentLength: largeFile.size,
386
+ contentType: largeFile.type
387
+ })
388
+
389
+ // Download a large file efficiently
390
+ const stream = await vaultFile.downloadStream()
391
+ // Process stream in chunks without loading entire file
392
+ ```
393
+
394
+ ### Abort Requests
395
+
396
+ All methods that make network requests support AbortSignal for request cancellation:
397
+
398
+ ```ts
399
+ const controller = new AbortController()
400
+
401
+ // Cancel after 5 seconds
402
+ setTimeout(() => controller.abort(), 5000)
403
+
404
+ try {
405
+ const vaultFile = await VaultFile.fromContent({
406
+ name: 'document.txt',
407
+ content: file,
408
+ config
409
+ }, { signal: controller.signal })
410
+
411
+ // Upload with abort signal
412
+ await vaultFile.upload(undefined, undefined, { signal: controller.signal })
413
+
414
+ console.log('Upload successful')
415
+ }
416
+ catch (error) {
417
+ if (error.name === 'AbortError') {
418
+ console.log('Upload was cancelled')
419
+ }
420
+ else {
421
+ throw error
422
+ }
423
+ }
424
+ ```
425
+
426
+ You can also cancel downloads and other operations:
427
+
428
+ ```ts
429
+ const controller = new AbortController()
430
+
431
+ // Start download
432
+ const downloadPromise = vaultFile.download('blob', { signal: controller.signal })
433
+
434
+ // Cancel if user clicks a button
435
+ cancelButton.addEventListener('click', () => controller.abort())
436
+
437
+ try {
438
+ const blob = await downloadPromise
439
+ console.log('Download complete:', blob.size)
440
+ }
441
+ catch (error) {
442
+ if (error.name === 'AbortError') {
443
+ console.log('Download cancelled by user')
444
+ }
445
+ }
446
+ ```
447
+
448
+ ### Working with Metadata
449
+
450
+ ```ts
451
+ const vaultFile = await VaultFile.fromVaultReference({
452
+ reference: 'vault://abc123...',
453
+ config
454
+ })
162
455
 
163
- const apiKey = '[some-api-key]'
456
+ // Load metadata
457
+ await vaultFile.populateMetadata()
164
458
 
165
- const authStrategy = new APIKeyAuthStrategy(apiKey)
459
+ console.log(vaultFile.metadata.originalFileName)
460
+ console.log(vaultFile.metadata.mimeType)
461
+ console.log(vaultFile.metadata.size)
462
+ console.log(vaultFile.metadata.workspaceId)
166
463
  ```
package/dist/index.cjs CHANGED
@@ -221,7 +221,7 @@ async function detectFileMimeType(blob) {
221
221
  }
222
222
 
223
223
  const name = "@meistrari/vault-sdk";
224
- const version = "1.6.2";
224
+ const version = "1.6.3";
225
225
  const license = "UNLICENSED";
226
226
  const repository = {
227
227
  type: "git",
package/dist/index.mjs CHANGED
@@ -219,7 +219,7 @@ async function detectFileMimeType(blob) {
219
219
  }
220
220
 
221
221
  const name = "@meistrari/vault-sdk";
222
- const version = "1.6.2";
222
+ const version = "1.6.3";
223
223
  const license = "UNLICENSED";
224
224
  const repository = {
225
225
  type: "git",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@meistrari/vault-sdk",
3
- "version": "1.6.2",
3
+ "version": "1.6.3",
4
4
  "license": "UNLICENSED",
5
5
  "repository": {
6
6
  "type": "git",