gt-sanity 2.0.7 → 2.0.8
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.
- package/README.md +3 -0
- package/dist/index.d.mts +13 -14
- package/dist/index.d.ts +13 -14
- package/dist/index.js +54 -14
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +54 -14
- package/dist/index.mjs.map +1 -1
- package/package.json +2 -2
- package/src/adapter/core.ts +10 -0
- package/src/adapter/types.ts +6 -5
- package/src/configuration/baseDocumentLevelConfig/documentLevelPatch.ts +2 -1
- package/src/configuration/baseDocumentLevelConfig/helpers/createI18nDocAndPatchMetadata.ts +3 -1
- package/src/configuration/baseDocumentLevelConfig/helpers/patchI18nDoc.test.ts +52 -0
- package/src/configuration/baseDocumentLevelConfig/helpers/patchI18nDoc.ts +20 -2
- package/src/index.ts +4 -0
- package/src/utils/__tests__/forEachMatchingField.test.ts +71 -1
- package/src/utils/applyDocuments.ts +56 -5
- package/src/utils/serialize.ts +8 -5
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "gt-sanity",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.8",
|
|
4
4
|
"description": "General Translation integration with Sanity",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"sanity",
|
|
@@ -52,7 +52,7 @@
|
|
|
52
52
|
"jsonpointer": "^5.0.1",
|
|
53
53
|
"@sanity/document-internationalization": "^6.0.6",
|
|
54
54
|
"lodash.merge": "^4.6.2",
|
|
55
|
-
"generaltranslation": "8.2.
|
|
55
|
+
"generaltranslation": "8.2.7"
|
|
56
56
|
},
|
|
57
57
|
"devDependencies": {
|
|
58
58
|
"@portabletext/types": "^2.0.15",
|
package/src/adapter/core.ts
CHANGED
|
@@ -3,6 +3,7 @@ import { libraryDefaultLocale } from 'generaltranslation/internal';
|
|
|
3
3
|
import type { Secrets } from '../types';
|
|
4
4
|
import type {
|
|
5
5
|
TranslateDocumentFilter,
|
|
6
|
+
DedupeFields,
|
|
6
7
|
IgnoreFields,
|
|
7
8
|
SkipFields,
|
|
8
9
|
} from './types';
|
|
@@ -25,6 +26,7 @@ export class GTConfig {
|
|
|
25
26
|
singletons: string[];
|
|
26
27
|
singletonMapping: (sourceDocumentId: string, locale: string) => string;
|
|
27
28
|
ignoreFields: IgnoreFields[];
|
|
29
|
+
dedupeFields: DedupeFields[];
|
|
28
30
|
skipFields: SkipFields[];
|
|
29
31
|
translateDocuments: TranslateDocumentFilter[];
|
|
30
32
|
additionalStopTypes: string[];
|
|
@@ -41,6 +43,7 @@ export class GTConfig {
|
|
|
41
43
|
singletons: string[],
|
|
42
44
|
singletonMapping: (sourceDocumentId: string, locale: string) => string,
|
|
43
45
|
ignoreFields: IgnoreFields[],
|
|
46
|
+
dedupeFields: DedupeFields[],
|
|
44
47
|
skipFields: SkipFields[],
|
|
45
48
|
translateDocuments: TranslateDocumentFilter[],
|
|
46
49
|
additionalStopTypes: string[] = [],
|
|
@@ -55,6 +58,7 @@ export class GTConfig {
|
|
|
55
58
|
this.singletons = singletons;
|
|
56
59
|
this.singletonMapping = singletonMapping;
|
|
57
60
|
this.ignoreFields = ignoreFields;
|
|
61
|
+
this.dedupeFields = dedupeFields;
|
|
58
62
|
this.skipFields = skipFields;
|
|
59
63
|
this.translateDocuments = translateDocuments;
|
|
60
64
|
this.additionalStopTypes = additionalStopTypes;
|
|
@@ -76,6 +80,7 @@ export class GTConfig {
|
|
|
76
80
|
[],
|
|
77
81
|
[],
|
|
78
82
|
[],
|
|
83
|
+
[],
|
|
79
84
|
{},
|
|
80
85
|
{},
|
|
81
86
|
[]
|
|
@@ -92,6 +97,7 @@ export class GTConfig {
|
|
|
92
97
|
singletons: string[],
|
|
93
98
|
singletonMapping: (sourceDocumentId: string, locale: string) => string,
|
|
94
99
|
ignoreFields: IgnoreFields[],
|
|
100
|
+
dedupeFields: DedupeFields[],
|
|
95
101
|
skipFields: SkipFields[],
|
|
96
102
|
translateDocuments: TranslateDocumentFilter[],
|
|
97
103
|
additionalStopTypes: string[] = [],
|
|
@@ -106,6 +112,7 @@ export class GTConfig {
|
|
|
106
112
|
this.singletons = singletons;
|
|
107
113
|
this.singletonMapping = singletonMapping;
|
|
108
114
|
this.ignoreFields = ignoreFields;
|
|
115
|
+
this.dedupeFields = dedupeFields;
|
|
109
116
|
this.skipFields = skipFields;
|
|
110
117
|
this.translateDocuments = translateDocuments;
|
|
111
118
|
this.additionalStopTypes = additionalStopTypes;
|
|
@@ -137,6 +144,9 @@ export class GTConfig {
|
|
|
137
144
|
getIgnoreFields() {
|
|
138
145
|
return this.ignoreFields;
|
|
139
146
|
}
|
|
147
|
+
getDedupeFields() {
|
|
148
|
+
return this.dedupeFields;
|
|
149
|
+
}
|
|
140
150
|
getSkipFields() {
|
|
141
151
|
return this.skipFields;
|
|
142
152
|
}
|
package/src/adapter/types.ts
CHANGED
|
@@ -1,12 +1,13 @@
|
|
|
1
|
-
export type
|
|
1
|
+
export type FieldMatcher = {
|
|
2
2
|
documentId?: string;
|
|
3
3
|
fields?: { property: string; type?: string }[];
|
|
4
4
|
};
|
|
5
5
|
|
|
6
|
-
export type
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
6
|
+
export type IgnoreFields = FieldMatcher;
|
|
7
|
+
|
|
8
|
+
export type DedupeFields = FieldMatcher;
|
|
9
|
+
|
|
10
|
+
export type SkipFields = FieldMatcher;
|
|
10
11
|
|
|
11
12
|
export type TranslateDocumentFilter = {
|
|
12
13
|
documentId?: string;
|
|
@@ -35,7 +35,9 @@ export async function createI18nDocAndPatchMetadata(
|
|
|
35
35
|
sourceDocument,
|
|
36
36
|
rest,
|
|
37
37
|
pluginConfig.getIgnoreFields(),
|
|
38
|
-
pluginConfig.getSkipFields()
|
|
38
|
+
pluginConfig.getSkipFields(),
|
|
39
|
+
pluginConfig.getDedupeFields(),
|
|
40
|
+
localeId
|
|
39
41
|
);
|
|
40
42
|
|
|
41
43
|
// Check if this is a singleton document and apply singleton mapping
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { afterEach, describe, expect, test, vi } from 'vitest';
|
|
2
|
+
import { pluginConfig } from '../../../adapter/core';
|
|
3
|
+
import { patchI18nDoc } from './patchI18nDoc';
|
|
4
|
+
|
|
5
|
+
describe('patchI18nDoc', () => {
|
|
6
|
+
afterEach(() => {
|
|
7
|
+
vi.restoreAllMocks();
|
|
8
|
+
});
|
|
9
|
+
|
|
10
|
+
test('preserves existing translated dedupe fields during re-import', async () => {
|
|
11
|
+
vi.spyOn(pluginConfig, 'getIgnoreFields').mockReturnValue([]);
|
|
12
|
+
vi.spyOn(pluginConfig, 'getSkipFields').mockReturnValue([]);
|
|
13
|
+
vi.spyOn(pluginConfig, 'getDedupeFields').mockReturnValue([
|
|
14
|
+
{ fields: [{ property: '$.slug', type: 'slug' }] },
|
|
15
|
+
]);
|
|
16
|
+
|
|
17
|
+
const commit = vi.fn().mockResolvedValue({});
|
|
18
|
+
const patch = vi.fn().mockReturnValue({ commit });
|
|
19
|
+
const client = { patch } as any;
|
|
20
|
+
|
|
21
|
+
await patchI18nDoc(
|
|
22
|
+
'doc-1',
|
|
23
|
+
'drafts.doc-1-es',
|
|
24
|
+
{
|
|
25
|
+
_id: 'doc-1',
|
|
26
|
+
_type: 'article',
|
|
27
|
+
title: 'About',
|
|
28
|
+
slug: { _type: 'slug', current: 'about' },
|
|
29
|
+
},
|
|
30
|
+
{
|
|
31
|
+
_id: 'doc-1',
|
|
32
|
+
_type: 'article',
|
|
33
|
+
title: 'Acerca de',
|
|
34
|
+
},
|
|
35
|
+
{ title: 'Acerca de' },
|
|
36
|
+
client,
|
|
37
|
+
{
|
|
38
|
+
_id: 'drafts.doc-1-es',
|
|
39
|
+
_type: 'article',
|
|
40
|
+
title: 'Acerca de',
|
|
41
|
+
slug: { _type: 'slug', current: 'custom-spanish-slug' },
|
|
42
|
+
}
|
|
43
|
+
);
|
|
44
|
+
|
|
45
|
+
expect(patch).toHaveBeenCalledWith('drafts.doc-1-es', {
|
|
46
|
+
set: expect.objectContaining({
|
|
47
|
+
title: 'Acerca de',
|
|
48
|
+
slug: { _type: 'slug', current: 'custom-spanish-slug' },
|
|
49
|
+
}),
|
|
50
|
+
});
|
|
51
|
+
});
|
|
52
|
+
});
|
|
@@ -1,7 +1,12 @@
|
|
|
1
1
|
// adapted from https://github.com/sanity-io/sanity-translations-tab. See LICENSE.md for more details.
|
|
2
2
|
|
|
3
3
|
import { SanityClient, SanityDocumentLike } from 'sanity';
|
|
4
|
-
import
|
|
4
|
+
import JSONPointer from 'jsonpointer';
|
|
5
|
+
import {
|
|
6
|
+
applyDocuments,
|
|
7
|
+
deleteMatchingFields,
|
|
8
|
+
forEachMatchingField,
|
|
9
|
+
} from '../../../utils/applyDocuments';
|
|
5
10
|
import { pluginConfig } from '../../../adapter/core';
|
|
6
11
|
|
|
7
12
|
const SYSTEM_FIELDS = ['_id', '_rev', '_updatedAt', 'language'];
|
|
@@ -14,7 +19,8 @@ export async function patchI18nDoc(
|
|
|
14
19
|
sourceDocument: SanityDocumentLike,
|
|
15
20
|
mergedDocument: SanityDocumentLike,
|
|
16
21
|
translatedFields: Record<string, any>,
|
|
17
|
-
client: SanityClient
|
|
22
|
+
client: SanityClient,
|
|
23
|
+
existingDocument?: SanityDocumentLike
|
|
18
24
|
): Promise<void> {
|
|
19
25
|
const cleanedMerge: Record<string, any> = {};
|
|
20
26
|
Object.entries(mergedDocument).forEach(([key, value]) => {
|
|
@@ -43,6 +49,18 @@ export async function patchI18nDoc(
|
|
|
43
49
|
pluginConfig.getIgnoreFields(),
|
|
44
50
|
pluginConfig.getSkipFields()
|
|
45
51
|
);
|
|
52
|
+
const dedupeFields = pluginConfig.getDedupeFields();
|
|
53
|
+
deleteMatchingFields(sourceDocumentId, appliedDocument, dedupeFields);
|
|
54
|
+
if (existingDocument) {
|
|
55
|
+
forEachMatchingField(
|
|
56
|
+
sourceDocumentId,
|
|
57
|
+
existingDocument,
|
|
58
|
+
dedupeFields,
|
|
59
|
+
(result) => {
|
|
60
|
+
JSONPointer.set(appliedDocument, result.pointer, result.value);
|
|
61
|
+
}
|
|
62
|
+
);
|
|
63
|
+
}
|
|
46
64
|
const newDocument = await client
|
|
47
65
|
.patch(i18nDocId, { set: appliedDocument })
|
|
48
66
|
.commit();
|
package/src/index.ts
CHANGED
|
@@ -61,6 +61,7 @@ import { gt, pluginConfig } from './adapter/core';
|
|
|
61
61
|
import { libraryDefaultLocale } from 'generaltranslation/internal';
|
|
62
62
|
import { getLocaleProperties } from 'generaltranslation';
|
|
63
63
|
import type {
|
|
64
|
+
DedupeFields,
|
|
64
65
|
IgnoreFields,
|
|
65
66
|
SkipFields,
|
|
66
67
|
TranslateDocumentFilter,
|
|
@@ -83,6 +84,7 @@ export type GTPluginConfig = Omit<
|
|
|
83
84
|
// By default, the translated singleton document is is `${sourceDocumentId}-${locale}`
|
|
84
85
|
singletonMapping?: (sourceDocumentId: string, locale: string) => string;
|
|
85
86
|
ignoreFields?: IgnoreFields[];
|
|
87
|
+
dedupeFields?: DedupeFields[];
|
|
86
88
|
skipFields?: SkipFields[];
|
|
87
89
|
languageField?: string;
|
|
88
90
|
translateDocuments?: TranslateDocumentFilter[] | string[];
|
|
@@ -122,6 +124,7 @@ export const gtPlugin = definePlugin<GTPluginConfig>(
|
|
|
122
124
|
singletons,
|
|
123
125
|
singletonMapping,
|
|
124
126
|
ignoreFields,
|
|
127
|
+
dedupeFields,
|
|
125
128
|
skipFields,
|
|
126
129
|
translateDocuments,
|
|
127
130
|
secretsNamespace = SECRETS_NAMESPACE,
|
|
@@ -153,6 +156,7 @@ export const gtPlugin = definePlugin<GTPluginConfig>(
|
|
|
153
156
|
singletonMapping ||
|
|
154
157
|
((sourceDocumentId, locale) => `${sourceDocumentId}-${locale}`),
|
|
155
158
|
ignoreFields || [],
|
|
159
|
+
dedupeFields || [],
|
|
156
160
|
skipFields || [],
|
|
157
161
|
normalizedTranslateDocuments || [],
|
|
158
162
|
additionalStopTypes,
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, expect, test, vi } from 'vitest';
|
|
2
|
-
import { forEachMatchingField } from '../applyDocuments';
|
|
2
|
+
import { applyDocuments, forEachMatchingField } from '../applyDocuments';
|
|
3
3
|
import type { IgnoreFields } from '../../adapter/types';
|
|
4
4
|
|
|
5
5
|
describe('forEachMatchingField', () => {
|
|
@@ -169,3 +169,73 @@ describe('forEachMatchingField', () => {
|
|
|
169
169
|
expect(cb.mock.calls[0][0].pointer).toBe('/metadata/seo/title');
|
|
170
170
|
});
|
|
171
171
|
});
|
|
172
|
+
|
|
173
|
+
describe('applyDocuments dedupe fields', () => {
|
|
174
|
+
test('restores slug fields with a locale suffix', () => {
|
|
175
|
+
const sourceDoc = {
|
|
176
|
+
_id: 'doc-1',
|
|
177
|
+
title: 'Hello',
|
|
178
|
+
slug: { _type: 'slug', current: 'hello-world' },
|
|
179
|
+
};
|
|
180
|
+
const translatedDoc = {
|
|
181
|
+
_id: 'doc-1-es',
|
|
182
|
+
title: 'Hola',
|
|
183
|
+
};
|
|
184
|
+
|
|
185
|
+
const result = applyDocuments(
|
|
186
|
+
'doc-1',
|
|
187
|
+
sourceDoc,
|
|
188
|
+
translatedDoc,
|
|
189
|
+
[],
|
|
190
|
+
[],
|
|
191
|
+
[{ fields: [{ property: '$.slug' }] }],
|
|
192
|
+
'es'
|
|
193
|
+
);
|
|
194
|
+
|
|
195
|
+
expect(result).toEqual({
|
|
196
|
+
_id: 'doc-1-es',
|
|
197
|
+
title: 'Hola',
|
|
198
|
+
slug: { _type: 'slug', current: 'hello-world-es' },
|
|
199
|
+
});
|
|
200
|
+
});
|
|
201
|
+
|
|
202
|
+
test('dedupes string fields directly when the JSONPath targets a string', () => {
|
|
203
|
+
const sourceDoc = {
|
|
204
|
+
_id: 'doc-1',
|
|
205
|
+
title: 'Hello',
|
|
206
|
+
slug: { _type: 'slug', current: 'hello-world' },
|
|
207
|
+
};
|
|
208
|
+
|
|
209
|
+
const result = applyDocuments(
|
|
210
|
+
'doc-1',
|
|
211
|
+
sourceDoc,
|
|
212
|
+
{ title: 'Bonjour' },
|
|
213
|
+
[],
|
|
214
|
+
[],
|
|
215
|
+
[{ fields: [{ property: '$.slug.current' }] }],
|
|
216
|
+
'fr-CA'
|
|
217
|
+
);
|
|
218
|
+
|
|
219
|
+
expect(result.slug.current).toBe('hello-world-fr-ca');
|
|
220
|
+
});
|
|
221
|
+
|
|
222
|
+
test('does not append the same locale suffix twice', () => {
|
|
223
|
+
const sourceDoc = {
|
|
224
|
+
_id: 'doc-1',
|
|
225
|
+
title: 'Hello',
|
|
226
|
+
slug: { _type: 'slug', current: 'hello-world-fr' },
|
|
227
|
+
};
|
|
228
|
+
|
|
229
|
+
const result = applyDocuments(
|
|
230
|
+
'doc-1',
|
|
231
|
+
sourceDoc,
|
|
232
|
+
{ title: 'Bonjour' },
|
|
233
|
+
[],
|
|
234
|
+
[],
|
|
235
|
+
[{ fields: [{ property: '$.slug' }] }],
|
|
236
|
+
'fr'
|
|
237
|
+
);
|
|
238
|
+
|
|
239
|
+
expect(result.slug.current).toBe('hello-world-fr');
|
|
240
|
+
});
|
|
241
|
+
});
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import { JSONPath } from 'jsonpath-plus';
|
|
2
2
|
import JSONPointer from 'jsonpointer';
|
|
3
|
-
import type {
|
|
3
|
+
import type { DedupeFields, FieldMatcher, SkipFields } from '../adapter/types';
|
|
4
4
|
|
|
5
5
|
export function forEachMatchingField(
|
|
6
6
|
documentId: string,
|
|
7
7
|
document: Record<string, any>,
|
|
8
|
-
fields:
|
|
8
|
+
fields: FieldMatcher[],
|
|
9
9
|
callback: (result: {
|
|
10
10
|
pointer: string;
|
|
11
11
|
value: any;
|
|
@@ -67,7 +67,7 @@ export function forEachMatchingField(
|
|
|
67
67
|
export function deleteMatchingFields(
|
|
68
68
|
documentId: string,
|
|
69
69
|
document: Record<string, any>,
|
|
70
|
-
fields:
|
|
70
|
+
fields: FieldMatcher[]
|
|
71
71
|
): void {
|
|
72
72
|
const arrayRemovals: Array<{ parent: any[]; index: number }> = [];
|
|
73
73
|
|
|
@@ -93,8 +93,10 @@ export function applyDocuments(
|
|
|
93
93
|
documentId: string,
|
|
94
94
|
sourceDocument: Record<string, any>,
|
|
95
95
|
targetDocument: Record<string, any>,
|
|
96
|
-
ignore:
|
|
97
|
-
skip: SkipFields[] = []
|
|
96
|
+
ignore: FieldMatcher[],
|
|
97
|
+
skip: SkipFields[] = [],
|
|
98
|
+
dedupe: DedupeFields[] = [],
|
|
99
|
+
localeId?: string
|
|
98
100
|
) {
|
|
99
101
|
// Deep copy both documents so mutations (e.g. skip-field deletions) never affect the originals
|
|
100
102
|
const mergedDocument = JSON.parse(JSON.stringify(sourceDocument));
|
|
@@ -110,8 +112,57 @@ export function applyDocuments(
|
|
|
110
112
|
JSONPointer.set(mergedDocument, result.pointer, result.value);
|
|
111
113
|
});
|
|
112
114
|
|
|
115
|
+
// Restore de-duped fields from the source document with a deterministic locale suffix.
|
|
116
|
+
forEachMatchingField(documentId, sourceDocument, dedupe, (result) => {
|
|
117
|
+
JSONPointer.set(
|
|
118
|
+
mergedDocument,
|
|
119
|
+
result.pointer,
|
|
120
|
+
dedupeFieldValue(result.value, localeId)
|
|
121
|
+
);
|
|
122
|
+
});
|
|
123
|
+
|
|
113
124
|
// Remove skip fields from merged document
|
|
114
125
|
deleteMatchingFields(documentId, mergedDocument, skip);
|
|
115
126
|
|
|
116
127
|
return mergedDocument;
|
|
117
128
|
}
|
|
129
|
+
|
|
130
|
+
function dedupeFieldValue(value: any, localeId?: string): any {
|
|
131
|
+
if (!localeId) return value;
|
|
132
|
+
|
|
133
|
+
if (typeof value === 'string') {
|
|
134
|
+
return appendLocaleSuffix(value, localeId);
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
if (
|
|
138
|
+
value &&
|
|
139
|
+
typeof value === 'object' &&
|
|
140
|
+
!Array.isArray(value) &&
|
|
141
|
+
typeof value.current === 'string'
|
|
142
|
+
) {
|
|
143
|
+
return {
|
|
144
|
+
...value,
|
|
145
|
+
current: appendLocaleSuffix(value.current, localeId),
|
|
146
|
+
};
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
return value;
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
function appendLocaleSuffix(value: string, localeId: string): string {
|
|
153
|
+
if (!value) return value;
|
|
154
|
+
|
|
155
|
+
const suffix = createLocaleSuffix(localeId);
|
|
156
|
+
if (!suffix || value.endsWith(suffix)) return value;
|
|
157
|
+
|
|
158
|
+
return `${value}${suffix}`;
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
function createLocaleSuffix(localeId: string): string {
|
|
162
|
+
const normalized = localeId
|
|
163
|
+
.toLowerCase()
|
|
164
|
+
.replace(/[^a-z0-9]+/g, '-')
|
|
165
|
+
.replace(/^-|-$/g, '');
|
|
166
|
+
|
|
167
|
+
return normalized ? `-${normalized}` : '';
|
|
168
|
+
}
|
package/src/utils/serialize.ts
CHANGED
|
@@ -10,7 +10,7 @@ import { PortableTextHtmlComponents } from '@portabletext/to-html';
|
|
|
10
10
|
import { pluginConfig } from '../adapter/core';
|
|
11
11
|
import merge from 'lodash.merge';
|
|
12
12
|
import { deleteMatchingFields } from './applyDocuments';
|
|
13
|
-
import type {
|
|
13
|
+
import type { FieldMatcher } from '../adapter/types';
|
|
14
14
|
|
|
15
15
|
export function deserializeDocument(document: string) {
|
|
16
16
|
const deserializers = merge(
|
|
@@ -45,7 +45,8 @@ export function serializeDocument(
|
|
|
45
45
|
|
|
46
46
|
const docToSerialize = stripIgnoredFields(
|
|
47
47
|
document,
|
|
48
|
-
pluginConfig.getIgnoreFields()
|
|
48
|
+
pluginConfig.getIgnoreFields(),
|
|
49
|
+
pluginConfig.getDedupeFields()
|
|
49
50
|
);
|
|
50
51
|
|
|
51
52
|
const serialized = BaseDocumentSerializer(schema).serializeDocument(
|
|
@@ -60,16 +61,18 @@ export function serializeDocument(
|
|
|
60
61
|
|
|
61
62
|
function stripIgnoredFields(
|
|
62
63
|
document: SanityDocument,
|
|
63
|
-
ignoreFields:
|
|
64
|
+
ignoreFields: FieldMatcher[],
|
|
65
|
+
dedupeFields: FieldMatcher[]
|
|
64
66
|
): SanityDocument {
|
|
65
|
-
|
|
67
|
+
const fieldsToStrip = [...ignoreFields, ...dedupeFields];
|
|
68
|
+
if (fieldsToStrip.length === 0) return document;
|
|
66
69
|
|
|
67
70
|
const strippedDoc = JSON.parse(JSON.stringify(document)) as SanityDocument;
|
|
68
71
|
|
|
69
72
|
deleteMatchingFields(
|
|
70
73
|
document._id.replace('drafts.', ''),
|
|
71
74
|
strippedDoc,
|
|
72
|
-
|
|
75
|
+
fieldsToStrip
|
|
73
76
|
);
|
|
74
77
|
|
|
75
78
|
return strippedDoc;
|