@nocobase/server 2.0.0-alpha.21 → 2.0.0-alpha.23

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.
@@ -219,7 +219,7 @@ export declare class Application<StateT = DefaultState, ContextT = DefaultContex
219
219
  get environment(): Environment;
220
220
  protected _cronJobManager: CronJobManager;
221
221
  get cronJobManager(): CronJobManager;
222
- get mainDataSource(): SequelizeDataSource;
222
+ get mainDataSource(): SequelizeDataSource<import("@nocobase/data-source-manager").DatabaseIntrospector>;
223
223
  get db(): Database;
224
224
  get resourceManager(): import("@nocobase/resourcer").ResourceManager;
225
225
  /**
package/lib/index.d.ts CHANGED
@@ -22,6 +22,7 @@ export * from './event-queue';
22
22
  export * from './background-job-manager';
23
23
  export * from './worker-id-allocator';
24
24
  export * from './redis-connection-manager';
25
+ export * from './main-data-source';
25
26
  export declare const OFFICIAL_PLUGIN_PREFIX = "@nocobase/plugin-";
26
27
  export { appendToBuiltInPlugins, findAllPlugins, findBuiltInPlugins, findLocalPlugins, packageNameTrim, } from './plugin-manager/findPackageNames';
27
28
  export { runPluginStaticImports } from './run-plugin-static-imports';
package/lib/index.js CHANGED
@@ -64,6 +64,7 @@ __reExport(src_exports, require("./event-queue"), module.exports);
64
64
  __reExport(src_exports, require("./background-job-manager"), module.exports);
65
65
  __reExport(src_exports, require("./worker-id-allocator"), module.exports);
66
66
  __reExport(src_exports, require("./redis-connection-manager"), module.exports);
67
+ __reExport(src_exports, require("./main-data-source"), module.exports);
67
68
  var import_findPackageNames = require("./plugin-manager/findPackageNames");
68
69
  var import_run_plugin_static_imports = require("./run-plugin-static-imports");
69
70
  const OFFICIAL_PLUGIN_PREFIX = "@nocobase/plugin-";
@@ -90,5 +91,6 @@ const OFFICIAL_PLUGIN_PREFIX = "@nocobase/plugin-";
90
91
  ...require("./event-queue"),
91
92
  ...require("./background-job-manager"),
92
93
  ...require("./worker-id-allocator"),
93
- ...require("./redis-connection-manager")
94
+ ...require("./redis-connection-manager"),
95
+ ...require("./main-data-source")
94
96
  });
@@ -6,7 +6,18 @@
6
6
  * This project is dual-licensed under AGPL-3.0 and NocoBase Commercial License.
7
7
  * For more information, please refer to: https://www.nocobase.com/agreement.
8
8
  */
9
+ import { Context } from '@nocobase/actions';
9
10
  import { DataSourceOptions, SequelizeDataSource } from '@nocobase/data-source-manager';
11
+ type MainDataSourceStatus = 'loaded' | 'loading';
10
12
  export declare class MainDataSource extends SequelizeDataSource {
13
+ status: MainDataSourceStatus;
11
14
  init(options?: DataSourceOptions): void;
15
+ readTables(): Promise<{
16
+ name: string;
17
+ }[]>;
18
+ private tables2Collections;
19
+ loadTables(ctx: Context, tables: string[]): Promise<void>;
20
+ private getLoadedCollections;
21
+ syncFieldsFromDatabase(ctx: any, collectionNames?: string[]): Promise<void>;
12
22
  }
