@budibase/server 2.4.26 → 2.4.27-alpha.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/builder/assets/{index.b0e3aca6.css → index.68ae453c.css} +2 -2
- package/builder/assets/{index.9e2f47ef.js → index.a661155b.js} +351 -350
- package/builder/index.html +2 -2
- package/dist/api/controllers/datasource.js +2 -1
- package/dist/api/controllers/public/metrics.js +113 -0
- package/dist/api/controllers/row/external.js +16 -8
- package/dist/api/controllers/row/index.js +5 -1
- package/dist/api/controllers/row/internal.js +1 -10
- package/dist/api/controllers/row/utils.js +3 -4
- package/dist/api/controllers/table/external.js +16 -12
- package/dist/api/controllers/table/utils.js +15 -1
- package/dist/api/routes/public/index.js +8 -0
- package/dist/api/routes/public/metrics.js +30 -0
- package/dist/constants/index.js +2 -1
- package/dist/integrations/googlesheets.js +125 -59
- package/dist/integrations/utils.js +17 -2
- package/dist/package.json +7 -7
- package/dist/tsconfig.build.tsbuildinfo +1 -1
- package/package.json +8 -8
- package/specs/openapi.json +39 -0
- package/specs/openapi.yaml +169 -0
- package/specs/resources/application.ts +11 -0
- package/specs/resources/index.ts +2 -0
- package/specs/resources/metrics.ts +81 -0
- package/src/api/controllers/datasource.ts +2 -1
- package/src/api/controllers/public/metrics.ts +251 -0
- package/src/api/controllers/row/external.ts +26 -16
- package/src/api/controllers/row/index.ts +7 -2
- package/src/api/controllers/row/internal.ts +0 -7
- package/src/api/controllers/row/utils.ts +3 -4
- package/src/api/controllers/table/external.ts +24 -17
- package/src/api/controllers/table/index.ts +9 -9
- package/src/api/controllers/table/utils.ts +18 -2
- package/src/api/routes/public/index.ts +10 -1
- package/src/api/routes/public/metrics.ts +28 -0
- package/src/api/routes/public/tests/metrics.spec.js +34 -0
- package/src/constants/index.ts +1 -0
- package/src/definitions/openapi.ts +15 -0
- package/src/integrations/googlesheets.ts +143 -71
- package/src/integrations/utils.ts +16 -4
package/builder/index.html
CHANGED
|
@@ -10,8 +10,8 @@
|
|
|
10
10
|
href="https://fonts.googleapis.com/css2?family=Source+Sans+Pro:wght@400;600;700&display=swap"
|
|
11
11
|
rel="stylesheet"
|
|
12
12
|
/>
|
|
13
|
-
<script type="module" crossorigin src="/builder/assets/index.
|
|
14
|
-
<link rel="stylesheet" href="/builder/assets/index.
|
|
13
|
+
<script type="module" crossorigin src="/builder/assets/index.a661155b.js"></script>
|
|
14
|
+
<link rel="stylesheet" href="/builder/assets/index.68ae453c.css">
|
|
15
15
|
</head>
|
|
16
16
|
<body id="app">
|
|
17
17
|
|
|
@@ -74,7 +74,8 @@ function buildSchemaFromDb(ctx) {
|
|
|
74
74
|
setDefaultDisplayColumns(datasource);
|
|
75
75
|
const dbResp = yield db.put(datasource);
|
|
76
76
|
datasource._rev = dbResp.rev;
|
|
77
|
-
const
|
|
77
|
+
const cleanedDatasource = yield sdk_1.default.datasources.removeSecretSingle(datasource);
|
|
78
|
+
const response = { datasource: cleanedDatasource };
|
|
78
79
|
if (error) {
|
|
79
80
|
response.error = error;
|
|
80
81
|
}
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
3
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
4
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
5
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
6
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
7
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
8
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
9
|
+
});
|
|
10
|
+
};
|
|
11
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
12
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
13
|
+
};
|
|
14
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
+
exports.convertToOpenMetrics = exports.fetch = void 0;
|
|
16
|
+
const backend_core_1 = require("@budibase/backend-core");
|
|
17
|
+
const pro_1 = require("@budibase/pro");
|
|
18
|
+
const os_1 = __importDefault(require("os"));
|
|
19
|
+
function fetch(ctx) {
|
|
20
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
21
|
+
// *** OPERATING SYSTEM ***
|
|
22
|
+
const freeMem = os_1.default.freemem();
|
|
23
|
+
const totalMem = os_1.default.totalmem();
|
|
24
|
+
const usedMem = totalMem - freeMem;
|
|
25
|
+
const uptime = os_1.default.uptime();
|
|
26
|
+
// *** APPS ***
|
|
27
|
+
const allDatabases = yield backend_core_1.db.getAllDbs();
|
|
28
|
+
const devAppIDs = yield backend_core_1.db.getDevAppIDs();
|
|
29
|
+
const prodAppIDs = yield backend_core_1.db.getProdAppIDs();
|
|
30
|
+
const allAppIds = yield backend_core_1.db.getAllApps({ idsOnly: true });
|
|
31
|
+
// *** USERS ***
|
|
32
|
+
const usersObject = yield backend_core_1.users.getAllUserIds();
|
|
33
|
+
// *** QUOTAS ***
|
|
34
|
+
const usage = yield pro_1.quotas.getQuotaUsage();
|
|
35
|
+
const license = yield pro_1.licensing.cache.getCachedLicense();
|
|
36
|
+
const appsQuotaUsage = usage.usageQuota.apps;
|
|
37
|
+
const rowsQuotaUsage = usage.usageQuota.rows;
|
|
38
|
+
const pluginsQuotaUsage = usage.usageQuota.plugins;
|
|
39
|
+
const userGroupsQuotaUsage = usage.usageQuota.userGroups;
|
|
40
|
+
const queryQuotaUsage = usage.monthly.current.queries;
|
|
41
|
+
const automationsQuotaUsage = usage.monthly.current.automations;
|
|
42
|
+
const appsQuotaLimit = license.quotas.usage.static.apps.value;
|
|
43
|
+
const rowsQuotaLimit = license.quotas.usage.static.rows.value;
|
|
44
|
+
const userGroupsQuotaLimit = license.quotas.usage.static.userGroups.value;
|
|
45
|
+
const pluginsQuotaLimit = license.quotas.usage.static.plugins.value;
|
|
46
|
+
const queryQuotaLimit = license.quotas.usage.monthly.queries.value;
|
|
47
|
+
const automationsQuotaLimit = license.quotas.usage.monthly.automations.value;
|
|
48
|
+
// *** BUILD THE OUTPUT STRING ***
|
|
49
|
+
var outputString = "";
|
|
50
|
+
// **** budibase_os_uptime ****
|
|
51
|
+
outputString += convertToOpenMetrics("budibase_os_uptime", "Time in seconds that the host operating system has been up", "counter", uptime);
|
|
52
|
+
// **** budibase_os_free_mem ****
|
|
53
|
+
outputString += convertToOpenMetrics("budibase_os_free_mem", "Bytes of memory free for usage on the host operating system", "gauge", freeMem);
|
|
54
|
+
// **** budibase_os_total_mem ****
|
|
55
|
+
outputString += convertToOpenMetrics("budibase_os_total_mem", "Total bytes of memory on the host operating system", "gauge", totalMem);
|
|
56
|
+
// **** budibase_os_used_mem ****
|
|
57
|
+
outputString += convertToOpenMetrics("budibase_os_used_mem", "Total bytes of memory in use on the host operating system", "gauge", usedMem);
|
|
58
|
+
// **** budibase_os_load1 ****
|
|
59
|
+
outputString += convertToOpenMetrics("budibase_os_load1", "Host operating system load average", "gauge", os_1.default.loadavg()[0]);
|
|
60
|
+
// **** budibase_os_load5 ****
|
|
61
|
+
outputString += convertToOpenMetrics("budibase_os_load5", "Host operating system load average", "gauge", os_1.default.loadavg()[1]);
|
|
62
|
+
// **** budibase_os_load15 ****
|
|
63
|
+
outputString += convertToOpenMetrics("budibase_os_load15", "Host operating system load average", "gauge", os_1.default.loadavg()[2]);
|
|
64
|
+
// **** budibase_tenant_user_count ****
|
|
65
|
+
outputString += convertToOpenMetrics("budibase_tenant_user_count", "The number of users created", "gauge", usersObject.length);
|
|
66
|
+
// **** budibase_tenant_app_count ****
|
|
67
|
+
outputString += convertToOpenMetrics("budibase_tenant_app_count", "The number of apps created by a user", "gauge", allAppIds.length);
|
|
68
|
+
// **** budibase_tenant_production_app_count ****
|
|
69
|
+
outputString += convertToOpenMetrics("budibase_tenant_production_app_count", "The number of apps a user has published", "gauge", prodAppIDs.length);
|
|
70
|
+
// **** budibase_tenant_dev_app_count ****
|
|
71
|
+
outputString += convertToOpenMetrics("budibase_tenant_dev_app_count", "The number of apps a user has unpublished in development", "gauge", devAppIDs.length);
|
|
72
|
+
// **** budibase_tenant_db_count ****
|
|
73
|
+
outputString += convertToOpenMetrics("budibase_tenant_db_count", "The number of couchdb databases including global tables such as _users", "gauge", allDatabases.length);
|
|
74
|
+
// **** budibase_quota_usage_apps ****
|
|
75
|
+
outputString += convertToOpenMetrics("budibase_quota_usage_apps", "The number of apps created", "gauge", appsQuotaUsage);
|
|
76
|
+
// **** budibase_quota_limit_apps ****
|
|
77
|
+
outputString += convertToOpenMetrics("budibase_quota_limit_apps", "The limit on the number of apps that can be created", "gauge", appsQuotaLimit == -1 ? Number.MAX_SAFE_INTEGER : appsQuotaLimit);
|
|
78
|
+
// **** budibase_quota_usage_rows ****
|
|
79
|
+
outputString += convertToOpenMetrics("budibase_quota_usage_rows", "The number of database rows used from the quota", "gauge", rowsQuotaUsage);
|
|
80
|
+
// **** budibase_quota_limit_rows ****
|
|
81
|
+
outputString += convertToOpenMetrics("budibase_quota_limit_rows", "The limit on the number of rows that can be created", "gauge", rowsQuotaLimit == -1 ? Number.MAX_SAFE_INTEGER : rowsQuotaLimit);
|
|
82
|
+
// **** budibase_quota_usage_plugins ****
|
|
83
|
+
outputString += convertToOpenMetrics("budibase_quota_usage_plugins", "The number of plugins in use", "gauge", pluginsQuotaUsage);
|
|
84
|
+
// **** budibase_quota_limit_plugins ****
|
|
85
|
+
outputString += convertToOpenMetrics("budibase_quota_limit_plugins", "The limit on the number of plugins that can be created", "gauge", pluginsQuotaLimit == -1 ? Number.MAX_SAFE_INTEGER : pluginsQuotaLimit);
|
|
86
|
+
// **** budibase_quota_usage_user_groups ****
|
|
87
|
+
outputString += convertToOpenMetrics("budibase_quota_usage_user_groups", "The number of user groups created", "gauge", userGroupsQuotaUsage);
|
|
88
|
+
// **** budibase_quota_limit_user_groups ****
|
|
89
|
+
outputString += convertToOpenMetrics("budibase_quota_limit_user_groups", "The limit on the number of user groups that can be created", "gauge", userGroupsQuotaLimit == -1 ? Number.MAX_SAFE_INTEGER : userGroupsQuotaLimit);
|
|
90
|
+
// **** budibase_quota_usage_queries ****
|
|
91
|
+
outputString += convertToOpenMetrics("budibase_quota_usage_queries", "The number of queries used in the current month", "gauge", queryQuotaUsage);
|
|
92
|
+
// **** budibase_quota_limit_queries ****
|
|
93
|
+
outputString += convertToOpenMetrics("budibase_quota_limit_queries", "The limit on the number of queries for the current month", "gauge", queryQuotaLimit == -1 ? Number.MAX_SAFE_INTEGER : queryQuotaLimit);
|
|
94
|
+
// **** budibase_quota_usage_automations ****
|
|
95
|
+
outputString += convertToOpenMetrics("budibase_quota_usage_automations", "The number of automations used in the current month", "gauge", automationsQuotaUsage);
|
|
96
|
+
// **** budibase_quota_limit_automations ****
|
|
97
|
+
outputString += convertToOpenMetrics("budibase_quota_limit_automations", "The limit on the number of automations that can be created", "gauge", automationsQuotaLimit == -1
|
|
98
|
+
? Number.MAX_SAFE_INTEGER
|
|
99
|
+
: automationsQuotaLimit);
|
|
100
|
+
ctx.body = outputString;
|
|
101
|
+
ctx.set("Content-Type", "text/plain");
|
|
102
|
+
});
|
|
103
|
+
}
|
|
104
|
+
exports.fetch = fetch;
|
|
105
|
+
function convertToOpenMetrics(metricName, metricHelp, metricType, metricValue) {
|
|
106
|
+
return `# HELP ${metricName} ${metricHelp}.
|
|
107
|
+
# TYPE ${metricName} ${metricType}
|
|
108
|
+
${metricName} ${metricValue}\n`;
|
|
109
|
+
}
|
|
110
|
+
exports.convertToOpenMetrics = convertToOpenMetrics;
|
|
111
|
+
exports.default = {
|
|
112
|
+
fetch,
|
|
113
|
+
};
|
|
@@ -46,7 +46,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
46
46
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
47
47
|
};
|
|
48
48
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
49
|
-
exports.fetchEnrichedRow = exports.exportRows = exports.
|
|
49
|
+
exports.fetchEnrichedRow = exports.exportRows = exports.search = exports.bulkDestroy = exports.destroy = exports.find = exports.fetch = exports.fetchView = exports.save = exports.patch = exports.handleRequest = void 0;
|
|
50
50
|
const constants_1 = require("../../../constants");
|
|
51
51
|
const utils_1 = require("../../../integrations/utils");
|
|
52
52
|
const ExternalRequest_1 = require("./ExternalRequest");
|
|
@@ -54,6 +54,7 @@ const exporters = __importStar(require("../view/exporters"));
|
|
|
54
54
|
const fileSystem_1 = require("../../../utilities/fileSystem");
|
|
55
55
|
const types_1 = require("@budibase/types");
|
|
56
56
|
const sdk_1 = __importDefault(require("../../../sdk"));
|
|
57
|
+
const utils = __importStar(require("./utils"));
|
|
57
58
|
const { cleanExportRows } = require("./utils");
|
|
58
59
|
function handleRequest(operation, tableId, opts) {
|
|
59
60
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -83,6 +84,13 @@ function patch(ctx) {
|
|
|
83
84
|
const id = inputs._id;
|
|
84
85
|
// don't save the ID to db
|
|
85
86
|
delete inputs._id;
|
|
87
|
+
const validateResult = yield utils.validate({
|
|
88
|
+
row: inputs,
|
|
89
|
+
tableId,
|
|
90
|
+
});
|
|
91
|
+
if (!validateResult.valid) {
|
|
92
|
+
throw { validation: validateResult.errors };
|
|
93
|
+
}
|
|
86
94
|
return handleRequest(types_1.Operation.UPDATE, tableId, {
|
|
87
95
|
id: (0, utils_1.breakRowIdField)(id),
|
|
88
96
|
row: inputs,
|
|
@@ -95,6 +103,13 @@ function save(ctx) {
|
|
|
95
103
|
return __awaiter(this, void 0, void 0, function* () {
|
|
96
104
|
const inputs = ctx.request.body;
|
|
97
105
|
const tableId = ctx.params.tableId;
|
|
106
|
+
const validateResult = yield utils.validate({
|
|
107
|
+
row: inputs,
|
|
108
|
+
tableId,
|
|
109
|
+
});
|
|
110
|
+
if (!validateResult.valid) {
|
|
111
|
+
throw { validation: validateResult.errors };
|
|
112
|
+
}
|
|
98
113
|
return handleRequest(types_1.Operation.CREATE, tableId, {
|
|
99
114
|
row: inputs,
|
|
100
115
|
includeSqlRelationships: types_1.IncludeRelationship.EXCLUDE,
|
|
@@ -225,13 +240,6 @@ function search(ctx) {
|
|
|
225
240
|
});
|
|
226
241
|
}
|
|
227
242
|
exports.search = search;
|
|
228
|
-
function validate(ctx) {
|
|
229
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
230
|
-
// can't validate external right now - maybe in future
|
|
231
|
-
return { valid: true };
|
|
232
|
-
});
|
|
233
|
-
}
|
|
234
|
-
exports.validate = validate;
|
|
235
243
|
function exportRows(ctx) {
|
|
236
244
|
return __awaiter(this, void 0, void 0, function* () {
|
|
237
245
|
const { datasourceId, tableName } = (0, utils_1.breakExternalTableId)(ctx.params.tableId);
|
|
@@ -37,6 +37,7 @@ const pro_1 = require("@budibase/pro");
|
|
|
37
37
|
const internal = __importStar(require("./internal"));
|
|
38
38
|
const external = __importStar(require("./external"));
|
|
39
39
|
const utils_1 = require("../../../integrations/utils");
|
|
40
|
+
const utils = __importStar(require("./utils"));
|
|
40
41
|
function pickApi(tableId) {
|
|
41
42
|
if ((0, utils_1.isExternalTable)(tableId)) {
|
|
42
43
|
return external;
|
|
@@ -171,7 +172,10 @@ exports.search = search;
|
|
|
171
172
|
function validate(ctx) {
|
|
172
173
|
return __awaiter(this, void 0, void 0, function* () {
|
|
173
174
|
const tableId = getTableId(ctx);
|
|
174
|
-
ctx.body = yield
|
|
175
|
+
ctx.body = yield utils.validate({
|
|
176
|
+
row: ctx.request.body,
|
|
177
|
+
tableId,
|
|
178
|
+
});
|
|
175
179
|
});
|
|
176
180
|
}
|
|
177
181
|
exports.validate = validate;
|
|
@@ -46,7 +46,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
46
46
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
47
47
|
};
|
|
48
48
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
49
|
-
exports.fetchEnrichedRow = exports.exportRows = exports.
|
|
49
|
+
exports.fetchEnrichedRow = exports.exportRows = exports.search = exports.bulkDestroy = exports.destroy = exports.find = exports.fetch = exports.fetchView = exports.save = exports.patch = void 0;
|
|
50
50
|
const linkRows = __importStar(require("../../../db/linkedRows"));
|
|
51
51
|
const utils_1 = require("../../../db/utils");
|
|
52
52
|
const userController = __importStar(require("../user"));
|
|
@@ -392,15 +392,6 @@ function search(ctx) {
|
|
|
392
392
|
});
|
|
393
393
|
}
|
|
394
394
|
exports.search = search;
|
|
395
|
-
function validate(ctx) {
|
|
396
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
397
|
-
return utils.validate({
|
|
398
|
-
tableId: ctx.params.tableId,
|
|
399
|
-
row: ctx.request.body,
|
|
400
|
-
});
|
|
401
|
-
});
|
|
402
|
-
}
|
|
403
|
-
exports.validate = validate;
|
|
404
395
|
function exportRows(ctx) {
|
|
405
396
|
return __awaiter(this, void 0, void 0, function* () {
|
|
406
397
|
const db = backend_core_1.context.getAppDB();
|
|
@@ -41,10 +41,10 @@ const userController = __importStar(require("../user"));
|
|
|
41
41
|
const constants_1 = require("../../../constants");
|
|
42
42
|
const backend_core_1 = require("@budibase/backend-core");
|
|
43
43
|
const query_1 = require("../../../integrations/base/query");
|
|
44
|
-
const validateJs = require("validate.js");
|
|
45
|
-
const { cloneDeep } = require("lodash/fp");
|
|
46
44
|
const exporters_1 = require("../view/exporters");
|
|
47
45
|
const sdk_1 = __importDefault(require("../../../sdk"));
|
|
46
|
+
const validateJs = require("validate.js");
|
|
47
|
+
const { cloneDeep } = require("lodash/fp");
|
|
48
48
|
validateJs.extend(validateJs.validators.datetime, {
|
|
49
49
|
parse: function (value) {
|
|
50
50
|
return new Date(value).getTime();
|
|
@@ -88,8 +88,7 @@ function validate({ tableId, row, table, }) {
|
|
|
88
88
|
return __awaiter(this, void 0, void 0, function* () {
|
|
89
89
|
let fetchedTable;
|
|
90
90
|
if (!table) {
|
|
91
|
-
|
|
92
|
-
fetchedTable = yield db.get(tableId);
|
|
91
|
+
fetchedTable = yield sdk_1.default.tables.getTable(tableId);
|
|
93
92
|
}
|
|
94
93
|
else {
|
|
95
94
|
fetchedTable = table;
|
|
@@ -150,16 +150,16 @@ function isRelationshipSetup(column) {
|
|
|
150
150
|
}
|
|
151
151
|
function save(ctx) {
|
|
152
152
|
return __awaiter(this, void 0, void 0, function* () {
|
|
153
|
-
const
|
|
154
|
-
const renamed =
|
|
153
|
+
const inputs = ctx.request.body;
|
|
154
|
+
const renamed = inputs === null || inputs === void 0 ? void 0 : inputs._rename;
|
|
155
155
|
// can't do this right now
|
|
156
|
-
delete
|
|
156
|
+
delete inputs.rows;
|
|
157
157
|
const datasourceId = getDatasourceId(ctx.request.body);
|
|
158
158
|
// table doesn't exist already, note that it is created
|
|
159
|
-
if (!
|
|
160
|
-
|
|
159
|
+
if (!inputs._id) {
|
|
160
|
+
inputs.created = true;
|
|
161
161
|
}
|
|
162
|
-
let tableToSave = Object.assign({ type: "table", _id: (0, utils_1.buildExternalTableId)(datasourceId,
|
|
162
|
+
let tableToSave = Object.assign({ type: "table", _id: (0, utils_1.buildExternalTableId)(datasourceId, inputs.name) }, inputs);
|
|
163
163
|
let oldTable;
|
|
164
164
|
if (ctx.request.body && ctx.request.body._id) {
|
|
165
165
|
oldTable = yield sdk_1.default.tables.getTable(ctx.request.body._id);
|
|
@@ -172,6 +172,8 @@ function save(ctx) {
|
|
|
172
172
|
if (!datasource.entities) {
|
|
173
173
|
datasource.entities = {};
|
|
174
174
|
}
|
|
175
|
+
// GSheets is a specific case - only ever has a static primary key
|
|
176
|
+
tableToSave = (0, utils_2.setStaticSchemas)(datasource, tableToSave);
|
|
175
177
|
const oldTables = cloneDeep(datasource.entities);
|
|
176
178
|
const tables = datasource.entities;
|
|
177
179
|
const extraTablesToUpdate = [];
|
|
@@ -187,7 +189,7 @@ function save(ctx) {
|
|
|
187
189
|
const relatedColumnName = schema.fieldName;
|
|
188
190
|
const relationType = schema.relationshipType;
|
|
189
191
|
if (relationType === types_1.RelationshipTypes.MANY_TO_MANY) {
|
|
190
|
-
const junctionTable = generateManyLinkSchema(datasource, schema,
|
|
192
|
+
const junctionTable = generateManyLinkSchema(datasource, schema, tableToSave, relatedTable);
|
|
191
193
|
if (tables[junctionTable.name]) {
|
|
192
194
|
throw "Junction table already exists, cannot create another relationship.";
|
|
193
195
|
}
|
|
@@ -195,8 +197,10 @@ function save(ctx) {
|
|
|
195
197
|
extraTablesToUpdate.push(junctionTable);
|
|
196
198
|
}
|
|
197
199
|
else {
|
|
198
|
-
const fkTable = relationType === types_1.RelationshipTypes.ONE_TO_MANY
|
|
199
|
-
|
|
200
|
+
const fkTable = relationType === types_1.RelationshipTypes.ONE_TO_MANY
|
|
201
|
+
? tableToSave
|
|
202
|
+
: relatedTable;
|
|
203
|
+
const foreignKey = generateLinkSchema(schema, tableToSave, relatedTable, relationType);
|
|
200
204
|
fkTable.schema[foreignKey] = (0, utils_2.foreignKeyStructure)(foreignKey);
|
|
201
205
|
if (fkTable.constrained == null) {
|
|
202
206
|
fkTable.constrained = [];
|
|
@@ -205,11 +209,11 @@ function save(ctx) {
|
|
|
205
209
|
fkTable.constrained.push(foreignKey);
|
|
206
210
|
}
|
|
207
211
|
// foreign key is in other table, need to save it to external
|
|
208
|
-
if (fkTable._id !==
|
|
212
|
+
if (fkTable._id !== tableToSave._id) {
|
|
209
213
|
extraTablesToUpdate.push(fkTable);
|
|
210
214
|
}
|
|
211
215
|
}
|
|
212
|
-
generateRelatedSchema(schema, relatedTable,
|
|
216
|
+
generateRelatedSchema(schema, relatedTable, tableToSave, relatedColumnName);
|
|
213
217
|
schema.main = true;
|
|
214
218
|
}
|
|
215
219
|
cleanupRelationships(tableToSave, tables, oldTable);
|
|
@@ -264,7 +268,7 @@ function bulkImport(ctx) {
|
|
|
264
268
|
if (!rows || !(0, schema_1.isRows)(rows) || !(0, schema_1.isSchema)(schema)) {
|
|
265
269
|
ctx.throw(400, "Provided data import information is invalid.");
|
|
266
270
|
}
|
|
267
|
-
const parsedRows =
|
|
271
|
+
const parsedRows = (0, schema_1.parse)(rows, schema);
|
|
268
272
|
yield (0, external_1.handleRequest)(types_1.Operation.BULK_CREATE, table._id, {
|
|
269
273
|
rows: parsedRows,
|
|
270
274
|
});
|
|
@@ -12,7 +12,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
12
12
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
13
13
|
};
|
|
14
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
-
exports.TableSaveFunctions = exports.hasTypeChanged = exports.areSwitchableTypes = exports.foreignKeyStructure = exports.generateJunctionTableName = exports.generateForeignKey = exports.checkForViewUpdates = exports.checkStaticTables = exports.handleSearchIndexes = exports.handleDataImport = exports.importToRows = exports.makeSureTableUpToDate = exports.checkForColumnUpdates = exports.clearColumns = void 0;
|
|
15
|
+
exports.TableSaveFunctions = exports.setStaticSchemas = exports.hasTypeChanged = exports.areSwitchableTypes = exports.foreignKeyStructure = exports.generateJunctionTableName = exports.generateForeignKey = exports.checkForViewUpdates = exports.checkStaticTables = exports.handleSearchIndexes = exports.handleDataImport = exports.importToRows = exports.makeSureTableUpToDate = exports.checkForColumnUpdates = exports.clearColumns = void 0;
|
|
16
16
|
const schema_1 = require("../../../utilities/schema");
|
|
17
17
|
const utils_1 = require("../../../db/utils");
|
|
18
18
|
const lodash_1 = require("lodash");
|
|
@@ -24,6 +24,7 @@ const viewBuilder_1 = __importDefault(require("../view/viewBuilder"));
|
|
|
24
24
|
const fp_1 = require("lodash/fp");
|
|
25
25
|
const pro_1 = require("@budibase/pro");
|
|
26
26
|
const backend_core_1 = require("@budibase/backend-core");
|
|
27
|
+
const types_1 = require("@budibase/types");
|
|
27
28
|
function clearColumns(table, columnNames) {
|
|
28
29
|
return __awaiter(this, void 0, void 0, function* () {
|
|
29
30
|
const db = backend_core_1.context.getAppDB();
|
|
@@ -356,5 +357,18 @@ function hasTypeChanged(table, oldTable) {
|
|
|
356
357
|
return false;
|
|
357
358
|
}
|
|
358
359
|
exports.hasTypeChanged = hasTypeChanged;
|
|
360
|
+
// used for external tables, some of them will have static schemas that need
|
|
361
|
+
// to be hard set
|
|
362
|
+
function setStaticSchemas(datasource, table) {
|
|
363
|
+
var _a;
|
|
364
|
+
// GSheets is a specific case - only ever has a static primary key
|
|
365
|
+
if (table && datasource.source === types_1.SourceName.GOOGLE_SHEETS) {
|
|
366
|
+
table.primary = [constants_1.GOOGLE_SHEETS_PRIMARY_KEY];
|
|
367
|
+
// if there is an id column, remove it, should never exist in GSheets
|
|
368
|
+
(_a = table.schema) === null || _a === void 0 ? true : delete _a.id;
|
|
369
|
+
}
|
|
370
|
+
return table;
|
|
371
|
+
}
|
|
372
|
+
exports.setStaticSchemas = setStaticSchemas;
|
|
359
373
|
const _TableSaveFunctions = TableSaveFunctions;
|
|
360
374
|
exports.TableSaveFunctions = _TableSaveFunctions;
|
|
@@ -5,6 +5,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
exports.shutdown = void 0;
|
|
7
7
|
const applications_1 = __importDefault(require("./applications"));
|
|
8
|
+
const metrics_1 = __importDefault(require("./metrics"));
|
|
8
9
|
const queries_1 = __importDefault(require("./queries"));
|
|
9
10
|
const tables_1 = __importDefault(require("./tables"));
|
|
10
11
|
const rows_1 = __importDefault(require("./rows"));
|
|
@@ -86,6 +87,12 @@ function addToRouter(endpoints) {
|
|
|
86
87
|
}
|
|
87
88
|
}
|
|
88
89
|
}
|
|
90
|
+
function applyAdminRoutes(endpoints) {
|
|
91
|
+
addMiddleware(endpoints.read, backend_core_1.middleware.builderOrAdmin);
|
|
92
|
+
addMiddleware(endpoints.write, backend_core_1.middleware.builderOrAdmin);
|
|
93
|
+
addToRouter(endpoints.read);
|
|
94
|
+
addToRouter(endpoints.write);
|
|
95
|
+
}
|
|
89
96
|
function applyRoutes(endpoints, permType, resource, subResource) {
|
|
90
97
|
const paramMiddleware = subResource
|
|
91
98
|
? (0, resourceId_1.paramSubResource)(resource, subResource)
|
|
@@ -107,6 +114,7 @@ function applyRoutes(endpoints, permType, resource, subResource) {
|
|
|
107
114
|
addToRouter(endpoints.read);
|
|
108
115
|
addToRouter(endpoints.write);
|
|
109
116
|
}
|
|
117
|
+
applyAdminRoutes(metrics_1.default);
|
|
110
118
|
applyRoutes(applications_1.default, PermissionType.APP, "appId");
|
|
111
119
|
applyRoutes(tables_1.default, PermissionType.TABLE, "tableId");
|
|
112
120
|
applyRoutes(users_1.default, PermissionType.USER, "userId");
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const metrics_1 = __importDefault(require("../../controllers/public/metrics"));
|
|
7
|
+
const Endpoint_1 = __importDefault(require("./utils/Endpoint"));
|
|
8
|
+
const read = [];
|
|
9
|
+
/**
|
|
10
|
+
* @openapi
|
|
11
|
+
* /metrics:
|
|
12
|
+
* get:
|
|
13
|
+
* operationId: metricsGet
|
|
14
|
+
* summary: Retrieve Budibase tenant metrics
|
|
15
|
+
* description: Output metrics in OpenMetrics format compatible with Prometheus
|
|
16
|
+
* tags:
|
|
17
|
+
* - metrics
|
|
18
|
+
* responses:
|
|
19
|
+
* 200:
|
|
20
|
+
* description: Returns tenant metrics.
|
|
21
|
+
* content:
|
|
22
|
+
* text/plain:
|
|
23
|
+
* schema:
|
|
24
|
+
* type: string
|
|
25
|
+
* examples:
|
|
26
|
+
* metrics:
|
|
27
|
+
* $ref: '#/components/examples/metrics'
|
|
28
|
+
*/
|
|
29
|
+
read.push(new Endpoint_1.default("get", "/metrics", metrics_1.default.fetch));
|
|
30
|
+
exports.default = { read };
|
package/dist/constants/index.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.MAX_AUTOMATION_RECURRING_ERRORS = exports.ObjectStoreBuckets = exports.AutomationErrors = exports.BuildSchemaErrors = exports.InvalidColumns = exports.MetadataTypes = exports.BaseQueryVerbs = exports.OBJ_STORE_DIRECTORY = exports.AutoFieldDefaultNames = exports.AutoFieldSubTypes = exports.USERS_TABLE_SCHEMA = exports.SortDirection = exports.DatasourceAuthTypes = exports.DataSourceOperation = exports.AuthTypes = exports.FormulaTypes = exports.SwitchableTypes = exports.CanSwitchTypes = exports.NoEmptyFilterStrings = exports.FilterTypes = exports.RelationshipTypes = exports.FieldTypes = void 0;
|
|
3
|
+
exports.GOOGLE_SHEETS_PRIMARY_KEY = exports.MAX_AUTOMATION_RECURRING_ERRORS = exports.ObjectStoreBuckets = exports.AutomationErrors = exports.BuildSchemaErrors = exports.InvalidColumns = exports.MetadataTypes = exports.BaseQueryVerbs = exports.OBJ_STORE_DIRECTORY = exports.AutoFieldDefaultNames = exports.AutoFieldSubTypes = exports.USERS_TABLE_SCHEMA = exports.SortDirection = exports.DatasourceAuthTypes = exports.DataSourceOperation = exports.AuthTypes = exports.FormulaTypes = exports.SwitchableTypes = exports.CanSwitchTypes = exports.NoEmptyFilterStrings = exports.FilterTypes = exports.RelationshipTypes = exports.FieldTypes = void 0;
|
|
4
4
|
const backend_core_1 = require("@budibase/backend-core");
|
|
5
5
|
var types_1 = require("@budibase/types");
|
|
6
6
|
Object.defineProperty(exports, "FieldTypes", { enumerable: true, get: function () { return types_1.FieldType; } });
|
|
@@ -178,3 +178,4 @@ var AutomationErrors;
|
|
|
178
178
|
// pass through the list from the auth/core lib
|
|
179
179
|
exports.ObjectStoreBuckets = backend_core_1.objectStore.ObjectStoreBuckets;
|
|
180
180
|
exports.MAX_AUTOMATION_RECURRING_ERRORS = 5;
|
|
181
|
+
exports.GOOGLE_SHEETS_PRIMARY_KEY = "rowNumber";
|