Close DDD refactor and remove generated asset proxy
This commit is contained in:
@@ -3,6 +3,15 @@ import { basename, join, relative } from 'node:path';
|
||||
|
||||
const repoRoot = process.cwd();
|
||||
const cratesDir = join(repoRoot, 'server-rs', 'crates');
|
||||
const spacetimeModuleSrcDir = join(cratesDir, 'spacetime-module', 'src');
|
||||
const spacetimeMigrationPath = join(spacetimeModuleSrcDir, 'migration.rs');
|
||||
const spacetimeTableCatalogPath = join(
|
||||
repoRoot,
|
||||
'docs',
|
||||
'technical',
|
||||
'SPACETIMEDB_TABLE_CATALOG.md',
|
||||
);
|
||||
const migrationExcludedTables = new Set(['database_migration_operator']);
|
||||
const requiredModuleFiles = [
|
||||
'domain.rs',
|
||||
'commands.rs',
|
||||
@@ -79,6 +88,113 @@ function listRustFiles(dir) {
|
||||
return files;
|
||||
}
|
||||
|
||||
function collectSpacetimeTables() {
|
||||
if (!existsSync(spacetimeModuleSrcDir)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
const tableByAccessor = new Map();
|
||||
const tablePattern =
|
||||
/#\[spacetimedb::table\(([\s\S]*?)\)\]\s*(?:#\[[^\]]+\]\s*)*(?:pub\s+)?struct\s+([A-Za-z0-9_]+)/gu;
|
||||
|
||||
for (const rustFile of listRustFiles(spacetimeModuleSrcDir)) {
|
||||
const text = readText(rustFile);
|
||||
let match;
|
||||
while ((match = tablePattern.exec(text)) !== null) {
|
||||
const accessorMatch = /accessor\s*=\s*([A-Za-z0-9_]+)/u.exec(match[1]);
|
||||
if (!accessorMatch) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const accessor = accessorMatch[1];
|
||||
const relativePath = normalizePath(relative(repoRoot, rustFile));
|
||||
const previous = tableByAccessor.get(accessor);
|
||||
if (previous) {
|
||||
failures.push(
|
||||
`SpacetimeDB table accessor ${accessor} 重复定义于 ${previous.path} 与 ${relativePath}`,
|
||||
);
|
||||
continue;
|
||||
}
|
||||
|
||||
tableByAccessor.set(accessor, {
|
||||
accessor,
|
||||
structName: match[2],
|
||||
path: relativePath,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return [...tableByAccessor.values()].sort((left, right) =>
|
||||
left.accessor.localeCompare(right.accessor),
|
||||
);
|
||||
}
|
||||
|
||||
function collectMigrationTables() {
|
||||
if (!existsSync(spacetimeMigrationPath)) {
|
||||
return new Set();
|
||||
}
|
||||
|
||||
const migrationText = readText(spacetimeMigrationPath);
|
||||
const macroMatch =
|
||||
/macro_rules!\s+migration_tables\s*\{[\s\S]*?\$macro_name!\s*\{([\s\S]*?)\n\s*\}\s*\n\s*\};\s*\n\}/u.exec(
|
||||
migrationText,
|
||||
);
|
||||
if (!macroMatch) {
|
||||
failures.push('migration.rs 无法解析 migration_tables! 白名单');
|
||||
return new Set();
|
||||
}
|
||||
|
||||
return new Set(
|
||||
[...macroMatch[1].matchAll(/\b([a-z][a-z0-9_]*)\b/gu)]
|
||||
.map((match) => match[1])
|
||||
.filter((name) => !['arg'].includes(name)),
|
||||
);
|
||||
}
|
||||
|
||||
function collectCatalogTables() {
|
||||
if (!existsSync(spacetimeTableCatalogPath)) {
|
||||
return new Set();
|
||||
}
|
||||
|
||||
const catalogText = readText(spacetimeTableCatalogPath);
|
||||
return new Set(
|
||||
[...catalogText.matchAll(/^### `([^`]+)`/gmu)].map((match) => match[1]),
|
||||
);
|
||||
}
|
||||
|
||||
function checkSpacetimeTableCatalogAndMigration() {
|
||||
const tables = collectSpacetimeTables();
|
||||
const tableNames = new Set(tables.map((table) => table.accessor));
|
||||
const migrationTables = collectMigrationTables();
|
||||
const catalogTables = collectCatalogTables();
|
||||
|
||||
for (const table of tables) {
|
||||
if (!migrationExcludedTables.has(table.accessor) && !migrationTables.has(table.accessor)) {
|
||||
failures.push(
|
||||
`${table.path}: SpacetimeDB 表 ${table.accessor} 缺少 migration.rs 白名单`,
|
||||
);
|
||||
}
|
||||
|
||||
if (!catalogTables.has(table.accessor)) {
|
||||
failures.push(
|
||||
`${table.path}: SpacetimeDB 表 ${table.accessor} 缺少 SPACETIMEDB_TABLE_CATALOG.md 目录项`,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
for (const tableName of migrationTables) {
|
||||
if (!tableNames.has(tableName)) {
|
||||
failures.push(`migration.rs 白名单包含不存在的 SpacetimeDB 表 ${tableName}`);
|
||||
}
|
||||
}
|
||||
|
||||
for (const tableName of catalogTables) {
|
||||
if (!tableNames.has(tableName)) {
|
||||
failures.push(`SPACETIMEDB_TABLE_CATALOG.md 包含不存在的 SpacetimeDB 表 ${tableName}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function collectModuleCrates() {
|
||||
return readdirSync(cratesDir)
|
||||
.filter((name) => name.startsWith('module-'))
|
||||
@@ -144,6 +260,8 @@ for (const crateName of moduleCrates) {
|
||||
}
|
||||
}
|
||||
|
||||
checkSpacetimeTableCatalogAndMigration();
|
||||
|
||||
if (failures.length > 0) {
|
||||
console.error('server-rs DDD boundary check failed:');
|
||||
for (const failure of failures) {
|
||||
|
||||
Reference in New Issue
Block a user