@gigadrive/sdk 0.8.5 → 0.9.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/README.md CHANGED
@@ -186,6 +186,12 @@ Accepted inputs: browser `File`/`Blob`, Node `Buffer`/`Uint8Array`/`ArrayBuffer`
186
186
  a Node filesystem `path`, or a Node readable `stream` (with `contentLength` and
187
187
  `checksumSha256`).
188
188
 
189
+ Empty files such as `.gitkeep` or `__init__.py` work with every input kind. The
190
+ API stores a zero-byte object when the upload session is created, so nothing is
191
+ transferred, `waitForCompletion` returns without polling, and the result always
192
+ includes `object`. For an empty `stream`, pass `contentLength: 0`; the empty
193
+ SHA-256 is filled in for you.
194
+
189
195
  #### Many files at once
190
196
 
191
197
  ```ts
@@ -246,6 +252,81 @@ const { items: models } = await client.aiGateway.listModels();
246
252
  Organization-scoped governance (usage analytics, budgets, policies) lives under
247
253
  `client.organizations.aiGateway`.
248
254
 
255
+ ## Custom domains
256
+
257
+ Attach a hostname you own to an application. The response lists the DNS records to publish; Gigadrive
258
+ Network then verifies ownership, checks DNS and issues the certificate on its own.
259
+
260
+ ```ts
261
+ import { DomainNotActiveError } from '@gigadrive/sdk';
262
+
263
+ const domain = await client.applications.domains.add('app-id', { hostname: 'shop.example.com' });
264
+ for (const record of domain.requiredRecords) {
265
+ console.log(record.type, record.host, record.value);
266
+ }
267
+
268
+ try {
269
+ await client.applications.domains.waitUntilActive('app-id', domain.id, {
270
+ timeoutMs: 15 * 60_000,
271
+ onState: (current) => console.log(current.state),
272
+ });
273
+ } catch (error) {
274
+ if (!(error instanceof DomainNotActiveError)) throw error;
275
+ // `reason` is `timeout`, `failed`, `suspended` or `removing`; `domain.error` explains what to fix.
276
+ console.error(error.reason, error.domain.error?.message);
277
+ }
278
+ ```
279
+
280
+ Redirect a domain, or serve a branch instead of production:
281
+
282
+ ```ts
283
+ await client.applications.domains.update('app-id', domain.id, {
284
+ target: { type: 'redirect', to: 'www.example.com', statusCode: 308 },
285
+ });
286
+ ```
287
+
288
+ Verifying the registrable domain once lets every application of the organization attach hostnames
289
+ below it without another TXT record:
290
+
291
+ ```ts
292
+ const claim = await client.organizations.domains.add('org-id', 'example.com');
293
+ console.log(claim.record.host, claim.record.value); // publish this TXT record
294
+ await client.organizations.domains.verify('org-id', claim.id);
295
+ ```
296
+
297
+ ## Queues
298
+
299
+ Queues deliver work to your app in the background, now or later. A queue with a consumer path is a push queue: Gigadrive Network POSTs each message to that path on your deployment. Without one it is a pull queue that you drain with `receive()`.
300
+
301
+ ```ts
302
+ import { NonRetryableError, queue, RetryLaterError } from '@gigadrive/sdk';
303
+
304
+ export const emails = queue<{ to: string; template: string }>('emails');
305
+
306
+ // Send now, after a delay, or at a time (up to a year ahead).
307
+ await emails.send({ to: 'jane@example.com', template: 'welcome' });
308
+ await emails.send({ to: 'jane@example.com', template: 'nudge' }, { delay: '3d', deduplicationKey: 'nudge:jane' });
309
+
310
+ // app/api/queues/emails/route.ts: the push consumer. Signatures are verified for you.
311
+ export const POST = emails.handler(async (email, { attempt }) => {
312
+ if (!templates.has(email.template)) throw new NonRetryableError('Unknown template'); // dead-letter now
313
+ if (await mailer.isThrottled()) throw new RetryLaterError('1m'); // defer without spending an attempt
314
+ await mailer.send(email); // returning acknowledges the message
315
+ });
316
+ ```
317
+
318
+ Declare the push consumer and any cron schedules in `gigadrive.yaml`, or create them from code with `emails.ensure({ consumerPath: '/api/queues/emails' })` and `emails.schedule(...)`.
319
+
320
+ Pull consumers lease messages and settle them:
321
+
322
+ ```ts
323
+ const jobs = queue<{ id: string }>('jobs');
324
+
325
+ await jobs.consume(async (job) => processJob(job.id), { maxMessages: 10, stopWhenEmpty: true });
326
+ ```
327
+
328
+ `client.queues` exposes the full REST surface (queues, messages, dead letters, schedules), and `createWorkflowQueue()` runs the [Workflow SDK](https://workflow-sdk.dev) on Gigadrive Network queues.
329
+
249
330
  ## Pagination
250
331
 
251
332
  List endpoints accept `page` / `perPage` / `cursor` and return `{ items, total }`