quickbase-js 1.1.0 → 2.0.0-alpha.2

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 (95) hide show
  1. package/README.md +351 -227
  2. package/dist/auth/index.d.ts +15 -0
  3. package/dist/auth/index.d.ts.map +1 -0
  4. package/dist/auth/index.js +29 -0
  5. package/dist/auth/index.js.map +1 -0
  6. package/dist/auth/sso-token.d.ts +28 -0
  7. package/dist/auth/sso-token.d.ts.map +1 -0
  8. package/dist/auth/sso-token.js +108 -0
  9. package/dist/auth/sso-token.js.map +1 -0
  10. package/dist/auth/temp-token.d.ts +31 -0
  11. package/dist/auth/temp-token.d.ts.map +1 -0
  12. package/dist/auth/temp-token.js +121 -0
  13. package/dist/auth/temp-token.js.map +1 -0
  14. package/dist/auth/token-cache.d.ts +44 -0
  15. package/dist/auth/token-cache.d.ts.map +1 -0
  16. package/dist/auth/token-cache.js +84 -0
  17. package/dist/auth/token-cache.js.map +1 -0
  18. package/dist/auth/types.d.ts +44 -0
  19. package/dist/auth/types.d.ts.map +1 -0
  20. package/dist/auth/types.js +5 -0
  21. package/dist/auth/types.js.map +1 -0
  22. package/dist/auth/user-token.d.ts +17 -0
  23. package/dist/auth/user-token.d.ts.map +1 -0
  24. package/dist/auth/user-token.js +30 -0
  25. package/dist/auth/user-token.js.map +1 -0
  26. package/dist/client/index.d.ts +12 -0
  27. package/dist/client/index.d.ts.map +1 -0
  28. package/dist/client/index.js +8 -0
  29. package/dist/client/index.js.map +1 -0
  30. package/dist/client/pagination.d.ts +131 -0
  31. package/dist/client/pagination.d.ts.map +1 -0
  32. package/dist/client/pagination.js +226 -0
  33. package/dist/client/pagination.js.map +1 -0
  34. package/dist/client/request.d.ts +40 -0
  35. package/dist/client/request.d.ts.map +1 -0
  36. package/dist/client/request.js +194 -0
  37. package/dist/client/request.js.map +1 -0
  38. package/dist/client/retry.d.ts +41 -0
  39. package/dist/client/retry.d.ts.map +1 -0
  40. package/dist/client/retry.js +122 -0
  41. package/dist/client/retry.js.map +1 -0
  42. package/dist/client/throttle.d.ts +46 -0
  43. package/dist/client/throttle.d.ts.map +1 -0
  44. package/dist/client/throttle.js +85 -0
  45. package/dist/client/throttle.js.map +1 -0
  46. package/dist/core/config.d.ts +13 -0
  47. package/dist/core/config.d.ts.map +1 -0
  48. package/dist/core/config.js +120 -0
  49. package/dist/core/config.js.map +1 -0
  50. package/dist/core/dates.d.ts +18 -0
  51. package/dist/core/dates.d.ts.map +1 -0
  52. package/dist/core/dates.js +58 -0
  53. package/dist/core/dates.js.map +1 -0
  54. package/dist/core/errors.d.ts +134 -0
  55. package/dist/core/errors.d.ts.map +1 -0
  56. package/dist/core/errors.js +185 -0
  57. package/dist/core/errors.js.map +1 -0
  58. package/dist/core/index.d.ts +10 -0
  59. package/dist/core/index.d.ts.map +1 -0
  60. package/dist/core/index.js +9 -0
  61. package/dist/core/index.js.map +1 -0
  62. package/dist/core/logger.d.ts +41 -0
  63. package/dist/core/logger.d.ts.map +1 -0
  64. package/dist/core/logger.js +96 -0
  65. package/dist/core/logger.js.map +1 -0
  66. package/dist/core/types.d.ts +154 -0
  67. package/dist/core/types.d.ts.map +1 -0
  68. package/dist/core/types.js +23 -0
  69. package/dist/core/types.js.map +1 -0
  70. package/dist/generated/client.d.ts +18 -0
  71. package/dist/generated/client.d.ts.map +1 -0
  72. package/dist/generated/client.js +1390 -0
  73. package/dist/generated/client.js.map +1 -0
  74. package/dist/generated/types.d.ts +3827 -0
  75. package/dist/generated/types.d.ts.map +1 -0
  76. package/dist/generated/types.js +8 -0
  77. package/dist/generated/types.js.map +1 -0
  78. package/dist/index.d.ts +89 -0
  79. package/dist/index.d.ts.map +1 -0
  80. package/dist/index.js +99 -0
  81. package/dist/index.js.map +1 -0
  82. package/dist/quickbase.esm.js +7 -0
  83. package/dist/quickbase.esm.js.map +7 -0
  84. package/dist/quickbase.min.js +7 -0
  85. package/dist/quickbase.min.js.map +7 -0
  86. package/package.json +57 -86
  87. package/dist/esm/quickbase.d.ts +0 -8094
  88. package/dist/esm/quickbase.js +0 -8330
  89. package/dist/esm/quickbase.js.map +0 -1
  90. package/dist/esm/quickbase.min.js +0 -2
  91. package/dist/esm/quickbase.min.js.map +0 -1
  92. package/dist/umd/quickbase.umd.js +0 -8906
  93. package/dist/umd/quickbase.umd.js.map +0 -1
  94. package/dist/umd/quickbase.umd.min.js +0 -2
  95. package/dist/umd/quickbase.umd.min.js.map +0 -1
