@stackshift-cloud/sdk 1.1.0 → 1.3.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.
Files changed (45) hide show
  1. package/README.md +79 -1
  2. package/dist/ai-credits.d.ts +78 -0
  3. package/dist/ai-credits.js +15 -0
  4. package/dist/assets-dam-types.d.ts +259 -0
  5. package/dist/assets-dam-types.js +1 -0
  6. package/dist/assets-dam.d.ts +106 -0
  7. package/dist/assets-dam.js +52 -0
  8. package/dist/assets-video-types.d.ts +116 -0
  9. package/dist/assets-video-types.js +1 -0
  10. package/dist/assets-video.d.ts +25 -0
  11. package/dist/assets-video.js +19 -0
  12. package/dist/assets.d.ts +5 -1
  13. package/dist/assets.js +11 -2
  14. package/dist/client.d.ts +6 -0
  15. package/dist/client.js +14 -0
  16. package/dist/generated/assets-contract.d.ts +531 -1
  17. package/dist/generated/assets-contract.js +106 -0
  18. package/dist/index.d.ts +16 -0
  19. package/dist/index.js +9 -0
  20. package/dist/mail-advanced-types.d.ts +9 -0
  21. package/dist/mail-billing.d.ts +34 -0
  22. package/dist/mail-billing.js +7 -0
  23. package/dist/mail-brands.d.ts +35 -0
  24. package/dist/mail-brands.js +17 -0
  25. package/dist/mail-campaigns.d.ts +72 -10
  26. package/dist/mail-campaigns.js +25 -2
  27. package/dist/mail-marketing.d.ts +84 -0
  28. package/dist/mail-marketing.js +24 -0
  29. package/dist/mail-migration.d.ts +16 -0
  30. package/dist/mail-migration.js +10 -0
  31. package/dist/mail-otp-types.d.ts +4 -0
  32. package/dist/mail-simulation.d.ts +4 -0
  33. package/dist/mail-simulation.js +1 -0
  34. package/dist/mail-subscribers.d.ts +39 -0
  35. package/dist/mail-subscribers.js +1 -0
  36. package/dist/mail-template-types.d.ts +8 -0
  37. package/dist/mail-tracking.d.ts +59 -0
  38. package/dist/mail-tracking.js +14 -0
  39. package/dist/mail-webhook-types.d.ts +4 -1
  40. package/dist/mail.d.ts +12 -0
  41. package/dist/mail.js +19 -0
  42. package/dist/types.d.ts +13 -0
  43. package/dist/workload-security.d.ts +172 -0
  44. package/dist/workload-security.js +50 -0
  45. package/package.json +2 -2
