directus

Форк
0
/
schema.ts 
73 строки · 2.2 Кб
1
import type { Accountability } from '@directus/types';
2
import type { Knex } from 'knex';
3
import getDatabase from '../database/index.js';
4
import { ForbiddenError } from '@directus/errors';
5
import type {
6
	AbstractServiceOptions,
7
	Snapshot,
8
	SnapshotDiff,
9
	SnapshotDiffWithHash,
10
	SnapshotWithHash,
11
} from '../types/index.js';
12
import { applyDiff } from '../utils/apply-diff.js';
13
import { getSnapshotDiff } from '../utils/get-snapshot-diff.js';
14
import { getSnapshot } from '../utils/get-snapshot.js';
15
import { getVersionedHash } from '../utils/get-versioned-hash.js';
16
import { validateApplyDiff } from '../utils/validate-diff.js';
17
import { validateSnapshot } from '../utils/validate-snapshot.js';
18

19
export class SchemaService {
20
	knex: Knex;
21
	accountability: Accountability | null;
22

23
	constructor(options: Omit<AbstractServiceOptions, 'schema'>) {
24
		this.knex = options.knex ?? getDatabase();
25
		this.accountability = options.accountability ?? null;
26
	}
27

28
	async snapshot(): Promise<Snapshot> {
29
		if (this.accountability?.admin !== true) throw new ForbiddenError();
30

31
		const currentSnapshot = await getSnapshot({ database: this.knex });
32

33
		return currentSnapshot;
34
	}
35

36
	async apply(payload: SnapshotDiffWithHash): Promise<void> {
37
		if (this.accountability?.admin !== true) throw new ForbiddenError();
38

39
		const currentSnapshot = await this.snapshot();
40
		const snapshotWithHash = this.getHashedSnapshot(currentSnapshot);
41

42
		if (!validateApplyDiff(payload, snapshotWithHash)) return;
43

44
		await applyDiff(currentSnapshot, payload.diff, { database: this.knex });
45
	}
46

47
	async diff(
48
		snapshot: Snapshot,
49
		options?: { currentSnapshot?: Snapshot; force?: boolean },
50
	): Promise<SnapshotDiff | null> {
51
		if (this.accountability?.admin !== true) throw new ForbiddenError();
52

53
		validateSnapshot(snapshot, options?.force);
54

55
		const currentSnapshot = options?.currentSnapshot ?? (await getSnapshot({ database: this.knex }));
56
		const diff = getSnapshotDiff(currentSnapshot, snapshot);
57

58
		if (diff.collections.length === 0 && diff.fields.length === 0 && diff.relations.length === 0) {
59
			return null;
60
		}
61

62
		return diff;
63
	}
64

65
	getHashedSnapshot(snapshot: Snapshot): SnapshotWithHash {
66
		const snapshotHash = getVersionedHash(snapshot);
67

68
		return {
69
			...snapshot,
70
			hash: snapshotHash,
71
		};
72
	}
73
}
74

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.