@boltic/sdk 0.0.6 → 0.0.8
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 +107 -1
- package/dist/databases/index.d.ts +263 -40
- package/dist/databases/index.js +1 -1
- package/dist/databases/index.js.map +1 -1
- package/dist/databases/index.mjs +2 -2
- package/dist/databases/index.mjs.map +1 -1
- package/dist/databases/test-client-BuQuW6Y-.js +2 -0
- package/dist/databases/test-client-BuQuW6Y-.js.map +1 -0
- package/dist/databases/{test-client-rQ1AmTo6.mjs → test-client-D8i2zDgI.mjs} +994 -171
- package/dist/databases/test-client-D8i2zDgI.mjs.map +1 -0
- package/dist/databases/testing.d.ts +249 -103
- package/dist/databases/testing.js +1 -1
- package/dist/databases/testing.mjs +1 -1
- package/dist/sdk.js +929 -171
- package/dist/sdk.js.map +1 -1
- package/dist/sdk.mjs +929 -171
- package/dist/sdk.mjs.map +1 -1
- package/dist/types/index.d.ts +213 -40
- package/package.json +11 -8
- package/dist/databases/test-client-DfOmma3t.js +0 -2
- package/dist/databases/test-client-DfOmma3t.js.map +0 -1
- package/dist/databases/test-client-rQ1AmTo6.mjs.map +0 -1
package/dist/sdk.mjs
CHANGED
|
@@ -109,6 +109,12 @@ let AuthManager$1 = class AuthManager {
|
|
|
109
109
|
}
|
|
110
110
|
}
|
|
111
111
|
};
|
|
112
|
+
function isErrorResponse(response) {
|
|
113
|
+
return "error" in response && response.error !== void 0;
|
|
114
|
+
}
|
|
115
|
+
function isListResponse(response) {
|
|
116
|
+
return "pagination" in response;
|
|
117
|
+
}
|
|
112
118
|
class ValidationError extends Error {
|
|
113
119
|
constructor(message, failures = []) {
|
|
114
120
|
super(message);
|
|
@@ -228,7 +234,7 @@ class AuthManager2 {
|
|
|
228
234
|
};
|
|
229
235
|
}
|
|
230
236
|
// Custom inspect method for Node.js console logging
|
|
231
|
-
[Symbol.for("nodejs.util.inspect.custom")]() {
|
|
237
|
+
[/* @__PURE__ */ Symbol.for("nodejs.util.inspect.custom")]() {
|
|
232
238
|
return this.toString();
|
|
233
239
|
}
|
|
234
240
|
}
|
|
@@ -505,14 +511,16 @@ class InterceptorManagerImpl {
|
|
|
505
511
|
}
|
|
506
512
|
async executeRequestInterceptors(config) {
|
|
507
513
|
let result = config;
|
|
508
|
-
for (const interceptor of this.requestInterceptors.values()) {
|
|
514
|
+
for (const interceptor of Array.from(this.requestInterceptors.values())) {
|
|
509
515
|
result = await interceptor(result);
|
|
510
516
|
}
|
|
511
517
|
return result;
|
|
512
518
|
}
|
|
513
519
|
async executeResponseInterceptors(response) {
|
|
514
520
|
let result = response;
|
|
515
|
-
for (const { fulfilled } of
|
|
521
|
+
for (const { fulfilled } of Array.from(
|
|
522
|
+
this.responseInterceptors.values()
|
|
523
|
+
)) {
|
|
516
524
|
if (fulfilled) {
|
|
517
525
|
result = await fulfilled(result);
|
|
518
526
|
}
|
|
@@ -521,7 +529,7 @@ class InterceptorManagerImpl {
|
|
|
521
529
|
}
|
|
522
530
|
async executeErrorInterceptors(error) {
|
|
523
531
|
let result = error;
|
|
524
|
-
for (const { rejected } of this.responseInterceptors.values()) {
|
|
532
|
+
for (const { rejected } of Array.from(this.responseInterceptors.values())) {
|
|
525
533
|
if (rejected) {
|
|
526
534
|
result = await rejected(result);
|
|
527
535
|
}
|
|
@@ -728,7 +736,7 @@ class ConfigManager {
|
|
|
728
736
|
return safeConfig;
|
|
729
737
|
}
|
|
730
738
|
// Custom inspect method for Node.js console logging
|
|
731
|
-
[Symbol.for("nodejs.util.inspect.custom")]() {
|
|
739
|
+
[/* @__PURE__ */ Symbol.for("nodejs.util.inspect.custom")]() {
|
|
732
740
|
return this.toString();
|
|
733
741
|
}
|
|
734
742
|
}
|
|
@@ -750,6 +758,13 @@ function filterArrayFields(arr, fields) {
|
|
|
750
758
|
}
|
|
751
759
|
return arr.map((obj) => filterObjectFields(obj, fields));
|
|
752
760
|
}
|
|
761
|
+
function addDbIdToUrl(url, dbId) {
|
|
762
|
+
if (!dbId || dbId === "") {
|
|
763
|
+
return url;
|
|
764
|
+
}
|
|
765
|
+
const separator = url.includes("?") ? "&" : "?";
|
|
766
|
+
return `${url}${separator}db_id=${encodeURIComponent(dbId)}`;
|
|
767
|
+
}
|
|
753
768
|
const COLUMN_ENDPOINTS = {
|
|
754
769
|
list: {
|
|
755
770
|
path: "/tables/{table_id}/fields/list",
|
|
@@ -983,7 +998,8 @@ class ColumnsApiClient {
|
|
|
983
998
|
async listColumns(tableId, options = {}) {
|
|
984
999
|
try {
|
|
985
1000
|
const endpoint = COLUMN_ENDPOINTS.list;
|
|
986
|
-
|
|
1001
|
+
let url = `${this.baseURL}${buildEndpointPath$1(endpoint, { table_id: tableId })}?no_cache=true`;
|
|
1002
|
+
url = addDbIdToUrl(url, options.db_id);
|
|
987
1003
|
const response = await this.httpAdapter.request({
|
|
988
1004
|
url,
|
|
989
1005
|
method: endpoint.method,
|
|
@@ -1452,7 +1468,8 @@ class TablesApiClient {
|
|
|
1452
1468
|
async createTable(request, options = {}) {
|
|
1453
1469
|
try {
|
|
1454
1470
|
const endpoint = TABLE_ENDPOINTS.create;
|
|
1455
|
-
|
|
1471
|
+
let url = `${this.baseURL}${endpoint.path}`;
|
|
1472
|
+
url = addDbIdToUrl(url, options.db_id);
|
|
1456
1473
|
const transformedRequest = transformTableCreateRequest(request, options);
|
|
1457
1474
|
const response = await this.httpAdapter.request({
|
|
1458
1475
|
url,
|
|
@@ -1472,7 +1489,8 @@ class TablesApiClient {
|
|
|
1472
1489
|
async listTables(options = {}) {
|
|
1473
1490
|
try {
|
|
1474
1491
|
const endpoint = TABLE_ENDPOINTS.list;
|
|
1475
|
-
|
|
1492
|
+
let url = `${this.baseURL}${endpoint.path}`;
|
|
1493
|
+
url = addDbIdToUrl(url, options.db_id);
|
|
1476
1494
|
const response = await this.httpAdapter.request({
|
|
1477
1495
|
url,
|
|
1478
1496
|
method: endpoint.method,
|
|
@@ -1498,7 +1516,8 @@ class TablesApiClient {
|
|
|
1498
1516
|
async getTable(tableId, options = {}) {
|
|
1499
1517
|
try {
|
|
1500
1518
|
const endpoint = TABLE_ENDPOINTS.get;
|
|
1501
|
-
|
|
1519
|
+
let url = `${this.baseURL}${buildEndpointPath(endpoint, { table_id: tableId })}`;
|
|
1520
|
+
url = addDbIdToUrl(url, options.db_id);
|
|
1502
1521
|
const response = await this.httpAdapter.request({
|
|
1503
1522
|
url,
|
|
1504
1523
|
method: endpoint.method,
|
|
@@ -1522,9 +1541,10 @@ class TablesApiClient {
|
|
|
1522
1541
|
*/
|
|
1523
1542
|
async updateTable(tableId, updates) {
|
|
1524
1543
|
try {
|
|
1525
|
-
const { fields, ...updateData } = updates;
|
|
1544
|
+
const { fields, db_id, ...updateData } = updates;
|
|
1526
1545
|
const endpoint = TABLE_ENDPOINTS.update;
|
|
1527
|
-
|
|
1546
|
+
let url = `${this.baseURL}${buildEndpointPath(endpoint, { table_id: tableId })}`;
|
|
1547
|
+
url = addDbIdToUrl(url, db_id);
|
|
1528
1548
|
const response = await this.httpAdapter.request({
|
|
1529
1549
|
url,
|
|
1530
1550
|
method: endpoint.method,
|
|
@@ -1547,10 +1567,11 @@ class TablesApiClient {
|
|
|
1547
1567
|
/**
|
|
1548
1568
|
* Delete a table
|
|
1549
1569
|
*/
|
|
1550
|
-
async deleteTable(tableId) {
|
|
1570
|
+
async deleteTable(tableId, options = {}) {
|
|
1551
1571
|
try {
|
|
1552
1572
|
const endpoint = TABLE_ENDPOINTS.delete;
|
|
1553
|
-
|
|
1573
|
+
let url = `${this.baseURL}${buildEndpointPath(endpoint, { table_id: tableId })}`;
|
|
1574
|
+
url = addDbIdToUrl(url, options.db_id);
|
|
1554
1575
|
const response = await this.httpAdapter.request({
|
|
1555
1576
|
url,
|
|
1556
1577
|
method: endpoint.method,
|
|
@@ -1605,12 +1626,6 @@ class TablesApiClient {
|
|
|
1605
1626
|
};
|
|
1606
1627
|
}
|
|
1607
1628
|
}
|
|
1608
|
-
function isErrorResponse(response) {
|
|
1609
|
-
return "error" in response && response.error !== void 0;
|
|
1610
|
-
}
|
|
1611
|
-
function isListResponse(response) {
|
|
1612
|
-
return "pagination" in response;
|
|
1613
|
-
}
|
|
1614
1629
|
class BaseResource {
|
|
1615
1630
|
constructor(client, basePath) {
|
|
1616
1631
|
this.client = client;
|
|
@@ -1711,13 +1726,16 @@ class TableResource extends BaseResource {
|
|
|
1711
1726
|
/**
|
|
1712
1727
|
* Create a new table
|
|
1713
1728
|
*/
|
|
1714
|
-
async create(data) {
|
|
1729
|
+
async create(data, dbId) {
|
|
1715
1730
|
try {
|
|
1716
1731
|
const processedData = { ...data };
|
|
1717
1732
|
if (data.fields && data.fields.length > 0) {
|
|
1718
1733
|
processedData.fields = await this.processFieldsDefaults(data.fields);
|
|
1719
1734
|
}
|
|
1720
|
-
const result = await this.tablesApiClient.createTable(
|
|
1735
|
+
const result = await this.tablesApiClient.createTable(
|
|
1736
|
+
processedData,
|
|
1737
|
+
dbId ? { db_id: dbId } : {}
|
|
1738
|
+
);
|
|
1721
1739
|
if (isErrorResponse(result)) {
|
|
1722
1740
|
throw new ApiError(
|
|
1723
1741
|
result.error.message || "Create table failed",
|
|
@@ -1800,12 +1818,17 @@ class TableResource extends BaseResource {
|
|
|
1800
1818
|
/**
|
|
1801
1819
|
* Find all tables with optional filtering
|
|
1802
1820
|
*/
|
|
1803
|
-
async findAll(options = {}) {
|
|
1821
|
+
async findAll(options = {}, dbId) {
|
|
1804
1822
|
try {
|
|
1805
1823
|
const apiRequest = this.transformTableQueryToApiRequest(options);
|
|
1806
|
-
const
|
|
1807
|
-
apiRequest
|
|
1808
|
-
|
|
1824
|
+
const requestPayload = {
|
|
1825
|
+
page: apiRequest.page,
|
|
1826
|
+
filters: apiRequest.filters,
|
|
1827
|
+
sort: apiRequest.sort,
|
|
1828
|
+
...dbId && { db_id: dbId },
|
|
1829
|
+
...options.fields && { fields: options.fields }
|
|
1830
|
+
};
|
|
1831
|
+
const result = await this.tablesApiClient.listTables(requestPayload);
|
|
1809
1832
|
if (isErrorResponse(result)) {
|
|
1810
1833
|
throw new ApiError(
|
|
1811
1834
|
result.error.message || "List tables failed",
|
|
@@ -1821,7 +1844,7 @@ class TableResource extends BaseResource {
|
|
|
1821
1844
|
/**
|
|
1822
1845
|
* Find a single table by ID or name
|
|
1823
1846
|
*/
|
|
1824
|
-
async findOne(options) {
|
|
1847
|
+
async findOne(options, dbId) {
|
|
1825
1848
|
try {
|
|
1826
1849
|
if (!options.where?.id && !options.where?.name) {
|
|
1827
1850
|
throw new ValidationError(
|
|
@@ -1830,7 +1853,8 @@ class TableResource extends BaseResource {
|
|
|
1830
1853
|
}
|
|
1831
1854
|
if (options.where?.id) {
|
|
1832
1855
|
const result = await this.tablesApiClient.getTable(
|
|
1833
|
-
options.where.id
|
|
1856
|
+
options.where.id,
|
|
1857
|
+
dbId ? { db_id: dbId } : {}
|
|
1834
1858
|
);
|
|
1835
1859
|
if (isErrorResponse(result)) {
|
|
1836
1860
|
if (result.error.code === "TABLE_NOT_FOUND") {
|
|
@@ -1858,9 +1882,13 @@ class TableResource extends BaseResource {
|
|
|
1858
1882
|
],
|
|
1859
1883
|
sort: []
|
|
1860
1884
|
};
|
|
1861
|
-
const
|
|
1862
|
-
apiRequest
|
|
1863
|
-
|
|
1885
|
+
const requestPayload = {
|
|
1886
|
+
page: apiRequest.page,
|
|
1887
|
+
filters: apiRequest.filters,
|
|
1888
|
+
sort: apiRequest.sort,
|
|
1889
|
+
...dbId && { db_id: dbId }
|
|
1890
|
+
};
|
|
1891
|
+
const listResult = await this.tablesApiClient.listTables(requestPayload);
|
|
1864
1892
|
if (isErrorResponse(listResult)) {
|
|
1865
1893
|
throw new ApiError(
|
|
1866
1894
|
listResult.error.message || "Find table by name failed",
|
|
@@ -1881,21 +1909,21 @@ class TableResource extends BaseResource {
|
|
|
1881
1909
|
/**
|
|
1882
1910
|
* Find a single table by name
|
|
1883
1911
|
*/
|
|
1884
|
-
async findByName(name) {
|
|
1885
|
-
return this.findOne({ where: { name } });
|
|
1912
|
+
async findByName(name, dbId) {
|
|
1913
|
+
return this.findOne({ where: { name } }, dbId);
|
|
1886
1914
|
}
|
|
1887
1915
|
/**
|
|
1888
1916
|
* Find a single table by ID
|
|
1889
1917
|
*/
|
|
1890
|
-
async findById(id) {
|
|
1891
|
-
return this.findOne({ where: { id } });
|
|
1918
|
+
async findById(id, dbId) {
|
|
1919
|
+
return this.findOne({ where: { id } }, dbId);
|
|
1892
1920
|
}
|
|
1893
1921
|
/**
|
|
1894
1922
|
* Update a table by name
|
|
1895
1923
|
*/
|
|
1896
|
-
async update(name, data) {
|
|
1924
|
+
async update(name, data, dbId) {
|
|
1897
1925
|
try {
|
|
1898
|
-
const tableResult = await this.findByName(name);
|
|
1926
|
+
const tableResult = await this.findByName(name, dbId);
|
|
1899
1927
|
if (!tableResult.data) {
|
|
1900
1928
|
throw new ApiError(`Table '${name}' not found`, 404);
|
|
1901
1929
|
}
|
|
@@ -1907,7 +1935,7 @@ class TableResource extends BaseResource {
|
|
|
1907
1935
|
}
|
|
1908
1936
|
const result = await this.tablesApiClient.updateTable(
|
|
1909
1937
|
tableResult.data.id,
|
|
1910
|
-
data
|
|
1938
|
+
dbId ? { ...data, db_id: dbId } : data
|
|
1911
1939
|
);
|
|
1912
1940
|
if (isErrorResponse(result)) {
|
|
1913
1941
|
throw new ApiError(
|
|
@@ -1924,9 +1952,9 @@ class TableResource extends BaseResource {
|
|
|
1924
1952
|
/**
|
|
1925
1953
|
* Delete a table by name
|
|
1926
1954
|
*/
|
|
1927
|
-
async delete(name) {
|
|
1955
|
+
async delete(name, dbId) {
|
|
1928
1956
|
try {
|
|
1929
|
-
const tableResult = await this.findByName(name);
|
|
1957
|
+
const tableResult = await this.findByName(name, dbId);
|
|
1930
1958
|
if (!tableResult.data) {
|
|
1931
1959
|
throw new ApiError(`Table '${name}' not found`, 404);
|
|
1932
1960
|
}
|
|
@@ -1937,7 +1965,8 @@ class TableResource extends BaseResource {
|
|
|
1937
1965
|
);
|
|
1938
1966
|
}
|
|
1939
1967
|
const result = await this.tablesApiClient.deleteTable(
|
|
1940
|
-
tableResult.data.id
|
|
1968
|
+
tableResult.data.id,
|
|
1969
|
+
dbId ? { db_id: dbId } : {}
|
|
1941
1970
|
);
|
|
1942
1971
|
if (isErrorResponse(result)) {
|
|
1943
1972
|
throw new ApiError(
|
|
@@ -1954,11 +1983,15 @@ class TableResource extends BaseResource {
|
|
|
1954
1983
|
/**
|
|
1955
1984
|
* Rename a table
|
|
1956
1985
|
*/
|
|
1957
|
-
async rename(oldName, newName) {
|
|
1986
|
+
async rename(oldName, newName, dbId) {
|
|
1958
1987
|
try {
|
|
1959
|
-
const result = await this.update(
|
|
1960
|
-
|
|
1961
|
-
|
|
1988
|
+
const result = await this.update(
|
|
1989
|
+
oldName,
|
|
1990
|
+
{
|
|
1991
|
+
name: newName
|
|
1992
|
+
},
|
|
1993
|
+
dbId
|
|
1994
|
+
);
|
|
1962
1995
|
return result;
|
|
1963
1996
|
} catch (error) {
|
|
1964
1997
|
throw error instanceof ApiError ? error : new ApiError(this.formatError(error), 500);
|
|
@@ -1967,11 +2000,15 @@ class TableResource extends BaseResource {
|
|
|
1967
2000
|
/**
|
|
1968
2001
|
* Set table access permissions
|
|
1969
2002
|
*/
|
|
1970
|
-
async setAccess(request) {
|
|
2003
|
+
async setAccess(request, dbId) {
|
|
1971
2004
|
try {
|
|
1972
|
-
const result = await this.update(
|
|
1973
|
-
|
|
1974
|
-
|
|
2005
|
+
const result = await this.update(
|
|
2006
|
+
request.table_name,
|
|
2007
|
+
{
|
|
2008
|
+
is_shared: request.is_shared
|
|
2009
|
+
},
|
|
2010
|
+
dbId
|
|
2011
|
+
);
|
|
1975
2012
|
return result;
|
|
1976
2013
|
} catch (error) {
|
|
1977
2014
|
throw error instanceof ApiError ? error : new ApiError(this.formatError(error), 500);
|
|
@@ -2362,6 +2399,658 @@ class ColumnResource extends BaseResource {
|
|
|
2362
2399
|
return tableInfo?.id || null;
|
|
2363
2400
|
}
|
|
2364
2401
|
}
|
|
2402
|
+
const DATABASE_ENDPOINTS = {
|
|
2403
|
+
create: {
|
|
2404
|
+
path: "/tables/databases",
|
|
2405
|
+
method: "POST",
|
|
2406
|
+
authenticated: true
|
|
2407
|
+
},
|
|
2408
|
+
list: {
|
|
2409
|
+
path: "/tables/databases/list",
|
|
2410
|
+
method: "POST",
|
|
2411
|
+
authenticated: true
|
|
2412
|
+
},
|
|
2413
|
+
update: {
|
|
2414
|
+
path: "/tables/databases/{db_id}",
|
|
2415
|
+
method: "PATCH",
|
|
2416
|
+
authenticated: true
|
|
2417
|
+
},
|
|
2418
|
+
delete: {
|
|
2419
|
+
path: "/tables/databases/{db_id}",
|
|
2420
|
+
method: "DELETE",
|
|
2421
|
+
authenticated: true
|
|
2422
|
+
},
|
|
2423
|
+
listJobs: {
|
|
2424
|
+
path: "/tables/databases/jobs/list",
|
|
2425
|
+
method: "POST",
|
|
2426
|
+
authenticated: true
|
|
2427
|
+
},
|
|
2428
|
+
pollDeleteStatus: {
|
|
2429
|
+
path: "/tables/databases/delete-status/{job_id}",
|
|
2430
|
+
method: "GET",
|
|
2431
|
+
authenticated: true
|
|
2432
|
+
}
|
|
2433
|
+
};
|
|
2434
|
+
const buildDatabaseEndpointPath = (endpoint, params = {}) => {
|
|
2435
|
+
let path = endpoint.path;
|
|
2436
|
+
Object.entries(params).forEach(([key, value]) => {
|
|
2437
|
+
path = path.replace(`{${key}}`, value);
|
|
2438
|
+
});
|
|
2439
|
+
return path;
|
|
2440
|
+
};
|
|
2441
|
+
class DatabasesApiClient {
|
|
2442
|
+
constructor(apiKey, config = {}) {
|
|
2443
|
+
this.config = { apiKey, ...config };
|
|
2444
|
+
this.httpAdapter = createHttpAdapter();
|
|
2445
|
+
const environment = config.environment || "prod";
|
|
2446
|
+
const region = config.region || "asia-south1";
|
|
2447
|
+
this.baseURL = this.getBaseURL(environment, region);
|
|
2448
|
+
}
|
|
2449
|
+
getBaseURL(environment, region) {
|
|
2450
|
+
const regionConfig = REGION_CONFIGS[region];
|
|
2451
|
+
if (!regionConfig) {
|
|
2452
|
+
throw new Error(`Unsupported region: ${region}`);
|
|
2453
|
+
}
|
|
2454
|
+
const envConfig = regionConfig[environment];
|
|
2455
|
+
if (!envConfig) {
|
|
2456
|
+
throw new Error(
|
|
2457
|
+
`Unsupported environment: ${environment} for region: ${region}`
|
|
2458
|
+
);
|
|
2459
|
+
}
|
|
2460
|
+
return `${envConfig.baseURL}/v1`;
|
|
2461
|
+
}
|
|
2462
|
+
/**
|
|
2463
|
+
* Create a new database
|
|
2464
|
+
*/
|
|
2465
|
+
async createDatabase(request) {
|
|
2466
|
+
try {
|
|
2467
|
+
const endpoint = DATABASE_ENDPOINTS.create;
|
|
2468
|
+
const url = `${this.baseURL}${endpoint.path}`;
|
|
2469
|
+
const response = await this.httpAdapter.request({
|
|
2470
|
+
url,
|
|
2471
|
+
method: endpoint.method,
|
|
2472
|
+
headers: {
|
|
2473
|
+
"Content-Type": "application/json",
|
|
2474
|
+
"x-boltic-token": this.config.apiKey
|
|
2475
|
+
},
|
|
2476
|
+
data: request,
|
|
2477
|
+
timeout: this.config.timeout
|
|
2478
|
+
});
|
|
2479
|
+
return response.data;
|
|
2480
|
+
} catch (error) {
|
|
2481
|
+
return this.handleError(error);
|
|
2482
|
+
}
|
|
2483
|
+
}
|
|
2484
|
+
/**
|
|
2485
|
+
* List databases with pagination, sorting, and filtering
|
|
2486
|
+
*/
|
|
2487
|
+
async listDatabases(request = {}, queryParams, options) {
|
|
2488
|
+
try {
|
|
2489
|
+
const endpoint = DATABASE_ENDPOINTS.list;
|
|
2490
|
+
let url = `${this.baseURL}${endpoint.path}`;
|
|
2491
|
+
const params = new URLSearchParams();
|
|
2492
|
+
if (queryParams?.connector_id) {
|
|
2493
|
+
params.append("connector_id", queryParams.connector_id);
|
|
2494
|
+
}
|
|
2495
|
+
if (queryParams?.add_default_if_missing) {
|
|
2496
|
+
params.append(
|
|
2497
|
+
"add_default_if_missing",
|
|
2498
|
+
queryParams.add_default_if_missing
|
|
2499
|
+
);
|
|
2500
|
+
}
|
|
2501
|
+
if (params.toString()) {
|
|
2502
|
+
url += `?${params.toString()}`;
|
|
2503
|
+
}
|
|
2504
|
+
const response = await this.httpAdapter.request({
|
|
2505
|
+
url,
|
|
2506
|
+
method: endpoint.method,
|
|
2507
|
+
headers: {
|
|
2508
|
+
"Content-Type": "application/json",
|
|
2509
|
+
"x-boltic-token": this.config.apiKey
|
|
2510
|
+
},
|
|
2511
|
+
data: request,
|
|
2512
|
+
timeout: this.config.timeout
|
|
2513
|
+
});
|
|
2514
|
+
const result = response.data;
|
|
2515
|
+
if (options?.fields && !("error" in result)) {
|
|
2516
|
+
return {
|
|
2517
|
+
...result,
|
|
2518
|
+
data: filterArrayFields(
|
|
2519
|
+
result.data,
|
|
2520
|
+
options.fields
|
|
2521
|
+
)
|
|
2522
|
+
};
|
|
2523
|
+
}
|
|
2524
|
+
return result;
|
|
2525
|
+
} catch (error) {
|
|
2526
|
+
return this.handleError(error);
|
|
2527
|
+
}
|
|
2528
|
+
}
|
|
2529
|
+
/**
|
|
2530
|
+
* Update a database
|
|
2531
|
+
*/
|
|
2532
|
+
async updateDatabase(dbId, request) {
|
|
2533
|
+
try {
|
|
2534
|
+
const endpoint = DATABASE_ENDPOINTS.update;
|
|
2535
|
+
const path = buildDatabaseEndpointPath(endpoint, { db_id: dbId });
|
|
2536
|
+
const url = `${this.baseURL}${path}`;
|
|
2537
|
+
const response = await this.httpAdapter.request({
|
|
2538
|
+
url,
|
|
2539
|
+
method: endpoint.method,
|
|
2540
|
+
headers: {
|
|
2541
|
+
"Content-Type": "application/json",
|
|
2542
|
+
"x-boltic-token": this.config.apiKey
|
|
2543
|
+
},
|
|
2544
|
+
data: request,
|
|
2545
|
+
timeout: this.config.timeout
|
|
2546
|
+
});
|
|
2547
|
+
return response.data;
|
|
2548
|
+
} catch (error) {
|
|
2549
|
+
return this.handleError(error);
|
|
2550
|
+
}
|
|
2551
|
+
}
|
|
2552
|
+
/**
|
|
2553
|
+
* Delete a database (initiates deletion job)
|
|
2554
|
+
*/
|
|
2555
|
+
async deleteDatabase(dbId) {
|
|
2556
|
+
try {
|
|
2557
|
+
const endpoint = DATABASE_ENDPOINTS.delete;
|
|
2558
|
+
const path = buildDatabaseEndpointPath(endpoint, { db_id: dbId });
|
|
2559
|
+
const url = `${this.baseURL}${path}`;
|
|
2560
|
+
const response = await this.httpAdapter.request({
|
|
2561
|
+
url,
|
|
2562
|
+
method: endpoint.method,
|
|
2563
|
+
headers: {
|
|
2564
|
+
"Content-Type": "application/json",
|
|
2565
|
+
"x-boltic-token": this.config.apiKey
|
|
2566
|
+
},
|
|
2567
|
+
timeout: this.config.timeout
|
|
2568
|
+
});
|
|
2569
|
+
return response.data;
|
|
2570
|
+
} catch (error) {
|
|
2571
|
+
return this.handleError(error);
|
|
2572
|
+
}
|
|
2573
|
+
}
|
|
2574
|
+
/**
|
|
2575
|
+
* List database jobs
|
|
2576
|
+
*/
|
|
2577
|
+
async listDatabaseJobs(request = {}, options) {
|
|
2578
|
+
try {
|
|
2579
|
+
const endpoint = DATABASE_ENDPOINTS.listJobs;
|
|
2580
|
+
const url = `${this.baseURL}${endpoint.path}`;
|
|
2581
|
+
const response = await this.httpAdapter.request({
|
|
2582
|
+
url,
|
|
2583
|
+
method: endpoint.method,
|
|
2584
|
+
headers: {
|
|
2585
|
+
"Content-Type": "application/json",
|
|
2586
|
+
"x-boltic-token": this.config.apiKey
|
|
2587
|
+
},
|
|
2588
|
+
data: request,
|
|
2589
|
+
timeout: this.config.timeout
|
|
2590
|
+
});
|
|
2591
|
+
const result = response.data;
|
|
2592
|
+
if (options?.fields && !("error" in result)) {
|
|
2593
|
+
return {
|
|
2594
|
+
...result,
|
|
2595
|
+
data: filterArrayFields(
|
|
2596
|
+
result.data,
|
|
2597
|
+
options.fields
|
|
2598
|
+
)
|
|
2599
|
+
};
|
|
2600
|
+
}
|
|
2601
|
+
return result;
|
|
2602
|
+
} catch (error) {
|
|
2603
|
+
return this.handleError(error);
|
|
2604
|
+
}
|
|
2605
|
+
}
|
|
2606
|
+
/**
|
|
2607
|
+
* Poll deletion status for a database job
|
|
2608
|
+
*/
|
|
2609
|
+
async pollDeleteStatus(jobId) {
|
|
2610
|
+
try {
|
|
2611
|
+
const endpoint = DATABASE_ENDPOINTS.pollDeleteStatus;
|
|
2612
|
+
const path = buildDatabaseEndpointPath(endpoint, { job_id: jobId });
|
|
2613
|
+
const url = `${this.baseURL}${path}`;
|
|
2614
|
+
const response = await this.httpAdapter.request({
|
|
2615
|
+
url,
|
|
2616
|
+
method: endpoint.method,
|
|
2617
|
+
headers: {
|
|
2618
|
+
"Content-Type": "application/json",
|
|
2619
|
+
"x-boltic-token": this.config.apiKey
|
|
2620
|
+
},
|
|
2621
|
+
timeout: this.config.timeout
|
|
2622
|
+
});
|
|
2623
|
+
return response.data;
|
|
2624
|
+
} catch (error) {
|
|
2625
|
+
return this.handleError(error);
|
|
2626
|
+
}
|
|
2627
|
+
}
|
|
2628
|
+
/**
|
|
2629
|
+
* Handle API errors and convert to standard error format
|
|
2630
|
+
*/
|
|
2631
|
+
handleError(error) {
|
|
2632
|
+
if (this.config.debug) {
|
|
2633
|
+
console.error("[DatabasesApiClient] Error:", error);
|
|
2634
|
+
}
|
|
2635
|
+
const hasErrorProperty = (err) => {
|
|
2636
|
+
return typeof err === "object" && err !== null && "error" in err && typeof err.error === "object" && err.error !== null;
|
|
2637
|
+
};
|
|
2638
|
+
const hasResponseError = (err) => {
|
|
2639
|
+
return typeof err === "object" && err !== null && "response" in err && typeof err.response === "object" && err.response !== null && "data" in err.response && typeof err.response.data === "object" && err.response.data !== null && "error" in err.response.data;
|
|
2640
|
+
};
|
|
2641
|
+
const isStandardError = (err) => {
|
|
2642
|
+
return err instanceof Error;
|
|
2643
|
+
};
|
|
2644
|
+
if (hasErrorProperty(error)) {
|
|
2645
|
+
const errorWithError = error;
|
|
2646
|
+
return {
|
|
2647
|
+
error: {
|
|
2648
|
+
code: typeof errorWithError.error.code === "number" ? String(errorWithError.error.code) : errorWithError.error.code || "UNKNOWN_ERROR",
|
|
2649
|
+
message: errorWithError.error.message || "An error occurred",
|
|
2650
|
+
meta: errorWithError.error.meta || []
|
|
2651
|
+
}
|
|
2652
|
+
};
|
|
2653
|
+
}
|
|
2654
|
+
if (hasResponseError(error)) {
|
|
2655
|
+
const errorWithResponse = error;
|
|
2656
|
+
return {
|
|
2657
|
+
error: {
|
|
2658
|
+
code: typeof errorWithResponse.response.data.error.code === "number" ? String(errorWithResponse.response.data.error.code) : errorWithResponse.response.data.error.code || "UNKNOWN_ERROR",
|
|
2659
|
+
message: errorWithResponse.response.data.error.message || "An error occurred",
|
|
2660
|
+
meta: errorWithResponse.response.data.error.meta || []
|
|
2661
|
+
}
|
|
2662
|
+
};
|
|
2663
|
+
}
|
|
2664
|
+
if (isStandardError(error)) {
|
|
2665
|
+
const standardError = error;
|
|
2666
|
+
return {
|
|
2667
|
+
error: {
|
|
2668
|
+
code: standardError.code || "UNKNOWN_ERROR",
|
|
2669
|
+
message: standardError.message || "An unexpected error occurred",
|
|
2670
|
+
meta: []
|
|
2671
|
+
}
|
|
2672
|
+
};
|
|
2673
|
+
}
|
|
2674
|
+
return {
|
|
2675
|
+
error: {
|
|
2676
|
+
code: "UNKNOWN_ERROR",
|
|
2677
|
+
message: "An unexpected error occurred",
|
|
2678
|
+
meta: []
|
|
2679
|
+
}
|
|
2680
|
+
};
|
|
2681
|
+
}
|
|
2682
|
+
}
|
|
2683
|
+
class DatabaseResource extends BaseResource {
|
|
2684
|
+
constructor(client) {
|
|
2685
|
+
super(client, "/v1/tables/databases");
|
|
2686
|
+
this.apiClient = new DatabasesApiClient(client.getConfig().apiKey, {
|
|
2687
|
+
environment: client.getConfig().environment,
|
|
2688
|
+
region: client.getConfig().region,
|
|
2689
|
+
timeout: client.getConfig().timeout,
|
|
2690
|
+
debug: client.getConfig().debug
|
|
2691
|
+
});
|
|
2692
|
+
}
|
|
2693
|
+
/**
|
|
2694
|
+
* Create a new database
|
|
2695
|
+
*
|
|
2696
|
+
* @param request - Database creation request
|
|
2697
|
+
* @returns Promise with created database or error
|
|
2698
|
+
*
|
|
2699
|
+
* @example
|
|
2700
|
+
* ```typescript
|
|
2701
|
+
* const result = await client.databases.create({
|
|
2702
|
+
* db_name: 'My Database',
|
|
2703
|
+
* db_internal_name: 'my-database',
|
|
2704
|
+
* resource_id: 'boltic'
|
|
2705
|
+
* });
|
|
2706
|
+
* ```
|
|
2707
|
+
*/
|
|
2708
|
+
async create(request) {
|
|
2709
|
+
const result = await this.apiClient.createDatabase(request);
|
|
2710
|
+
if ("error" in result) {
|
|
2711
|
+
return {
|
|
2712
|
+
error: {
|
|
2713
|
+
code: typeof result.error.code === "number" ? String(result.error.code) : result.error.code,
|
|
2714
|
+
message: result.error.message,
|
|
2715
|
+
meta: result.error.meta
|
|
2716
|
+
}
|
|
2717
|
+
};
|
|
2718
|
+
}
|
|
2719
|
+
return result;
|
|
2720
|
+
}
|
|
2721
|
+
/**
|
|
2722
|
+
* List all databases with optional filtering and pagination
|
|
2723
|
+
* By default, only shows active databases
|
|
2724
|
+
*
|
|
2725
|
+
* @param options - Query options for listing databases
|
|
2726
|
+
* @returns Promise with list of databases or error
|
|
2727
|
+
*
|
|
2728
|
+
* @example
|
|
2729
|
+
* ```typescript
|
|
2730
|
+
* // List all active databases (default)
|
|
2731
|
+
* const result = await client.databases.findAll();
|
|
2732
|
+
*
|
|
2733
|
+
* // List with pagination
|
|
2734
|
+
* const result = await client.databases.findAll({
|
|
2735
|
+
* page: { page_no: 1, page_size: 10 }
|
|
2736
|
+
* });
|
|
2737
|
+
*
|
|
2738
|
+
* // List with sorting
|
|
2739
|
+
* const result = await client.databases.findAll({
|
|
2740
|
+
* sort: [{ field: 'db_name', direction: 'asc' }]
|
|
2741
|
+
* });
|
|
2742
|
+
* ```
|
|
2743
|
+
*/
|
|
2744
|
+
async findAll(options) {
|
|
2745
|
+
const request = {};
|
|
2746
|
+
if (options?.page) {
|
|
2747
|
+
request.page = options.page;
|
|
2748
|
+
}
|
|
2749
|
+
if (options?.sort) {
|
|
2750
|
+
request.sort = options.sort;
|
|
2751
|
+
}
|
|
2752
|
+
if (options?.filters) {
|
|
2753
|
+
const filtersWithoutStatus = options.filters.filter(
|
|
2754
|
+
(f) => f.field !== "status"
|
|
2755
|
+
);
|
|
2756
|
+
request.filters = [
|
|
2757
|
+
...filtersWithoutStatus,
|
|
2758
|
+
{ field: "status", operator: "=", values: ["ACTIVE"] }
|
|
2759
|
+
];
|
|
2760
|
+
} else {
|
|
2761
|
+
request.filters = [
|
|
2762
|
+
{ field: "status", operator: "=", values: ["ACTIVE"] }
|
|
2763
|
+
];
|
|
2764
|
+
}
|
|
2765
|
+
const queryParams = {};
|
|
2766
|
+
if (options?.connector_id) {
|
|
2767
|
+
queryParams.connector_id = options.connector_id;
|
|
2768
|
+
}
|
|
2769
|
+
if (options?.add_default_if_missing !== void 0) {
|
|
2770
|
+
queryParams.add_default_if_missing = options.add_default_if_missing ? "true" : "false";
|
|
2771
|
+
}
|
|
2772
|
+
const result = await this.apiClient.listDatabases(
|
|
2773
|
+
request,
|
|
2774
|
+
queryParams,
|
|
2775
|
+
options
|
|
2776
|
+
);
|
|
2777
|
+
if ("error" in result) {
|
|
2778
|
+
return {
|
|
2779
|
+
error: {
|
|
2780
|
+
code: typeof result.error.code === "number" ? String(result.error.code) : result.error.code,
|
|
2781
|
+
message: result.error.message,
|
|
2782
|
+
meta: result.error.meta
|
|
2783
|
+
}
|
|
2784
|
+
};
|
|
2785
|
+
}
|
|
2786
|
+
if ("pagination" in result && result.pagination) {
|
|
2787
|
+
const pagination = result.pagination;
|
|
2788
|
+
return {
|
|
2789
|
+
...result,
|
|
2790
|
+
pagination: {
|
|
2791
|
+
total_count: pagination.total_count,
|
|
2792
|
+
total_pages: pagination.total_pages ?? Math.ceil(pagination.total_count / pagination.per_page),
|
|
2793
|
+
current_page: pagination.current_page,
|
|
2794
|
+
per_page: pagination.per_page,
|
|
2795
|
+
type: "page"
|
|
2796
|
+
}
|
|
2797
|
+
};
|
|
2798
|
+
}
|
|
2799
|
+
return result;
|
|
2800
|
+
}
|
|
2801
|
+
/**
|
|
2802
|
+
* Get a specific database by internal name (slug)
|
|
2803
|
+
*
|
|
2804
|
+
* @param dbInternalName - Database internal name (slug)
|
|
2805
|
+
* @param options - Query options (e.g., fields to return)
|
|
2806
|
+
* @returns Promise with database or error
|
|
2807
|
+
*
|
|
2808
|
+
* @example
|
|
2809
|
+
* ```typescript
|
|
2810
|
+
* const result = await client.databases.findOne('my_database_slug');
|
|
2811
|
+
* ```
|
|
2812
|
+
*/
|
|
2813
|
+
async findOne(dbInternalName, options) {
|
|
2814
|
+
const result = await this.findAll({
|
|
2815
|
+
filters: [
|
|
2816
|
+
{
|
|
2817
|
+
field: "db_internal_name",
|
|
2818
|
+
operator: "=",
|
|
2819
|
+
values: [dbInternalName]
|
|
2820
|
+
}
|
|
2821
|
+
],
|
|
2822
|
+
fields: options?.fields,
|
|
2823
|
+
page: { page_no: 1, page_size: 1 }
|
|
2824
|
+
});
|
|
2825
|
+
if (isErrorResponse(result)) {
|
|
2826
|
+
return result;
|
|
2827
|
+
}
|
|
2828
|
+
if (result.data.length === 0) {
|
|
2829
|
+
return {
|
|
2830
|
+
error: {
|
|
2831
|
+
code: "NOT_FOUND",
|
|
2832
|
+
message: `Database with internal name '${dbInternalName}' not found`,
|
|
2833
|
+
meta: []
|
|
2834
|
+
}
|
|
2835
|
+
};
|
|
2836
|
+
}
|
|
2837
|
+
return {
|
|
2838
|
+
data: result.data[0],
|
|
2839
|
+
message: "Database found"
|
|
2840
|
+
};
|
|
2841
|
+
}
|
|
2842
|
+
/**
|
|
2843
|
+
* Get the default database
|
|
2844
|
+
*
|
|
2845
|
+
* @returns Promise with default database or error
|
|
2846
|
+
*
|
|
2847
|
+
* @example
|
|
2848
|
+
* ```typescript
|
|
2849
|
+
* const result = await client.databases.getDefault();
|
|
2850
|
+
* ```
|
|
2851
|
+
*/
|
|
2852
|
+
async getDefault() {
|
|
2853
|
+
const result = await this.findAll({
|
|
2854
|
+
filters: [{ field: "is_default", operator: "=", values: [true] }],
|
|
2855
|
+
page: { page_no: 1, page_size: 1 }
|
|
2856
|
+
});
|
|
2857
|
+
if (isErrorResponse(result)) {
|
|
2858
|
+
return result;
|
|
2859
|
+
}
|
|
2860
|
+
if (result.data.length === 0) {
|
|
2861
|
+
return {
|
|
2862
|
+
error: {
|
|
2863
|
+
code: "NOT_FOUND",
|
|
2864
|
+
message: "Default database not found",
|
|
2865
|
+
meta: []
|
|
2866
|
+
}
|
|
2867
|
+
};
|
|
2868
|
+
}
|
|
2869
|
+
return {
|
|
2870
|
+
data: result.data[0],
|
|
2871
|
+
message: "Default database found"
|
|
2872
|
+
};
|
|
2873
|
+
}
|
|
2874
|
+
/**
|
|
2875
|
+
* Update a database
|
|
2876
|
+
* Only allows updating the display name (db_name)
|
|
2877
|
+
*
|
|
2878
|
+
* @param dbInternalName - Database internal name (slug)
|
|
2879
|
+
* @param request - Update request (only db_name is allowed)
|
|
2880
|
+
* @returns Promise with updated database or error
|
|
2881
|
+
*
|
|
2882
|
+
* @example
|
|
2883
|
+
* ```typescript
|
|
2884
|
+
* const result = await client.databases.update('my_database_slug', {
|
|
2885
|
+
* db_name: 'Updated Database Name'
|
|
2886
|
+
* });
|
|
2887
|
+
* ```
|
|
2888
|
+
*/
|
|
2889
|
+
async update(dbInternalName, request) {
|
|
2890
|
+
const dbInfo = await this.findOne(dbInternalName);
|
|
2891
|
+
if (isErrorResponse(dbInfo)) {
|
|
2892
|
+
return {
|
|
2893
|
+
error: {
|
|
2894
|
+
code: "DATABASE_NOT_FOUND",
|
|
2895
|
+
message: `Database with internal name '${dbInternalName}' not found`,
|
|
2896
|
+
meta: []
|
|
2897
|
+
}
|
|
2898
|
+
};
|
|
2899
|
+
}
|
|
2900
|
+
const dbId = dbInfo.data.id;
|
|
2901
|
+
const updateRequest = {
|
|
2902
|
+
db_name: request.db_name
|
|
2903
|
+
};
|
|
2904
|
+
const result = await this.apiClient.updateDatabase(dbId, updateRequest);
|
|
2905
|
+
if ("error" in result) {
|
|
2906
|
+
return {
|
|
2907
|
+
error: {
|
|
2908
|
+
code: typeof result.error.code === "number" ? String(result.error.code) : result.error.code,
|
|
2909
|
+
message: result.error.message,
|
|
2910
|
+
meta: result.error.meta
|
|
2911
|
+
}
|
|
2912
|
+
};
|
|
2913
|
+
}
|
|
2914
|
+
return result;
|
|
2915
|
+
}
|
|
2916
|
+
/**
|
|
2917
|
+
* Delete a database (initiates async deletion job)
|
|
2918
|
+
*
|
|
2919
|
+
* @param dbInternalName - Database internal name (slug)
|
|
2920
|
+
* @returns Promise with job details or error
|
|
2921
|
+
*
|
|
2922
|
+
* @example
|
|
2923
|
+
* ```typescript
|
|
2924
|
+
* const result = await client.databases.delete('my_database_slug');
|
|
2925
|
+
* if (!result.error) {
|
|
2926
|
+
* console.log('Deletion job started:', result.data.job_id);
|
|
2927
|
+
* // Poll for status
|
|
2928
|
+
* const status = await client.databases.pollDeleteStatus(result.data.job_id);
|
|
2929
|
+
* }
|
|
2930
|
+
* ```
|
|
2931
|
+
*/
|
|
2932
|
+
async delete(dbInternalName) {
|
|
2933
|
+
const dbInfo = await this.findOne(dbInternalName);
|
|
2934
|
+
if (isErrorResponse(dbInfo)) {
|
|
2935
|
+
return {
|
|
2936
|
+
error: {
|
|
2937
|
+
code: "DATABASE_NOT_FOUND",
|
|
2938
|
+
message: `Database with internal name '${dbInternalName}' not found`,
|
|
2939
|
+
meta: []
|
|
2940
|
+
}
|
|
2941
|
+
};
|
|
2942
|
+
}
|
|
2943
|
+
if (dbInfo.data.is_default) {
|
|
2944
|
+
return {
|
|
2945
|
+
error: {
|
|
2946
|
+
code: "CANNOT_DELETE_DEFAULT",
|
|
2947
|
+
message: "Cannot delete the default database",
|
|
2948
|
+
meta: []
|
|
2949
|
+
}
|
|
2950
|
+
};
|
|
2951
|
+
}
|
|
2952
|
+
const dbId = dbInfo.data.id;
|
|
2953
|
+
const result = await this.apiClient.deleteDatabase(dbId);
|
|
2954
|
+
if ("error" in result) {
|
|
2955
|
+
return {
|
|
2956
|
+
error: {
|
|
2957
|
+
code: typeof result.error.code === "number" ? String(result.error.code) : result.error.code,
|
|
2958
|
+
message: result.error.message,
|
|
2959
|
+
meta: result.error.meta
|
|
2960
|
+
}
|
|
2961
|
+
};
|
|
2962
|
+
}
|
|
2963
|
+
return result;
|
|
2964
|
+
}
|
|
2965
|
+
/**
|
|
2966
|
+
* List database jobs (e.g., deletion jobs)
|
|
2967
|
+
*
|
|
2968
|
+
* @param options - Query options for listing jobs
|
|
2969
|
+
* @returns Promise with list of jobs or error
|
|
2970
|
+
*
|
|
2971
|
+
* @example
|
|
2972
|
+
* ```typescript
|
|
2973
|
+
* // List all jobs
|
|
2974
|
+
* const result = await client.databases.listJobs();
|
|
2975
|
+
*
|
|
2976
|
+
* // List jobs deleted by current user
|
|
2977
|
+
* const result = await client.databases.listJobs({
|
|
2978
|
+
* deleted_by_me: true
|
|
2979
|
+
* });
|
|
2980
|
+
* ```
|
|
2981
|
+
*/
|
|
2982
|
+
async listJobs(options) {
|
|
2983
|
+
const request = {};
|
|
2984
|
+
if (options?.deleted_by_me !== void 0) {
|
|
2985
|
+
request.deleted_by_me = options.deleted_by_me;
|
|
2986
|
+
}
|
|
2987
|
+
if (options?.page) {
|
|
2988
|
+
request.page = options.page;
|
|
2989
|
+
}
|
|
2990
|
+
if (options?.sort) {
|
|
2991
|
+
request.sort = options.sort;
|
|
2992
|
+
}
|
|
2993
|
+
if (options?.filters) {
|
|
2994
|
+
request.filters = options.filters;
|
|
2995
|
+
}
|
|
2996
|
+
const result = await this.apiClient.listDatabaseJobs(request, options);
|
|
2997
|
+
if ("error" in result) {
|
|
2998
|
+
return {
|
|
2999
|
+
error: {
|
|
3000
|
+
code: typeof result.error.code === "number" ? String(result.error.code) : result.error.code,
|
|
3001
|
+
message: result.error.message,
|
|
3002
|
+
meta: result.error.meta
|
|
3003
|
+
}
|
|
3004
|
+
};
|
|
3005
|
+
}
|
|
3006
|
+
if ("pagination" in result && result.pagination) {
|
|
3007
|
+
const pagination = result.pagination;
|
|
3008
|
+
const normalizedResult = {
|
|
3009
|
+
...result,
|
|
3010
|
+
pagination: {
|
|
3011
|
+
total_count: pagination.total_count,
|
|
3012
|
+
total_pages: pagination.total_pages ?? Math.ceil(pagination.total_count / pagination.per_page),
|
|
3013
|
+
current_page: pagination.current_page,
|
|
3014
|
+
per_page: pagination.per_page,
|
|
3015
|
+
type: "page"
|
|
3016
|
+
}
|
|
3017
|
+
};
|
|
3018
|
+
return normalizedResult;
|
|
3019
|
+
}
|
|
3020
|
+
return {
|
|
3021
|
+
...result,
|
|
3022
|
+
data: result.data || []
|
|
3023
|
+
};
|
|
3024
|
+
}
|
|
3025
|
+
/**
|
|
3026
|
+
* Poll the status of a database deletion job
|
|
3027
|
+
*
|
|
3028
|
+
* @param jobId - Job ID
|
|
3029
|
+
* @returns Promise with job status or error
|
|
3030
|
+
*
|
|
3031
|
+
* @example
|
|
3032
|
+
* ```typescript
|
|
3033
|
+
* const status = await client.databases.pollDeleteStatus('job-uuid');
|
|
3034
|
+
* if (!status.error) {
|
|
3035
|
+
* console.log('Job status:', status.data.status);
|
|
3036
|
+
* console.log('Message:', status.data.message);
|
|
3037
|
+
* }
|
|
3038
|
+
* ```
|
|
3039
|
+
*/
|
|
3040
|
+
async pollDeleteStatus(jobId) {
|
|
3041
|
+
const result = await this.apiClient.pollDeleteStatus(jobId);
|
|
3042
|
+
if ("error" in result) {
|
|
3043
|
+
return {
|
|
3044
|
+
error: {
|
|
3045
|
+
code: typeof result.error.code === "number" ? String(result.error.code) : result.error.code,
|
|
3046
|
+
message: result.error.message,
|
|
3047
|
+
meta: result.error.meta
|
|
3048
|
+
}
|
|
3049
|
+
};
|
|
3050
|
+
}
|
|
3051
|
+
return result;
|
|
3052
|
+
}
|
|
3053
|
+
}
|
|
2365
3054
|
const INDEX_ENDPOINTS = {
|
|
2366
3055
|
create: {
|
|
2367
3056
|
path: "/tables/indexes/{table_id}",
|
|
@@ -2411,10 +3100,11 @@ class IndexesApiClient {
|
|
|
2411
3100
|
}
|
|
2412
3101
|
return `${envConfig.baseURL}/v1`;
|
|
2413
3102
|
}
|
|
2414
|
-
async addIndex(tableId, request) {
|
|
3103
|
+
async addIndex(tableId, request, dbId) {
|
|
2415
3104
|
try {
|
|
2416
3105
|
const endpoint = INDEX_ENDPOINTS.create;
|
|
2417
|
-
|
|
3106
|
+
let url = `${this.baseURL}${buildIndexEndpointPath(endpoint, { table_id: tableId })}`;
|
|
3107
|
+
url = addDbIdToUrl(url, dbId);
|
|
2418
3108
|
const response = await this.httpAdapter.request({
|
|
2419
3109
|
url,
|
|
2420
3110
|
method: endpoint.method,
|
|
@@ -2427,10 +3117,11 @@ class IndexesApiClient {
|
|
|
2427
3117
|
return this.formatErrorResponse(error);
|
|
2428
3118
|
}
|
|
2429
3119
|
}
|
|
2430
|
-
async listIndexes(tableId, query) {
|
|
3120
|
+
async listIndexes(tableId, query, dbId) {
|
|
2431
3121
|
try {
|
|
2432
3122
|
const endpoint = INDEX_ENDPOINTS.list;
|
|
2433
|
-
|
|
3123
|
+
let url = `${this.baseURL}${buildIndexEndpointPath(endpoint, { table_id: tableId })}`;
|
|
3124
|
+
url = addDbIdToUrl(url, dbId);
|
|
2434
3125
|
const response = await this.httpAdapter.request({
|
|
2435
3126
|
url,
|
|
2436
3127
|
method: endpoint.method,
|
|
@@ -2443,10 +3134,11 @@ class IndexesApiClient {
|
|
|
2443
3134
|
return this.formatErrorResponse(error);
|
|
2444
3135
|
}
|
|
2445
3136
|
}
|
|
2446
|
-
async deleteIndex(tableId, request) {
|
|
3137
|
+
async deleteIndex(tableId, request, dbId) {
|
|
2447
3138
|
try {
|
|
2448
3139
|
const endpoint = INDEX_ENDPOINTS.delete;
|
|
2449
|
-
|
|
3140
|
+
let url = `${this.baseURL}${buildIndexEndpointPath(endpoint, { table_id: tableId })}`;
|
|
3141
|
+
url = addDbIdToUrl(url, dbId);
|
|
2450
3142
|
const response = await this.httpAdapter.request({
|
|
2451
3143
|
url,
|
|
2452
3144
|
method: endpoint.method,
|
|
@@ -2516,15 +3208,15 @@ class IndexResource {
|
|
|
2516
3208
|
});
|
|
2517
3209
|
this.tableResource = new TableResource(client);
|
|
2518
3210
|
}
|
|
2519
|
-
async resolveTableId(tableName) {
|
|
2520
|
-
const tableResult = await this.tableResource.findByName(tableName);
|
|
3211
|
+
async resolveTableId(tableName, dbId) {
|
|
3212
|
+
const tableResult = await this.tableResource.findByName(tableName, dbId);
|
|
2521
3213
|
if (!tableResult.data) throw new Error(`Table not found: ${tableName}`);
|
|
2522
3214
|
return tableResult.data.id;
|
|
2523
3215
|
}
|
|
2524
|
-
async addIndex(tableName, request) {
|
|
3216
|
+
async addIndex(tableName, request, dbId) {
|
|
2525
3217
|
try {
|
|
2526
|
-
const tableId = await this.resolveTableId(tableName);
|
|
2527
|
-
return await this.apiClient.addIndex(tableId, request);
|
|
3218
|
+
const tableId = await this.resolveTableId(tableName, dbId);
|
|
3219
|
+
return await this.apiClient.addIndex(tableId, request, dbId);
|
|
2528
3220
|
} catch (error) {
|
|
2529
3221
|
return {
|
|
2530
3222
|
error: {
|
|
@@ -2535,10 +3227,10 @@ class IndexResource {
|
|
|
2535
3227
|
};
|
|
2536
3228
|
}
|
|
2537
3229
|
}
|
|
2538
|
-
async listIndexes(tableName, query) {
|
|
3230
|
+
async listIndexes(tableName, query, dbId) {
|
|
2539
3231
|
try {
|
|
2540
|
-
const tableId = await this.resolveTableId(tableName);
|
|
2541
|
-
return await this.apiClient.listIndexes(tableId, query);
|
|
3232
|
+
const tableId = await this.resolveTableId(tableName, dbId);
|
|
3233
|
+
return await this.apiClient.listIndexes(tableId, query, dbId);
|
|
2542
3234
|
} catch (error) {
|
|
2543
3235
|
return {
|
|
2544
3236
|
error: {
|
|
@@ -2549,11 +3241,11 @@ class IndexResource {
|
|
|
2549
3241
|
};
|
|
2550
3242
|
}
|
|
2551
3243
|
}
|
|
2552
|
-
async deleteIndex(tableName, indexName) {
|
|
3244
|
+
async deleteIndex(tableName, indexName, dbId) {
|
|
2553
3245
|
try {
|
|
2554
|
-
const tableId = await this.resolveTableId(tableName);
|
|
3246
|
+
const tableId = await this.resolveTableId(tableName, dbId);
|
|
2555
3247
|
const request = { index_name: indexName };
|
|
2556
|
-
return await this.apiClient.deleteIndex(tableId, request);
|
|
3248
|
+
return await this.apiClient.deleteIndex(tableId, request, dbId);
|
|
2557
3249
|
} catch (error) {
|
|
2558
3250
|
return {
|
|
2559
3251
|
error: {
|
|
@@ -2660,7 +3352,7 @@ class RecordsApiClient {
|
|
|
2660
3352
|
/**
|
|
2661
3353
|
* Insert a single record
|
|
2662
3354
|
*/
|
|
2663
|
-
async insertRecord(request) {
|
|
3355
|
+
async insertRecord(request, dbId) {
|
|
2664
3356
|
try {
|
|
2665
3357
|
const { table_id, fields, ...recordData } = request;
|
|
2666
3358
|
if (!table_id) {
|
|
@@ -2669,7 +3361,8 @@ class RecordsApiClient {
|
|
|
2669
3361
|
);
|
|
2670
3362
|
}
|
|
2671
3363
|
const endpoint = RECORD_ENDPOINTS.insert;
|
|
2672
|
-
|
|
3364
|
+
let url = `${this.baseURL}${buildRecordEndpointPath(endpoint, { table_id })}`;
|
|
3365
|
+
url = addDbIdToUrl(url, dbId);
|
|
2673
3366
|
const response = await this.httpAdapter.request({
|
|
2674
3367
|
url,
|
|
2675
3368
|
method: endpoint.method,
|
|
@@ -2692,7 +3385,7 @@ class RecordsApiClient {
|
|
|
2692
3385
|
/**
|
|
2693
3386
|
* Insert multiple records in bulk
|
|
2694
3387
|
*/
|
|
2695
|
-
async insertManyRecords(records, tableId, options = { validation: true }) {
|
|
3388
|
+
async insertManyRecords(records, tableId, options = { validation: true }, dbId) {
|
|
2696
3389
|
try {
|
|
2697
3390
|
if (!tableId) {
|
|
2698
3391
|
return this.formatErrorResponse(
|
|
@@ -2713,6 +3406,7 @@ class RecordsApiClient {
|
|
|
2713
3406
|
if (queryParams.toString()) {
|
|
2714
3407
|
url += `?${queryParams.toString()}`;
|
|
2715
3408
|
}
|
|
3409
|
+
url = addDbIdToUrl(url, dbId);
|
|
2716
3410
|
const response = await this.httpAdapter.request({
|
|
2717
3411
|
url,
|
|
2718
3412
|
method: endpoint.method,
|
|
@@ -2728,7 +3422,7 @@ class RecordsApiClient {
|
|
|
2728
3422
|
/**
|
|
2729
3423
|
* Get a single record by ID
|
|
2730
3424
|
*/
|
|
2731
|
-
async getRecord(recordId, tableId, options = {}) {
|
|
3425
|
+
async getRecord(recordId, tableId, options = {}, dbId) {
|
|
2732
3426
|
try {
|
|
2733
3427
|
if (!tableId) {
|
|
2734
3428
|
return this.formatErrorResponse(
|
|
@@ -2736,10 +3430,11 @@ class RecordsApiClient {
|
|
|
2736
3430
|
);
|
|
2737
3431
|
}
|
|
2738
3432
|
const endpoint = RECORD_ENDPOINTS.get;
|
|
2739
|
-
|
|
3433
|
+
let url = `${this.baseURL}${buildRecordEndpointPath(endpoint, {
|
|
2740
3434
|
table_id: tableId,
|
|
2741
3435
|
record_id: recordId
|
|
2742
3436
|
})}`;
|
|
3437
|
+
url = addDbIdToUrl(url, dbId);
|
|
2743
3438
|
const response = await this.httpAdapter.request({
|
|
2744
3439
|
url,
|
|
2745
3440
|
method: endpoint.method,
|
|
@@ -2761,7 +3456,7 @@ class RecordsApiClient {
|
|
|
2761
3456
|
/**
|
|
2762
3457
|
* List records with filtering and pagination
|
|
2763
3458
|
*/
|
|
2764
|
-
async listRecords(options = {}) {
|
|
3459
|
+
async listRecords(options = {}, dbId) {
|
|
2765
3460
|
try {
|
|
2766
3461
|
const { table_id, ...queryOptions } = options;
|
|
2767
3462
|
if (!table_id) {
|
|
@@ -2770,7 +3465,8 @@ class RecordsApiClient {
|
|
|
2770
3465
|
);
|
|
2771
3466
|
}
|
|
2772
3467
|
const endpoint = RECORD_ENDPOINTS.list;
|
|
2773
|
-
|
|
3468
|
+
let url = `${this.baseURL}${buildRecordEndpointPath(endpoint, { table_id })}`;
|
|
3469
|
+
url = addDbIdToUrl(url, dbId);
|
|
2774
3470
|
const response = await this.httpAdapter.request({
|
|
2775
3471
|
url,
|
|
2776
3472
|
method: endpoint.method,
|
|
@@ -2793,7 +3489,7 @@ class RecordsApiClient {
|
|
|
2793
3489
|
/**
|
|
2794
3490
|
* Update records by filters
|
|
2795
3491
|
*/
|
|
2796
|
-
async updateRecords(request) {
|
|
3492
|
+
async updateRecords(request, dbId) {
|
|
2797
3493
|
try {
|
|
2798
3494
|
const { table_id, set, filters, fields, ...rest } = request;
|
|
2799
3495
|
if (!table_id) {
|
|
@@ -2810,7 +3506,8 @@ class RecordsApiClient {
|
|
|
2810
3506
|
apiPayload.fields = fields;
|
|
2811
3507
|
}
|
|
2812
3508
|
const endpoint = RECORD_ENDPOINTS.update;
|
|
2813
|
-
|
|
3509
|
+
let url = `${this.baseURL}${buildRecordEndpointPath(endpoint, { table_id })}`;
|
|
3510
|
+
url = addDbIdToUrl(url, dbId);
|
|
2814
3511
|
const response = await this.httpAdapter.request({
|
|
2815
3512
|
url,
|
|
2816
3513
|
method: endpoint.method,
|
|
@@ -2833,7 +3530,7 @@ class RecordsApiClient {
|
|
|
2833
3530
|
/**
|
|
2834
3531
|
* Update a single record by ID
|
|
2835
3532
|
*/
|
|
2836
|
-
async updateRecordById(recordId, request) {
|
|
3533
|
+
async updateRecordById(recordId, request, dbId) {
|
|
2837
3534
|
try {
|
|
2838
3535
|
const { table_id, ...updateOptions } = request;
|
|
2839
3536
|
if (!table_id) {
|
|
@@ -2842,10 +3539,11 @@ class RecordsApiClient {
|
|
|
2842
3539
|
);
|
|
2843
3540
|
}
|
|
2844
3541
|
const endpoint = RECORD_ENDPOINTS.updateById;
|
|
2845
|
-
|
|
3542
|
+
let url = `${this.baseURL}${buildRecordEndpointPath(endpoint, {
|
|
2846
3543
|
record_id: recordId,
|
|
2847
3544
|
table_id
|
|
2848
3545
|
})}`;
|
|
3546
|
+
url = addDbIdToUrl(url, dbId);
|
|
2849
3547
|
const response = await this.httpAdapter.request({
|
|
2850
3548
|
url,
|
|
2851
3549
|
method: endpoint.method,
|
|
@@ -2868,7 +3566,7 @@ class RecordsApiClient {
|
|
|
2868
3566
|
/**
|
|
2869
3567
|
* Unified delete records method that supports both record_ids and filters
|
|
2870
3568
|
*/
|
|
2871
|
-
async deleteRecords(request) {
|
|
3569
|
+
async deleteRecords(request, dbId) {
|
|
2872
3570
|
try {
|
|
2873
3571
|
const { table_id } = request;
|
|
2874
3572
|
if (!table_id) {
|
|
@@ -2878,7 +3576,8 @@ class RecordsApiClient {
|
|
|
2878
3576
|
}
|
|
2879
3577
|
const transformedRequest = transformDeleteRequest(request);
|
|
2880
3578
|
const endpoint = RECORD_ENDPOINTS.delete;
|
|
2881
|
-
|
|
3579
|
+
let url = `${this.baseURL}${buildRecordEndpointPath(endpoint, { table_id })}`;
|
|
3580
|
+
url = addDbIdToUrl(url, dbId);
|
|
2882
3581
|
const response = await this.httpAdapter.request({
|
|
2883
3582
|
url,
|
|
2884
3583
|
method: endpoint.method,
|
|
@@ -2894,11 +3593,14 @@ class RecordsApiClient {
|
|
|
2894
3593
|
/**
|
|
2895
3594
|
* Delete a single record by ID
|
|
2896
3595
|
*/
|
|
2897
|
-
async deleteRecordById(recordId, request) {
|
|
2898
|
-
return this.deleteRecords(
|
|
2899
|
-
|
|
2900
|
-
|
|
2901
|
-
|
|
3596
|
+
async deleteRecordById(recordId, request, dbId) {
|
|
3597
|
+
return this.deleteRecords(
|
|
3598
|
+
{
|
|
3599
|
+
record_ids: [recordId],
|
|
3600
|
+
table_id: request.table_id
|
|
3601
|
+
},
|
|
3602
|
+
dbId
|
|
3603
|
+
);
|
|
2902
3604
|
}
|
|
2903
3605
|
buildHeaders() {
|
|
2904
3606
|
return {
|
|
@@ -2961,9 +3663,9 @@ class RecordResource {
|
|
|
2961
3663
|
/**
|
|
2962
3664
|
* Insert a single record
|
|
2963
3665
|
*/
|
|
2964
|
-
async insert(tableName, data) {
|
|
3666
|
+
async insert(tableName, data, dbId) {
|
|
2965
3667
|
try {
|
|
2966
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3668
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
2967
3669
|
if (!tableInfo) {
|
|
2968
3670
|
return {
|
|
2969
3671
|
error: {
|
|
@@ -2983,7 +3685,7 @@ class RecordResource {
|
|
|
2983
3685
|
...completeDataResult,
|
|
2984
3686
|
table_id: tableInfo.id
|
|
2985
3687
|
};
|
|
2986
|
-
const result = await this.apiClient.insertRecord(requestData);
|
|
3688
|
+
const result = await this.apiClient.insertRecord(requestData, dbId);
|
|
2987
3689
|
if (isErrorResponse(result)) {
|
|
2988
3690
|
return result;
|
|
2989
3691
|
}
|
|
@@ -3000,7 +3702,7 @@ class RecordResource {
|
|
|
3000
3702
|
/**
|
|
3001
3703
|
* Insert multiple records in bulk
|
|
3002
3704
|
*/
|
|
3003
|
-
async insertMany(tableName, records, options = { validation: true }) {
|
|
3705
|
+
async insertMany(tableName, records, options = { validation: true }, dbId) {
|
|
3004
3706
|
try {
|
|
3005
3707
|
if (!records || !Array.isArray(records) || records.length === 0) {
|
|
3006
3708
|
return {
|
|
@@ -3010,7 +3712,7 @@ class RecordResource {
|
|
|
3010
3712
|
}
|
|
3011
3713
|
};
|
|
3012
3714
|
}
|
|
3013
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3715
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
3014
3716
|
if (!tableInfo) {
|
|
3015
3717
|
return {
|
|
3016
3718
|
error: {
|
|
@@ -3022,7 +3724,8 @@ class RecordResource {
|
|
|
3022
3724
|
const result = await this.apiClient.insertManyRecords(
|
|
3023
3725
|
records,
|
|
3024
3726
|
tableInfo.id,
|
|
3025
|
-
options
|
|
3727
|
+
options,
|
|
3728
|
+
dbId
|
|
3026
3729
|
);
|
|
3027
3730
|
if (isErrorResponse(result)) {
|
|
3028
3731
|
return result;
|
|
@@ -3040,9 +3743,9 @@ class RecordResource {
|
|
|
3040
3743
|
/**
|
|
3041
3744
|
* Get a single record by ID
|
|
3042
3745
|
*/
|
|
3043
|
-
async get(tableName, recordId) {
|
|
3746
|
+
async get(tableName, recordId, dbId) {
|
|
3044
3747
|
try {
|
|
3045
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3748
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
3046
3749
|
if (!tableInfo) {
|
|
3047
3750
|
return {
|
|
3048
3751
|
error: {
|
|
@@ -3051,7 +3754,12 @@ class RecordResource {
|
|
|
3051
3754
|
}
|
|
3052
3755
|
};
|
|
3053
3756
|
}
|
|
3054
|
-
const result = await this.apiClient.getRecord(
|
|
3757
|
+
const result = await this.apiClient.getRecord(
|
|
3758
|
+
recordId,
|
|
3759
|
+
tableInfo.id,
|
|
3760
|
+
{ fields: void 0 },
|
|
3761
|
+
dbId
|
|
3762
|
+
);
|
|
3055
3763
|
if (isErrorResponse(result)) {
|
|
3056
3764
|
return result;
|
|
3057
3765
|
}
|
|
@@ -3068,9 +3776,9 @@ class RecordResource {
|
|
|
3068
3776
|
/**
|
|
3069
3777
|
* List records with filtering and pagination
|
|
3070
3778
|
*/
|
|
3071
|
-
async list(tableName, options = {}) {
|
|
3779
|
+
async list(tableName, options = {}, dbId) {
|
|
3072
3780
|
try {
|
|
3073
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3781
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
3074
3782
|
if (!tableInfo) {
|
|
3075
3783
|
return {
|
|
3076
3784
|
error: {
|
|
@@ -3080,7 +3788,7 @@ class RecordResource {
|
|
|
3080
3788
|
};
|
|
3081
3789
|
}
|
|
3082
3790
|
const requestOptions = { ...options, table_id: tableInfo.id };
|
|
3083
|
-
const result = await this.apiClient.listRecords(requestOptions);
|
|
3791
|
+
const result = await this.apiClient.listRecords(requestOptions, dbId);
|
|
3084
3792
|
if (isErrorResponse(result)) {
|
|
3085
3793
|
return result;
|
|
3086
3794
|
}
|
|
@@ -3097,9 +3805,9 @@ class RecordResource {
|
|
|
3097
3805
|
/**
|
|
3098
3806
|
* Update records by filters
|
|
3099
3807
|
*/
|
|
3100
|
-
async update(tableName, options) {
|
|
3808
|
+
async update(tableName, options, dbId) {
|
|
3101
3809
|
try {
|
|
3102
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3810
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
3103
3811
|
if (!tableInfo) {
|
|
3104
3812
|
return {
|
|
3105
3813
|
error: {
|
|
@@ -3109,7 +3817,7 @@ class RecordResource {
|
|
|
3109
3817
|
};
|
|
3110
3818
|
}
|
|
3111
3819
|
const requestOptions = { ...options, table_id: tableInfo.id };
|
|
3112
|
-
const result = await this.apiClient.updateRecords(requestOptions);
|
|
3820
|
+
const result = await this.apiClient.updateRecords(requestOptions, dbId);
|
|
3113
3821
|
if (isErrorResponse(result)) {
|
|
3114
3822
|
return result;
|
|
3115
3823
|
}
|
|
@@ -3126,9 +3834,9 @@ class RecordResource {
|
|
|
3126
3834
|
/**
|
|
3127
3835
|
* Update a single record by ID
|
|
3128
3836
|
*/
|
|
3129
|
-
async updateById(tableName, recordId, data) {
|
|
3837
|
+
async updateById(tableName, recordId, data, dbId) {
|
|
3130
3838
|
try {
|
|
3131
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3839
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
3132
3840
|
if (!tableInfo) {
|
|
3133
3841
|
return {
|
|
3134
3842
|
error: {
|
|
@@ -3144,7 +3852,8 @@ class RecordResource {
|
|
|
3144
3852
|
};
|
|
3145
3853
|
const result = await this.apiClient.updateRecordById(
|
|
3146
3854
|
recordId,
|
|
3147
|
-
requestOptions
|
|
3855
|
+
requestOptions,
|
|
3856
|
+
dbId
|
|
3148
3857
|
);
|
|
3149
3858
|
if (isErrorResponse(result)) {
|
|
3150
3859
|
return result;
|
|
@@ -3162,9 +3871,9 @@ class RecordResource {
|
|
|
3162
3871
|
/**
|
|
3163
3872
|
* Unified delete method that supports both record IDs and filters
|
|
3164
3873
|
*/
|
|
3165
|
-
async delete(tableName, options) {
|
|
3874
|
+
async delete(tableName, options, dbId) {
|
|
3166
3875
|
try {
|
|
3167
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3876
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
3168
3877
|
if (!tableInfo) {
|
|
3169
3878
|
return {
|
|
3170
3879
|
error: {
|
|
@@ -3174,7 +3883,7 @@ class RecordResource {
|
|
|
3174
3883
|
};
|
|
3175
3884
|
}
|
|
3176
3885
|
const requestOptions = { ...options, table_id: tableInfo.id };
|
|
3177
|
-
const result = await this.apiClient.deleteRecords(requestOptions);
|
|
3886
|
+
const result = await this.apiClient.deleteRecords(requestOptions, dbId);
|
|
3178
3887
|
if (isErrorResponse(result)) {
|
|
3179
3888
|
return result;
|
|
3180
3889
|
}
|
|
@@ -3191,9 +3900,9 @@ class RecordResource {
|
|
|
3191
3900
|
/**
|
|
3192
3901
|
* Delete a single record by ID
|
|
3193
3902
|
*/
|
|
3194
|
-
async deleteById(tableName, recordId) {
|
|
3903
|
+
async deleteById(tableName, recordId, dbId) {
|
|
3195
3904
|
try {
|
|
3196
|
-
const tableInfo = await this.getTableInfo(tableName);
|
|
3905
|
+
const tableInfo = await this.getTableInfo(tableName, dbId);
|
|
3197
3906
|
if (!tableInfo) {
|
|
3198
3907
|
return {
|
|
3199
3908
|
error: {
|
|
@@ -3202,9 +3911,13 @@ class RecordResource {
|
|
|
3202
3911
|
}
|
|
3203
3912
|
};
|
|
3204
3913
|
}
|
|
3205
|
-
const result = await this.apiClient.deleteRecordById(
|
|
3206
|
-
|
|
3207
|
-
|
|
3914
|
+
const result = await this.apiClient.deleteRecordById(
|
|
3915
|
+
recordId,
|
|
3916
|
+
{
|
|
3917
|
+
table_id: tableInfo.id
|
|
3918
|
+
},
|
|
3919
|
+
dbId
|
|
3920
|
+
);
|
|
3208
3921
|
if (isErrorResponse(result)) {
|
|
3209
3922
|
return result;
|
|
3210
3923
|
}
|
|
@@ -3221,10 +3934,10 @@ class RecordResource {
|
|
|
3221
3934
|
/**
|
|
3222
3935
|
* Helper method to get table information by name
|
|
3223
3936
|
*/
|
|
3224
|
-
async getTableInfo(tableName) {
|
|
3937
|
+
async getTableInfo(tableName, dbId) {
|
|
3225
3938
|
try {
|
|
3226
3939
|
const tableResource = new TableResource(this.client);
|
|
3227
|
-
const tableResult = await tableResource.findByName(tableName);
|
|
3940
|
+
const tableResult = await tableResource.findByName(tableName, dbId);
|
|
3228
3941
|
if (tableResult.data) {
|
|
3229
3942
|
return {
|
|
3230
3943
|
id: tableResult.data.id,
|
|
@@ -3576,7 +4289,7 @@ class BaseApiClient {
|
|
|
3576
4289
|
};
|
|
3577
4290
|
}
|
|
3578
4291
|
// Custom inspect method for Node.js console logging
|
|
3579
|
-
[Symbol.for("nodejs.util.inspect.custom")]() {
|
|
4292
|
+
[/* @__PURE__ */ Symbol.for("nodejs.util.inspect.custom")]() {
|
|
3580
4293
|
return this.toString();
|
|
3581
4294
|
}
|
|
3582
4295
|
}
|
|
@@ -3587,10 +4300,13 @@ class SqlApiClient extends BaseApiClient {
|
|
|
3587
4300
|
/**
|
|
3588
4301
|
* Convert natural language to SQL query (streaming)
|
|
3589
4302
|
*/
|
|
3590
|
-
async textToSQL(request) {
|
|
4303
|
+
async textToSQL(request, dbId) {
|
|
3591
4304
|
try {
|
|
3592
4305
|
const endpoint = SQL_ENDPOINTS.textToSQL;
|
|
3593
|
-
|
|
4306
|
+
let url = `${this.baseURL}${buildSqlEndpointPath(endpoint)}`;
|
|
4307
|
+
if (dbId) {
|
|
4308
|
+
url += `?db_id=${encodeURIComponent(dbId)}`;
|
|
4309
|
+
}
|
|
3594
4310
|
const response = await this.httpAdapter.request({
|
|
3595
4311
|
url,
|
|
3596
4312
|
method: endpoint.method,
|
|
@@ -3615,10 +4331,13 @@ class SqlApiClient extends BaseApiClient {
|
|
|
3615
4331
|
/**
|
|
3616
4332
|
* Execute SQL query
|
|
3617
4333
|
*/
|
|
3618
|
-
async executeSQL(request) {
|
|
4334
|
+
async executeSQL(request, dbId) {
|
|
3619
4335
|
try {
|
|
3620
4336
|
const endpoint = SQL_ENDPOINTS.executeSQL;
|
|
3621
|
-
|
|
4337
|
+
let url = `${this.baseURL}${buildSqlEndpointPath(endpoint)}`;
|
|
4338
|
+
if (dbId) {
|
|
4339
|
+
url += `?db_id=${encodeURIComponent(dbId)}`;
|
|
4340
|
+
}
|
|
3622
4341
|
const response = await this.httpAdapter.request({
|
|
3623
4342
|
url,
|
|
3624
4343
|
method: endpoint.method,
|
|
@@ -3675,9 +4394,9 @@ class SqlResource {
|
|
|
3675
4394
|
* @returns AsyncIterable<string> for streaming SQL generation
|
|
3676
4395
|
*
|
|
3677
4396
|
*/
|
|
3678
|
-
async textToSQL(prompt, options = {}) {
|
|
4397
|
+
async textToSQL(prompt, options = {}, dbId) {
|
|
3679
4398
|
const request = transformTextToSQLRequest(prompt, options);
|
|
3680
|
-
const response = await this.sqlApiClient.textToSQL(request);
|
|
4399
|
+
const response = await this.sqlApiClient.textToSQL(request, dbId);
|
|
3681
4400
|
if ("error" in response && response.error !== void 0) {
|
|
3682
4401
|
throw response;
|
|
3683
4402
|
}
|
|
@@ -3690,8 +4409,8 @@ class SqlResource {
|
|
|
3690
4409
|
* @returns Promise<ExecuteSQLApiResponse> with raw API response following Boltic API Response Structure
|
|
3691
4410
|
*
|
|
3692
4411
|
*/
|
|
3693
|
-
async executeSQL(query) {
|
|
3694
|
-
const response = await this.sqlApiClient.executeSQL({ query });
|
|
4412
|
+
async executeSQL(query, dbId) {
|
|
4413
|
+
const response = await this.sqlApiClient.executeSQL({ query }, dbId);
|
|
3695
4414
|
if (isErrorResponse(response)) {
|
|
3696
4415
|
return response;
|
|
3697
4416
|
}
|
|
@@ -4040,25 +4759,75 @@ class BolticClient {
|
|
|
4040
4759
|
this.recordResource = new RecordResource(this.baseClient);
|
|
4041
4760
|
this.sqlResource = new SqlResource(this.baseClient);
|
|
4042
4761
|
this.indexResource = new IndexResource(this.baseClient);
|
|
4043
|
-
this.
|
|
4044
|
-
|
|
4045
|
-
};
|
|
4762
|
+
this.databaseResource = new DatabaseResource(this.baseClient);
|
|
4763
|
+
this.currentDatabase = null;
|
|
4046
4764
|
}
|
|
4765
|
+
/**
|
|
4766
|
+
* Get current database context
|
|
4767
|
+
*/
|
|
4047
4768
|
getCurrentDatabase() {
|
|
4048
4769
|
return this.currentDatabase;
|
|
4049
4770
|
}
|
|
4771
|
+
/**
|
|
4772
|
+
* Switch to a different database using its internal name (slug).
|
|
4773
|
+
* All subsequent operations will use this database.
|
|
4774
|
+
*
|
|
4775
|
+
* If no internal name is provided, the SDK will switch back to the default database.
|
|
4776
|
+
*
|
|
4777
|
+
* @param dbInternalName - Database internal name/slug to switch to. If omitted or empty, default DB is used.
|
|
4778
|
+
*
|
|
4779
|
+
* @example
|
|
4780
|
+
* ```typescript
|
|
4781
|
+
* // Switch to a specific database by slug
|
|
4782
|
+
* await client.useDatabase('my_database_slug');
|
|
4783
|
+
*
|
|
4784
|
+
* // Switch back to default database
|
|
4785
|
+
* await client.useDatabase();
|
|
4786
|
+
* ```
|
|
4787
|
+
*/
|
|
4788
|
+
async useDatabase(dbInternalName) {
|
|
4789
|
+
if (!dbInternalName || dbInternalName === "") {
|
|
4790
|
+
this.currentDatabase = null;
|
|
4791
|
+
return;
|
|
4792
|
+
}
|
|
4793
|
+
const result = await this.databaseResource.findOne(dbInternalName);
|
|
4794
|
+
if (isErrorResponse(result)) {
|
|
4795
|
+
throw new Error(
|
|
4796
|
+
result.error.message || `Failed to switch database to internal name '${dbInternalName}'`
|
|
4797
|
+
);
|
|
4798
|
+
}
|
|
4799
|
+
const db = result.data;
|
|
4800
|
+
this.currentDatabase = {
|
|
4801
|
+
databaseId: db.id,
|
|
4802
|
+
dbInternalName: db.db_internal_name || dbInternalName
|
|
4803
|
+
};
|
|
4804
|
+
}
|
|
4805
|
+
// Direct database operations
|
|
4806
|
+
get databases() {
|
|
4807
|
+
return {
|
|
4808
|
+
create: (data) => this.databaseResource.create(data),
|
|
4809
|
+
findAll: (options) => this.databaseResource.findAll(options),
|
|
4810
|
+
findOne: (dbInternalName, options) => this.databaseResource.findOne(dbInternalName, options),
|
|
4811
|
+
getDefault: () => this.databaseResource.getDefault(),
|
|
4812
|
+
update: (dbInternalName, data) => this.databaseResource.update(dbInternalName, data),
|
|
4813
|
+
delete: (dbInternalName) => this.databaseResource.delete(dbInternalName),
|
|
4814
|
+
listJobs: (options) => this.databaseResource.listJobs(options),
|
|
4815
|
+
pollDeleteStatus: (jobId) => this.databaseResource.pollDeleteStatus(jobId)
|
|
4816
|
+
};
|
|
4817
|
+
}
|
|
4050
4818
|
// Direct table operations
|
|
4051
4819
|
get tables() {
|
|
4820
|
+
const dbId = this.currentDatabase?.databaseId;
|
|
4052
4821
|
return {
|
|
4053
|
-
create: (data) => this.tableResource.create(data),
|
|
4054
|
-
findAll: (options) => this.tableResource.findAll(options),
|
|
4055
|
-
findById: (id) => this.tableResource.findById(id),
|
|
4056
|
-
findByName: (name) => this.tableResource.findByName(name),
|
|
4057
|
-
findOne: (options) => this.tableResource.findOne(options),
|
|
4058
|
-
update: (name, data) => this.tableResource.update(name, data),
|
|
4059
|
-
delete: (name) => this.tableResource.delete(name),
|
|
4060
|
-
rename: (oldName, newName) => this.tableResource.rename(oldName, newName),
|
|
4061
|
-
setAccess: (request) => this.tableResource.setAccess(request)
|
|
4822
|
+
create: (data) => this.tableResource.create(data, dbId),
|
|
4823
|
+
findAll: (options) => this.tableResource.findAll(options, dbId),
|
|
4824
|
+
findById: (id) => this.tableResource.findById(id, dbId),
|
|
4825
|
+
findByName: (name) => this.tableResource.findByName(name, dbId),
|
|
4826
|
+
findOne: (options) => this.tableResource.findOne(options, dbId),
|
|
4827
|
+
update: (name, data) => this.tableResource.update(name, data, dbId),
|
|
4828
|
+
delete: (name) => this.tableResource.delete(name, dbId),
|
|
4829
|
+
rename: (oldName, newName) => this.tableResource.rename(oldName, newName, dbId),
|
|
4830
|
+
setAccess: (request) => this.tableResource.setAccess(request, dbId)
|
|
4062
4831
|
};
|
|
4063
4832
|
}
|
|
4064
4833
|
// Direct column operations
|
|
@@ -4086,53 +4855,40 @@ class BolticClient {
|
|
|
4086
4855
|
const tableBuilder = createTableBuilder({ name });
|
|
4087
4856
|
return tableBuilder;
|
|
4088
4857
|
}
|
|
4089
|
-
//
|
|
4858
|
+
// Table-scoped operations for method chaining
|
|
4090
4859
|
from(tableName) {
|
|
4860
|
+
const dbId = this.currentDatabase?.databaseId;
|
|
4091
4861
|
return {
|
|
4092
|
-
//
|
|
4093
|
-
|
|
4094
|
-
|
|
4095
|
-
|
|
4096
|
-
|
|
4097
|
-
update: (columnName, updates) => this.columnResource.update(tableName, columnName, updates),
|
|
4098
|
-
delete: (columnName) => this.columnResource.delete(tableName, columnName)
|
|
4862
|
+
// Index operations for this table
|
|
4863
|
+
indexes: () => ({
|
|
4864
|
+
addIndex: (payload) => this.indexResource.addIndex(tableName, payload, dbId),
|
|
4865
|
+
listIndexes: (query) => this.indexResource.listIndexes(tableName, query, dbId),
|
|
4866
|
+
deleteIndex: (indexName) => this.indexResource.deleteIndex(tableName, indexName, dbId)
|
|
4099
4867
|
}),
|
|
4100
4868
|
// Record operations for this table
|
|
4101
4869
|
records: () => ({
|
|
4102
|
-
insert: (data) => this.recordResource.insert(tableName, data),
|
|
4103
|
-
insertMany: (records, options) => this.recordResource.insertMany(tableName, records, options),
|
|
4104
|
-
findOne: (recordId) => this.recordResource.get(tableName, recordId),
|
|
4105
|
-
update: (options) => this.recordResource.update(tableName, options),
|
|
4106
|
-
updateById: (recordId, data) => this.recordResource.updateById(tableName, recordId, data),
|
|
4107
|
-
|
|
4108
|
-
|
|
4109
|
-
// Single record delete method
|
|
4110
|
-
deleteById: (recordId) => this.recordResource.deleteById(tableName, recordId)
|
|
4111
|
-
}),
|
|
4112
|
-
// Fluent record builder for this table
|
|
4113
|
-
record: () => createRecordBuilder({
|
|
4114
|
-
tableName,
|
|
4115
|
-
recordResource: this.recordResource
|
|
4116
|
-
}),
|
|
4117
|
-
// Indexes - Method 2: Function chaining under from(tableName)
|
|
4118
|
-
indexes: () => ({
|
|
4119
|
-
addIndex: (payload) => this.indexResource.addIndex(tableName, payload),
|
|
4120
|
-
listIndexes: (query) => this.indexResource.listIndexes(tableName, query),
|
|
4121
|
-
deleteIndex: (indexName) => this.indexResource.deleteIndex(tableName, indexName)
|
|
4870
|
+
insert: (data) => this.recordResource.insert(tableName, data, dbId),
|
|
4871
|
+
insertMany: (records, options) => this.recordResource.insertMany(tableName, records, options, dbId),
|
|
4872
|
+
findOne: (recordId) => this.recordResource.get(tableName, recordId, dbId),
|
|
4873
|
+
update: (options) => this.recordResource.update(tableName, options, dbId),
|
|
4874
|
+
updateById: (recordId, data) => this.recordResource.updateById(tableName, recordId, data, dbId),
|
|
4875
|
+
delete: (options) => this.recordResource.delete(tableName, options, dbId),
|
|
4876
|
+
deleteById: (recordId) => this.recordResource.deleteById(tableName, recordId, dbId)
|
|
4122
4877
|
})
|
|
4123
4878
|
};
|
|
4124
4879
|
}
|
|
4125
4880
|
// Direct record operations
|
|
4126
4881
|
get records() {
|
|
4882
|
+
const dbId = this.currentDatabase?.databaseId;
|
|
4127
4883
|
return {
|
|
4128
|
-
insert: (tableName, data) => this.recordResource.insert(tableName, data),
|
|
4129
|
-
insertMany: (tableName, records, options) => this.recordResource.insertMany(tableName, records, options),
|
|
4130
|
-
findAll: (tableName, options) => this.recordResource.list(tableName, options),
|
|
4131
|
-
findOne: (tableName, recordId) => this.recordResource.get(tableName, recordId),
|
|
4132
|
-
update: (tableName, options) => this.recordResource.update(tableName, options),
|
|
4133
|
-
updateById: (tableName, recordId, data) => this.recordResource.updateById(tableName, recordId, data),
|
|
4134
|
-
delete: (tableName, options) => this.recordResource.delete(tableName, options),
|
|
4135
|
-
deleteById: (tableName, recordId) => this.recordResource.deleteById(tableName, recordId)
|
|
4884
|
+
insert: (tableName, data) => this.recordResource.insert(tableName, data, dbId),
|
|
4885
|
+
insertMany: (tableName, records, options) => this.recordResource.insertMany(tableName, records, options, dbId),
|
|
4886
|
+
findAll: (tableName, options) => this.recordResource.list(tableName, options, dbId),
|
|
4887
|
+
findOne: (tableName, recordId) => this.recordResource.get(tableName, recordId, dbId),
|
|
4888
|
+
update: (tableName, options) => this.recordResource.update(tableName, options, dbId),
|
|
4889
|
+
updateById: (tableName, recordId, data) => this.recordResource.updateById(tableName, recordId, data, dbId),
|
|
4890
|
+
delete: (tableName, options) => this.recordResource.delete(tableName, options, dbId),
|
|
4891
|
+
deleteById: (tableName, recordId) => this.recordResource.deleteById(tableName, recordId, dbId)
|
|
4136
4892
|
};
|
|
4137
4893
|
}
|
|
4138
4894
|
// Method 4: Create fluent record builder
|
|
@@ -4144,9 +4900,10 @@ class BolticClient {
|
|
|
4144
4900
|
}
|
|
4145
4901
|
// Direct SQL operations
|
|
4146
4902
|
get sql() {
|
|
4903
|
+
const dbId = this.currentDatabase?.databaseId;
|
|
4147
4904
|
return {
|
|
4148
|
-
textToSQL: (prompt, options) => this.sqlResource.textToSQL(prompt, options),
|
|
4149
|
-
executeSQL: (query) => this.sqlResource.executeSQL(query)
|
|
4905
|
+
textToSQL: (prompt, options) => this.sqlResource.textToSQL(prompt, options, dbId),
|
|
4906
|
+
executeSQL: (query) => this.sqlResource.executeSQL(query, dbId)
|
|
4150
4907
|
};
|
|
4151
4908
|
}
|
|
4152
4909
|
// SQL resource access for testing
|
|
@@ -4230,6 +4987,7 @@ class BolticClient {
|
|
|
4230
4987
|
this.recordResource = new RecordResource(this.baseClient);
|
|
4231
4988
|
this.sqlResource = new SqlResource(this.baseClient);
|
|
4232
4989
|
this.indexResource = new IndexResource(this.baseClient);
|
|
4990
|
+
this.databaseResource = new DatabaseResource(this.baseClient);
|
|
4233
4991
|
}
|
|
4234
4992
|
// Security methods to prevent API key exposure
|
|
4235
4993
|
toString() {
|
|
@@ -4247,7 +5005,7 @@ class BolticClient {
|
|
|
4247
5005
|
};
|
|
4248
5006
|
}
|
|
4249
5007
|
// Custom inspect method for Node.js console logging
|
|
4250
|
-
[Symbol.for("nodejs.util.inspect.custom")]() {
|
|
5008
|
+
[/* @__PURE__ */ Symbol.for("nodejs.util.inspect.custom")]() {
|
|
4251
5009
|
return this.toString();
|
|
4252
5010
|
}
|
|
4253
5011
|
}
|