@@ -0,0 +1,15 @@
1
+ /**
2
+ * Authentication module exports
3
+ */
4
+ export type { AuthStrategy, AuthContext, CachedToken } from './types.js';
5
+ export { UserTokenStrategy } from './user-token.js';
6
+ export { TempTokenStrategy } from './temp-token.js';
7
+ export { SsoTokenStrategy } from './sso-token.js';
8
+ export { TokenCache } from './token-cache.js';
9
+ import type { AuthConfig } from '../core/types.js';
10
+ import type { AuthStrategy, AuthContext } from './types.js';
11
+ /**
12
+ * Factory function to create the appropriate auth strategy
13
+ */
14
+ export declare function createAuthStrategy(authConfig: AuthConfig, context: AuthContext): AuthStrategy;
15
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/auth/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,YAAY,EAAE,YAAY,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AACzE,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AAClD,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAE9C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AACnD,OAAO,KAAK,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAK5D;;GAEG;AACH,wBAAgB,kBAAkB,CAChC,UAAU,EAAE,UAAU,EACtB,OAAO,EAAE,WAAW,GACnB,YAAY,CAiBd"}
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Authentication module exports
3
+ */
4
+ export { UserTokenStrategy } from './user-token.js';
5
+ export { TempTokenStrategy } from './temp-token.js';
6
+ export { SsoTokenStrategy } from './sso-token.js';
7
+ export { TokenCache } from './token-cache.js';
8
+ import { UserTokenStrategy } from './user-token.js';
9
+ import { TempTokenStrategy } from './temp-token.js';
10
+ import { SsoTokenStrategy } from './sso-token.js';
11
+ /**
12
+ * Factory function to create the appropriate auth strategy
13
+ */
14
+ export function createAuthStrategy(authConfig, context) {
15
+ switch (authConfig.type) {
16
+ case 'user-token':
17
+ return new UserTokenStrategy(authConfig.userToken, context);
18
+ case 'temp-token':
19
+ return new TempTokenStrategy(authConfig.userToken, context, {
20
+ appToken: authConfig.appToken,
21
+ tokenLifespanMs: authConfig.tokenLifespanMs,
22
+ });
23
+ case 'sso':
24
+ return new SsoTokenStrategy(authConfig.samlToken, context);
25
+ default:
26
+ throw new Error(`Unknown auth type: ${authConfig.type}`);
27
+ }
28
+ }
29
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/auth/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAGH,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AAClD,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAI9C,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AAElD;;GAEG;AACH,MAAM,UAAU,kBAAkB,CAChC,UAAsB,EACtB,OAAoB;IAEpB,QAAQ,UAAU,CAAC,IAAI,EAAE,CAAC;QACxB,KAAK,YAAY;YACf,OAAO,IAAI,iBAAiB,CAAC,UAAU,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC;QAE9D,KAAK,YAAY;YACf,OAAO,IAAI,iBAAiB,CAAC,UAAU,CAAC,SAAS,EAAE,OAAO,EAAE;gBAC1D,QAAQ,EAAE,UAAU,CAAC,QAAQ;gBAC7B,eAAe,EAAE,UAAU,CAAC,eAAe;aAC5C,CAAC,CAAC;QAEL,KAAK,KAAK;YACR,OAAO,IAAI,gBAAgB,CAAC,UAAU,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC;QAE7D;YACE,MAAM,IAAI,KAAK,CAAC,sBAAuB,UAA+B,CAAC,IAAI,EAAE,CAAC,CAAC;IACnF,CAAC;AACH,CAAC"}
@@ -0,0 +1,28 @@
1
+ /**
2
+ * SSO Token Authentication Strategy
3
+ *
4
+ * Exchanges a SAML token for a QuickBase temporary token via OAuth token exchange.
5
+ */
6
+ import type { AuthStrategy, AuthContext } from './types.js';
7
+ export declare class SsoTokenStrategy implements AuthStrategy {
8
+ private readonly samlToken;
9
+ private readonly realm;
10
+ private readonly baseUrl;
11
+ private readonly fetchApi;
12
+ private readonly logger;
13
+ private readonly cache;
14
+ /**
15
+ * Track pending SSO token exchange to deduplicate concurrent requests
16
+ */
17
+ private pendingExchange;
18
+ constructor(samlToken: string, context: AuthContext, options?: {
19
+ tokenLifespanMs?: number;
20
+ });
21
+ private get cacheKey();
22
+ getToken(_dbid?: string): Promise<string>;
23
+ private exchangeToken;
24
+ getAuthorizationHeader(token: string): string;
25
+ handleAuthError(_dbid?: string): Promise<boolean>;
26
+ invalidate(_dbid?: string): void;
27
+ }
28
+ //# sourceMappingURL=sso-token.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sso-token.d.ts","sourceRoot":"","sources":["../../src/auth/sso-token.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAM5D,qBAAa,gBAAiB,YAAW,YAAY;IACnD,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAS;IACnC,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAS;IAC/B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAS;IACjC,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAe;IACxC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAChC,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAa;IAEnC;;OAEG;IACH,OAAO,CAAC,eAAe,CAAgC;gBAGrD,SAAS,EAAE,MAAM,EACjB,OAAO,EAAE,WAAW,EACpB,OAAO,CAAC,EAAE;QAAE,eAAe,CAAC,EAAE,MAAM,CAAA;KAAE;IAaxC,OAAO,KAAK,QAAQ,GAEnB;IAEK,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;YA2BjC,aAAa;IA+C3B,sBAAsB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM;IAIvC,eAAe,CAAC,KAAK,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAevD,UAAU,CAAC,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI;CAIjC"}
@@ -0,0 +1,108 @@
1
+ /**
2
+ * SSO Token Authentication Strategy
3
+ *
4
+ * Exchanges a SAML token for a QuickBase temporary token via OAuth token exchange.
5
+ */
6
+ import { TokenCache } from './token-cache.js';
7
+ import { DEFAULT_CONFIG } from '../core/types.js';
8
+ import { AuthenticationError } from '../core/errors.js';
9
+ export class SsoTokenStrategy {
10
+ samlToken;
11
+ realm;
12
+ baseUrl;
13
+ fetchApi;
14
+ logger;
15
+ cache;
16
+ /**
17
+ * Track pending SSO token exchange to deduplicate concurrent requests
18
+ */
19
+ pendingExchange = null;
20
+ constructor(samlToken, context, options) {
21
+ this.samlToken = samlToken;
22
+ this.realm = context.realm;
23
+ this.baseUrl = context.baseUrl;
24
+ this.fetchApi = context.fetchApi;
25
+ this.logger = context.logger;
26
+ // SSO tokens are global, not per-dbid, so we use a single cache key
27
+ this.cache = new TokenCache(options?.tokenLifespanMs ?? DEFAULT_CONFIG.tempTokenLifespanMs);
28
+ }
29
+ get cacheKey() {
30
+ return '__sso__';
31
+ }
32
+ async getToken(_dbid) {
33
+ // Check cache first
34
+ const cachedToken = this.cache.get(this.cacheKey);
35
+ if (cachedToken) {
36
+ this.logger.token('cache-hit');
37
+ return cachedToken;
38
+ }
39
+ this.logger.token('cache-miss');
40
+ // Check if there's already an exchange in progress
41
+ if (this.pendingExchange) {
42
+ this.logger.debug('Waiting for existing SSO token exchange');
43
+ return this.pendingExchange;
44
+ }
45
+ // Exchange SAML token for QuickBase token
46
+ const exchangePromise = this.exchangeToken();
47
+ this.pendingExchange = exchangePromise;
48
+ try {
49
+ return await exchangePromise;
50
+ }
51
+ finally {
52
+ this.pendingExchange = null;
53
+ }
54
+ }
55
+ async exchangeToken() {
56
+ this.logger.token('fetch');
57
+ const url = `${this.baseUrl}/auth/oauth/token`;
58
+ const body = new URLSearchParams({
59
+ grant_type: 'urn:ietf:params:oauth:grant-type:token-exchange',
60
+ requested_token_type: 'urn:quickbase:params:oauth:token-type:temp_token',
61
+ subject_token: this.samlToken,
62
+ subject_token_type: 'urn:ietf:params:oauth:token-type:saml2',
63
+ });
64
+ const response = await this.fetchApi(url, {
65
+ method: 'POST',
66
+ headers: {
67
+ 'QB-Realm-Hostname': `${this.realm}.quickbase.com`,
68
+ 'Content-Type': 'application/x-www-form-urlencoded',
69
+ },
70
+ body: body.toString(),
71
+ });
72
+ if (!response.ok) {
73
+ const errorText = await response.text();
74
+ throw new AuthenticationError(`SSO token exchange failed: ${response.status} ${errorText}`, { rayId: response.headers.get('qb-api-ray') || undefined });
75
+ }
76
+ const data = await response.json();
77
+ const token = data.access_token;
78
+ if (!token) {
79
+ throw new AuthenticationError('No access_token in SSO exchange response');
80
+ }
81
+ // Cache the token
82
+ this.cache.set(this.cacheKey, token);
83
+ this.logger.debug('Cached new SSO token');
84
+ return token;
85
+ }
86
+ getAuthorizationHeader(token) {
87
+ return `QB-TEMP-TOKEN ${token}`;
88
+ }
89
+ async handleAuthError(_dbid) {
90
+ // Invalidate the cached token
91
+ this.invalidate();
92
+ // Try to exchange for a new token
93
+ try {
94
+ this.logger.token('refresh');
95
+ await this.getToken();
96
+ return true;
97
+ }
98
+ catch (error) {
99
+ this.logger.error('Failed to refresh SSO token', error);
100
+ return false;
101
+ }
102
+ }
103
+ invalidate(_dbid) {
104
+ this.logger.token('expire');
105
+ this.cache.clear();
106
+ }
107
+ }
108
+ //# sourceMappingURL=sso-token.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sso-token.js","sourceRoot":"","sources":["../../src/auth/sso-token.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,31 @@
1
+ /**
2
+ * Temporary Token Authentication Strategy
3
+ *
4
+ * Fetches database-specific temporary tokens from the QuickBase API.
5
+ * Tokens are cached and automatically refreshed when expired.
6
+ */
7
+ import type { AuthStrategy, AuthContext } from './types.js';
8
+ export declare class TempTokenStrategy implements AuthStrategy {
9
+ private readonly userToken?;
10
+ private readonly appToken?;
11
+ private readonly realm;
12
+ private readonly baseUrl;
13
+ private readonly fetchApi;
14
+ private readonly logger;
15
+ private readonly cache;
16
+ /**
17
+ * Track pending token fetches to deduplicate concurrent requests
18
+ * This prevents multiple simultaneous API calls for the same dbid
19
+ */
20
+ private readonly pendingFetches;
21
+ constructor(userToken: string | undefined, context: AuthContext, options?: {
22
+ appToken?: string;
23
+ tokenLifespanMs?: number;
24
+ });
25
+ getToken(dbid?: string): Promise<string>;
26
+ private fetchToken;
27
+ getAuthorizationHeader(token: string): string;
28
+ handleAuthError(dbid?: string): Promise<boolean>;
29
+ invalidate(dbid?: string): void;
30
+ }
31
+ //# sourceMappingURL=temp-token.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"temp-token.d.ts","sourceRoot":"","sources":["../../src/auth/temp-token.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAM5D,qBAAa,iBAAkB,YAAW,YAAY;IACpD,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAC,CAAS;IACpC,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAS;IACnC,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAS;IAC/B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAS;IACjC,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAe;IACxC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAChC,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAa;IAEnC;;;OAGG;IACH,OAAO,CAAC,QAAQ,CAAC,cAAc,CAAsC;gBAGnE,SAAS,EAAE,MAAM,GAAG,SAAS,EAC7B,OAAO,EAAE,WAAW,EACpB,OAAO,CAAC,EAAE;QAAE,QAAQ,CAAC,EAAE,MAAM,CAAC;QAAC,eAAe,CAAC,EAAE,MAAM,CAAA;KAAE;IAarD,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;YAiChC,UAAU;IA2CxB,sBAAsB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM;IAIvC,eAAe,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAoBtD,UAAU,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,IAAI;CAShC"}
@@ -0,0 +1,121 @@
1
+ /**
2
+ * Temporary Token Authentication Strategy
3
+ *
4
+ * Fetches database-specific temporary tokens from the QuickBase API.
5
+ * Tokens are cached and automatically refreshed when expired.
6
+ */
7
+ import { TokenCache } from './token-cache.js';
8
+ import { DEFAULT_CONFIG } from '../core/types.js';
9
+ import { AuthenticationError } from '../core/errors.js';
10
+ export class TempTokenStrategy {
11
+ userToken;
12
+ appToken;
13
+ realm;
14
+ baseUrl;
15
+ fetchApi;
16
+ logger;
17
+ cache;
18
+ /**
19
+ * Track pending token fetches to deduplicate concurrent requests
20
+ * This prevents multiple simultaneous API calls for the same dbid
21
+ */
22
+ pendingFetches = new Map();
23
+ constructor(userToken, context, options) {
24
+ this.userToken = userToken;
25
+ this.appToken = options?.appToken;
26
+ this.realm = context.realm;
27
+ this.baseUrl = context.baseUrl;
28
+ this.fetchApi = context.fetchApi;
29
+ this.logger = context.logger;
30
+ this.cache = new TokenCache(options?.tokenLifespanMs ?? DEFAULT_CONFIG.tempTokenLifespanMs);
31
+ }
32
+ async getToken(dbid) {
33
+ if (!dbid) {
34
+ throw new Error('Database ID (dbid) is required for temporary token authentication');
35
+ }
36
+ // Check cache first
37
+ const cachedToken = this.cache.get(dbid);
38
+ if (cachedToken) {
39
+ this.logger.token('cache-hit', dbid);
40
+ return cachedToken;
41
+ }
42
+ this.logger.token('cache-miss', dbid);
43
+ // Check if there's already a fetch in progress for this dbid
44
+ const pendingFetch = this.pendingFetches.get(dbid);
45
+ if (pendingFetch) {
46
+ this.logger.debug(`Waiting for existing token fetch for dbid: ${dbid}`);
47
+ return pendingFetch;
48
+ }
49
+ // Fetch new token
50
+ const fetchPromise = this.fetchToken(dbid);
51
+ this.pendingFetches.set(dbid, fetchPromise);
52
+ try {
53
+ const token = await fetchPromise;
54
+ return token;
55
+ }
56
+ finally {
57
+ this.pendingFetches.delete(dbid);
58
+ }
59
+ }
60
+ async fetchToken(dbid) {
61
+ this.logger.token('fetch', dbid);
62
+ const url = `${this.baseUrl}/auth/temporary/${dbid}`;
63
+ const headers = {
64
+ 'QB-Realm-Hostname': `${this.realm}.quickbase.com`,
65
+ 'Authorization': `QB-USER-TOKEN ${this.userToken}`,
66
+ 'Content-Type': 'application/json',
67
+ };
68
+ if (this.appToken) {
69
+ headers['QB-App-Token'] = this.appToken;
70
+ }
71
+ const response = await this.fetchApi(url, {
72
+ method: 'GET',
73
+ headers,
74
+ });
75
+ if (!response.ok) {
76
+ const errorText = await response.text();
77
+ throw new AuthenticationError(`Failed to fetch temporary token for ${dbid}: ${response.status} ${errorText}`, { rayId: response.headers.get('qb-api-ray') || undefined });
78
+ }
79
+ const data = await response.json();
80
+ const token = data.temporaryAuthorization;
81
+ if (!token) {
82
+ throw new AuthenticationError(`No temporary token in response for ${dbid}`);
83
+ }
84
+ // Cache the token
85
+ this.cache.set(dbid, token);
86
+ this.logger.debug(`Cached new token for dbid: ${dbid}`);
87
+ return token;
88
+ }
89
+ getAuthorizationHeader(token) {
90
+ return `QB-TEMP-TOKEN ${token}`;
91
+ }
92
+ async handleAuthError(dbid) {
93
+ if (!dbid) {
94
+ this.logger.debug('Auth error without dbid - cannot refresh temp token');
95
+ return false;
96
+ }
97
+ // Invalidate the cached token
98
+ this.invalidate(dbid);
99
+ // Try to fetch a new token
100
+ try {
101
+ this.logger.token('refresh', dbid);
102
+ await this.getToken(dbid);
103
+ return true;
104
+ }
105
+ catch (error) {
106
+ this.logger.error(`Failed to refresh temp token for ${dbid}`, error);
107
+ return false;
108
+ }
109
+ }
110
+ invalidate(dbid) {
111
+ if (dbid) {
112
+ this.logger.token('expire', dbid);
113
+ this.cache.delete(dbid);
114
+ }
115
+ else {
116
+ // Invalidate all tokens
117
+ this.cache.clear();
118
+ }
119
+ }
120
+ }
121
+ //# sourceMappingURL=temp-token.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"temp-token.js","sourceRoot":"","sources":["../../src/auth/temp-token.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,44 @@
1
+ /**
2
+ * Token cache with TTL support
3
+ *
4
+ * Manages cached temporary tokens with expiration handling.
5
+ * Tokens are stored per-dbid since QuickBase temp tokens are database-specific.
6
+ */
7
+ export declare class TokenCache {
8
+ private readonly cache;
9
+ private readonly defaultLifespanMs;
10
+ constructor(defaultLifespanMs: number);
11
+ /**
12
+ * Get a cached token if it exists and is not expired
13
+ */
14
+ get(dbid: string): string | null;
15
+ /**
16
+ * Store a token with optional custom lifespan
17
+ */
18
+ set(dbid: string, token: string, lifespanMs?: number): void;
19
+ /**
20
+ * Remove a specific token from cache
21
+ */
22
+ delete(dbid: string): boolean;
23
+ /**
24
+ * Clear all cached tokens
25
+ */
26
+ clear(): void;
27
+ /**
28
+ * Check if a token exists and is valid
29
+ */
30
+ has(dbid: string): boolean;
31
+ /**
32
+ * Get time until token expires (in ms), or null if not cached
33
+ */
34
+ getTimeToExpiry(dbid: string): number | null;
35
+ /**
36
+ * Get the number of cached tokens
37
+ */
38
+ get size(): number;
39
+ /**
40
+ * Remove expired entries from cache
41
+ */
42
+ private cleanup;
43
+ }
44
+ //# sourceMappingURL=token-cache.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"token-cache.d.ts","sourceRoot":"","sources":["../../src/auth/token-cache.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,qBAAa,UAAU;IACrB,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAkC;IACxD,OAAO,CAAC,QAAQ,CAAC,iBAAiB,CAAS;gBAE/B,iBAAiB,EAAE,MAAM;IAIrC;;OAEG;IACH,GAAG,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI;IAehC;;OAEG;IACH,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI;IAK3D;;OAEG;IACH,MAAM,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO;IAI7B;;OAEG;IACH,KAAK,IAAI,IAAI;IAIb;;OAEG;IACH,GAAG,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO;IAI1B;;OAEG;IACH,eAAe,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI;IAS5C;;OAEG;IACH,IAAI,IAAI,IAAI,MAAM,CAIjB;IAED;;OAEG;IACH,OAAO,CAAC,OAAO;CAQhB"}
@@ -0,0 +1,84 @@
1
+ /**
2
+ * Token cache with TTL support
3
+ *
4
+ * Manages cached temporary tokens with expiration handling.
5
+ * Tokens are stored per-dbid since QuickBase temp tokens are database-specific.
6
+ */
7
+ export class TokenCache {
8
+ cache = new Map();
9
+ defaultLifespanMs;
10
+ constructor(defaultLifespanMs) {
11
+ this.defaultLifespanMs = defaultLifespanMs;
12
+ }
13
+ /**
14
+ * Get a cached token if it exists and is not expired
15
+ */
16
+ get(dbid) {
17
+ const entry = this.cache.get(dbid);
18
+ if (!entry) {
19
+ return null;
20
+ }
21
+ // Check if token is expired (with 10 second buffer)
22
+ if (Date.now() >= entry.expiresAt - 10000) {
23
+ this.cache.delete(dbid);
24
+ return null;
25
+ }
26
+ return entry.token;
27
+ }
28
+ /**
29
+ * Store a token with optional custom lifespan
30
+ */
31
+ set(dbid, token, lifespanMs) {
32
+ const expiresAt = Date.now() + (lifespanMs ?? this.defaultLifespanMs);
33
+ this.cache.set(dbid, { token, expiresAt });
34
+ }
35
+ /**
36
+ * Remove a specific token from cache
37
+ */
38
+ delete(dbid) {
39
+ return this.cache.delete(dbid);
40
+ }
41
+ /**
42
+ * Clear all cached tokens
43
+ */
44
+ clear() {
45
+ this.cache.clear();
46
+ }
47
+ /**
48
+ * Check if a token exists and is valid
49
+ */
50
+ has(dbid) {
51
+ return this.get(dbid) !== null;
52
+ }
53
+ /**
54
+ * Get time until token expires (in ms), or null if not cached
55
+ */
56
+ getTimeToExpiry(dbid) {
57
+ const entry = this.cache.get(dbid);
58
+ if (!entry) {
59
+ return null;
60
+ }
61
+ const ttl = entry.expiresAt - Date.now();
62
+ return ttl > 0 ? ttl : null;
63
+ }
64
+ /**
65
+ * Get the number of cached tokens
66
+ */
67
+ get size() {
68
+ // Clean up expired entries first
69
+ this.cleanup();
70
+ return this.cache.size;
71
+ }
72
+ /**
73
+ * Remove expired entries from cache
74
+ */
75
+ cleanup() {
76
+ const now = Date.now();
77
+ for (const [dbid, entry] of this.cache) {
78
+ if (now >= entry.expiresAt) {
79
+ this.cache.delete(dbid);
80
+ }
81
+ }
82
+ }
83
+ }
84
+ //# sourceMappingURL=token-cache.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"token-cache.js","sourceRoot":"","sources":["../../src/auth/token-cache.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,MAAM,OAAO,UAAU;IACJ,KAAK,GAAG,IAAI,GAAG,EAAuB,CAAC;IACvC,iBAAiB,CAAS;IAE3C,YAAY,iBAAyB;QACnC,IAAI,CAAC,iBAAiB,GAAG,iBAAiB,CAAC;IAC7C,CAAC;IAED;;OAEG;IACH,GAAG,CAAC,IAAY;QACd,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;QACnC,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,OAAO,IAAI,CAAC;QACd,CAAC;QAED,oDAAoD;QACpD,IAAI,IAAI,CAAC,GAAG,EAAE,IAAI,KAAK,CAAC,SAAS,GAAG,KAAK,EAAE,CAAC;YAC1C,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;YACxB,OAAO,IAAI,CAAC;QACd,CAAC;QAED,OAAO,KAAK,CAAC,KAAK,CAAC;IACrB,CAAC;IAED;;OAEG;IACH,GAAG,CAAC,IAAY,EAAE,KAAa,EAAE,UAAmB;QAClD,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,CAAC,UAAU,IAAI,IAAI,CAAC,iBAAiB,CAAC,CAAC;QACtE,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,IAAI,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,CAAC;IAC7C,CAAC;IAED;;OAEG;IACH,MAAM,CAAC,IAAY;QACjB,OAAO,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;IACjC,CAAC;IAED;;OAEG;IACH,KAAK;QACH,IAAI,CAAC,KAAK,CAAC,KAAK,EAAE,CAAC;IACrB,CAAC;IAED;;OAEG;IACH,GAAG,CAAC,IAAY;QACd,OAAO,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,IAAI,CAAC;IACjC,CAAC;IAED;;OAEG;IACH,eAAe,CAAC,IAAY;QAC1B,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;QACnC,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,OAAO,IAAI,CAAC;QACd,CAAC;QACD,MAAM,GAAG,GAAG,KAAK,CAAC,SAAS,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACzC,OAAO,GAAG,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC;IAC9B,CAAC;IAED;;OAEG;IACH,IAAI,IAAI;QACN,iCAAiC;QACjC,IAAI,CAAC,OAAO,EAAE,CAAC;QACf,OAAO,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC;IACzB,CAAC;IAED;;OAEG;IACK,OAAO;QACb,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACvB,KAAK,MAAM,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC;YACvC,IAAI,GAAG,IAAI,KAAK,CAAC,SAAS,EAAE,CAAC;gBAC3B,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;YAC1B,CAAC;QACH,CAAC;IACH,CAAC;CACF"}
@@ -0,0 +1,44 @@
1
+ /**
2
+ * Authentication strategy types
3
+ */
4
+ import type { Logger } from '../core/logger.js';
5
+ /**
6
+ * Interface that all auth strategies must implement
7
+ */
8
+ export interface AuthStrategy {
9
+ /**
10
+ * Get a valid token for the given database ID
11
+ * @param dbid - The database ID (required for temp tokens)
12
+ */
13
+ getToken(dbid?: string): Promise<string>;
14
+ /**
15
+ * Get the authorization header value
16
+ */
17
+ getAuthorizationHeader(token: string): string;
18
+ /**
19
+ * Handle authentication errors (e.g., refresh token on 401)
20
+ * @returns true if token was refreshed and request should be retried
21
+ */
22
+ handleAuthError(dbid?: string): Promise<boolean>;
23
+ /**
24
+ * Invalidate cached tokens (if applicable)
25
+ */
26
+ invalidate(dbid?: string): void;
27
+ }
28
+ /**
29
+ * Context passed to auth strategy constructors
30
+ */
31
+ export interface AuthContext {
32
+ realm: string;
33
+ baseUrl: string;
34
+ fetchApi: typeof fetch;
35
+ logger: Logger;
36
+ }
37
+ /**
38
+ * Token cache entry
39
+ */
40
+ export interface CachedToken {
41
+ token: string;
42
+ expiresAt: number;
43
+ }
44
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/auth/types.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,mBAAmB,CAAC;AAEhD;;GAEG;AACH,MAAM,WAAW,YAAY;IAC3B;;;OAGG;IACH,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAEzC;;OAEG;IACH,sBAAsB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAAC;IAE9C;;;OAGG;IACH,eAAe,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IAEjD;;OAEG;IACH,UAAU,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CACjC;AAED;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,OAAO,KAAK,CAAC;IACvB,MAAM,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;CACnB"}
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Authentication strategy types
3
+ */
4
+ export {};
5
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/auth/types.ts"],"names":[],"mappings":"AAAA;;GAEG"}
@@ -0,0 +1,17 @@
1
+ /**
2
+ * User Token Authentication Strategy
3
+ *
4
+ * Simplest auth method - uses a persistent user token directly.
5
+ * Token is passed in the Authorization header as "QB-USER-TOKEN {token}"
6
+ */
7
+ import type { AuthStrategy, AuthContext } from './types.js';
8
+ export declare class UserTokenStrategy implements AuthStrategy {
9
+ private readonly userToken;
10
+ private readonly logger;
11
+ constructor(userToken: string, context: AuthContext);
12
+ getToken(_dbid?: string): Promise<string>;
13
+ getAuthorizationHeader(token: string): string;
14
+ handleAuthError(_dbid?: string): Promise<boolean>;
15
+ invalidate(_dbid?: string): void;
16
+ }
17
+ //# sourceMappingURL=user-token.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"user-token.d.ts","sourceRoot":"","sources":["../../src/auth/user-token.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAG5D,qBAAa,iBAAkB,YAAW,YAAY;IACpD,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAS;IACnC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;gBAEpB,SAAS,EAAE,MAAM,EAAE,OAAO,EAAE,WAAW;IAK7C,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAK/C,sBAAsB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM;IAIvC,eAAe,CAAC,KAAK,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAMvD,UAAU,CAAC,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI;CAGjC"}
@@ -0,0 +1,30 @@
1
+ /**
2
+ * User Token Authentication Strategy
3
+ *
4
+ * Simplest auth method - uses a persistent user token directly.
5
+ * Token is passed in the Authorization header as "QB-USER-TOKEN {token}"
6
+ */
7
+ export class UserTokenStrategy {
8
+ userToken;
9
+ logger;
10
+ constructor(userToken, context) {
11
+ this.userToken = userToken;
12
+ this.logger = context.logger;
13
+ }
14
+ async getToken(_dbid) {
15
+ // User tokens don't change, just return the configured token
16
+ return this.userToken;
17
+ }
18
+ getAuthorizationHeader(token) {
19
+ return `QB-USER-TOKEN ${token}`;
20
+ }
21
+ async handleAuthError(_dbid) {
22
+ // User tokens can't be refreshed - if auth fails, it's a permanent failure
23
+ this.logger.debug('Auth error with user token - cannot refresh');
24
+ return false;
25
+ }
26
+ invalidate(_dbid) {
27
+ // No-op for user tokens - they don't have cached state
28
+ }
29
+ }
30
+ //# sourceMappingURL=user-token.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"user-token.js","sourceRoot":"","sources":["../../src/auth/user-token.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAKH,MAAM,OAAO,iBAAiB;IACX,SAAS,CAAS;IAClB,MAAM,CAAS;IAEhC,YAAY,SAAiB,EAAE,OAAoB;QACjD,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC3B,IAAI,CAAC,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAC/B,CAAC;IAED,KAAK,CAAC,QAAQ,CAAC,KAAc;QAC3B,6DAA6D;QAC7D,OAAO,IAAI,CAAC,SAAS,CAAC;IACxB,CAAC;IAED,sBAAsB,CAAC,KAAa;QAClC,OAAO,iBAAiB,KAAK,EAAE,CAAC;IAClC,CAAC;IAED,KAAK,CAAC,eAAe,CAAC,KAAc;QAClC,2EAA2E;QAC3E,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,6CAA6C,CAAC,CAAC;QACjE,OAAO,KAAK,CAAC;IACf,CAAC;IAED,UAAU,CAAC,KAAc;QACvB,uDAAuD;IACzD,CAAC;CACF"}
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Client module exports
3
+ */
4
+ export type { RequestOptions, RequestExecutorOptions } from './request.js';
5
+ export { executeRequest, createRequestExecutor } from './request.js';
6
+ export type { Throttle } from './throttle.js';
7
+ export { SlidingWindowThrottle, NoOpThrottle, createThrottle } from './throttle.js';
8
+ export type { RetryOptions } from './retry.js';
9
+ export { calculateBackoffDelay, getRetryDelay, extractRateLimitInfo, sleep, isRetryableStatus, executeWithRetry, } from './retry.js';
10
+ export type { PaginationOptions, PaginationMetadata, PaginatedResponse, PaginationType, RequestExecutor, PaginatedRequestExecutor, } from './pagination.js';
11
+ export { PaginatedRequest, createPaginatedRequest, detectPaginationType, hasMorePages, findDataKey, isPaginatedResponse, } from './pagination.js';
12
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/client/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,YAAY,EAAE,cAAc,EAAE,sBAAsB,EAAE,MAAM,cAAc,CAAC;AAC3E,OAAO,EAAE,cAAc,EAAE,qBAAqB,EAAE,MAAM,cAAc,CAAC;AAErE,YAAY,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAC9C,OAAO,EAAE,qBAAqB,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAEpF,YAAY,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAC/C,OAAO,EACL,qBAAqB,EACrB,aAAa,EACb,oBAAoB,EACpB,KAAK,EACL,iBAAiB,EACjB,gBAAgB,GACjB,MAAM,YAAY,CAAC;AAEpB,YAAY,EACV,iBAAiB,EACjB,kBAAkB,EAClB,iBAAiB,EACjB,cAAc,EACd,eAAe,EACf,wBAAwB,GACzB,MAAM,iBAAiB,CAAC;AACzB,OAAO,EACL,gBAAgB,EAChB,sBAAsB,EACtB,oBAAoB,EACpB,YAAY,EACZ,WAAW,EACX,mBAAmB,GACpB,MAAM,iBAAiB,CAAC"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * Client module exports
3
+ */
4
+ export { executeRequest, createRequestExecutor } from './request.js';
5
+ export { SlidingWindowThrottle, NoOpThrottle, createThrottle } from './throttle.js';
6
+ export { calculateBackoffDelay, getRetryDelay, extractRateLimitInfo, sleep, isRetryableStatus, executeWithRetry, } from './retry.js';
7
+ export { PaginatedRequest, createPaginatedRequest, detectPaginationType, hasMorePages, findDataKey, isPaginatedResponse, } from './pagination.js';
8
+ //# sourceMappingURL=index.js.map