@thinkai/tai-api-contract 2.2.9 → 2.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.
@@ -1,7 +1,7 @@
1
1
  openapi: 3.0.3
2
2
  info:
3
3
  title: ThinkAI API
4
- version: 2.2.9
4
+ version: 2.3.0
5
5
  description: >
6
6
  Contract surface for the AI Driven SDLC backend used by ThinkAI.
7
7
  Workspace-scoped routes use `/workspaces/{workspaceId}/...`.
@@ -752,6 +752,211 @@ paths:
752
752
  schema:
753
753
  $ref: "#/components/schemas/ErrorMessageDto"
754
754
 
755
+ /workspaces/{workspaceId}/integrations/ai-tool/{provider}/refresh:
756
+ post:
757
+ tags: [Integrations]
758
+ summary: Refresh AI tool integration snapshots
759
+ operationId: refreshWorkspaceAiTool
760
+ description: >
761
+ Provider-agnostic refresh. Returns 409 when an advisory-lock refresh is already in progress.
762
+ On upstream auth/rate/network failures, returns `200` with `{ ok:false, error }` so the SPA can render inline error.
763
+ parameters:
764
+ - $ref: "#/components/parameters/WorkspaceId"
765
+ - name: provider
766
+ in: path
767
+ required: true
768
+ schema:
769
+ type: string
770
+ enum: [cursor]
771
+ responses:
772
+ "200":
773
+ description: Refresh result
774
+ content:
775
+ application/json:
776
+ schema:
777
+ $ref: "#/components/schemas/AiToolRefreshResponseDto"
778
+ examples:
779
+ ok:
780
+ value: { ok: true }
781
+ invalid_token:
782
+ value: { ok: false, error: invalid_token }
783
+ "401":
784
+ $ref: "#/components/responses/Unauthorized"
785
+ "403":
786
+ $ref: "#/components/responses/Forbidden"
787
+ "404":
788
+ description: Provider source missing for this workspace
789
+ content:
790
+ application/json:
791
+ schema:
792
+ $ref: "#/components/schemas/AiToolRefreshResponseDto"
793
+ example:
794
+ ok: false
795
+ error: no_source
796
+ "409":
797
+ description: Refresh already in progress
798
+ content:
799
+ application/json:
800
+ schema:
801
+ $ref: "#/components/schemas/AiToolRefreshResponseDto"
802
+ example:
803
+ ok: false
804
+ error: already_in_progress
805
+
806
+ /workspaces/{workspaceId}/integrations/ai-tool/{provider}/seats:
807
+ get:
808
+ tags: [Integrations]
809
+ summary: List latest AI-tool seats
810
+ operationId: getWorkspaceAiToolSeats
811
+ parameters:
812
+ - $ref: "#/components/parameters/WorkspaceId"
813
+ - name: provider
814
+ in: path
815
+ required: true
816
+ schema:
817
+ type: string
818
+ enum: [cursor]
819
+ responses:
820
+ "200":
821
+ description: Seats
822
+ content:
823
+ application/json:
824
+ schema:
825
+ type: object
826
+ required: [seats]
827
+ properties:
828
+ seats:
829
+ type: array
830
+ items:
831
+ $ref: "#/components/schemas/AiToolSeatDto"
832
+ "401":
833
+ $ref: "#/components/responses/Unauthorized"
834
+ "403":
835
+ $ref: "#/components/responses/Forbidden"
836
+
837
+ /workspaces/{workspaceId}/integrations/ai-tool/{provider}/daily-usage:
838
+ get:
839
+ tags: [Integrations]
840
+ summary: List AI-tool daily usage
841
+ operationId: getWorkspaceAiToolDailyUsage
842
+ parameters:
843
+ - $ref: "#/components/parameters/WorkspaceId"
844
+ - name: provider
845
+ in: path
846
+ required: true
847
+ schema:
848
+ type: string
849
+ enum: [cursor]
850
+ - name: from
851
+ in: query
852
+ required: false
853
+ schema:
854
+ type: string
855
+ format: date
856
+ - name: to
857
+ in: query
858
+ required: false
859
+ schema:
860
+ type: string
861
+ format: date
862
+ - name: externalId
863
+ in: query
864
+ required: false
865
+ schema:
866
+ type: string
867
+ responses:
868
+ "200":
869
+ description: Usage rows
870
+ content:
871
+ application/json:
872
+ schema:
873
+ type: object
874
+ required: [rows]
875
+ properties:
876
+ rows:
877
+ type: array
878
+ items:
879
+ $ref: "#/components/schemas/AiToolDailyUsageRowDto"
880
+ "401":
881
+ $ref: "#/components/responses/Unauthorized"
882
+ "403":
883
+ $ref: "#/components/responses/Forbidden"
884
+
885
+ /workspaces/{workspaceId}/integrations/ai-tool/{provider}/spend:
886
+ get:
887
+ tags: [Integrations]
888
+ summary: List AI-tool spend
889
+ operationId: getWorkspaceAiToolSpend
890
+ parameters:
891
+ - $ref: "#/components/parameters/WorkspaceId"
892
+ - name: provider
893
+ in: path
894
+ required: true
895
+ schema:
896
+ type: string
897
+ enum: [cursor]
898
+ - name: cycleStartMs
899
+ in: query
900
+ required: false
901
+ schema:
902
+ type: integer
903
+ format: int64
904
+ responses:
905
+ "200":
906
+ description: Spend rows
907
+ content:
908
+ application/json:
909
+ schema:
910
+ type: object
911
+ required: [rows]
912
+ properties:
913
+ rows:
914
+ type: array
915
+ items:
916
+ $ref: "#/components/schemas/AiToolSpendRowDto"
917
+ "401":
918
+ $ref: "#/components/responses/Unauthorized"
919
+ "403":
920
+ $ref: "#/components/responses/Forbidden"
921
+
922
+ /workspaces/{workspaceId}/integrations/ai-tool/{provider}/status:
923
+ get:
924
+ tags: [Integrations]
925
+ summary: Get last refresh status
926
+ operationId: getWorkspaceAiToolRefreshStatus
927
+ parameters:
928
+ - $ref: "#/components/parameters/WorkspaceId"
929
+ - name: provider
930
+ in: path
931
+ required: true
932
+ schema:
933
+ type: string
934
+ enum: [cursor]
935
+ responses:
936
+ "200":
937
+ description: Refresh status
938
+ content:
939
+ application/json:
940
+ schema:
941
+ type: object
942
+ required: [status]
943
+ properties:
944
+ status:
945
+ $ref: "#/components/schemas/AiToolRefreshStatusDto"
946
+ "401":
947
+ $ref: "#/components/responses/Unauthorized"
948
+ "403":
949
+ $ref: "#/components/responses/Forbidden"
950
+ "404":
951
+ description: No refresh status yet (or provider source missing)
952
+ content:
953
+ application/json:
954
+ schema:
955
+ $ref: "#/components/schemas/AiToolRefreshResponseDto"
956
+ example:
957
+ ok: false
958
+ error: no_source
959
+
755
960
  /integrations/github/callback:
