directus

Форк
0
/
versions.ts 
273 строки · 6.6 Кб
1
import { ErrorCode, InvalidPayloadError, isDirectusError } from '@directus/errors';
2
import type { PrimaryKey } from '@directus/types';
3
import express from 'express';
4
import { assign } from 'lodash-es';
5
import { respond } from '../middleware/respond.js';
6
import useCollection from '../middleware/use-collection.js';
7
import { validateBatch } from '../middleware/validate-batch.js';
8
import { MetaService } from '../services/meta.js';
9
import { VersionsService } from '../services/versions.js';
10
import asyncHandler from '../utils/async-handler.js';
11
import { sanitizeQuery } from '../utils/sanitize-query.js';
12

13
const router = express.Router();
14

15
router.use(useCollection('directus_versions'));
16

17
router.post(
18
	'/',
19
	asyncHandler(async (req, res, next) => {
20
		const service = new VersionsService({
21
			accountability: req.accountability,
22
			schema: req.schema,
23
		});
24

25
		const savedKeys: PrimaryKey[] = [];
26

27
		if (Array.isArray(req.body)) {
28
			const keys = await service.createMany(req.body);
29
			savedKeys.push(...keys);
30
		} else {
31
			const primaryKey = await service.createOne(req.body);
32
			savedKeys.push(primaryKey);
33
		}
34

35
		try {
36
			if (Array.isArray(req.body)) {
37
				const records = await service.readMany(savedKeys, req.sanitizedQuery);
38
				res.locals['payload'] = { data: records };
39
			} else {
40
				const record = await service.readOne(savedKeys[0]!, req.sanitizedQuery);
41
				res.locals['payload'] = { data: record };
42
			}
43
		} catch (error: any) {
44
			if (isDirectusError(error, ErrorCode.Forbidden)) {
45
				return next();
46
			}
47

48
			throw error;
49
		}
50

51
		return next();
52
	}),
53
	respond,
54
);
55

56
const readHandler = asyncHandler(async (req, res, next) => {
57
	const service = new VersionsService({
58
		accountability: req.accountability,
59
		schema: req.schema,
60
	});
61

62
	const metaService = new MetaService({
63
		accountability: req.accountability,
64
		schema: req.schema,
65
	});
66

67
	let result;
68

69
	if (req.singleton) {
70
		result = await service.readSingleton(req.sanitizedQuery);
71
	} else if (req.body.keys) {
72
		result = await service.readMany(req.body.keys, req.sanitizedQuery);
73
	} else {
74
		result = await service.readByQuery(req.sanitizedQuery);
75
	}
76

77
	const meta = await metaService.getMetaForQuery(req.collection, req.sanitizedQuery);
78

79
	res.locals['payload'] = { data: result, meta };
80
	return next();
81
});
82

83
router.get('/', validateBatch('read'), readHandler, respond);
84
router.search('/', validateBatch('read'), readHandler, respond);
85

86
router.get(
87
	'/:pk',
88
	asyncHandler(async (req, res, next) => {
89
		const service = new VersionsService({
90
			accountability: req.accountability,
91
			schema: req.schema,
92
		});
93

94
		const record = await service.readOne(req.params['pk']!, req.sanitizedQuery);
95

96
		res.locals['payload'] = { data: record || null };
97
		return next();
98
	}),
99
	respond,
100
);
101

102
router.patch(
103
	'/',
104
	validateBatch('update'),
105
	asyncHandler(async (req, res, next) => {
106
		const service = new VersionsService({
107
			accountability: req.accountability,
108
			schema: req.schema,
109
		});
110

111
		let keys: PrimaryKey[] = [];
112

113
		if (Array.isArray(req.body)) {
114
			keys = await service.updateBatch(req.body);
115
		} else if (req.body.keys) {
116
			keys = await service.updateMany(req.body.keys, req.body.data);
117
		} else {
118
			const sanitizedQuery = sanitizeQuery(req.body.query, req.accountability);
119
			keys = await service.updateByQuery(sanitizedQuery, req.body.data);
120
		}
121

122
		try {
123
			const result = await service.readMany(keys, req.sanitizedQuery);
124
			res.locals['payload'] = { data: result || null };
125
		} catch (error: any) {
126
			if (isDirectusError(error, ErrorCode.Forbidden)) {
127
				return next();
128
			}
129

130
			throw error;
131
		}
132

133
		return next();
134
	}),
135
	respond,
136
);
137

