@canmingir/link-express 1.6.10 → 1.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (56) hide show
  1. package/.eslintrc.ts +29 -0
  2. package/index.ts +2 -0
  3. package/package.json +55 -12
  4. package/{prepare.js → prepare.ts} +1 -1
  5. package/src/{authorization.js → authorization.ts} +31 -9
  6. package/src/config.ts +112 -0
  7. package/src/dynamodb.ts +24 -0
  8. package/src/{error.js → error.ts} +30 -11
  9. package/src/express.ts +66 -0
  10. package/src/lib/{settings.js → settings.ts} +16 -4
  11. package/src/lib/test.ts +68 -0
  12. package/src/logger.ts +36 -0
  13. package/src/metrics/{dbMetrics.js → dbMetrics.ts} +37 -14
  14. package/src/models/Organization.model.ts +27 -0
  15. package/src/models/Permission.model.ts +48 -0
  16. package/src/models/Project.model.ts +50 -0
  17. package/src/models/Settings.model.ts +31 -0
  18. package/src/models/{index.js → index.ts} +8 -8
  19. package/src/platform.ts +55 -0
  20. package/src/postgres.ts +309 -0
  21. package/src/routes/index.ts +8 -0
  22. package/src/routes/metrics.ts +13 -0
  23. package/src/routes/oauth.ts +267 -0
  24. package/src/routes/{organizations.js → organizations.ts} +10 -8
  25. package/src/routes/{permissions.js → permissions.ts} +8 -6
  26. package/src/routes/{projects.js → projects.ts} +22 -16
  27. package/src/routes/settings.ts +31 -0
  28. package/src/schemas/{Organization.js → Organization.ts} +2 -2
  29. package/src/schemas/{Permission.js → Permission.ts} +2 -2
  30. package/src/schemas/{Project.js → Project.ts} +2 -2
  31. package/src/schemas/index.ts +5 -0
  32. package/src/sequelize.ts +13 -0
  33. package/src/{test.js → test.ts} +11 -13
  34. package/src/types/Organization.ts +9 -0
  35. package/src/types/Permission.ts +13 -0
  36. package/src/types/Project.ts +14 -0
  37. package/src/types/index.ts +5 -0
  38. package/tsconfig.json +32 -0
  39. package/.eslintrc.js +0 -20
  40. package/index.js +0 -1
  41. package/src/config.js +0 -21
  42. package/src/dynamodb.js +0 -18
  43. package/src/express.js +0 -58
  44. package/src/lib/test.js +0 -69
  45. package/src/models/Organization.js +0 -17
  46. package/src/models/Permission.js +0 -33
  47. package/src/models/Project.js +0 -37
  48. package/src/models/Settings.js +0 -21
  49. package/src/openapi.js +0 -40
  50. package/src/platform.js +0 -46
  51. package/src/postgres.js +0 -308
  52. package/src/routes/index.js +0 -15
  53. package/src/routes/metrics.js +0 -12
  54. package/src/routes/oauth.js +0 -213
  55. package/src/routes/settings.js +0 -25
  56. package/src/schemas/index.js +0 -5
@@ -1,6 +1,30 @@
1
- const promClient = require("prom-client");
1
+ import promClient from "prom-client";
2
+
3
+ interface PushgatewayConfig {
4
+ url: string;
5
+ jobName: string;
6
+ instance?: string;
7
+ interval: number;
8
+ }
9
+
10
+ interface MetricsConfig {
11
+ url?: string;
12
+ pushGateway: {
13
+ jobName?: string;
14
+ instance?: string;
15
+ };
16
+ interval?: number;
17
+ }
2
18
 