756
961
  get:
757
962
  tags: [Integrations]
@@ -1662,6 +1867,101 @@ components:
1662
1867
  error:
1663
1868
  type: string
1664
1869
 
1870
+ AiToolSeatDto:
1871
+ type: object
1872
+ required: [externalId, email, isRemoved]
1873
+ properties:
1874
+ externalId:
1875
+ type: string
1876
+ email:
1877
+ type: string
1878
+ displayName:
1879
+ type: string
1880
+ nullable: true
1881
+ role:
1882
+ type: string
1883
+ nullable: true
1884
+ isRemoved:
1885
+ type: boolean
1886
+ payload:
1887
+ type: object
1888
+ additionalProperties: true
1889
+
1890
+ AiToolDailyUsageRowDto:
1891
+ type: object
1892
+ required: [day, externalId, isActive]
1893
+ properties:
1894
+ day:
1895
+ type: string
1896
+ format: date
1897
+ externalId:
1898
+ type: string
1899
+ email:
1900
+ type: string
1901
+ nullable: true
1902
+ isActive:
1903
+ type: boolean
1904
+ mostUsedModel:
1905
+ type: string
1906
+ nullable: true
1907
+ payload:
1908
+ type: object
1909
+ additionalProperties: true
1910
+
1911
+ AiToolSpendRowDto:
1912
+ type: object
1913
+ required: [billingCycleStartMs, externalId, spendCents]
1914
+ properties:
1915
+ billingCycleStartMs:
1916
+ type: integer
1917
+ format: int64
1918
+ externalId:
1919
+ type: string
1920
+ email:
1921
+ type: string
1922
+ nullable: true
1923
+ spendCents:
1924
+ type: integer
1925
+ format: int64
1926
+ payload:
1927
+ type: object
1928
+ additionalProperties: true
1929
+
1930
+ AiToolRefreshStatusDto:
1931
+ type: object
1932
+ required: [lastAttemptAt, counts]
1933
+ properties:
1934
+ lastAttemptAt:
1935
+ type: string
1936
+ format: date-time
1937
+ lastSuccessAt:
1938
+ type: string
1939
+ format: date-time
1940
+ nullable: true
1941
+ lastErrorKind:
1942
+ type: string
1943
+ nullable: true
1944
+ lastErrorMessage:
1945
+ type: string
1946
+ nullable: true
1947
+ durationMs:
1948
+ type: integer
1949
+ format: int64
1950
+ nullable: true
1951
+ counts:
1952
+ type: object
1953
+ additionalProperties: true
1954
+
1955
+ AiToolRefreshResponseDto:
1956
+ type: object
1957
+ required: [ok]
1958
+ properties:
1959
+ ok:
1960
+ type: boolean
1961
+ error:
1962
+ type: string
1963
+ nullable: true
1964
+
1665
1965
  DashboardProductivityMetricsDto:
