8ed0e6ffa8
统一当前工作树与基线提交按 Cargo lib.path 扫描可达模块 补充保留旧源码误报与真实 accessor 重复回归测试 更新旧创作模板退役方案和项目排障记忆
65 lines
2.4 KiB
TypeScript
65 lines
2.4 KiB
TypeScript
import { describe, expect, it } from 'vitest';
|
|
|
|
import {
|
|
collectTablesFromSources,
|
|
listReachableRustFiles,
|
|
} from './check-spacetime-schema-guard.mjs';
|
|
|
|
const manifestPath = 'server-rs/crates/spacetime-module/Cargo.toml';
|
|
const sourceRoot = 'server-rs/crates/spacetime-module/src';
|
|
|
|
type SourceFiles = Record<string, string>;
|
|
|
|
function createSourceReader(files: SourceFiles) {
|
|
const sources = new Map(Object.entries(files));
|
|
return (path: string) => sources.get(path) ?? null;
|
|
}
|
|
|
|
function collectReachableTables(files: SourceFiles) {
|
|
const readSource = createSourceReader(files);
|
|
const paths = listReachableRustFiles(readSource);
|
|
return {
|
|
paths,
|
|
result: collectTablesFromSources(
|
|
paths.map((path: string) => ({ path, text: readSource(path) ?? '' })),
|
|
),
|
|
};
|
|
}
|
|
|
|
function tableSource(structName: string, accessor: string) {
|
|
return `#[spacetimedb::table(accessor = ${accessor})]\npub struct ${structName} {\n pub id: u64,\n}\n`;
|
|
}
|
|
|
|
describe('SpacetimeDB schema guard module reachability', () => {
|
|
it('ignores duplicate accessors in retained but unreachable legacy sources', () => {
|
|
const activePath = `${sourceRoot}/active.rs`;
|
|
const shellPath = `${sourceRoot}/legacy_schema/example.rs`;
|
|
const retiredPath = `${sourceRoot}/example.rs`;
|
|
const { paths, result } = collectReachableTables({
|
|
[manifestPath]: '[lib]\npath = "src/active.rs"\n',
|
|
[activePath]: '#[path = "legacy_schema/example.rs"]\nmod example;\n',
|
|
[shellPath]: tableSource('ExampleSchemaShell', 'example'),
|
|
[retiredPath]: tableSource('RetiredExample', 'example'),
|
|
});
|
|
|
|
expect(paths).toEqual([activePath, shellPath]);
|
|
expect(result.failures).toEqual([]);
|
|
expect([...result.tables.keys()]).toEqual(['example']);
|
|
});
|
|
|
|
it('still rejects duplicate accessors when both definitions are reachable', () => {
|
|
const activePath = `${sourceRoot}/active.rs`;
|
|
const firstPath = `${sourceRoot}/first.rs`;
|
|
const secondPath = `${sourceRoot}/second.rs`;
|
|
const { result } = collectReachableTables({
|
|
[manifestPath]: '[lib]\npath = "src/active.rs"\n',
|
|
[activePath]: 'mod first;\nmod second;\n',
|
|
[firstPath]: tableSource('FirstExample', 'example'),
|
|
[secondPath]: tableSource('SecondExample', 'example'),
|
|
});
|
|
|
|
expect(result.failures).toHaveLength(1);
|
|
expect(result.failures[0]).toMatch(/table accessor example 重复定义/u);
|
|
});
|
|
});
|