23
+ export {};
@@ -32,6 +32,7 @@ __export(main_data_source_exports, {
32
32
  module.exports = __toCommonJS(main_data_source_exports);
33
33
  var import_data_source_manager = require("@nocobase/data-source-manager");
34
34
  const _MainDataSource = class _MainDataSource extends import_data_source_manager.SequelizeDataSource {
35
+ status = "loaded";
35
36
  init(options = {}) {
36
37
  const { acl, resourceManager, database } = options;
37
38
  this.acl = acl;
@@ -48,6 +49,133 @@ const _MainDataSource = class _MainDataSource extends import_data_source_manager
48
49
  this.resourceManager.use(this.acl.middleware(), { group: "acl", after: "auth" });
49
50
  }
50
51
  }
52
+ async readTables() {
53
+ const allTables = await this.introspector.getTableList();
54
+ const existsCollections = this.collectionManager.db.collections;
55
+ const existsTables = Array.from(existsCollections.values()).map(
56
+ (collection) => collection.model.tableName
57
+ );
58
+ const diffTables = allTables.filter((table) => !existsTables.includes(table));
59
+ return diffTables.map((name) => ({ name }));
60
+ }
61
+ async tables2Collections(tableNames) {
62
+ const db = this.collectionManager.db;
63
+ const results = await Promise.all(
64
+ tableNames.map(async (tableName) => {
65
+ let tableInfo;
66
+ if (typeof tableName === "string") {
67
+ tableInfo = { tableName };
68
+ if (db.options.schema) {
69
+ tableInfo.schema = db.options.schema;
70
+ }
71
+ } else {
72
+ tableInfo = tableName;
73
+ }
74
+ try {
75
+ return await this.introspector.getCollection({ tableInfo });
76
+ } catch (e) {
77
+ if (e.message.includes("No description found for")) {
78
+ return null;
79
+ }
80
+ throw e;
81
+ }
82
+ })
83
+ );
84
+ return results.filter(Boolean);
85
+ }
86
+ async loadTables(ctx, tables) {
87
+ const repo = this.collectionManager.db.getRepository("collections");
88
+ const existsCollections = this.collectionManager.db.collections;
89
+ const existsTables = Array.from(existsCollections.values()).map(
90
+ (collection) => collection.model.tableName
91
+ );
92
+ const toAddTables = tables.filter((table) => !existsTables.includes(table));
93
+ if (toAddTables.length) {
94
+ try {
95
+ this.status = "loading";
96
+ const results = await this.tables2Collections(toAddTables);
97
+ const values = results.map((result) => ({
98
+ ...result,
99
+ underscored: false
100
+ }));
101
+ await repo.create({ values, context: ctx });
102
+ } catch (e) {
103
+ throw e;
104
+ } finally {
105
+ this.status = "loaded";
106
+ }
107
+ }
108
+ }
109
+ async getLoadedCollections(filter) {
110
+ const db = this.collectionManager.db;
111
+ const loadedCollections = await db.getRepository("collections").find({
112
+ appends: ["fields"],
113
+ filter: {
114
+ hidden: false,
115
+ ...filter
116
+ }
117
+ });
118
+ const collections = loadedCollections.filter((collection) => {
119
+ var _a;
120
+ return ((_a = collection.options) == null ? void 0 : _a.from) !== "db2cm";
121
+ });
122
+ const loadedData = {};
123
+ for (const collection of collections) {
124
+ const c = db.getCollection(collection.name);
125
+ loadedData[c.tableName()] = {
126
+ ...collection.toJSON(),
127
+ fields: collection.fields.map((field) => {
128
+ const f = c.getField(field.name);
129
+ return {
130
+ columnName: f == null ? void 0 : f.columnName(),
131
+ ...field.toJSON()
132
+ };
133
+ })
134
+ };
135
+ }
136
+ return loadedData;
137
+ }
138
+ async syncFieldsFromDatabase(ctx, collectionNames) {
139
+ let filter = {};
140
+ if (collectionNames == null ? void 0 : collectionNames.length) {
141
+ filter = {
142
+ name: collectionNames
143
+ };
144
+ }
145
+ const db = this.collectionManager.db;
146
+ const loadedCollections = await this.getLoadedCollections(filter);
147
+ const tableNames = Object.values(loadedCollections).map(({ name }) => {
148
+ const collection = db.getCollection(name);
149
+ return collection.getTableNameWithSchema();
150
+ });
151
+ let collections = [];
152
+ try {
153
+ collections = await this.tables2Collections(tableNames);
154
+ } catch (err) {
155
+ ctx.log.error(err);
156
+ }
157
+ const toLoadCollections = this.mergeWithLoadedCollections(collections, loadedCollections);
158
+ for (const values of toLoadCollections) {
159
+ const existsFields = loadedCollections[values.tableName].fields;
160
+ const deletedFields = existsFields.filter((field) => !values.fields.find((f) => f.name === field.name));
161
+ await db.sequelize.transaction(async (transaction) => {
162
+ for (const field of deletedFields) {
163
+ await db.getRepository("fields").destroy({
164
+ filterByTk: field.key,
165
+ context: ctx,
166
+ transaction
167
+ });
168
+ }
169
+ await db.getRepository("collections").update({
170
+ filterByTk: values.name,
171
+ values,
172
+ updateAssociationValues: ["fields"],
173
+ context: ctx,
174
+ transaction
175
+ });
176
+ });
177
+ }
178
+ }
51
179
  };
52
180
  __name(_MainDataSource, "MainDataSource");
53
181
  let MainDataSource = _MainDataSource;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nocobase/server",
3
- "version": "2.0.0-alpha.21",
3
+ "version": "2.0.0-alpha.23",
4
4
  "main": "lib/index.js",
5
5
  "types": "./lib/index.d.ts",
6
6
  "license": "AGPL-3.0",
@@ -10,20 +10,20 @@
10
10
  "@koa/cors": "^5.0.0",
11
11
  "@koa/multer": "^3.1.0",
12
12
  "@koa/router": "^13.1.0",
13
- "@nocobase/acl": "2.0.0-alpha.21",
14
- "@nocobase/actions": "2.0.0-alpha.21",
15
- "@nocobase/auth": "2.0.0-alpha.21",
16
- "@nocobase/cache": "2.0.0-alpha.21",
17
- "@nocobase/data-source-manager": "2.0.0-alpha.21",
18
- "@nocobase/database": "2.0.0-alpha.21",
19
- "@nocobase/evaluators": "2.0.0-alpha.21",
20
- "@nocobase/lock-manager": "2.0.0-alpha.21",
21
- "@nocobase/logger": "2.0.0-alpha.21",
22
- "@nocobase/resourcer": "2.0.0-alpha.21",
23
- "@nocobase/sdk": "2.0.0-alpha.21",
24
- "@nocobase/snowflake-id": "2.0.0-alpha.21",
25
- "@nocobase/telemetry": "2.0.0-alpha.21",
26
- "@nocobase/utils": "2.0.0-alpha.21",
13
+ "@nocobase/acl": "2.0.0-alpha.23",
14
+ "@nocobase/actions": "2.0.0-alpha.23",
15
+ "@nocobase/auth": "2.0.0-alpha.23",
16
+ "@nocobase/cache": "2.0.0-alpha.23",
17
+ "@nocobase/data-source-manager": "2.0.0-alpha.23",
18
+ "@nocobase/database": "2.0.0-alpha.23",
19
+ "@nocobase/evaluators": "2.0.0-alpha.23",
20
+ "@nocobase/lock-manager": "2.0.0-alpha.23",
21
+ "@nocobase/logger": "2.0.0-alpha.23",
22
+ "@nocobase/resourcer": "2.0.0-alpha.23",
23
+ "@nocobase/sdk": "2.0.0-alpha.23",
24
+ "@nocobase/snowflake-id": "2.0.0-alpha.23",
25
+ "@nocobase/telemetry": "2.0.0-alpha.23",
26
+ "@nocobase/utils": "2.0.0-alpha.23",
27
27
  "@types/decompress": "4.2.7",
28
28
  "@types/ini": "^1.3.31",
29
29
  "@types/koa-send": "^4.1.3",
@@ -59,5 +59,5 @@
59
59
  "@types/serve-handler": "^6.1.1",
60
60
  "@types/ws": "^8.5.5"
61
61
  },
62
- "gitHead": "0398c85e979d09e834952e71c5c1a1ccf1a3a8e1"
62
+ "gitHead": "ea67a7ad1c12fce26e0fff992f33de10901eff6a"
63
63
  }