haystack-contracts 1.0.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 ADDED
@@ -0,0 +1,88 @@
1
+ # haystack-contracts
2
+
3
+ TypeScript API contracts for the **Haystack Robotics platform** — shared between the backend API and any frontend/SDK consumer.
4
+
5
+ ## Install
6
+
7
+ ```bash
8
+ npm install haystack-contracts
9
+ # or
10
+ pnpm add haystack-contracts
11
+ # or
12
+ yarn add haystack-contracts
13
+ ```
14
+
15
+ ## Usage
16
+
17
+ ### Response envelope typing
18
+
19
+ ```typescript
20
+ import type { ApiResponse, ApiErrorResponse, PaginatedResponse } from 'haystack-contracts';
21
+
22
+ // Type your API call results
23
+ const response: ApiResponse<BotSummaryResponse[]> = await fetch('/api/v1/robots/bots/summary')
24
+ .then(r => r.json());
25
+
26
+ // response.success → true
27
+ // response.statusCode → 200
28
+ // response.data → BotSummaryResponse[]
29
+ // response.timestamp → "2026-02-25T16:00:00.000Z"
30
+ ```
31
+
32
+ ### Request payload typing
33
+
34
+ ```typescript
35
+ import type {
36
+ CreateTenantPayload,
37
+ CreateUserPayload,
38
+ WebhookPayload,
39
+ } from 'haystack-contracts';
40
+
41
+ const body: CreateTenantPayload = {
42
+ name: 'Acme Corp',
43
+ slug: 'acme-corp',
44
+ status: 'ACTIVE',
45
+ };
46
+ ```
47
+
48
+ ### Full type inventory
49
+
50
+ #### Response Envelope
51
+ | Type | Description |
52
+ |------|-------------|
53
+ | `ApiResponse<T>` | `{ success: true, statusCode, data: T, timestamp }` |
54
+ | `ApiErrorResponse` | `{ success: false, statusCode, data: null, error, timestamp, path }` |
55
+ | `PaginationMeta` | `{ page, limit, total, totalPages }` |
56
+ | `PaginatedResponse<T>` | `ApiResponse<T[]>` + `PaginationMeta` |
57
+
58
+ #### Robots
59
+ | Type | Description |
60
+ |------|-------------|
61
+ | `Robot` | Robot entry from Nimbus Cloud |
62
+ | `Metric` | Robot metric from Nimbus Cloud |
63
+ | `WebhookBasicData` | Nested BasicData block in Cognimbus webhook |
64
+ | `WebhookPayload` | Full Cognimbus webhook payload (nested + flat formats) |
65
+ | `BotSummaryResponse` | Current bot status from local DB |
66
+ | `BotHistoryResponse` | Single bot status history record |
67
+ | `BotStateChangeResponse` | Single online↔offline transition record |
68
+
69
+ #### Tenants
70
+ | Type | Description |
71
+ |------|-------------|
72
+ | `TenantStatus` | `'ACTIVE' \| 'SUSPENDED' \| 'INACTIVE'` |
73
+ | `CreateTenantPayload` | POST /tenants body |
74
+ | `UpdateTenantPayload` | PATCH /tenants/:id body |
75
+ | `TenantResponse` | Tenant resource shape |
76
+
77
+ #### Users
78
+ | Type | Description |
79
+ |------|-------------|
80
+ | `UserRole` | `'SUPER_ADMIN' \| 'ADMIN' \| 'OPERATOR' \| 'VIEWER'` |
81
+ | `CreateUserPayload` | POST /users body |
82
+ | `UpdateUserPayload` | PATCH /users/:id body |
83
+ | `UserResponse` | User resource shape |
84
+
85
+ ## Package details
86
+ - **Zero runtime code** — types only, fully tree-shakeable
87
+ - **Dual format** — CJS (`dist/index.cjs`) + ESM (`dist/index.js`)
88
+ - **TypeScript declarations** — `dist/index.d.ts`
@@ -0,0 +1,170 @@
1
+ /**
2
+ * Standard success response returned by all Haystack API endpoints.
3
+ * @template T The shape of the `data` payload.
4
+ */
5
+ interface ApiResponse<T = unknown> {
6
+ /** Always `true` for success responses */
7
+ success: true;
8
+ /** HTTP status code (e.g. 200, 201) */
9
+ statusCode: number;
10
+ /** The response payload */
11
+ data: T;
12
+ /** ISO 8601 timestamp of the response */
13
+ timestamp: string;
14
+ }
15
+ /**
16
+ * Standard error response returned when a request fails.
17
+ */
18
+ interface ApiErrorResponse {
19
+ /** Always `false` for error responses */
20
+ success: false;
21
+ /** HTTP status code (e.g. 400, 404, 500) */
22
+ statusCode: number;
23
+ /** Always null on errors */
24
+ data: null;
25
+ /** Error details object */
26
+ error: {
27
+ /** Human-readable error message */
28
+ message: string | string[];
29
+ /** Additional error fields, e.g. validation errors */
30
+ [key: string]: unknown;
31
+ };
32
+ /** ISO 8601 timestamp of the response */
33
+ timestamp: string;
34
+ /** The request path that triggered the error */
35
+ path: string;
36
+ }
37
+ interface PaginationMeta {
38
+ page: number;
39
+ limit: number;
40
+ total: number;
41
+ totalPages: number;
42
+ }
43
+ interface PaginatedResponse<T = unknown> extends ApiResponse<T[]> {
44
+ meta: PaginationMeta;
45
+ }
46
+
47
+ /**
48
+ * A robot entry from Nimbus Cloud.
49
+ */
50
+ interface Robot {
51
+ robotId: string;
52
+ name?: string;
53
+ status?: string;
54
+ lastOnline?: string;
55
+ [key: string]: unknown;
56
+ }
57
+ /**
58
+ * A metric type available for robots.
59
+ */
60
+ interface Metric {
61
+ metricId: number;
62
+ name?: string;
63
+ value?: unknown;
64
+ timestamp?: string;
65
+ [key: string]: unknown;
66
+ }
67
+ /**
68
+ * The nested BasicData block inside a Cognimbus webhook payload.
69
+ */
70
+ interface WebhookBasicData {
71
+ /** Robot ID (PascalCase — Cognimbus default) */
72
+ Id?: string;
73
+ /** Robot ID (camelCase — alternative) */
74
+ robotId?: string;
75
+ /** Robot name (PascalCase) */
76
+ Name?: string;
77
+ /** Robot name (camelCase) */
78
+ robotName?: string;
79
+ /** Online flag (PascalCase) */
80
+ IsOnline?: boolean;
81
+ /** Online flag (camelCase) */
82
+ isOnline?: boolean;
83
+ }
84
+ /**
85
+ * Full Cognimbus webhook payload.
86
+ * Supports both nested (`BasicData.*`) and flat (`robotId`, `isOnline`) formats.
87
+ */
88
+ interface WebhookPayload extends WebhookBasicData {
89
+ BasicData?: WebhookBasicData;
90
+ LastTimeSeen?: string;
91
+ lastTimeSeen?: string;
92
+ AgentVersion?: string;
93
+ agentVersion?: string;
94
+ /** Tenant this robot belongs to */
95
+ tenantId?: string;
96
+ }
97
+ type TenantStatus = 'ACTIVE' | 'SUSPENDED' | 'INACTIVE';
98
+ interface CreateTenantPayload {
99
+ name: string;
100
+ slug: string;
101
+ industry?: string;
102
+ status?: TenantStatus;
103
+ contactEmail?: string;
104
+ }
105
+ interface UpdateTenantPayload extends Partial<CreateTenantPayload> {
106
+ }
107
+ interface TenantResponse {
108
+ id: string;
109
+ name: string;
110
+ slug: string;
111
+ industry: string | null;
112
+ status: TenantStatus;
113
+ contactEmail: string | null;
114
+ logoUrl: string | null;
115
+ createdAt: string;
116
+ updatedAt: string;
117
+ }
118
+ type UserRole = 'SUPER_ADMIN' | 'ADMIN' | 'OPERATOR' | 'VIEWER';
119
+ interface CreateUserPayload {
120
+ email: string;
121
+ password: string;
122
+ firstName: string;
123
+ lastName: string;
124
+ role?: UserRole;
125
+ tenantId?: string;
126
+ }
127
+ interface UpdateUserPayload extends Partial<CreateUserPayload> {
128
+ }
129
+ interface UserResponse {
130
+ id: string;
131
+ email: string;
132
+ firstName: string;
133
+ lastName: string;
134
+ role: UserRole;
135
+ isActive: boolean;
136
+ tenantId: string | null;
137
+ createdAt: string;
138
+ updatedAt: string;
139
+ }
140
+ interface BotSummaryResponse {
141
+ robotId: string;
142
+ robotName: string;
143
+ isOnline: boolean;
144
+ lastTimeSeen: string | null;
145
+ lastOnlineTime: string | null;
146
+ agentVersion: string | null;
147
+ tenantId: string | null;
148
+ lastUpdated: string;
149
+ }
150
+ interface BotHistoryResponse {
151
+ id: number;
152
+ robotId: string;
153
+ robotName: string;
154
+ isOnline: boolean;
155
+ lastTimeSeen: string | null;
156
+ agentVersion: string | null;
157
+ tenantId: string | null;
158
+ timestamp: string;
159
+ }
160
+ interface BotStateChangeResponse {
161
+ id: number;
162
+ robotId: string;
163
+ robotName: string;
164
+ previousState: boolean;
165
+ newState: boolean;
166
+ tenantId: string | null;
167
+ timestamp: string;
168
+ }
169
+
170
+ export type { ApiErrorResponse, ApiResponse, BotHistoryResponse, BotStateChangeResponse, BotSummaryResponse, CreateTenantPayload, CreateUserPayload, Metric, PaginatedResponse, PaginationMeta, Robot, TenantResponse, TenantStatus, UpdateTenantPayload, UpdateUserPayload, UserResponse, UserRole, WebhookBasicData, WebhookPayload };
@@ -0,0 +1,170 @@
1
+ /**
2
+ * Standard success response returned by all Haystack API endpoints.
3
+ * @template T The shape of the `data` payload.
4
+ */
5
+ interface ApiResponse<T = unknown> {
6
+ /** Always `true` for success responses */
7
+ success: true;
8
+ /** HTTP status code (e.g. 200, 201) */
9
+ statusCode: number;
10
+ /** The response payload */
11
+ data: T;
12
+ /** ISO 8601 timestamp of the response */
13
+ timestamp: string;
14
+ }
15
+ /**
16
+ * Standard error response returned when a request fails.
17
+ */
18
+ interface ApiErrorResponse {
19
+ /** Always `false` for error responses */
20
+ success: false;
21
+ /** HTTP status code (e.g. 400, 404, 500) */
22
+ statusCode: number;
23
+ /** Always null on errors */
24
+ data: null;
25
+ /** Error details object */
26
+ error: {
27
+ /** Human-readable error message */
28
+ message: string | string[];
29
+ /** Additional error fields, e.g. validation errors */
30
+ [key: string]: unknown;
31
+ };
32
+ /** ISO 8601 timestamp of the response */
33
+ timestamp: string;
34
+ /** The request path that triggered the error */
35
+ path: string;
36
+ }
37
+ interface PaginationMeta {
38
+ page: number;
39
+ limit: number;
40
+ total: number;
41
+ totalPages: number;
42
+ }
43
+ interface PaginatedResponse<T = unknown> extends ApiResponse<T[]> {
44
+ meta: PaginationMeta;
45
+ }
46
+
47
+ /**
48
+ * A robot entry from Nimbus Cloud.
49
+ */
50
+ interface Robot {
51
+ robotId: string;
52
+ name?: string;
53
+ status?: string;
54
+ lastOnline?: string;
55
+ [key: string]: unknown;
56
+ }
57
+ /**
58
+ * A metric type available for robots.
59
+ */
60
+ interface Metric {
61
+ metricId: number;
62
+ name?: string;
63
+ value?: unknown;
64
+ timestamp?: string;
65
+ [key: string]: unknown;
66
+ }
67
+ /**
68
+ * The nested BasicData block inside a Cognimbus webhook payload.
69
+ */
70
+ interface WebhookBasicData {
71
+ /** Robot ID (PascalCase — Cognimbus default) */
72
+ Id?: string;
73
+ /** Robot ID (camelCase — alternative) */
74
+ robotId?: string;
75
+ /** Robot name (PascalCase) */
76
+ Name?: string;
77
+ /** Robot name (camelCase) */
78
+ robotName?: string;
79
+ /** Online flag (PascalCase) */
80
+ IsOnline?: boolean;
81
+ /** Online flag (camelCase) */
82
+ isOnline?: boolean;
83
+ }
84
+ /**
85
+ * Full Cognimbus webhook payload.
86
+ * Supports both nested (`BasicData.*`) and flat (`robotId`, `isOnline`) formats.
87
+ */
88
+ interface WebhookPayload extends WebhookBasicData {
89
+ BasicData?: WebhookBasicData;
90
+ LastTimeSeen?: string;
91
+ lastTimeSeen?: string;
92
+ AgentVersion?: string;
93
+ agentVersion?: string;
94
+ /** Tenant this robot belongs to */
95
+ tenantId?: string;
96
+ }
97
+ type TenantStatus = 'ACTIVE' | 'SUSPENDED' | 'INACTIVE';
98
+ interface CreateTenantPayload {
99
+ name: string;
100
+ slug: string;
101
+ industry?: string;
102
+ status?: TenantStatus;
103
+ contactEmail?: string;
104
+ }
105
+ interface UpdateTenantPayload extends Partial<CreateTenantPayload> {
106
+ }
107
+ interface TenantResponse {
108
+ id: string;
109
+ name: string;
110
+ slug: string;
111
+ industry: string | null;
112
+ status: TenantStatus;
113
+ contactEmail: string | null;
114
+ logoUrl: string | null;
115
+ createdAt: string;
116
+ updatedAt: string;
117
+ }
118
+ type UserRole = 'SUPER_ADMIN' | 'ADMIN' | 'OPERATOR' | 'VIEWER';
119
+ interface CreateUserPayload {
120
+ email: string;
121
+ password: string;
122
+ firstName: string;
123
+ lastName: string;
124
+ role?: UserRole;
125
+ tenantId?: string;
126
+ }
127
+ interface UpdateUserPayload extends Partial<CreateUserPayload> {
128
+ }
129
+ interface UserResponse {
130
+ id: string;
131
+ email: string;
132
+ firstName: string;
133
+ lastName: string;
134
+ role: UserRole;
135
+ isActive: boolean;
136
+ tenantId: string | null;
137
+ createdAt: string;
138
+ updatedAt: string;
139
+ }
140
+ interface BotSummaryResponse {
141
+ robotId: string;
142
+ robotName: string;
143
+ isOnline: boolean;
144
+ lastTimeSeen: string | null;
145
+ lastOnlineTime: string | null;
146
+ agentVersion: string | null;
147
+ tenantId: string | null;
148
+ lastUpdated: string;
149
+ }
150
+ interface BotHistoryResponse {
151
+ id: number;
152
+ robotId: string;
153
+ robotName: string;
154
+ isOnline: boolean;
155
+ lastTimeSeen: string | null;
156
+ agentVersion: string | null;
157
+ tenantId: string | null;
158
+ timestamp: string;
159
+ }
160
+ interface BotStateChangeResponse {
161
+ id: number;
162
+ robotId: string;
163
+ robotName: string;
164
+ previousState: boolean;
165
+ newState: boolean;
166
+ tenantId: string | null;
167
+ timestamp: string;
168
+ }
169
+
170
+ export type { ApiErrorResponse, ApiResponse, BotHistoryResponse, BotStateChangeResponse, BotSummaryResponse, CreateTenantPayload, CreateUserPayload, Metric, PaginatedResponse, PaginationMeta, Robot, TenantResponse, TenantStatus, UpdateTenantPayload, UpdateUserPayload, UserResponse, UserRole, WebhookBasicData, WebhookPayload };
package/dist/index.js ADDED
@@ -0,0 +1,2 @@
1
+ 'use strict';
2
+
package/dist/index.mjs ADDED
@@ -0,0 +1 @@
1
+
package/package.json ADDED
@@ -0,0 +1,36 @@
1
+ {
2
+ "name": "haystack-contracts",
3
+ "version": "1.0.0",
4
+ "description": "TypeScript API contracts (request payloads + response shapes) for the Haystack Robotics platform",
5
+ "author": "Haystack Robotics",
6
+ "license": "MIT",
7
+ "keywords": [
8
+ "haystack",
9
+ "robotics",
10
+ "api-contracts",
11
+ "typescript",
12
+ "types"
13
+ ],
14
+ "main": "./dist/index.cjs",
15
+ "module": "./dist/index.js",
16
+ "types": "./dist/index.d.ts",
17
+ "exports": {
18
+ ".": {
19
+ "types": "./dist/index.d.ts",
20
+ "import": "./dist/index.js",
21
+ "require": "./dist/index.cjs"
22
+ }
23
+ },
24
+ "files": [
25
+ "dist"
26
+ ],
27
+ "scripts": {
28
+ "build": "tsup",
29
+ "prepublishOnly": "pnpm run build",
30
+ "typecheck": "tsc --noEmit"
31
+ },
32
+ "devDependencies": {
33
+ "tsup": "^8.5.1",
34
+ "typescript": "^5.9.3"
35
+ }
36
+ }