lazypock 0.1.2 → 0.1.5
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 +44 -42
- package/dist/{chunk-3MZJ5HCD.js → chunk-Y6PMBL2S.js} +7 -5
- package/dist/{chunk-3MZJ5HCD.js.map → chunk-Y6PMBL2S.js.map} +1 -1
- package/dist/cli.cjs +9 -7
- package/dist/cli.cjs.map +1 -1
- package/dist/cli.global.js +9 -7
- package/dist/cli.global.js.map +1 -1
- package/dist/cli.js +4 -4
- package/dist/cli.js.map +1 -1
- package/dist/index.cjs +189 -133
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +98 -78
- package/dist/index.d.ts +98 -78
- package/dist/index.global.js +188 -133
- package/dist/index.global.js.map +1 -1
- package/dist/index.js +183 -130
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/cli.ts +7 -4
- package/src/codegen.ts +6 -4
- package/src/collection.ts +64 -10
- package/src/collections.ts +200 -0
- package/src/index.ts +2 -0
- package/src/lazypock.ts +5 -170
package/dist/cli.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/cli.ts"],"sourcesContent":["#!/usr/bin/env node\n// ── Codegen CLI ─────────────────────────────────────────\n// `lazypock` — fetches the live collection schema from a Lazypock\n// API and writes a fully-typed `lazypock.types.ts` module.\n//\n// Auth methods (pick one):\n// 1. Superuser email + password:\n// npx lazypock --url http://localhost:4000/api --email admin@... --password ...\n// 2. API key (recommended, generated from the Settings dashboard):\n// npx lazypock --url http://localhost:4000/api --
|
|
1
|
+
{"version":3,"sources":["../src/cli.ts"],"sourcesContent":["#!/usr/bin/env node\n// ── Codegen CLI ─────────────────────────────────────────\n// `lazypock` — fetches the live collection schema from a Lazypock\n// API and writes a fully-typed `lazypock.types.ts` module.\n//\n// Auth methods (pick one):\n// 1. Superuser email + password:\n// npx lazypock --url http://localhost:4000/api --email admin@... --password ...\n// 2. API key (recommended, generated from the Settings dashboard):\n// npx lazypock --url http://localhost:4000/api --apikey <key>\n//\n// Or via env vars (no flags):\n// LAZYPOCK_URL=... LAZYPOCK_API_KEY=... npx lazypock\n// LAZYPOCK_URL=... LAZYPOCK_EMAIL=... LAZYPOCK_PASSWORD=... npx lazypock\n//\n// NOTE: `lazypock-gen` remains as a deprecated alias for backwards\n// compatibility. Both invoke the same executable.\n\nimport { writeFile } from \"node:fs/promises\";\nimport { resolve } from \"node:path\";\nimport { generateTypes } from \"./codegen\";\nimport type { CollectionsResponse } from \"./schema\";\n\ninterface CliOptions {\n\turl: string;\n\temail: string;\n\tpassword: string;\n\tapiKey: string;\n\tout: string;\n\tpackageName: string;\n\tskipSystem: boolean;\n}\n\nfunction fail(msg: string): never {\n\tconsole.error(`\\n❌ ${msg}\\n`);\n\tprocess.exit(1);\n}\n\nfunction parseArgs(argv: string[]): CliOptions {\n\tconst args = [...argv];\n\tconst get = (flag: string, envKey: string, def = \"\"): string => {\n\t\tconst i = args.indexOf(flag);\n\t\tif (i !== -1 && i + 1 < args.length) return args[i + 1];\n\t\treturn process.env[envKey] ?? def;\n\t};\n\tconst has = (flag: string): boolean => args.includes(flag);\n\n\tconst url = get(\"--url\", \"LAZYPOCK_URL\");\n\tconst email = get(\"--email\", \"LAZYPOCK_EMAIL\");\n\tconst password = get(\"--password\", \"LAZYPOCK_PASSWORD\");\n\tconst apiKey =\n\t\tget(\"--apikey\", \"LAZYPOCK_API_KEY\") || get(\"--api-key\", \"LAZYPOCK_API_KEY\");\n\n\tif (!url) fail(\"Missing API URL. Pass --url or set LAZYPOCK_URL.\");\n\tif (!apiKey) {\n\t\tif (!email)\n\t\t\tfail(\n\t\t\t\t\"Missing credentials. Pass --apikey, or --email + --password, or set LAZYPOCK_API_KEY / LAZYPOCK_EMAIL.\",\n\t\t\t);\n\t\tif (!password)\n\t\t\tfail(\"Missing password. Pass --password, or set LAZYPOCK_PASSWORD.\");\n\t}\n\n\tconst out =\n\t\tget(\"--output\", \"LAZYPOCK_OUT\") ||\n\t\tget(\"--out\", \"LAZYPOCK_OUT\", \"lazypock.types.ts\");\n\tconst packageName = get(\"--package\", \"LAZYPOCK_PACKAGE\", \"lazypock\");\n\n\treturn {\n\t\turl,\n\t\temail,\n\t\tpassword,\n\t\tapiKey,\n\t\tout,\n\t\tpackageName,\n\t\tskipSystem: has(\"--skip-system\"),\n\t};\n}\n\nasync function fetchCollections(\n\topts: CliOptions,\n): Promise<CollectionsResponse> {\n\tconst base = opts.url.replace(/\\/+$/, \"\");\n\n\tlet authKey: string;\n\tif (opts.apiKey) {\n\t\t// Step 1: use a stored API key directly (no login round-trip).\n\t\t// The key is sent as `Authorization: Bearer <key>` and recognised\n\t\t// by the backend's Auth.Plug as an API key.\n\t\tauthKey = opts.apiKey;\n\t} else {\n\t\t// Step 1: login as superuser to get a token\n\t\tconst loginRes = await fetch(base + \"/superusers/login\", {\n\t\t\tmethod: \"POST\",\n\t\t\theaders: { \"Content-Type\": \"application/json\" },\n\t\t\tbody: JSON.stringify({ email: opts.email, password: opts.password }),\n\t\t});\n\t\tif (!loginRes.ok) {\n\t\t\tconst text = await loginRes.text();\n\t\t\tfail(\n\t\t\t\t`Superuser login failed (${loginRes.status}). ${text.slice(0, 200)}`,\n\t\t\t);\n\t\t}\n\t\tconst loginData = (await loginRes.json()) as { token?: string };\n\t\tif (!loginData.token) fail(\"Login response did not include a token.\");\n\t\tauthKey = loginData.token;\n\t}\n\n\t// Step 2: fetch collections\n\tconst collRes = await fetch(base + \"/collections\", {\n\t\theaders: { Authorization: \"Bearer \" + authKey },\n\t});\n\tif (!collRes.ok) {\n\t\tconst text = await collRes.text();\n\t\tfail(\n\t\t\t`Failed to fetch collections (${collRes.status}). ${text.slice(0, 200)}`,\n\t\t);\n\t}\n\treturn (await collRes.json()) as CollectionsResponse;\n}\n\nasync function main(): Promise<void> {\n\tconst opts = parseArgs(process.argv.slice(2));\n\tconst authLabel = opts.apiKey\n\t\t? `API key ${opts.apiKey.slice(0, 4)}…${opts.apiKey.slice(-4)}`\n\t\t: opts.email;\n\tconsole.log(`\\n🔌 Connecting to ${opts.url} as ${authLabel} …`);\n\n\tconst { items } = await fetchCollections(opts);\n\tconsole.log(`📦 Found ${items.length} collection(s).`);\n\n\tconst source = generateTypes(items, {\n\t\tpackageName: opts.packageName,\n\t\tskipSystem: opts.skipSystem,\n\t});\n\n\tconst outPath = resolve(process.cwd(), opts.out);\n\tawait writeFile(outPath, source, \"utf8\");\n\tconsole.log(`✅ Wrote ${outPath} (${source.length} bytes).`);\n\tconsole.log(\n\t\t`\\nImport it in your app:\\n import { createClient } from './${opts.out.replace(/\\.ts$/, \"\")}';\\n`,\n\t);\n}\n\nmain().catch((err) => {\n\tconsole.error(err);\n\tprocess.exit(1);\n});\n"],"mappings":"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","names":[]}
|
package/dist/index.cjs
CHANGED
|
@@ -23,6 +23,7 @@ __export(index_exports, {
|
|
|
23
23
|
ApiError: () => ApiError,
|
|
24
24
|
AuthStore: () => AuthStore,
|
|
25
25
|
CollectionService: () => CollectionService,
|
|
26
|
+
CollectionsService: () => CollectionsService,
|
|
26
27
|
FilesService: () => FilesService,
|
|
27
28
|
LazypockClient: () => LazypockClient,
|
|
28
29
|
RealtimeService: () => RealtimeService,
|
|
@@ -353,17 +354,62 @@ var CollectionService = class {
|
|
|
353
354
|
return encodeURIComponent(id);
|
|
354
355
|
}
|
|
355
356
|
/**
|
|
356
|
-
*
|
|
357
|
-
*
|
|
358
|
-
* @param
|
|
357
|
+
* Fetch a paginated list of records (PocketBase `getList`).
|
|
358
|
+
*
|
|
359
|
+
* @param page Page number (default 1).
|
|
360
|
+
* @param perPage Records per page (default 30).
|
|
361
|
+
* @param options Query params (`filter`, `sort`, `expand`, `fields`) + request options.
|
|
359
362
|
*/
|
|
360
|
-
|
|
361
|
-
const
|
|
363
|
+
getList(page = 1, perPage = 30, options) {
|
|
364
|
+
const { ...rest } = options ?? {};
|
|
365
|
+
const qs = new URLSearchParams(
|
|
366
|
+
Object.fromEntries(
|
|
367
|
+
Object.entries({ page: String(page), perPage: String(perPage), ...rest }).map(
|
|
368
|
+
([k, v]) => [k, String(v)]
|
|
369
|
+
)
|
|
370
|
+
)
|
|
371
|
+
).toString();
|
|
362
372
|
return this.http.get(
|
|
363
|
-
"/" + this.encodeId(this.collectionName) + qs,
|
|
373
|
+
"/" + this.encodeId(this.collectionName) + "?" + qs,
|
|
364
374
|
options
|
|
365
375
|
);
|
|
366
376
|
}
|
|
377
|
+
/**
|
|
378
|
+
* Fetch all records at once (auto-paginates). Mirrors PocketBase's
|
|
379
|
+
* `pb.collection(name).getFullList()`.
|
|
380
|
+
*
|
|
381
|
+
* @param options Query params (`sort`, `filter`, `batch`, etc.) + request options.
|
|
382
|
+
*/
|
|
383
|
+
async getFullList(options) {
|
|
384
|
+
const { batch = 1e3, ...rest } = options ?? {};
|
|
385
|
+
const items = [];
|
|
386
|
+
let page = 1;
|
|
387
|
+
for (; ; ) {
|
|
388
|
+
const res = await this.getList(
|
|
389
|
+
page,
|
|
390
|
+
batch,
|
|
391
|
+
rest
|
|
392
|
+
);
|
|
393
|
+
if (!res || !res.items || res.items.length === 0) break;
|
|
394
|
+
items.push(...res.items);
|
|
395
|
+
if (page >= (res.totalPages ?? page)) break;
|
|
396
|
+
page += 1;
|
|
397
|
+
}
|
|
398
|
+
return items;
|
|
399
|
+
}
|
|
400
|
+
/**
|
|
401
|
+
* Fetch the first record matching a filter (PocketBase `getFirstListItem`).
|
|
402
|
+
*
|
|
403
|
+
* @param filter Filter expression (e.g. `title = 'x'`).
|
|
404
|
+
* @param options Optional request options.
|
|
405
|
+
*/
|
|
406
|
+
async getFirstListItem(filter, options) {
|
|
407
|
+
const res = await this.getList(1, 1, {
|
|
408
|
+
...options,
|
|
409
|
+
filter
|
|
410
|
+
});
|
|
411
|
+
return res?.items?.[0] ?? null;
|
|
412
|
+
}
|
|
367
413
|
/**
|
|
368
414
|
* Get a single record by ID.
|
|
369
415
|
* @param id Record ID.
|
|
@@ -808,6 +854,135 @@ var FilesService = class {
|
|
|
808
854
|
}
|
|
809
855
|
};
|
|
810
856
|
|
|
857
|
+
// src/collections.ts
|
|
858
|
+
var REGISTRY_TOPIC = "collections";
|
|
859
|
+
var CollectionsService = class {
|
|
860
|
+
/** @internal */
|
|
861
|
+
constructor(http, realtime) {
|
|
862
|
+
this.http = http;
|
|
863
|
+
this.realtime = realtime;
|
|
864
|
+
}
|
|
865
|
+
/**
|
|
866
|
+
* Fetch a paginated list of collections (admin).
|
|
867
|
+
*
|
|
868
|
+
* @param params Optional query params (`page`, `perPage`, `filter`, `sort`).
|
|
869
|
+
* @param options Optional request options.
|
|
870
|
+
*/
|
|
871
|
+
async getList(params, options) {
|
|
872
|
+
const qs = params ? "?" + new URLSearchParams(
|
|
873
|
+
Object.fromEntries(
|
|
874
|
+
Object.entries(params).map(([k, v]) => [k, String(v)])
|
|
875
|
+
)
|
|
876
|
+
).toString() : "";
|
|
877
|
+
return this.http?.get("/collections" + qs, options) ?? null;
|
|
878
|
+
}
|
|
879
|
+
/**
|
|
880
|
+
* Fetch all collections at once (auto-paginates). Mirrors PocketBase's
|
|
881
|
+
* `pb.collections.getFullList()` — defaults to listing everything.
|
|
882
|
+
*
|
|
883
|
+
* @param options Query params (`sort`, `batch`, etc.) or request options.
|
|
884
|
+
*/
|
|
885
|
+
async getFullList(options) {
|
|
886
|
+
if (!this.http) return [];
|
|
887
|
+
const { batch = 1e3, ...rest } = options ?? {};
|
|
888
|
+
const items = [];
|
|
889
|
+
let page = 1;
|
|
890
|
+
for (; ; ) {
|
|
891
|
+
const res = await this.getList({
|
|
892
|
+
...rest,
|
|
893
|
+
page,
|
|
894
|
+
perPage: batch
|
|
895
|
+
});
|
|
896
|
+
if (!res || !res.items || res.items.length === 0) break;
|
|
897
|
+
items.push(...res.items);
|
|
898
|
+
if (page >= (res.totalPages ?? page)) break;
|
|
899
|
+
page += 1;
|
|
900
|
+
}
|
|
901
|
+
return items;
|
|
902
|
+
}
|
|
903
|
+
/**
|
|
904
|
+
* Get a single collection by ID or name (admin).
|
|
905
|
+
*
|
|
906
|
+
* @param id Collection ID or name.
|
|
907
|
+
* @param options Optional request options.
|
|
908
|
+
*/
|
|
909
|
+
async getOne(id, options) {
|
|
910
|
+
return this.http?.get("/collections/" + encodeURIComponent(id), options) ?? null;
|
|
911
|
+
}
|
|
912
|
+
/**
|
|
913
|
+
* Create a new collection (admin).
|
|
914
|
+
*
|
|
915
|
+
* @param data Collection definition (name, type, fields, options, rules, etc.).
|
|
916
|
+
* @param options Optional request options.
|
|
917
|
+
*/
|
|
918
|
+
async create(data, options) {
|
|
919
|
+
return this.http?.post("/collections", data, options) ?? null;
|
|
920
|
+
}
|
|
921
|
+
/**
|
|
922
|
+
* Update an existing collection (admin).
|
|
923
|
+
*
|
|
924
|
+
* @param id Collection ID or name.
|
|
925
|
+
* @param data Updated collection fields.
|
|
926
|
+
* @param options Optional request options.
|
|
927
|
+
*/
|
|
928
|
+
async update(id, data, options) {
|
|
929
|
+
return this.http?.patch(
|
|
930
|
+
"/collections/" + encodeURIComponent(id),
|
|
931
|
+
data,
|
|
932
|
+
options
|
|
933
|
+
) ?? null;
|
|
934
|
+
}
|
|
935
|
+
/**
|
|
936
|
+
* Delete a collection (admin).
|
|
937
|
+
*
|
|
938
|
+
* @param id Collection ID or name.
|
|
939
|
+
* @param options Optional request options.
|
|
940
|
+
*/
|
|
941
|
+
async delete(id, options) {
|
|
942
|
+
const res = this.http?.delete(
|
|
943
|
+
"/collections/" + encodeURIComponent(id),
|
|
944
|
+
options
|
|
945
|
+
);
|
|
946
|
+
return res == null ? false : true;
|
|
947
|
+
}
|
|
948
|
+
/**
|
|
949
|
+
* Subscribe to collection registry changes.
|
|
950
|
+
*
|
|
951
|
+
* @param callback Received on every collection create/update/delete.
|
|
952
|
+
* @returns A function that unsubscribes this callback.
|
|
953
|
+
*/
|
|
954
|
+
subscribe(callback) {
|
|
955
|
+
if (!this.realtime) {
|
|
956
|
+
console.warn("[lazypock] No realtime service configured.");
|
|
957
|
+
return () => {
|
|
958
|
+
};
|
|
959
|
+
}
|
|
960
|
+
const handler = (raw) => {
|
|
961
|
+
callback({
|
|
962
|
+
action: normalizeAction2(raw.event),
|
|
963
|
+
collection: raw.payload ?? {},
|
|
964
|
+
topic: raw.topic
|
|
965
|
+
});
|
|
966
|
+
};
|
|
967
|
+
this.realtime.ensureConnected();
|
|
968
|
+
this.realtime.subscribe(REGISTRY_TOPIC, handler);
|
|
969
|
+
return () => this.realtime?.unsubscribe(REGISTRY_TOPIC, handler);
|
|
970
|
+
}
|
|
971
|
+
/**
|
|
972
|
+
* Unsubscribe all callbacks from the registry channel.
|
|
973
|
+
*/
|
|
974
|
+
unsubscribe() {
|
|
975
|
+
this.realtime?.unsubscribe(REGISTRY_TOPIC);
|
|
976
|
+
}
|
|
977
|
+
};
|
|
978
|
+
function normalizeAction2(event) {
|
|
979
|
+
const e = event.toLowerCase();
|
|
980
|
+
if (e === "create") return "create";
|
|
981
|
+
if (e === "update") return "update";
|
|
982
|
+
if (e === "delete") return "delete";
|
|
983
|
+
return "update";
|
|
984
|
+
}
|
|
985
|
+
|
|
811
986
|
// src/typegen.ts
|
|
812
987
|
function fieldTypeScriptType(field, fallback = "unknown") {
|
|
813
988
|
const opts = field.options ?? {};
|
|
@@ -968,11 +1143,13 @@ export function createClient(options: LazypockClientOptions): TypedClient {
|
|
|
968
1143
|
}
|
|
969
1144
|
|
|
970
1145
|
export class TypedClient extends LazypockClient {
|
|
971
|
-
override collection<
|
|
972
|
-
|
|
973
|
-
|
|
1146
|
+
override collection<T extends string>(name: T): T extends keyof LazypockCollections
|
|
1147
|
+
? CollectionService<LazypockCollections[T]>
|
|
1148
|
+
: CollectionService<unknown> {
|
|
1149
|
+
return super.collection(name) as T extends keyof LazypockCollections ? CollectionService<LazypockCollections[T]> : CollectionService<unknown>;
|
|
974
1150
|
}
|
|
975
|
-
}
|
|
1151
|
+
}
|
|
1152
|
+
`);
|
|
976
1153
|
return sections.join("\n\n") + "\n";
|
|
977
1154
|
}
|
|
978
1155
|
function renderInterface(opts) {
|
|
@@ -1006,6 +1183,7 @@ var LazypockClient = class {
|
|
|
1006
1183
|
this.realtime.setUrl(wsUrlFromBaseUrl(baseUrl));
|
|
1007
1184
|
}
|
|
1008
1185
|
this.files = new FilesService(this.http);
|
|
1186
|
+
this.collections = new CollectionsService(this.http, this.realtime);
|
|
1009
1187
|
if (options.types?.schemas) {
|
|
1010
1188
|
this.schemaByName = new Map(
|
|
1011
1189
|
options.types.schemas.map((s) => [s.name, s])
|
|
@@ -1166,129 +1344,6 @@ var LazypockClient = class {
|
|
|
1166
1344
|
health(options) {
|
|
1167
1345
|
return this.http.get("/health", options);
|
|
1168
1346
|
}
|
|
1169
|
-
// ── Collection Management (admin) ──
|
|
1170
|
-
/**
|
|
1171
|
-
* List all collections (admin).
|
|
1172
|
-
* @param q URL query string (e.g. `page=1&perPage=200`).
|
|
1173
|
-
* @param options Optional request options.
|
|
1174
|
-
*/
|
|
1175
|
-
listCollections(q, options) {
|
|
1176
|
-
return this.http.get(
|
|
1177
|
-
"/collections" + (q ? "?" + q : ""),
|
|
1178
|
-
options
|
|
1179
|
-
);
|
|
1180
|
-
}
|
|
1181
|
-
/**
|
|
1182
|
-
* Get a single collection by ID or name.
|
|
1183
|
-
* @param id Collection ID or name.
|
|
1184
|
-
* @param options Optional request options.
|
|
1185
|
-
*/
|
|
1186
|
-
getCollection(id, options) {
|
|
1187
|
-
return this.http.get(
|
|
1188
|
-
"/collections/" + encodeURIComponent(id),
|
|
1189
|
-
options
|
|
1190
|
-
);
|
|
1191
|
-
}
|
|
1192
|
-
/**
|
|
1193
|
-
* Create a new collection (admin).
|
|
1194
|
-
* @param data Collection definition (name, type, fields, options, rules, etc.).
|
|
1195
|
-
* @param options Optional request options.
|
|
1196
|
-
*/
|
|
1197
|
-
createCollection(data, options) {
|
|
1198
|
-
return this.http.post("/collections", data, options);
|
|
1199
|
-
}
|
|
1200
|
-
/**
|
|
1201
|
-
* Update an existing collection (admin).
|
|
1202
|
-
* @param id Collection ID or name.
|
|
1203
|
-
* @param data Updated collection fields.
|
|
1204
|
-
* @param options Optional request options.
|
|
1205
|
-
*/
|
|
1206
|
-
updateCollection(id, data, options) {
|
|
1207
|
-
return this.http.patch(
|
|
1208
|
-
"/collections/" + encodeURIComponent(id),
|
|
1209
|
-
data,
|
|
1210
|
-
options
|
|
1211
|
-
);
|
|
1212
|
-
}
|
|
1213
|
-
/**
|
|
1214
|
-
* Delete a collection (admin).
|
|
1215
|
-
* @param id Collection ID or name.
|
|
1216
|
-
* @param options Optional request options.
|
|
1217
|
-
*/
|
|
1218
|
-
deleteCollection(id, options) {
|
|
1219
|
-
return this.http.delete("/collections/" + encodeURIComponent(id), options);
|
|
1220
|
-
}
|
|
1221
|
-
// ── Records (dynamic collection) ──
|
|
1222
|
-
/**
|
|
1223
|
-
* List records from a dynamic collection with optional filter/sort/pagination.
|
|
1224
|
-
*
|
|
1225
|
-
* @param coll Collection name.
|
|
1226
|
-
* @param params Query parameters including:
|
|
1227
|
-
* - `filter` — PocketBase filter syntax (e.g. `title~'hello' && published=true`)
|
|
1228
|
-
* - `sort` — Comma-separated, `-` prefix for DESC (e.g. `-created,title`)
|
|
1229
|
-
* - `page` — Page number (default: 1)
|
|
1230
|
-
* - `perPage` — Items per page (default: 30, max: 200)
|
|
1231
|
-
* - `expand` — Comma-separated relation fields (e.g. `author,category`)
|
|
1232
|
-
* @param options Optional request options.
|
|
1233
|
-
*/
|
|
1234
|
-
listRecords(coll, params, options) {
|
|
1235
|
-
const qs = params ? "?" + new URLSearchParams(params).toString() : "";
|
|
1236
|
-
return this.http.get(
|
|
1237
|
-
"/" + encodeURIComponent(coll) + qs,
|
|
1238
|
-
options
|
|
1239
|
-
);
|
|
1240
|
-
}
|
|
1241
|
-
/**
|
|
1242
|
-
* Get a single record by ID.
|
|
1243
|
-
* @param coll Collection name.
|
|
1244
|
-
* @param id Record ID.
|
|
1245
|
-
* @param options Optional request options.
|
|
1246
|
-
*/
|
|
1247
|
-
getRecord(coll, id, options) {
|
|
1248
|
-
return this.http.get(
|
|
1249
|
-
"/" + encodeURIComponent(coll) + "/" + encodeURIComponent(id),
|
|
1250
|
-
options
|
|
1251
|
-
);
|
|
1252
|
-
}
|
|
1253
|
-
/**
|
|
1254
|
-
* Create a record in a dynamic collection.
|
|
1255
|
-
* @param coll Collection name.
|
|
1256
|
-
* @param data Record fields.
|
|
1257
|
-
* @param options Optional request options.
|
|
1258
|
-
*/
|
|
1259
|
-
createRecord(coll, data, options) {
|
|
1260
|
-
return this.http.post(
|
|
1261
|
-
"/" + encodeURIComponent(coll),
|
|
1262
|
-
data,
|
|
1263
|
-
options
|
|
1264
|
-
);
|
|
1265
|
-
}
|
|
1266
|
-
/**
|
|
1267
|
-
* Update a record in a dynamic collection.
|
|
1268
|
-
* @param coll Collection name.
|
|
1269
|
-
* @param id Record ID.
|
|
1270
|
-
* @param data Updated record fields.
|
|
1271
|
-
* @param options Optional request options.
|
|
1272
|
-
*/
|
|
1273
|
-
updateRecord(coll, id, data, options) {
|
|
1274
|
-
return this.http.patch(
|
|
1275
|
-
"/" + encodeURIComponent(coll) + "/" + encodeURIComponent(id),
|
|
1276
|
-
data,
|
|
1277
|
-
options
|
|
1278
|
-
);
|
|
1279
|
-
}
|
|
1280
|
-
/**
|
|
1281
|
-
* Delete a record from a dynamic collection.
|
|
1282
|
-
* @param coll Collection name.
|
|
1283
|
-
* @param id Record ID.
|
|
1284
|
-
* @param options Optional request options.
|
|
1285
|
-
*/
|
|
1286
|
-
deleteRecord(coll, id, options) {
|
|
1287
|
-
return this.http.delete(
|
|
1288
|
-
"/" + encodeURIComponent(coll) + "/" + encodeURIComponent(id),
|
|
1289
|
-
options
|
|
1290
|
-
);
|
|
1291
|
-
}
|
|
1292
1347
|
};
|
|
1293
1348
|
|
|
1294
1349
|
// src/client.ts
|
|
@@ -1305,6 +1360,7 @@ function createClient(options) {
|
|
|
1305
1360
|
ApiError,
|
|
1306
1361
|
AuthStore,
|
|
1307
1362
|
CollectionService,
|
|
1363
|
+
CollectionsService,
|
|
1308
1364
|
FilesService,
|
|
1309
1365
|
LazypockClient,
|
|
1310
1366
|
RealtimeService,
|