1666
1966
  type: object
1667
1967
  description: Nested metric groups; see TypeScript `DashboardProductivityMetricsDto` in @thinkai/tai-api-contract.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@thinkai/tai-api-contract",
3
- "version": "2.2.9",
3
+ "version": "2.3.0",
4
4
  "private": false,
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -293,6 +293,94 @@ export interface paths {
293
293
  patch?: never;
294
294
  trace?: never;
295
295
  };
296
+ "/workspaces/{workspaceId}/integrations/ai-tool/{provider}/refresh": {
297
+ parameters: {
298
+ query?: never;
299
+ header?: never;
300
+ path?: never;
301
+ cookie?: never;
302
+ };
303
+ get?: never;
304
+ put?: never;
305
+ /**
306
+ * Refresh AI tool integration snapshots
307
+ * @description Provider-agnostic refresh. Returns 409 when an advisory-lock refresh is already in progress. On upstream auth/rate/network failures, returns `200` with `{ ok:false, error }` so the SPA can render inline error.
308
+ */
309
+ post: operations["refreshWorkspaceAiTool"];
310
+ delete?: never;
311
+ options?: never;
312
+ head?: never;
313
+ patch?: never;
314
+ trace?: never;
315
+ };
316
+ "/workspaces/{workspaceId}/integrations/ai-tool/{provider}/seats": {
317
+ parameters: {
318
+ query?: never;
319
+ header?: never;
320
+ path?: never;
321
+ cookie?: never;
322
+ };
323
+ /** List latest AI-tool seats */
324
+ get: operations["getWorkspaceAiToolSeats"];
325
+ put?: never;
326
+ post?: never;
327
+ delete?: never;
328
+ options?: never;
329
+ head?: never;
330
+ patch?: never;
331
+ trace?: never;
332
+ };
333
+ "/workspaces/{workspaceId}/integrations/ai-tool/{provider}/daily-usage": {
334
+ parameters: {
335
+ query?: never;
336
+ header?: never;
337
+ path?: never;
338
+ cookie?: never;
339
+ };
340
+ /** List AI-tool daily usage */
341
+ get: operations["getWorkspaceAiToolDailyUsage"];
342
+ put?: never;
343
+ post?: never;
344
+ delete?: never;
345
+ options?: never;
346
+ head?: never;
347
+ patch?: never;
348
+ trace?: never;
349
+ };
350
+ "/workspaces/{workspaceId}/integrations/ai-tool/{provider}/spend": {
351
+ parameters: {
352
+ query?: never;
353
+ header?: never;
354
+ path?: never;
355
+ cookie?: never;
356
+ };
357
+ /** List AI-tool spend */
358
+ get: operations["getWorkspaceAiToolSpend"];
359
+ put?: never;
360
+ post?: never;
361
+ delete?: never;
362
+ options?: never;
363
+ head?: never;
364
+ patch?: never;
365
+ trace?: never;
366
+ };
367
+ "/workspaces/{workspaceId}/integrations/ai-tool/{provider}/status": {
368
+ parameters: {
369
+ query?: never;
370
+ header?: never;
371
+ path?: never;
372
+ cookie?: never;
373
+ };
374
+ /** Get last refresh status */
375
+ get: operations["getWorkspaceAiToolRefreshStatus"];
376
+ put?: never;
377
+ post?: never;
378
+ delete?: never;
379
+ options?: never;
380
+ head?: never;
381
+ patch?: never;
382
+ trace?: never;
383
+ };
296
384
  "/integrations/github/callback": {
297
385
  parameters: {
298
386
  query?: never;
@@ -773,6 +861,55 @@ export interface components {
773
861
  success: boolean;
774
862
  error?: string;
775
863
  };
864
+ AiToolSeatDto: {
865
+ externalId: string;
866
+ email: string;
867
+ displayName?: string | null;
868
+ role?: string | null;
869
+ isRemoved: boolean;
870
+ payload?: {
871
+ [key: string]: unknown;
872
+ };
873
+ };
874
+ AiToolDailyUsageRowDto: {
875
+ /** Format: date */
876
+ day: string;
877
+ externalId: string;
878
+ email?: string | null;
879
+ isActive: boolean;
880
+ mostUsedModel?: string | null;
881
+ payload?: {
882
+ [key: string]: unknown;
883
+ };
884
+ };
885
+ AiToolSpendRowDto: {
886
+ /** Format: int64 */
887
+ billingCycleStartMs: number;
888
+ externalId: string;
889
+ email?: string | null;
890
+ /** Format: int64 */
891
+ spendCents: number;
892
+ payload?: {
893
+ [key: string]: unknown;
894
+ };
895
+ };
896
+ AiToolRefreshStatusDto: {
897
+ /** Format: date-time */
898
+ lastAttemptAt: string;
899
+ /** Format: date-time */
900
+ lastSuccessAt?: string | null;
901
+ lastErrorKind?: string | null;
902
+ lastErrorMessage?: string | null;
903
+ /** Format: int64 */
904
+ durationMs?: number | null;
905
+ counts: {
906
+ [key: string]: unknown;
907
+ };
908
+ };
909
+ AiToolRefreshResponseDto: {
910
+ ok: boolean;
911
+ error?: string | null;
912
+ };
776
913
  /** @description Nested metric groups; see TypeScript `DashboardProductivityMetricsDto` in @thinkai/tai-api-contract. */
777
914
  DashboardProductivityMetricsDto: {
778
915
  [key: string]: unknown;
@@ -1245,6 +1382,11 @@ export type TenantSourceEntryDto = components['schemas']['TenantSourceEntryDto']
1245
1382
  export type CursorSourceDto = components['schemas']['CursorSourceDto'];
1246
1383
  export type WorkspaceConfigDto = components['schemas']['WorkspaceConfigDto'];
1247
1384
  export type TestConnectionResponseDto = components['schemas']['TestConnectionResponseDto'];
1385
+ export type AiToolSeatDto = components['schemas']['AiToolSeatDto'];
1386
+ export type AiToolDailyUsageRowDto = components['schemas']['AiToolDailyUsageRowDto'];
1387
+ export type AiToolSpendRowDto = components['schemas']['AiToolSpendRowDto'];
1388
+ export type AiToolRefreshStatusDto = components['schemas']['AiToolRefreshStatusDto'];
1389
+ export type AiToolRefreshResponseDto = components['schemas']['AiToolRefreshResponseDto'];
1248
1390
  export type DashboardProductivityMetricsDto = components['schemas']['DashboardProductivityMetricsDto'];
1249
1391
  export type DashboardProductivityDto = components['schemas']['DashboardProductivityDto'];
1250
1392
  export type DashboardProductivityHistoryDto = components['schemas']['DashboardProductivityHistoryDto'];
@@ -2027,6 +2169,190 @@ export interface operations {
2027
2169
  };
2028
2170
  };
2029
2171
  };
2172
+ refreshWorkspaceAiTool: {
2173
+ parameters: {
2174
+ query?: never;
2175
+ header?: never;
2176
+ path: {
2177
+ workspaceId: components["parameters"]["WorkspaceId"];
2178
+ provider: "cursor";
2179
+ };
2180
+ cookie?: never;
2181
+ };
2182
+ requestBody?: never;
2183
+ responses: {
2184
+ /** @description Refresh result */
2185
+ 200: {
2186
+ headers: {
2187
+ [name: string]: unknown;
2188
+ };
2189
+ content: {
2190
+ "application/json": components["schemas"]["AiToolRefreshResponseDto"];
2191
+ };
2192
+ };
2193
+ 401: components["responses"]["Unauthorized"];
2194
+ 403: components["responses"]["Forbidden"];
2195
+ /** @description Provider source missing for this workspace */
2196
+ 404: {
2197
+ headers: {
2198
+ [name: string]: unknown;
2199
+ };
2200
+ content: {
2201
+ /**
2202
+ * @example {
2203
+ * "ok": false,
2204
+ * "error": "no_source"
2205
+ * }
2206
+ */
2207
+ "application/json": components["schemas"]["AiToolRefreshResponseDto"];
2208
+ };
2209
+ };
2210
+ /** @description Refresh already in progress */
2211
+ 409: {
2212
+ headers: {
2213
+ [name: string]: unknown;
2214
+ };
2215
+ content: {
2216
+ /**
2217
+ * @example {
2218
+ * "ok": false,
2219
+ * "error": "already_in_progress"
2220
+ * }
2221
+ */
2222
+ "application/json": components["schemas"]["AiToolRefreshResponseDto"];
2223
+ };
2224
+ };
2225
+ };
2226
+ };
2227
+ getWorkspaceAiToolSeats: {
2228
+ parameters: {
2229
+ query?: never;
2230
+ header?: never;
2231
+ path: {
2232
+ workspaceId: components["parameters"]["WorkspaceId"];
2233
+ provider: "cursor";
2234
+ };
2235
+ cookie?: never;
2236
+ };
2237
+ requestBody?: never;
2238
+ responses: {
2239
+ /** @description Seats */
2240
+ 200: {
2241
+ headers: {
2242
+ [name: string]: unknown;
2243
+ };
2244
+ content: {
2245
+ "application/json": {
2246
+ seats: components["schemas"]["AiToolSeatDto"][];
2247
+ };
2248
+ };
2249
+ };
2250
+ 401: components["responses"]["Unauthorized"];
2251
+ 403: components["responses"]["Forbidden"];
2252
+ };
2253
+ };
2254
+ getWorkspaceAiToolDailyUsage: {
2255
+ parameters: {
2256
+ query?: {
2257
+ from?: string;
2258
+ to?: string;
2259
+ externalId?: string;
2260
+ };
2261
+ header?: never;
2262
+ path: {
2263
+ workspaceId: components["parameters"]["WorkspaceId"];
2264
+ provider: "cursor";
2265
+ };
2266
+ cookie?: never;
2267
+ };
2268
+ requestBody?: never;
2269
+ responses: {
2270
+ /** @description Usage rows */
2271
+ 200: {
2272
+ headers: {
2273
+ [name: string]: unknown;
2274
+ };
2275
+ content: {
2276
+ "application/json": {
2277
+ rows: components["schemas"]["AiToolDailyUsageRowDto"][];
2278
+ };
2279
+ };
2280
+ };
2281
+ 401: components["responses"]["Unauthorized"];
2282
+ 403: components["responses"]["Forbidden"];
2283
+ };
2284
+ };
2285
+ getWorkspaceAiToolSpend: {
2286
+ parameters: {
2287
+ query?: {
2288
+ cycleStartMs?: number;
2289
+ };
2290
+ header?: never;
2291
+ path: {
2292
+ workspaceId: components["parameters"]["WorkspaceId"];
2293
+ provider: "cursor";
2294
+ };
2295
+ cookie?: never;
2296
+ };
2297
+ requestBody?: never;
2298
+ responses: {
2299
+ /** @description Spend rows */
2300
+ 200: {
2301
+ headers: {
2302
+ [name: string]: unknown;
2303
+ };
2304
+ content: {
2305
+ "application/json": {
2306
+ rows: components["schemas"]["AiToolSpendRowDto"][];
2307
+ };
2308
+ };
2309
+ };
2310
+ 401: components["responses"]["Unauthorized"];
2311
+ 403: components["responses"]["Forbidden"];
2312
+ };
2313
+ };
2314
+ getWorkspaceAiToolRefreshStatus: {
2315
+ parameters: {
2316
+ query?: never;
2317
+ header?: never;
2318
+ path: {
2319
+ workspaceId: components["parameters"]["WorkspaceId"];
2320
+ provider: "cursor";
2321
+ };
2322
+ cookie?: never;
2323
+ };
2324
+ requestBody?: never;
2325
+ responses: {
2326
+ /** @description Refresh status */
2327
+ 200: {
2328
+ headers: {
2329
+ [name: string]: unknown;
2330
+ };
2331
+ content: {
2332
+ "application/json": {
2333
+ status: components["schemas"]["AiToolRefreshStatusDto"];
2334
+ };
2335
+ };
2336
+ };
2337
+ 401: components["responses"]["Unauthorized"];
2338
+ 403: components["responses"]["Forbidden"];
2339
+ /** @description No refresh status yet (or provider source missing) */
2340
+ 404: {
2341
+ headers: {
2342
+ [name: string]: unknown;
2343
+ };
2344
+ content: {
2345
+ /**
2346
+ * @example {
2347
+ * "ok": false,
2348
+ * "error": "no_source"
2349
+ * }
2350
+ */
2351
+ "application/json": components["schemas"]["AiToolRefreshResponseDto"];
2352
+ };
2353
+ };
2354
+ };
2355
+ };
2030
2356
  getGithubInstallCallback: {
2031
2357
  parameters: {
2032
2358
  query: {