@@ -0,0 +1,116 @@
1
+ export interface AssetVideoPackage {
2
+ id: string;
3
+ asset_space_id: string;
4
+ asset_id: string;
5
+ version_id: string;
6
+ source_checksum_sha256: string;
7
+ recipe_hash: string;
8
+ recipe: string;
9
+ processor_revision: string;
10
+ status: 'queued' | 'processing' | 'ready' | 'degraded' | 'failed' | 'cancelled';
11
+ phase: string;
12
+ progress_percent: number;
13
+ job_id?: string;
14
+ published_attempt?: string;
15
+ admitted_at?: string;
16
+ created_at: string;
17
+ updated_at: string;
18
+ failure_code: string;
19
+ metadata: {
20
+ asset_id: string;
21
+ duration_seconds: number;
22
+ width: number;
23
+ height: number;
24
+ codec: string;
25
+ bitrate: number;
26
+ frame_rate: number;
27
+ has_audio: boolean;
28
+ rotation: number;
29
+ created_at: string;
30
+ updated_at: string;
31
+ };
32
+ }
33
+ export interface AssetVideoWorkspace {
34
+ active?: AssetVideoPackage;
35
+ pending?: AssetVideoPackage;
36
+ source?: {
37
+ version_id: string;
38
+ scan_status: 'pending' | 'clean' | 'infected' | 'failed';
39
+ review_status: 'not_required' | 'pending' | 'approved' | 'rejected';
40
+ review_reason: string;
41
+ };
42
+ renditions: Array<{
43
+ id: string;
44
+ package_id?: string;
45
+ asset_id: string;
46
+ source_checksum_sha256: string;
47
+ kind: 'hls' | 'mp4' | 'poster';
48
+ profile: string;
49
+ width: number;
50
+ height: number;
51
+ size: number;
52
+ mime_type: string;
53
+ status: string;
54
+ created_at: string;
55
+ updated_at: string;
56
+ }>;
57
+ admission_enabled: boolean;
58
+ }
59
+ export interface AssetVideoCaptionInput {
60
+ /** Atomically replace this active track; the new reference receives a new ID. */
61
+ replace_caption_id?: string;
62
+ caption_asset_id: string;
63
+ caption_version_id: string;
64
+ language: string;
65
+ label: string;
66
+ kind: 'captions' | 'subtitles';
67
+ is_default?: boolean;
68
+ }
69
+ export interface AssetVideoCaption extends AssetVideoCaptionInput {
70
+ id: string;
71
+ asset_space_id: string;
72
+ asset_id: string;
73
+ version_id: string;
74
+ is_default: boolean;
75
+ }
76
+ export interface AssetPlaybackGrant {
77
+ has_audio: boolean;
78
+ session: {
79
+ id: string;
80
+ asset_space_id: string;
81
+ asset_id: string;
82
+ package_id: string;
83
+ version_id: string;
84
+ owner_id?: string;
85
+ is_private: boolean;
86
+ expires_at: string;
87
+ maximum_expires_at: string;
88
+ revoked_at?: string;
89
+ created_at: string;
90
+ };
91
+ credential: string;
92
+ hls: string;
93
+ mp4: string;
94
+ poster?: string;
95
+ captions: Array<{
96
+ id: string;
97
+ url: string;
98
+ language: string;
99
+ label: string;
100
+ kind: 'captions' | 'subtitles';
101
+ is_default: boolean;
102
+ }>;
103
+ }
104
+ export interface AssetPlaybackEvent {
105
+ sequence: number;
106
+ kind: 'startup' | 'rebuffer' | 'error' | 'quality' | 'watched' | 'completed';
107
+ value: number;
108
+ }
109
+ export interface AssetPlaybackAnalytics {
110
+ starts: number;
111
+ completions: number;
112
+ errors: number;
113
+ startup_ms: number;
114
+ rebuffer_ms: number;
115
+ watched_ms: number;
116
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,25 @@
1
+ import type { StackShift } from './client.js';
2
+ import type { AssetVideoWorkspace, AssetVideoPackage, AssetVideoCaption, AssetVideoCaptionInput, AssetPlaybackGrant, AssetPlaybackEvent, AssetPlaybackAnalytics } from './assets-video-types.js';
3
+ export declare class AssetVideoClient {
4
+ private readonly client;
5
+ constructor(client: StackShift);
6
+ workspace(assetId: string): Promise<AssetVideoWorkspace>;
7
+ process(assetId: string, versionId: string): Promise<AssetVideoPackage>;
8
+ createSession(assetId: string): Promise<AssetPlaybackGrant>;
9
+ renewSession(credential: string): Promise<AssetPlaybackGrant>;
10
+ revokeSession(assetId: string, sessionId: string): Promise<{
11
+ revoked: boolean;
12
+ }>;
13
+ captions(assetId: string, versionId: string): Promise<AssetVideoCaption[]>;
14
+ addCaption(assetId: string, versionId: string, input: AssetVideoCaptionInput): Promise<AssetVideoCaption>;
15
+ removeCaption(assetId: string, versionId: string, captionId: string): Promise<{
16
+ removed: boolean;
17
+ }>;
18
+ review(assetId: string, versionId: string, decision: 'approved' | 'rejected', reason: string): Promise<{
19
+ reviewed: boolean;
20
+ }>;
21
+ events(credential: string, events: AssetPlaybackEvent[]): Promise<{
22
+ accepted: boolean;
23
+ }>;
24
+ analytics(assetId: string): Promise<AssetPlaybackAnalytics>;
25
+ }
@@ -0,0 +1,19 @@
1
+ const assetPath = (id) => `/assets/${encodeURIComponent(id)}`;
2
+ const versionPath = (id, version) => `${assetPath(id)}/versions/${encodeURIComponent(version)}/video`;
3
+ export class AssetVideoClient {
4
+ client;
5
+ constructor(client) {
6
+ this.client = client;
7
+ }
8
+ workspace(assetId) { return this.client.request(`${assetPath(assetId)}/video`); }
9
+ process(assetId, versionId) { return this.client.request(versionPath(assetId, versionId), { method: 'POST' }); }
10
+ createSession(assetId) { return this.client.request(`${assetPath(assetId)}/playback-sessions`, { method: 'POST' }); }
11
+ renewSession(credential) { return this.client.playbackRequest('/sessions/renew', credential, {}); }
12
+ revokeSession(assetId, sessionId) { return this.client.request(`${assetPath(assetId)}/playback-sessions/${encodeURIComponent(sessionId)}`, { method: 'DELETE' }); }
13
+ captions(assetId, versionId) { return this.client.request(`${versionPath(assetId, versionId)}/captions`); }
14
+ addCaption(assetId, versionId, input) { return this.client.request(`${versionPath(assetId, versionId)}/captions`, { method: 'POST', body: input }); }
15
+ removeCaption(assetId, versionId, captionId) { return this.client.request(`${versionPath(assetId, versionId)}/captions/${encodeURIComponent(captionId)}`, { method: 'DELETE' }); }
16
+ review(assetId, versionId, decision, reason) { return this.client.request(`${versionPath(assetId, versionId)}/review`, { method: 'POST', body: { decision, reason } }); }
17
+ events(credential, events) { return this.client.playbackRequest('/events', credential, { events }); }
18
+ analytics(assetId) { return this.client.request(`${assetPath(assetId)}/video/analytics`); }
19
+ }
package/dist/assets.d.ts CHANGED
@@ -1,3 +1,5 @@
1
+ import { AssetDAMClient } from './assets-dam.js';
2
+ import { AssetVideoClient } from './assets-video.js';
1
3
  import type { StackShift } from './client.js';
2
4
  import { AssetConnectionsClient, AssetMigrationsClient, AssetStorageClient, AssetTextClient, AssetUploadCapabilitiesClient } from './assets-platform.js';
3
5
  import { AssetWorkflowsClient } from './asset-workflows.js';
@@ -9,6 +11,8 @@ export declare function assetTransformOptions(preset: AssetTransformPreset): Ass
9
11
  export declare function assetTransformSpec(options: AssetTransformOptions): string;
10
12
  export declare class AssetsClient {
11
13
  private readonly client;
14
+ readonly dam: AssetDAMClient;
15
+ readonly video: AssetVideoClient;
12
16
  readonly connections: AssetConnectionsClient;
13
17
  readonly storage: AssetStorageClient;
14
18
  readonly migrations: AssetMigrationsClient;
@@ -79,7 +83,7 @@ export declare class AssetsClient {
79
83
  description?: string;
80
84
  asset_ids?: string[];
81
85
  }): Promise<AssetCollection>;
82
- updateCollection(collectionId: string, input: {
86
+ updateCollection(collectionId: string, revision: number, input: {
83
87
  name: string;
84
88
  description?: string;
85
89
  asset_ids?: string[];
package/dist/assets.js CHANGED
@@ -1,3 +1,5 @@
1
+ import { AssetDAMClient } from './assets-dam.js';
2
+ import { AssetVideoClient } from './assets-video.js';
1
3
  import { AssetConnectionsClient, AssetMigrationsClient, AssetStorageClient, AssetTextClient, AssetUploadCapabilitiesClient } from './assets-platform.js';
2
4
  import { AssetWorkflowsClient } from './asset-workflows.js';
3
5
  import { ChunkedUploadController, putBlob, sha256Blob } from './upload-controller.js';
@@ -44,6 +46,8 @@ export function assetTransformSpec(options) {
44
46
  }
45
47
  export class AssetsClient {
46
48
  client;
49
+ dam;
50
+ video;
47
51
  connections;
48
52
  storage;
49
53
  migrations;
@@ -52,6 +56,8 @@ export class AssetsClient {
52
56
  workflows;
53
57
  constructor(client) {
54
58
  this.client = client;
59
+ this.dam = new AssetDAMClient(client);
60
+ this.video = new AssetVideoClient(client);
55
61
  this.connections = new AssetConnectionsClient(client);
56
62
  this.storage = new AssetStorageClient(client);
57
63
  this.migrations = new AssetMigrationsClient(client);
@@ -76,6 +82,9 @@ export class AssetsClient {
76
82
  append(query, 'type', options.type);
77
83
  append(query, 'folder', options.folder);
78
84
  append(query, 'checksum', options.checksum);
85
+ append(query, 'collection_id', options.collectionId);
86
+ append(query, 'duplicates', options.duplicates === undefined ? undefined : String(options.duplicates));
87
+ append(query, 'security', options.security);
79
88
  append(query, 'status', options.status);
80
89
  append(query, 'scan_status', options.scanStatus);
81
90
  append(query, 'replication_status', options.replicationStatus);
@@ -300,8 +309,8 @@ export class AssetsClient {
300
309
  createCollection(input) {
301
310
  return this.client.request('/assets/collections', { method: 'POST', body: input });
302
311
  }
303
- updateCollection(collectionId, input) {
304
- return this.client.request(`/assets/collections/${encodeURIComponent(collectionId)}`, { method: 'PUT', body: input });
312
+ updateCollection(collectionId, revision, input) {
313
+ return this.client.request(`/assets/collections/${encodeURIComponent(collectionId)}`, { method: 'PUT', body: input, headers: { 'If-Match': `"${revision}"` } });
305
314
  }
306
315
  deleteCollection(collectionId) {
307
316
  return this.client.request(`/assets/collections/${encodeURIComponent(collectionId)}`, { method: 'DELETE' });
package/dist/client.d.ts CHANGED
@@ -1,8 +1,12 @@
1
+ import { AICreditsClient } from './ai-credits.js';
1
2
  import { AssetsClient } from './assets.js';
2
3
  import { MailClient } from './mail.js';
3
4
  import { ProjectsClient } from './projects.js';
5
+ import { WorkloadSecurityClient } from './workload-security.js';
4
6
  import type { StackShiftOptions } from './types.js';
5
7
  export declare class StackShift {
8
+ readonly aiCredits: AICreditsClient;
9
+ readonly assetSpaceId?: string;
6
10
  readonly apiKey: string;
7
11
  readonly baseUrl: string;
8
12
  readonly mailBaseUrl: string;
@@ -10,6 +14,7 @@ export declare class StackShift {
10
14
  readonly projects: ProjectsClient;
11
15
  readonly assets: AssetsClient;
12
16
  readonly mail: MailClient;
17
+ readonly workloadSecurity: WorkloadSecurityClient;
13
18
  private readonly fetcher;
14
19
  constructor(options?: StackShiftOptions);
15
20
  request<T>(path: string, init?: {
@@ -27,6 +32,7 @@ export declare class StackShift {
27
32
  body?: unknown;
28
33
  headers?: Record<string, string>;
29
34
  }): Promise<T>;
35
+ playbackRequest<T>(path: '/sessions/renew' | '/events', credential: string, body: unknown): Promise<T>;
30
36
  private requestFrom;
31
37
  private fetchFrom;
32
38
  }
package/dist/client.js CHANGED
@@ -1,10 +1,14 @@
1
+ import { AICreditsClient } from './ai-credits.js';
1
2
  import { AssetsClient } from './assets.js';
2
3
  import { MailClient } from './mail.js';
3
4
  import { ProjectsClient } from './projects.js';
5
+ import { WorkloadSecurityClient } from './workload-security.js';
4
6
  const defaultBaseUrl = 'https://api.stackshift.cloud/api/v1';
5
7
  const defaultMailBaseUrl = 'https://api.stackshift.cloud/v1';
6
8
  const defaultCdnBaseUrl = 'https://cdn.stackshift.cloud';
7
9
  export class StackShift {
10
+ aiCredits;
11
+ assetSpaceId;
8
12
  apiKey;
9
13
  baseUrl;
10
14
  mailBaseUrl;
@@ -12,20 +16,24 @@ export class StackShift {
12
16
  projects;
13
17
  assets;
14
18
  mail;
19
+ workloadSecurity;
15
20
  fetcher;
16
21
  constructor(options = {}) {
17
22
  const apiKey = options.apiKey ?? env('STACKSHIFT_API_KEY');
18
23
  if (!apiKey) {
19
24
  throw new Error('StackShift SDK requires an apiKey');
20
25
  }
26
+ this.assetSpaceId = options.assetSpaceId;
21
27
  this.apiKey = apiKey;
22
28
  this.baseUrl = (options.baseUrl ?? defaultBaseUrl).replace(/\/$/, '');
23
29
  this.mailBaseUrl = (options.mailBaseUrl ?? defaultMailBaseUrl).replace(/\/$/, '');
24
30
  this.cdnBaseUrl = (options.cdnBaseUrl ?? defaultCdnBaseUrl).replace(/\/$/, '');
25
31
  this.fetcher = options.fetch ?? fetch;
32
+ this.aiCredits = new AICreditsClient(this);
26
33
  this.projects = new ProjectsClient(this);
27
34
  this.assets = new AssetsClient(this);
28
35
  this.mail = new MailClient(this);
36
+ this.workloadSecurity = new WorkloadSecurityClient(this);
29
37
  }
30
38
  async request(path, init = {}) {
31
39
  return this.requestFrom(this.baseUrl, path, init);
@@ -36,6 +44,11 @@ export class StackShift {
36
44
  async mailRequest(path, init = {}) {
37
45
  return this.requestFrom(this.mailBaseUrl, path, init);
38
46
  }
47
+ playbackRequest(path, credential, body) {
48
+ return this.requestFrom(new URL(this.baseUrl).origin, `/playback${path}`, {
49
+ method: 'POST', body, headers: { Authorization: `Bearer ${credential}` },
50
+ });
51
+ }
39
52
  async requestFrom(baseUrl, path, init) {
40
53
  const response = await this.fetchFrom(baseUrl, path, init);
41
54
  const raw = await response.text();
@@ -51,6 +64,7 @@ export class StackShift {
51
64
  method: init.method ?? 'GET',
52
65
  headers: stripUndefined({
53
66
  Authorization: `Bearer ${this.apiKey}`,
67
+ 'X-Asset-Space-ID': path.startsWith('/assets') ? this.assetSpaceId : undefined,
54
68
  'Content-Type': isFormData ? undefined : 'application/json',
55
69
  ...init.headers,
56
70
  }),