@jd-data-limited/easy-fm 4.0.14 → 4.1.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 (65) hide show
  1. package/package.json +12 -6
  2. package/src/FMError.d.ts +2 -2
  3. package/src/FMError.js +507 -508
  4. package/src/FMError.ts +510 -511
  5. package/src/bin/cli.js +7 -5
  6. package/src/bin/generateTypes.js +215 -121
  7. package/src/connection/FMHost.d.ts +28 -6
  8. package/src/connection/FMHost.js +52 -25
  9. package/src/connection/FMHost.ts +75 -43
  10. package/src/connection/HostBase.d.ts +7 -3
  11. package/src/connection/HostBase.ts +8 -4
  12. package/src/connection/database.d.ts +50 -17
  13. package/src/connection/database.js +94 -66
  14. package/src/connection/database.ts +125 -105
  15. package/src/connection/databaseBase.d.ts +11 -6
  16. package/src/connection/databaseBase.ts +9 -8
  17. package/src/connection/generateAuthorizationHeaders.d.ts +1 -1
  18. package/src/connection/generateAuthorizationHeaders.js +10 -10
  19. package/src/connection/generateAuthorizationHeaders.ts +21 -21
  20. package/src/databaseStructure.d.ts +2 -4
  21. package/src/databaseStructure.ts +3 -5
  22. package/src/index.d.ts +17 -17
  23. package/src/index.js +14 -14
  24. package/src/index.ts +28 -25
  25. package/src/layouts/layout.d.ts +17 -6
  26. package/src/layouts/layout.js +19 -8
  27. package/src/layouts/layout.ts +33 -23
  28. package/src/layouts/layoutBase.d.ts +5 -5
  29. package/src/layouts/layoutBase.ts +6 -6
  30. package/src/layouts/layoutInterface.d.ts +3 -5
  31. package/src/layouts/layoutInterface.ts +4 -6
  32. package/src/layouts/layoutRecordManager.d.ts +29 -6
  33. package/src/layouts/layoutRecordManager.js +32 -9
  34. package/src/layouts/layoutRecordManager.ts +42 -19
  35. package/src/layouts/recordFieldsMap.d.ts +2 -4
  36. package/src/layouts/recordFieldsMap.ts +2 -4
  37. package/src/models/apiResults.d.ts +7 -13
  38. package/src/models/apiResults.ts +58 -58
  39. package/src/records/field.d.ts +42 -12
  40. package/src/records/field.js +69 -59
  41. package/src/records/field.ts +102 -81
  42. package/src/records/getOperations/recordGetOperation.d.ts +44 -24
  43. package/src/records/getOperations/recordGetOperation.js +89 -58
  44. package/src/records/getOperations/recordGetOperation.ts +137 -108
  45. package/src/records/layoutRecord.d.ts +28 -14
  46. package/src/records/layoutRecord.js +75 -65
  47. package/src/records/layoutRecord.ts +126 -123
  48. package/src/records/layoutRecordBase.d.ts +2 -2
  49. package/src/records/layoutRecordBase.ts +3 -3
  50. package/src/records/portal.d.ts +19 -5
  51. package/src/records/portal.js +19 -5
  52. package/src/records/portal.ts +28 -16
  53. package/src/records/portalBase.d.ts +5 -5
  54. package/src/records/portalBase.ts +6 -6
  55. package/src/records/portalRecord.d.ts +16 -8
  56. package/src/records/portalRecord.js +16 -6
  57. package/src/records/portalRecord.ts +29 -19
  58. package/src/records/recordBase.d.ts +17 -7
  59. package/src/records/recordBase.js +32 -22
  60. package/src/records/recordBase.ts +50 -43
  61. package/src/types.d.ts +21 -24
  62. package/src/types.ts +55 -59
  63. package/src/utils/query.d.ts +12 -5
  64. package/src/utils/query.js +28 -9
  65. package/src/utils/query.ts +40 -15
@@ -2,149 +2,169 @@
2
2
  * Copyright (c) 2023-2024. See LICENSE file for more information
3
3
  */
4
4
 