138
router.patch(
139
	'/:pk',
140
	asyncHandler(async (req, res, next) => {
141
		const service = new VersionsService({
142
			accountability: req.accountability,
143
			schema: req.schema,
144
		});
145

146
		const primaryKey = await service.updateOne(req.params['pk']!, req.body);
147

148
		try {
149
			const record = await service.readOne(primaryKey, req.sanitizedQuery);
150
			res.locals['payload'] = { data: record || null };
151
		} catch (error: any) {
152
			if (isDirectusError(error, ErrorCode.Forbidden)) {
153
				return next();
154
			}
155

156
			throw error;
157
		}
158

159
		return next();
160
	}),
161
	respond,
162
);
163

164
router.delete(
165
	'/',
166
	validateBatch('delete'),
167
	asyncHandler(async (req, _res, next) => {
168
		const service = new VersionsService({
169
			accountability: req.accountability,
170
			schema: req.schema,
171
		});
172

173
		if (Array.isArray(req.body)) {
174
			await service.deleteMany(req.body);
175
		} else if (req.body.keys) {
176
			await service.deleteMany(req.body.keys);
177
		} else {
178
			const sanitizedQuery = sanitizeQuery(req.body.query, req.accountability);
179
			await service.deleteByQuery(sanitizedQuery);
180
		}
181

182
		return next();
183
	}),
184
	respond,
185
);
186

187
router.delete(
188
	'/:pk',
189
	asyncHandler(async (req, _res, next) => {
190
		const service = new VersionsService({
191
			accountability: req.accountability,
192
			schema: req.schema,
193
		});
194

195
		await service.deleteOne(req.params['pk']!);
196

197
		return next();
198
	}),
199
	respond,
200
);
201

202
router.get(
203
	'/:pk/compare',
204
	asyncHandler(async (req, res, next) => {
205
		const service = new VersionsService({
206
			accountability: req.accountability,
207
			schema: req.schema,
208
		});
209

210
		const version = await service.readOne(req.params['pk']!);
211

212
		const { outdated, mainHash } = await service.verifyHash(version['collection'], version['item'], version['hash']);
213

214
		const saves = await service.getVersionSavesById(version['id']);
215

216
		const current = assign({}, ...saves);
217

218
		const main = await service.getMainItem(version['collection'], version['item']);
219

220
		res.locals['payload'] = { data: { outdated, mainHash, current, main } };
221

222
		return next();
223
	}),
224
	respond,
225
);
226

227
router.post(
228
	'/:pk/save',
229
	asyncHandler(async (req, res, next) => {
230
		const service = new VersionsService({
231
			accountability: req.accountability,
232
			schema: req.schema,
233
		});
234

235
		const version = await service.readOne(req.params['pk']!);
236

237
		const mainItem = await service.getMainItem(version['collection'], version['item']);
238

239
		await service.save(req.params['pk']!, req.body);
240

241
		const saves = await service.getVersionSavesById(req.params['pk']!);
242

243
		const result = assign(mainItem, ...saves);
244

245
		res.locals['payload'] = { data: result || null };
246

247
		return next();
248
	}),
249
	respond,
250
);
251

252
router.post(
253
	'/:pk/promote',
254
	asyncHandler(async (req, res, next) => {
255
		if (typeof req.body.mainHash !== 'string') {
256
			throw new InvalidPayloadError({ reason: `"mainHash" field is required` });
257
		}
258

259
		const service = new VersionsService({
260
			accountability: req.accountability,
261
			schema: req.schema,
262
		});
263

264
		const updatedItemKey = await service.promote(req.params['pk']!, req.body.mainHash, req.body?.['fields']);
265

266
		res.locals['payload'] = { data: updatedItemKey || null };
267

268
		return next();
269
	}),
270
	respond,
271
);
272

273
export default router;
274

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

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

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

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