3
19
  class DBMetrics {
20
+ registry: promClient.Registry;
21
+ pushgatewayInterval: NodeJS.Timeout | null;
22
+ pushgatewayConfig: PushgatewayConfig | null;
23
+ dbReadOps: promClient.Counter<string>;
24
+ dbWriteOps: promClient.Counter<string>;
25
+ dbReadLatency: promClient.Histogram<string>;
26
+ dbWriteLatency: promClient.Histogram<string>;
27
+
4
28
  constructor() {
5
29
  this.registry = new promClient.Registry();
6
30
  this.pushgatewayInterval = null;
@@ -33,17 +57,17 @@ class DBMetrics {
33
57
  });
34
58
  }
35
59
 
36
- recordDbRead() {
60
+ recordDbRead(): () => number {
37
61
  this.dbReadOps.inc();
38
62
  return this.dbReadLatency.startTimer();
39
63
  }
40
64
 
41
- recordDbWrite() {
65
+ recordDbWrite(): () => number {
42
66
  this.dbWriteOps.inc();
43
67
  return this.dbWriteLatency.startTimer();
44
68
  }
45
69
 
46
- startPushgateway(metrics = {}) {
70
+ startPushgateway(metrics: MetricsConfig): void {
47
71
  this.pushgatewayConfig = {
48
72
  url: metrics.url || "http://localhost:9091",
49
73
  jobName: metrics.pushGateway.jobName || "api",
@@ -62,19 +86,18 @@ class DBMetrics {
62
86
  );
63
87
  }
64
88
 
65
- stopPushgateway() {
89
+ stopPushgateway(): void {
66
90
  if (this.pushgatewayInterval) {
67
91
  clearInterval(this.pushgatewayInterval);
68
- this.pushgatewayInterval = undefined;
92
+ this.pushgatewayInterval = null;
69
93
  console.log("Stopped pushing metrics to Pushgateway");
70
94
  }
71
95
  }
72
96
 
73
- async pushMetricsToGateway() {
97
+ async pushMetricsToGateway(): Promise<void> {
74
98
  if (!this.pushgatewayConfig) {
75
- throw new Error(
76
- "Pushgateway not configured. Call startPushgateway() first."
77
- );
99
+ console.error("[DBMetrics] Pushgateway not configured");
100
+ return;
78
101
  }
79
102
 
80
103
  try {
@@ -95,15 +118,15 @@ class DBMetrics {
95
118
  throw new Error(`HTTP ${response.status}: ${response.statusText}`);
96
119
  }
97
120
 
98
- console.log("Metrics pushed to Pushgateway successfully");
121
+ console.log("[DBMetrics] Metrics pushed to Pushgateway successfully");
99
122
  } catch (err) {
100
- console.error("Failed to push metrics to Pushgateway:", err);
123
+ console.error("[DBMetrics] Failed to push metrics to Pushgateway:", err);
101
124
  }
102
125
  }
103
126
 
104
- getPushgatewayConfig() {
127
+ getPushgatewayConfig(): PushgatewayConfig | null {
105
128
  return this.pushgatewayConfig;
106
129
  }
107
130
  }
108
131
 
109
- module.exports = { DBMetrics };
132
+ export { DBMetrics };
@@ -0,0 +1,27 @@
1
+ import {
2
+ Table,
3
+ Column,
4
+ Model,
5
+ DataType,
6
+ Default,
7
+ PrimaryKey,
8
+ AllowNull,
9
+ } from "sequelize-typescript";
10
+
11
+ @Table({
12
+ tableName: "Organization",
13
+ timestamps: false,
14
+ underscored: true,
15
+ })
16
+ class Organization extends Model {
17
+ @PrimaryKey
18
+ @Default(DataType.UUIDV4)
19
+ @Column(DataType.UUID)
20
+ declare id: string;
21
+
22
+ @AllowNull(false)
23
+ @Column(DataType.STRING)
24
+ declare name: string;
25
+ }
26
+
27
+ export default Organization;
@@ -0,0 +1,48 @@
1
+ import {
2
+ Table,
3
+ Column,
4
+ Model,
5
+ DataType,
6
+ Default,
7
+ PrimaryKey,
8
+ AllowNull,
9
+ ForeignKey,
10
+ } from "sequelize-typescript";
11
+ import Organization from "./Organization.model";
12
+ import Project from "./Project.model";
13
+
14
+ @Table({
15
+ tableName: "Permission",
16
+ timestamps: false,
17
+ underscored: true,
18
+ })
19
+ class Permission extends Model {
20
+ @PrimaryKey
21
+ @Default(DataType.UUIDV4)
22
+ @Column(DataType.UUID)
23
+ declare id: string;
24
+
25
+ @AllowNull(false)
26
+ @Column(DataType.UUID)
27
+ declare appId: string;
28
+
29
+ @AllowNull(false)
30
+ @ForeignKey(() => Organization)
31
+ @Column(DataType.UUID)
32
+ declare organizationId: string;
33
+
34
+ @AllowNull(false)
35
+ @ForeignKey(() => Project)
36
+ @Column(DataType.UUID)
37
+ declare projectId: string;
38
+
39
+ @AllowNull(false)
40
+ @Column(DataType.STRING)
41
+ declare userId: string;
42
+
43
+ @AllowNull(false)
44
+ @Column(DataType.STRING)
45
+ declare role: string;
46
+ }
47
+
48
+ export default Permission;
@@ -0,0 +1,50 @@
1
+ import {
2
+ Table,
3
+ Column,
4
+ Model,
5
+ DataType,
6
+ Default,
7
+ PrimaryKey,
8
+ AllowNull,
9
+ ForeignKey,
10
+ } from "sequelize-typescript";
11
+ import Organization from "./Organization.model";
12
+
13
+ @Table({
14
+ tableName: "Project",
15
+ timestamps: false,
16
+ underscored: true,
17
+ })
18
+ class Project extends Model {
19
+ @PrimaryKey
20
+ @Default(DataType.UUIDV4)
21
+ @Column(DataType.UUID)
22
+ declare id: string;
23
+
24
+ @AllowNull(false)
25
+ @Column(DataType.STRING)
26
+ declare name: string;
27
+
28
+ @AllowNull(false)
29
+ @Column(DataType.STRING)
30
+ declare icon: string;
31
+
32
+ @AllowNull(true)
33
+ @Column(DataType.STRING)
34
+ declare description: string | null;
35
+
36
+ @AllowNull(true)
37
+ @Column(DataType.STRING)
38
+ declare type: string | null;
39
+
40
+ @AllowNull(true)
41
+ @ForeignKey(() => Organization)
42
+ @Column(DataType.UUID)
43
+ declare organizationId: string | null;
44
+
45
+ @AllowNull(true)
46
+ @Column(DataType.STRING)
47
+ declare coach: string | null;
48
+ }
49
+
50
+ export default Project;
@@ -0,0 +1,31 @@
1
+ import {
2
+ Table,
3
+ Column,
4
+ Model,
5
+ DataType,
6
+ Default,
7
+ PrimaryKey,
8
+ AllowNull,
9
+ } from "sequelize-typescript";
10
+
11
+ @Table({
12
+ tableName: "Settings",
13
+ timestamps: false,
14
+ underscored: true,
15
+ })
16
+ class Settings extends Model {
17
+ @PrimaryKey
18
+ @Default(DataType.UUIDV4)
19
+ @Column(DataType.UUID)
20
+ declare id: string;
21
+
22
+ @AllowNull(false)
23
+ @Column(DataType.UUID)
24
+ declare projectId: string;
25
+
26
+ @AllowNull(false)
27
+ @Column(DataType.JSONB)
28
+ declare settings: Record<string, unknown>;
29
+ }
30
+
31
+ export default Settings;
@@ -1,11 +1,11 @@
1
- const Project = require("./Project");
2
- const Organization = require("./Organization");
3
- const Permission = require("./Permission");
4
- const Setting = require("./Settings");
1
+ import Project from "./Project.model";
2
+ import Organization from "./Organization.model";
3
+ import Permission from "./Permission.model";
4
+ import Setting from "./Settings.model";
5
5
 
6
6
  let _init = false;
7
7
 
8
- async function init() {
8
+ async function init(): Promise<boolean> {
9
9
  if (!_init) {
10
10
  _init = true;
11
11
  } else {
@@ -37,10 +37,10 @@ async function init() {
37
37
  as: "permissions",
38
38
  });
39
39
 
40
- Organization.addHook("beforeDestroy", async (organization) => {
40
+ Organization.addHook("beforeDestroy", async (organization: Organization) => {
41
41
  await Project.destroy({
42
42
  where: {
43
- organizationId: organization.id,
43
+ organizationId: organization.getDataValue("id"),
44
44
  },
45
45
  });
46
46
  });
@@ -48,4 +48,4 @@ async function init() {
48
48
  return true;
49
49
  }
50
50
 
51
- module.exports = { Project, Organization, Permission, init, Setting };
51
+ export { Project, Organization, Permission, init, Setting };
@@ -0,0 +1,55 @@
1
+ import * as authorization from "./authorization";
2
+ import * as error from "./error";
3
+ import { Application } from "express";
4
+ import { Sequelize } from "sequelize-typescript";
5
+ import { Config } from "./config";
6
+ import { DynamoDBDocumentClient } from "@aws-sdk/lib-dynamodb";
7
+ import type { Logger } from "pino";
8
+
9
+ let _express: Application;
10
+ let _postgres: { sequelize: Sequelize };
11
+ let _dynamodb: { docClient: DynamoDBDocumentClient };
12
+ let _logger: Logger | Console;
13
+
14
+ async function init(config: Partial<Config> = {}): Promise<void> {
15
+ const configModule = await import("./config.ts");
16
+ const { postgres, dynamodb, logger } = configModule.init(config as Config);
17
+
18
+ const expressModule = await import("./express.ts");
19
+ _express = (expressModule as any).default as Application;
20
+
21
+ if (logger) {
22
+ const loggerModule = await import("./logger.ts");
23
+ _logger = (loggerModule as any).default;
24
+ } else {
25
+ _logger = console;
26
+ }
27
+
28
+ if (postgres) {
29
+ const postgresModule = await import("./postgres.ts");
30
+ _postgres = { sequelize: postgresModule.sequelize };
31
+ }
32
+
33
+ if (dynamodb) {
34
+ const dynamodbModule = await import("./dynamodb.ts");
35
+ _dynamodb = { docClient: dynamodbModule.docClient };
36
+ }
37
+ }
38
+
39
+ const getModules = () => ({
40
+ Postgres: _postgres,
41
+ DynamoDB: _dynamodb,
42
+ Kafka: {},
43
+ });
44
+
45
+ const importModule = (pkg: string) => import(pkg);
46
+
47
+ export {
48
+ init,
49
+ _express as express,
50
+ getModules,
51
+ importModule,
52
+ authorization,
53
+ error,
54
+ _logger as logger,
55
+ };
@@ -0,0 +1,309 @@
1
+ import { Model, Sequelize } from "sequelize-typescript";
2
+ import config from "./config";
3
+ import path from "path";
4
+ import fs from "fs";
5
+ import { DBMetrics } from "./metrics/dbMetrics";
6
+ import { DestroyOptions, InstanceDestroyOptions } from "sequelize";
7
+
8
+ const appConfig = config();
9
+
10
+ const { postgres, project } = appConfig;
11
+
12
+ const metricsConfig = appConfig.metrics;
13
+
14
+ if (!postgres) {
15
+ throw new Error("Postgres configuration is required");
16
+ }
17
+
18
+ let dbMetrics: DBMetrics | null = null;
19
+
20
+ if (metricsConfig && metricsConfig.enabled) {
21
+ dbMetrics = new DBMetrics();
22
+ dbMetrics.startPushgateway(metricsConfig);
23
+ }
24
+
25
+ interface SequelizeOptions {
26
+ metricsTimer?: () => number;
27
+ metricsType?: string;
28
+ }
29
+
30
+ const originalDestroy = Model.prototype.destroy;
31
+ Model.prototype.destroy = async function (
32
+ options?: InstanceDestroyOptions
33
+ ): Promise<void> {
34
+ return originalDestroy.call(this, {
35
+ ...options,
36
+ individualHooks: true,
37
+ }) as Promise<void>;
38
+ };
39
+
40
+ const sequelize = new Sequelize(process.env.PG || postgres.uri, {
41
+ logging: postgres.debug && console.log,
42
+ models: [
43
+ path.join(__dirname, "models/*.model.ts"),
44
+ path.join(process.cwd(), "src/models/[A-Z]*.ts"),
45
+ ],
46
+ define: {
47
+ freezeTableName: true,
48
+ underscored: true,
49
+ timestamps: false,
50
+ paranoid: false,
51
+ },
52
+ hooks:
53
+ metricsConfig && metricsConfig.enabled
54
+ ? {
55
+ beforeFind: (options = {}) => {
56
+ const timer = dbMetrics!.dbReadLatency.startTimer();
57
+ (options as SequelizeOptions).metricsTimer = timer;
58
+ (options as SequelizeOptions).metricsType = "read";
59
+ },
60
+ afterFind: (_result, options = {}) => {
61
+ const opts = options as SequelizeOptions;
62
+ if (opts?.metricsTimer) {
63
+ opts.metricsTimer();
64
+ dbMetrics!.dbReadOps.inc();
65
+ }
66
+ },
67
+
68
+ beforeCreate: (_instance, options = {}) => {
69
+ const timer = dbMetrics!.dbWriteLatency.startTimer();
70
+ (options as SequelizeOptions).metricsTimer = timer;
71
+ (options as SequelizeOptions).metricsType = "write";
72
+ },
73
+ afterCreate: (_instance, options = {}) => {
74
+ const opts = options as SequelizeOptions;
75
+ if (opts?.metricsTimer) {
76
+ opts.metricsTimer();
77
+ dbMetrics!.dbWriteOps.inc();
78
+ }
79
+ },
80
+
81
+ beforeUpdate: (_instance, options = {}) => {
82
+ const timer = dbMetrics!.dbWriteLatency.startTimer();
83
+ (options as SequelizeOptions).metricsTimer = timer;
84
+ (options as SequelizeOptions).metricsType = "write";
85
+ },
86
+ afterUpdate: (_instance, options = {}) => {
87
+ const opts = options as SequelizeOptions;
88
+ if (opts?.metricsTimer) {
89
+ opts.metricsTimer();
90
+ dbMetrics!.dbWriteOps.inc();
91
+ }
92
+ },
93
+
94
+ beforeDestroy: (_instance, options = {}) => {
95
+ const timer = dbMetrics!.dbWriteLatency.startTimer();
96
+ (options as SequelizeOptions).metricsTimer = timer;
97
+ (options as SequelizeOptions).metricsType = "write";
98
+ },
99
+ afterDestroy: (_instance, options = {}) => {
100
+ const opts = options as SequelizeOptions;
101
+ if (opts?.metricsTimer) {
102
+ opts.metricsTimer();
103
+ dbMetrics!.dbWriteOps.inc();
104
+ }
105
+ },
106
+
107
+ beforeBulkCreate: (_instances, options = {}) => {
108
+ const timer = dbMetrics!.dbWriteLatency.startTimer();
109
+ (options as SequelizeOptions).metricsTimer = timer;
110
+ (options as SequelizeOptions).metricsType = "write";
111
+ },
112
+ afterBulkCreate: (instances, options = {}) => {
113
+ const opts = options as SequelizeOptions;
114
+ if (opts?.metricsTimer) {
115
+ opts.metricsTimer();
116
+ dbMetrics!.dbWriteOps.inc(instances.length || 1);
117
+ }
118
+ },
119
+
120
+ beforeBulkUpdate: (_instances, options = {}) => {
121
+ const timer = dbMetrics!.dbWriteLatency.startTimer();
122
+ (options as SequelizeOptions).metricsTimer = timer;
123
+ (options as SequelizeOptions).metricsType = "write";
124
+ },
125
+ afterBulkUpdate: (_instances, options = {}) => {
126
+ const opts = options as SequelizeOptions;
127
+ if (opts?.metricsTimer) {
128
+ opts.metricsTimer();
129
+ dbMetrics!.dbWriteOps.inc(1);
130
+ }
131
+ },
132
+
133
+ beforeBulkDestroy: (options = {}) => {
134
+ const timer = dbMetrics!.dbWriteLatency.startTimer();
135
+ (options as SequelizeOptions).metricsTimer = timer;
136
+ (options as SequelizeOptions).metricsType = "write";
137
+ },
138
+ afterBulkDestroy: (options = {}) => {
139
+ const opts = options as SequelizeOptions;
140
+ if (opts?.metricsTimer) {
141
+ opts.metricsTimer();
142
+ dbMetrics!.dbWriteOps.inc(1);
143
+ }
144
+ },
145
+ }
146
+ : {},
147
+ });
148
+
149
+ const seed = async (): Promise<void> => {
150
+ const currentWorkingDirectory = process.cwd();
151
+ const baseDir = path.join(currentWorkingDirectory, "src", "models");
152
+ const seedDir = path.join(currentWorkingDirectory, "src", "seeds");
153
+
154
+ if (!fs.existsSync(seedDir)) {
155
+ console.error(`[NUC] Seed directory not found at path: ${seedDir}`);
156
+ return;
157
+ }
158
+
159
+ if (!fs.existsSync(baseDir)) {
160
+ console.error(`[NUC] Model directory not found at path: ${baseDir}`);
161
+ return;
162
+ }
163
+
164
+ try {
165
+ if (project) {
166
+ const { seed: companiesSeed } = require("./seeds/Organization.json");
167
+
168
+ sequelize.models.Organization.bulkCreate(companiesSeed, {
169
+ validate: true,
170
+ });
171
+
172
+ console.log(`[NUC] Loading internal seed data for Organization`);
173
+
174
+ if (fs.existsSync(path.join(seedDir, "Organization.json"))) {
175
+ const seedData = require(path.join(seedDir, "Organization.json"));
176
+ const seed = seedData["seed"];
177
+ sequelize.models.Organization.bulkCreate(seed, {
178
+ validate: true,
179
+ });
180
+ console.log(`[NUC] Loading seed data for Organization`);
181
+ }
182
+
183
+ const { seed: projectSeed } = require("./seeds/Project.json");
184
+
185
+ try {
186
+ const { seed: extProjectSeed } = require(path.join(
187
+ seedDir,
188
+ "Project.json"
189
+ ));
190
+ if (extProjectSeed) {
191
+ projectSeed.push(...extProjectSeed);
192
+ }
193
+ console.log(
194
+ `[NUC] Loading internal${
195
+ extProjectSeed ? " and external" : ""
196
+ } seed data for Project`
197
+ );
198
+ } catch (error) {
199
+ console.log(`[NUC] Loading internal seed data for Project`);
200
+ }
201
+
202
+ sequelize.models.Project.bulkCreate(projectSeed, {
203
+ validate: true,
204
+ });
205
+ }
206
+ const fileNames = fs.readdirSync(baseDir).filter((fileName) => {
207
+ return !["index.ts"].includes(fileName);
208
+ });
209
+
210
+ const fileSequences = fileNames
211
+ .map((fileName) => {
212
+ const seedName = fileName.split(".")[0];
213
+ const seederPath = path.join(seedDir, `${seedName}.json`);
214
+
215
+ if (fs.existsSync(seederPath)) {
216
+ const seedData = require(seederPath);
217
+ return { sequence: seedData.sequence, fileName };
218
+ }
219
+ return null;
220
+ })
221
+ .filter(Boolean) as { sequence: number; fileName: string }[];
222
+
223
+ fileSequences.sort((a, b) => a.sequence - b.sequence);
224
+
225
+ for (const { fileName } of fileSequences) {
226
+ const seedName = fileName.split(".")[0];
227
+ const seederPath = path.join(seedDir, `${seedName}.json`);
228
+
229
+ try {
230
+ const seedData = require(seederPath);
231
+ const seed = seedData["seed"];
232
+
233
+ console.log(`[NUC] Loading seed data for ${fileName}`);
234
+
235
+ await sequelize.model(seedName).bulkCreate(seed, {
236
+ validate: true,
237
+ });
238
+ } catch (error) {
239
+ console.error(`[NUC] Error loading seed data for ${fileName}:`, error);
240
+ throw error;
241
+ }
242
+ }
243
+
244
+ if (project) {
245
+ const { seed: permissionsSeed } = require("./seeds/Permission.json");
246
+ try {
247
+ const { seed: extPermissionsSeed } = require(path.join(
248
+ seedDir,
249
+ "Permission.json"
250
+ ));
251
+ if (extPermissionsSeed) {
252
+ permissionsSeed.push(...extPermissionsSeed);
253
+ }
254
+ console.log(
255
+ `[NUC] Loading internal${
256
+ extPermissionsSeed ? " and external" : ""
257
+ } seed data for Permission`
258
+ );
259
+ } catch (error) {
260
+ console.log(`[NUC] Loading internal seed data for Permission`);
261
+ }
262
+
263
+ sequelize.models.Permission.bulkCreate(permissionsSeed, {
264
+ validate: true,
265
+ });
266
+
267
+ const { seed: settingsSeed } = require("./seeds/Settings.json");
268
+
269
+ try {
270
+ const { seed: extSettingsSeed } = require(path.join(
271
+ seedDir,
272
+ "Settings.json"
273
+ ));
274
+ if (extSettingsSeed) {
275
+ settingsSeed.push(...extSettingsSeed);
276
+ }
277
+ console.log(
278
+ `[NUC] Loading internal${
279
+ extSettingsSeed ? " and external" : ""
280
+ } seed data for Settings`
281
+ );
282
+ } catch (error) {
283
+ console.log(`[NUC] Loading internal seed data for Settings`);
284
+ }
285
+
286
+ sequelize.models.Settings.bulkCreate(settingsSeed, {
287
+ validate: true,
288
+ });
289
+ }
290
+ } catch (error) {
291
+ console.error("[NUC] Error during seed operation:", error);
292
+ throw error;
293
+ }
294
+ };
295
+
296
+ const associateModels = async (): Promise<void> => {
297
+ const models = await import("./models");
298
+ await models.init();
299
+ };
300
+
301
+ if (postgres.sync) {
302
+ setImmediate(async () => {
303
+ project && (await associateModels());
304
+ await sequelize.sync({ force: true });
305
+ await seed();
306
+ });
307
+ }
308
+
309
+ export { sequelize };
@@ -0,0 +1,8 @@
1
+ import metrics from "./metrics";
2
+ import permissions from "./permissions";
3
+ import oauth from "./oauth";
4
+ import organizations from "./organizations";
5
+ import projects from "./projects";
6
+ import settings from "./settings";
7
+
8
+ export { metrics, permissions, oauth, organizations, projects, settings };
@@ -0,0 +1,13 @@
1
+ import express, { Request, Response } from "express";
2
+ import os from "os";
3
+
4
+ const router = express.Router();
5
+
6
+ router.get("/", (_req: Request, res: Response) => {
7
+ res.json({
8
+ free: os.freemem(),
9
+ total: os.totalmem(),
10
+ });
11
+ });
12
+
13
+ export default router;