5
- import {EventEmitter} from "events";
6
- import {generateAuthorizationHeaders} from "./generateAuthorizationHeaders.js";
7
- import {FMError} from "../FMError.js";
8
- import {LayoutInterface} from "../layouts/layoutInterface.js";
9
- import {Layout} from "../layouts/layout.js";
10
- import HTTP_REDIRECT from "follow-redirects"
11
- import {
12
- databaseOptionsBase,
13
- databaseOptionsWithExternalSources,
14
- loginOptionsFileMaker,
15
- loginOptionsToken,
16
- Script
17
- } from "../types.js";
18
- import {HostBase} from "./HostBase.js"
19
- import {DatabaseBase} from "./databaseBase.js";
20
- import {ApiLayout, ApiResults} from "../models/apiResults.js";
21
- import {DatabaseStructure} from "../databaseStructure.js";
22
- import {IncomingMessage} from "http";
23
-
24
- type GetLayoutReturnType<T extends DatabaseStructure, R extends LayoutInterface | string> = R extends string ? T["layouts"][R] : R
25
-
5
+ import {EventEmitter} from 'events'
6
+ import {generateAuthorizationHeaders} from './generateAuthorizationHeaders.js'
7
+ import {FMError} from '../FMError.js'
8
+ import {type LayoutInterface} from '../layouts/layoutInterface.js'
9
+ import {Layout} from '../layouts/layout.js'
10
+ import HTTP_REDIRECT from 'follow-redirects'
11
+ import {type databaseOptionsBase, type databaseOptionsWithExternalSources, type Script} from '../types.js'
12
+ import {type HostBase} from './HostBase.js'
13
+ import {type DatabaseBase} from './databaseBase.js'
14
+ import {type ApiLayout, type ApiResults} from '../models/apiResults.js'
15
+ import {type DatabaseStructure} from '../databaseStructure.js'
16
+ import {type IncomingMessage} from 'http'
17
+
18
+ /**
19
+ * Represents a database connection.
20
+ * @template T - The structure of the database.
21
+ */
26
22
  export class Database<T extends DatabaseStructure> extends EventEmitter implements DatabaseBase {
27
- private _token: any;
28
- readonly host: HostBase;
29
- private connection_details: databaseOptionsWithExternalSources
30
- private cookies: { [key: string]: string } = {}
31
- readonly name: string;
23
+ private _token: string = ''
24
+ readonly host: HostBase
25
+ private readonly connection_details: databaseOptionsWithExternalSources
26
+ private cookies: Record<string, string> = {}
27
+ readonly name: string
32
28
  readonly debug: boolean
33
29
 
34
- constructor(host: HostBase, conn: databaseOptionsWithExternalSources) {
30
+ constructor (host: HostBase, conn: databaseOptionsWithExternalSources) {
35
31
  super()
36
32
  this.host = host
37
33
  this.name = conn.database
38
34
  this.connection_details = conn
39
- this.debug = !!conn.debug
35
+ this.debug = conn.debug ?? false
40
36
  }
41
37
 
42
- private generateExternalSourceLogin(data: databaseOptionsBase) {
43
- if (data.credentials.method === "filemaker") {
44
- let _data = <loginOptionsFileMaker>data.credentials
38
+ // eslint-disable-next-line @typescript-eslint/explicit-function-return-type
39
+ private generateExternalSourceLogin (data: databaseOptionsBase) {
40
+ if (data.credentials.method === 'filemaker') {
41
+ const _data = data.credentials
45
42
  return {
46
43
  database: data.database,
47
44
  username: _data.username,
48
45
  password: _data.password
49
46
  }
50
- }
51
- else {
52
- throw "Not yet supported login method"
47
+ } else {
48
+ throw new Error('Not yet supported login method')
53
49
  }
54
50
  }
55
51
 
56
- async logout(): Promise<void> {
57
- if (!this.token) throw new Error("Not logged in")
58
-
59
- let _fetch = await fetch(`${this.endpoint}/sessions/${this.token}`, {
60
- method: "DELETE",
52
+ /**
53
+ * Logs out the user by deleting the current session token.
54
+ * Throws an error if the user is not logged in.
55
+ *
56
+ * @returns {Promise<void>} A promise that resolves with no value once the logout is successful.
57
+ * @throws {Error} Throws an error if the user is not logged in.
58
+ */
59
+ async logout (): Promise<void> {
60
+ if (this.token === '') throw new Error('Not logged in')
61
+
62
+ const _fetch = await fetch(`${this.endpoint}/sessions/${this.token}`, {
63
+ method: 'DELETE',
61
64
  headers: {
62
- "content-type": "application/json"
65
+ 'content-type': 'application/json'
63
66
  }
64
67
  })
65
- let data = await _fetch.json()
68
+ await _fetch.json()
66
69
  // console.log(data)
67
- this._token = null
70
+ this._token = ''
68
71
  }
69
72
 
70
- async login(forceLogin = false) {
73
+ /**
74
+ * Logs in to the database. Not required, as this is often done automatically
75
+ *
76
+ * @param {boolean} [forceLogin=false] - Whether to force login even if already logged in.
77
+ * @throws {Error} - Throws an error if already logged in and forceLogin is false.
78
+ * @throws {FMError} - Throws an FMError if login fails.
79
+ * @return {Promise<string>} - Returns a promise that resolves to the access token upon successful login.
80
+ */
81
+ async login (forceLogin = false) {
82
+ // console.trace()
71
83
  // Reset cookies
72
84
  this.cookies = {}
73
85
 
74
86
  await this.host.getMetadata()
75
- if (this.token && !forceLogin) throw new Error("Already logged in. Run logout() first")
87
+ if (this.token !== '' && !forceLogin) throw new Error('Already logged in. Run logout() first')
76
88
 
77
- if (this.connection_details.credentials.method === "token") {
78
- this._token = (<loginOptionsToken>this.connection_details.credentials).token
89
+ if (this.connection_details.credentials.method === 'token') {
90
+ this._token = (this.connection_details.credentials).token
79
91
  return this.token
80
- }
81
- else {
92
+ } else {
82
93
  console.time()
83
- let url = new URL(`${this.endpoint}/sessions`)
94
+ const url = new URL(`${this.endpoint}/sessions`)
84
95
  url.hostname = this.host.hostname
85
- let res = await fetch(url, {
86
- method: "POST",
96
+ const res = await fetch(url, {
97
+ method: 'POST',
87
98
  headers: generateAuthorizationHeaders(this.connection_details.credentials) as unknown as HeadersInit,
88
99
  body: JSON.stringify({
89
100
  fmDataSource: this.connection_details.externalSources.map(i => {
90
- let _i = <databaseOptionsBase>i
101
+ const _i = i
91
102
  return this.generateExternalSourceLogin(_i)
92
103
  })
93
104
  })
94
105
  })
95
106
  console.time()
96
- let _res = <any>(await res.json())
107
+ const _res = (await res.json())
97
108
  if (res.status === 200) {
98
- this._token = res.headers.get('x-fm-data-access-token')
109
+ this._token = res.headers.get('x-fm-data-access-token') ?? ''
99
110
  return this._token
100
- }
101
- else {
102
- throw new FMError(_res.messages[0].code, _res.status, res)
111
+ } else {
112
+ throw new FMError(
113
+ _res.messages[0].code as string | number,
114
+ _res.status as number,
115
+ res
116
+ )
103
117
  }
104
118
  }
105
119
  }
106
120
 
107
- get token() {
121
+ get token () {
108
122
  return this._token
109
123
  }
110
124
 
111
- get endpoint(): string {
125
+ /**
126
+ * Returns the endpoint URL for the database connection.
127
+ *
128
+ * @returns {string} The endpoint URL.
129
+ */
130
+ get endpoint (): string {
112
131
  return `${this.host.hostname}/fmi/data/v2/databases/${this.name}`
113
132
  }
114
133
 
115
- async apiRequestRaw(url: string | Request, options: any = {}, autoRelogin = true): Promise<Response> {
116
- if (this.debug) console.log(`EASYFM DEBUG: ${options.method?.toString().toUpperCase() || "GET"} ${url instanceof Request ? url.url : url}`)
117
- if (!this.token) await this.login(true)
134
+ async _apiRequestRaw (url: string | Request, options: RequestInit & { headers?: Record<string, string> } = {}, autoRelogin = true): Promise<Response> {
135
+ if (this.debug) console.log(`EASYFM DEBUG: ${JSON.stringify(options)} ${url instanceof Request ? url.url : url}`)
136
+ if (this.token === '') await this.login(true)
118
137
 
119
138
  if (!options.headers) options.headers = {}
120
- options.headers["authorization"] = "Bearer " + this._token
121
- options.rejectUnauthorized = this.host.verify
139
+ options.headers.authorization = 'Bearer ' + this._token
140
+ // options.rejectUnauthorized = this.host.verify
122
141
 
123
- let _fetch = await fetch(url, options)
142
+ const _fetch = await fetch(url, options)
124
143
  if (_fetch.headers.get('set-cookie')) {
125
- for (let cookie of _fetch.headers.get('set-cookie') || []) {
126
- let cookie_split = cookie.split("=")
127
- this.cookies[cookie_split[0]] = cookie_split[1]
144
+ for (const cookie of _fetch.headers.get('set-cookie') ?? []) {
145
+ const cookieSplit = cookie.split('=')
146
+ this.cookies[cookieSplit[0]] = cookieSplit[1]
128
147
  }
129
148
  }
130
149
 
131
150
  if (_fetch.status === 401 && autoRelogin) {
132
151
  await this.login(true)
133
- return await this.apiRequestRaw(url, options, false)
152
+ return await this._apiRequestRaw(url, options, false)
134
153
  }
135
154
  return _fetch
136
155
  }
137
- async apiRequestJSON<T = any>(url: string | Request, options: any = {}): Promise<ApiResults<T>> {
156
+
157
+ async _apiRequestJSON<T = any>(url: string | Request, options: RequestInit & { headers?: Record<string, string> } = {}): Promise<ApiResults<T>> {
138
158
  if (!options.headers) options.headers = {}
139
- options.headers["content-type"] = options.headers["content-type"] ? options.headers["content-type"] : "application/json"
140
- let _fetch = await this.apiRequestRaw(url, options)
141
- let data = await _fetch.json() as ApiResults<T>
159
+ options.headers['content-type'] = options.headers['content-type'] ? options.headers['content-type'] : 'application/json'
160
+ const _fetch = await this._apiRequestRaw(url, options)
161
+ const data = await _fetch.json() as ApiResults<T>
142
162
 
143
163
  // Remove response if it is empty. This makes checking for an empty response easier
144
164
  if (data.response && Object.keys(data.response).length === 0) delete data.response
145
165
 
146
166
  // console.log(data.messages[0])
147
- if (data.messages[0].code !== "0") {
167
+ if (data.messages[0].code !== '0') {
148
168
  throw new FMError(data.messages[0].code, _fetch.status, data)
149
169
  }
150
170
 
@@ -152,72 +172,72 @@ export class Database<T extends DatabaseStructure> extends EventEmitter implemen
152
172
  return data
153
173
  }
154
174
 
155
- async listLayouts() {
156
- let req = await this.apiRequestJSON<{layouts: ApiLayout[]}>(`${this.endpoint}/layouts?page=2`)
175
+ /**
176
+ * Retrieves a list of layouts in the current FileMaker database.
177
+ *
178
+ * @returns {Promise<Layout[]>} A promise that resolves to an array of Layout objects.
179
+ * @throws {FMError} If there was an error retrieving the layouts.
180
+ */
181
+ async listLayouts () {
182
+ const req = await this._apiRequestJSON<{ layouts: ApiLayout[] }>(`${this.endpoint}/layouts?page=2`)
157
183
  if (!req.response) throw new FMError(req.messages[0].code, req.httpStatus, req.messages[0].message)
158
184
 
159
185
  const cycleLayoutNames = (layouts: ApiLayout[]) => {
160
- let names: string[] = []
161
- for (let layout of layouts) {
186
+ let names: string[] = []
187
+ for (const layout of layouts) {
162
188
  if (layout.folderLayoutNames) names = names.concat(cycleLayoutNames(layout.folderLayoutNames))
163
189
  else names.push(layout.name)
164
190
  }
165
191
  return names
166
192
  }
167
- let layoutNames
168
-
169
193
  return cycleLayoutNames(req.response.layouts).map(layout => new Layout(this, layout))
170
194
  }
171
195
 
172
- getLayout<R extends keyof T["layouts"]>(name: R): Layout<T["layouts"][R]>
173
- getLayout<R extends LayoutInterface>(name: string): Layout<R>
174
- getLayout(name: string): Layout<any> {
196
+ layout<R extends keyof T['layouts']>(name: R): Layout<T['layouts'][R]>
197
+ layout<R extends LayoutInterface>(name: string): Layout<R>
198
+ layout (name: string): Layout<any> {
175
199
  return new Layout<LayoutInterface>(this, name)
176
200
  }
177
201
 
178
- script(name: string, parameter = ""): Script {
179
- return ({name, parameter} as Script)
180
- }
181
-
182
- _tokenExpired() {
183
- this.emit("token_expired")
202
+ script (name: string, parameter = ''): Script {
203
+ return ({ name, parameter } satisfies Script)
184
204
  }
185
205
 
186
- streamURL(url: string): Promise<IncomingMessage> {
187
- return new Promise((resolve, reject) => {
188
- if (!url || typeof url !== "string") {
189
- throw new Error("URL is empty, or has invalid value")
206
+ async streamURL (url: string): Promise<IncomingMessage> {
207
+ return await new Promise((resolve, reject) => {
208
+ if (!url || typeof url !== 'string') {
209
+ throw new Error('URL is empty, or has invalid value')
190
210
  }
191
211
 
192
- let headers: {[key: string]: string} = {}
212
+ const headers: Record<string, string> = {}
193
213
  if (Object.keys(this.cookies).length !== 0) {
194
- headers["Cookie"] = Object.keys(this.cookies)
214
+ headers.Cookie = Object.keys(this.cookies)
195
215
  .map(key => {
196
- return key + "=" + this.cookies[key]
216
+ return key + '=' + this.cookies[key]
197
217
  })
198
- .join("; ")
218
+ .join('; ')
199
219
  }
200
220
 
201
- const check_for_cookies = (res: HTTP_REDIRECT.ResponseDetails) => {
221
+ const checkForCookies = (res: HTTP_REDIRECT.ResponseDetails) => {
202
222
  // Check for the 'set-cookie' header. If it exists, remember it and strip it for better security.
203
223
  if (res.headers['set-cookie']) {
204
- for (let cookie of res.headers['set-cookie']) {
205
- let cookie_split = cookie.split("=")
206
- this.cookies[cookie_split[0]] = cookie_split[1]
224
+ for (const cookie of res.headers['set-cookie']) {
225
+ const cookieSplit = cookie.split('=')
226
+ this.cookies[cookieSplit[0]] = cookieSplit[1]
207
227
  }
208
228
  res.headers['set-cookie'] = undefined
209
229
  }
210
230
  }
211
231
 
212
232
  // Automatically switch between the http and https modules, based on which is needed
213
- (url.startsWith("https") ? HTTP_REDIRECT.https : HTTP_REDIRECT.http).get(url, {
233
+ (url.startsWith('https') ? HTTP_REDIRECT.https : HTTP_REDIRECT.http).get(url, {
214
234
  headers,
215
- beforeRedirect: (options: any, res: any) => check_for_cookies(res)
235
+ beforeRedirect: (options: any, res: HTTP_REDIRECT.ResponseDetails) => { checkForCookies(res) }
216
236
  }, (res) => {
217
- check_for_cookies(res)
237
+ checkForCookies(res)
218
238
 
219
239
  resolve(res)
220
240
  })
221
241
  })
222
242
  }
223
- }
243
+ }
@@ -1,12 +1,17 @@
1
1
  /// <reference types="node" resolution-mode="require"/>
2
- import { HostBase } from "./HostBase.js";
3
- import { ApiResults } from "../models/apiResults.js";
4
- import { IncomingMessage } from "http";
2
+ import { type HostBase } from './HostBase.js';
3
+ import { type ApiResults } from '../models/apiResults.js';
4
+ import { type IncomingMessage } from 'http';
5
5
  export interface DatabaseBase {
6
6
  host: HostBase;
7
7
  readonly name: string;
8
8
  endpoint: string;
9
- apiRequestJSON<T = unknown>(url: string | Request, options?: RequestInit | undefined, autoRelogin?: boolean): Promise<ApiResults<T>>;
10
- apiRequestRaw(url: string | Request, options?: RequestInit | undefined): Promise<Response>;
11
- streamURL(url: string): Promise<IncomingMessage>;
9
+ token: string;
10
+ _apiRequestJSON: <T = unknown>(url: string | Request, options?: RequestInit & {
11
+ headers?: Record<string, string>;
12
+ } | undefined, autoRelogin?: boolean) => Promise<ApiResults<T>>;
13
+ _apiRequestRaw: (url: string | Request, options?: RequestInit & {
14
+ headers?: Record<string, string>;
15
+ } | undefined) => Promise<Response>;
16
+ streamURL: (url: string) => Promise<IncomingMessage>;
12
17
  }
@@ -2,18 +2,19 @@
2
2
  * Copyright (c) 2023-2024. See LICENSE file for more information
3
3
  */
4
4
 
5
- import {HostBase} from "./HostBase.js"
6
- import {ApiResults} from "../models/apiResults.js";
7
- import {IncomingMessage} from "http";
5
+ import {type HostBase} from './HostBase.js'
6
+ import {type ApiResults} from '../models/apiResults.js'
7
+ import {type IncomingMessage} from 'http'
8
8
 
9
9
  export interface DatabaseBase {
10
- host: HostBase,
10
+ host: HostBase
11
11
  readonly name: string
12
12
  endpoint: string
13
+ token: string
13
14
 
14
15
  // layouts: DatabaseStructure["layouts"]
15
16
 
16
- apiRequestJSON<T = unknown>(url: string | Request, options?: RequestInit | undefined, autoRelogin?: boolean): Promise<ApiResults<T>>
17
- apiRequestRaw(url: string | Request, options?: RequestInit | undefined): Promise<Response>
18
- streamURL(url: string): Promise<IncomingMessage>
19
- }
17
+ _apiRequestJSON: <T = unknown>(url: string | Request, options?: RequestInit & { headers?: Record<string, string> } | undefined, autoRelogin?: boolean) => Promise<ApiResults<T>>
18
+ _apiRequestRaw: (url: string | Request, options?: RequestInit & { headers?: Record<string, string> } | undefined) => Promise<Response>
19
+ streamURL: (url: string) => Promise<IncomingMessage>
20
+ }
@@ -1,2 +1,2 @@
1
- import { AuthorizationHeaders, AuthorizationHeadersOAuth, loginOptionsClaris, loginOptionsFileMaker, loginOptionsOAuth } from "../types.js";
1
+ import { type AuthorizationHeaders, type AuthorizationHeadersOAuth, type loginOptionsClaris, type loginOptionsFileMaker, type loginOptionsOAuth } from '../types.js';
2
2
  export declare function generateAuthorizationHeaders(credentials: loginOptionsOAuth | loginOptionsFileMaker | loginOptionsClaris): AuthorizationHeaders | AuthorizationHeadersOAuth;
@@ -3,21 +3,21 @@
3
3
  */
4
4
  export function generateAuthorizationHeaders(credentials) {
5
5
  switch (credentials.method) {
6
- case "filemaker":
6
+ case 'filemaker':
7
7
  return {
8
- "Content-Type": "application/json",
9
- "Authorization": "Basic " + Buffer.from(credentials.username + ":" + credentials.password).toString("base64")
8
+ 'Content-Type': 'application/json',
9
+ Authorization: 'Basic ' + Buffer.from((credentials).username + ':' + (credentials).password).toString('base64')
10
10
  };
11
- case "claris":
11
+ case 'claris':
12
12
  return {
13
- "Content-Type": "application/json",
14
- "Authorization": credentials.claris.fmid,
13
+ 'Content-Type': 'application/json',
14
+ Authorization: (credentials).claris.fmid
15
15
  };
16
- case "oauth":
16
+ case 'oauth':
17
17
  return {
18
- "Content-Type": "application/json",
19
- "X-FM-Data-OAuth-RequestId": credentials.oauth.requestId,
20
- "X-FM-Data-OAuth-Identifier": credentials.oauth.requestIdentifier
18
+ 'Content-Type': 'application/json',
19
+ 'X-FM-Data-OAuth-RequestId': (credentials).oauth.requestId,
20
+ 'X-FM-Data-OAuth-Identifier': (credentials).oauth.requestIdentifier
21
21
  };
22
22
  }
23
23
  }
@@ -3,30 +3,30 @@
3
3
  */
4
4
 
5
5
  import {
6
- AuthorizationHeaders,
7
- AuthorizationHeadersOAuth,
8
- loginOptionsClaris,
9
- loginOptionsFileMaker,
10
- loginOptionsOAuth
11
- } from "../types.js";
6
+ type AuthorizationHeaders,
7
+ type AuthorizationHeadersOAuth,
8
+ type loginOptionsClaris,
9
+ type loginOptionsFileMaker,
10
+ type loginOptionsOAuth
11
+ } from '../types.js'
12
12
 
13
- export function generateAuthorizationHeaders(credentials: loginOptionsOAuth | loginOptionsFileMaker | loginOptionsClaris): AuthorizationHeaders | AuthorizationHeadersOAuth {
13
+ export function generateAuthorizationHeaders (credentials: loginOptionsOAuth | loginOptionsFileMaker | loginOptionsClaris): AuthorizationHeaders | AuthorizationHeadersOAuth {
14
14
  switch (credentials.method) {
15
- case "filemaker":
15
+ case 'filemaker':
16
16
  return {
17
- "Content-Type": "application/json",
18
- "Authorization": "Basic " + Buffer.from((<loginOptionsFileMaker>credentials).username + ":" + (<loginOptionsFileMaker>credentials).password).toString("base64")
19
- } as AuthorizationHeaders
20
- case "claris":
17
+ 'Content-Type': 'application/json',
18
+ Authorization: 'Basic ' + Buffer.from((credentials).username + ':' + (credentials).password).toString('base64')
19
+ } satisfies AuthorizationHeaders
20
+ case 'claris':
21
21
  return {
22
- "Content-Type": "application/json",
23
- "Authorization": (<loginOptionsClaris>credentials).claris.fmid,
24
- } as AuthorizationHeaders
25
- case "oauth":
22
+ 'Content-Type': 'application/json',
23
+ Authorization: (credentials).claris.fmid
24
+ } satisfies AuthorizationHeaders
25
+ case 'oauth':
26
26
  return {
27
- "Content-Type": "application/json",
28
- "X-FM-Data-OAuth-RequestId": (<loginOptionsOAuth>credentials).oauth.requestId,
29
- "X-FM-Data-OAuth-Identifier": (<loginOptionsOAuth>credentials).oauth.requestIdentifier
30
- } as AuthorizationHeadersOAuth
27
+ 'Content-Type': 'application/json',
28
+ 'X-FM-Data-OAuth-RequestId': (credentials).oauth.requestId,
29
+ 'X-FM-Data-OAuth-Identifier': (credentials).oauth.requestIdentifier
30
+ } satisfies AuthorizationHeadersOAuth
31
31
  }
32
- }
32
+ }
@@ -1,6 +1,4 @@
1
- import { LayoutInterface } from "./layouts/layoutInterface.js";
1
+ import { type LayoutInterface } from './layouts/layoutInterface.js';
2
2
  export interface DatabaseStructure {
3
- layouts: {
4
- [key: string]: LayoutInterface;
5
- };
3
+ layouts: Record<string, LayoutInterface>;
6
4
  }
@@ -3,10 +3,8 @@
3
3
  */
4
4
 
5
5
  // import * as btoa from "btoa";
6
- import {LayoutInterface} from "./layouts/layoutInterface.js";
6
+ import {type LayoutInterface} from './layouts/layoutInterface.js'
7
7
 
8
8
  export interface DatabaseStructure {
9
- layouts: {
10
- [key: string]: LayoutInterface
11
- }
12
- }
9
+ layouts: Record<string, LayoutInterface>
10
+ }
package/src/index.d.ts CHANGED
@@ -1,18 +1,18 @@
1
- import FMHost from "./connection/FMHost.js";
2
- import { FMError } from "./FMError.js";
3
- import * as TYPES from "./types.js";
4
- import { PickPortals } from "./types.js";
5
- import { Database } from "./connection/database.js";
6
- import { Layout } from "./layouts/layout.js";
7
- import { RecordBase } from "./records/recordBase.js";
8
- import { LayoutRecord } from "./records/layoutRecord.js";
9
- import { LayoutInterface, PortalInterface } from "./layouts/layoutInterface.js";
10
- import { PortalRecord } from "./records/portalRecord.js";
11
- import { Portal } from "./records/portal.js";
12
- import { FindRequest, FindRequestRaw, RecordGetOperation } from "./records/getOperations/recordGetOperation.js";
13
- import { LayoutRecordManager } from "./layouts/layoutRecordManager.js";
14
- import { RecordFieldsMap } from "./layouts/recordFieldsMap.js";
15
- import { query, queryEscape } from "./utils/query.js";
16
- import { Container, Field } from "./records/field.js";
1
+ import FMHost from './connection/FMHost.js';
2
+ import { FMError } from './FMError.js';
3
+ import * as TYPES from './types.js';
4
+ import { type PickPortals } from './types.js';
5
+ import { Database } from './connection/database.js';
6
+ import { Layout } from './layouts/layout.js';
7
+ import { RecordBase } from './records/recordBase.js';
8
+ import { LayoutRecord } from './records/layoutRecord.js';
9
+ import { type LayoutInterface, type PortalInterface } from './layouts/layoutInterface.js';
10
+ import { PortalRecord } from './records/portalRecord.js';
11
+ import { Portal } from './records/portal.js';
12
+ import { type FindRequest, type FindRequestRaw, RecordGetOperation } from './records/getOperations/recordGetOperation.js';
13
+ import { LayoutRecordManager } from './layouts/layoutRecordManager.js';
14
+ import { type RecordFieldsMap } from './layouts/recordFieldsMap.js';
15
+ import { asDate, asTime, asTimestamp, query, queryEscape } from './utils/query.js';
16
+ import { type Container, Field } from './records/field.js';
17
17
  export default FMHost;
18
- export { FMError, TYPES, Database, Layout, RecordBase, LayoutRecord, LayoutInterface, RecordFieldsMap, PortalInterface, PortalRecord, Portal, Field, RecordGetOperation, LayoutRecordManager, Container, PickPortals, FindRequestRaw, FindRequest, query, queryEscape };
18
+ export { FMError, TYPES, Database, Layout, RecordBase, LayoutRecord, type LayoutInterface, type RecordFieldsMap, type PortalInterface, PortalRecord, Portal, Field, RecordGetOperation, LayoutRecordManager, type Container, type PickPortals, type FindRequestRaw, type FindRequest, query, queryEscape, asDate, asTime, asTimestamp };
package/src/index.js CHANGED
@@ -1,18 +1,18 @@
1
1
  /*
2
2
  * Copyright (c) 2023-2024. See LICENSE file for more information
3
3
  */
4
- import FMHost from "./connection/FMHost.js";
5
- import { FMError } from "./FMError.js";
6
- import * as TYPES from "./types.js";
7
- import { Database } from "./connection/database.js";
8
- import { Layout } from "./layouts/layout.js";
9
- import { RecordBase } from "./records/recordBase.js";
10
- import { LayoutRecord } from "./records/layoutRecord.js";
11
- import { PortalRecord } from "./records/portalRecord.js";
12
- import { Portal } from "./records/portal.js";
13
- import { RecordGetOperation } from "./records/getOperations/recordGetOperation.js";
14
- import { LayoutRecordManager } from "./layouts/layoutRecordManager.js";
15
- import { query, queryEscape } from "./utils/query.js";
16
- import { Field } from "./records/field.js";
4
+ import FMHost from './connection/FMHost.js';
5
+ import { FMError } from './FMError.js';
6
+ import * as TYPES from './types.js';
7
+ import { Database } from './connection/database.js';
8
+ import { Layout } from './layouts/layout.js';
9
+ import { RecordBase } from './records/recordBase.js';
10
+ import { LayoutRecord } from './records/layoutRecord.js';
11
+ import { PortalRecord } from './records/portalRecord.js';
12
+ import { Portal } from './records/portal.js';
13
+ import { RecordGetOperation } from './records/getOperations/recordGetOperation.js';
14
+ import { LayoutRecordManager } from './layouts/layoutRecordManager.js';
15
+ import { asDate, asTime, asTimestamp, query, queryEscape } from './utils/query.js';
16
+ import { Field } from './records/field.js';
17
17
  export default FMHost;
18
- export { FMError, TYPES, Database, Layout, RecordBase, LayoutRecord, PortalRecord, Portal, Field, RecordGetOperation, LayoutRecordManager, query, queryEscape };
18
+ export { FMError, TYPES, Database, Layout, RecordBase, LayoutRecord, PortalRecord, Portal, Field, RecordGetOperation, LayoutRecordManager, query, queryEscape, asDate, asTime, asTimestamp };