@strapi/utils 4.20.5 → 5.0.0-alpha.0
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/dist/async.d.ts +9 -6
- package/dist/async.d.ts.map +1 -1
- package/dist/content-types.d.ts +2 -4
- package/dist/content-types.d.ts.map +1 -1
- package/dist/convert-query-params.d.ts +11 -8
- package/dist/convert-query-params.d.ts.map +1 -1
- package/dist/env-helper.d.ts +3 -1
- package/dist/env-helper.d.ts.map +1 -1
- package/dist/index.d.ts +25 -33
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1444 -1444
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +1450 -1452
- package/dist/index.mjs.map +1 -1
- package/dist/machine-id.d.ts +3 -0
- package/dist/machine-id.d.ts.map +1 -0
- package/dist/package-manager.d.ts +7 -0
- package/dist/package-manager.d.ts.map +1 -0
- package/dist/primitives/arrays.d.ts +3 -0
- package/dist/primitives/arrays.d.ts.map +1 -0
- package/dist/primitives/dates.d.ts +3 -0
- package/dist/primitives/dates.d.ts.map +1 -0
- package/dist/primitives/index.d.ts +5 -0
- package/dist/primitives/index.d.ts.map +1 -0
- package/dist/primitives/objects.d.ts +3 -0
- package/dist/primitives/objects.d.ts.map +1 -0
- package/dist/{string-formatting.d.ts → primitives/strings.d.ts} +3 -6
- package/dist/primitives/strings.d.ts.map +1 -0
- package/dist/sanitize/index.d.ts.map +1 -1
- package/dist/sanitize/sanitizers.d.ts.map +1 -1
- package/dist/sanitize/visitors/expand-wildcard-populate.d.ts +4 -0
- package/dist/sanitize/visitors/expand-wildcard-populate.d.ts.map +1 -0
- package/dist/sanitize/visitors/index.d.ts +1 -0
- package/dist/sanitize/visitors/index.d.ts.map +1 -1
- package/dist/traverse/factory.d.ts +1 -1
- package/dist/traverse/query-populate.d.ts.map +1 -1
- package/dist/types.d.ts +1 -4
- package/dist/types.d.ts.map +1 -1
- package/dist/validate/index.d.ts +1 -0
- package/dist/validate/index.d.ts.map +1 -1
- package/dist/validate/utils.d.ts +2 -1
- package/dist/validate/utils.d.ts.map +1 -1
- package/dist/validate/validators.d.ts +2 -1
- package/dist/validate/validators.d.ts.map +1 -1
- package/dist/yup.d.ts +0 -1
- package/dist/yup.d.ts.map +1 -1
- package/package.json +10 -8
- package/dist/code-generator.d.ts +0 -3
- package/dist/code-generator.d.ts.map +0 -1
- package/dist/config.d.ts +0 -9
- package/dist/config.d.ts.map +0 -1
- package/dist/object-formatting.d.ts +0 -4
- package/dist/object-formatting.d.ts.map +0 -1
- package/dist/parse-multipart.d.ts +0 -7
- package/dist/parse-multipart.d.ts.map +0 -1
- package/dist/string-formatting.d.ts.map +0 -1
- package/dist/template-configuration.d.ts +0 -6
- package/dist/template-configuration.d.ts.map +0 -1
- package/dist/webhook.d.ts +0 -6
- package/dist/webhook.d.ts.map +0 -1
package/dist/index.mjs
CHANGED
|
@@ -1,10 +1,14 @@
|
|
|
1
|
-
import _$1, {
|
|
2
|
-
import {
|
|
3
|
-
import * as yup$1 from "yup";
|
|
4
|
-
import { HttpError } from "http-errors";
|
|
5
|
-
import slugify from "@sindresorhus/slugify";
|
|
1
|
+
import _$1, { kebabCase } from "lodash";
|
|
2
|
+
import { has, union, getOr, assoc, assign, cloneDeep, remove, eq, curry, isArray, isString, isNil, toPath, isObject, clone, pick, isEmpty, omit, trim, pipe as pipe$1, split, map as map$1, flatten, first, identity, constant, join, merge, mergeAll, get, toNumber, isInteger, defaults, trimChars, trimCharsEnd, trimCharsStart, isNumber } from "lodash/fp";
|
|
6
3
|
import pMap from "p-map";
|
|
4
|
+
import { HttpError } from "http-errors";
|
|
5
|
+
import { randomUUID } from "crypto";
|
|
6
|
+
import { machineIdSync } from "node-machine-id";
|
|
7
|
+
import * as yup$1 from "yup";
|
|
8
|
+
import execa from "execa";
|
|
9
|
+
import preferredPM from "preferred-pm";
|
|
7
10
|
import { Writable } from "node:stream";
|
|
11
|
+
import slugify from "@sindresorhus/slugify";
|
|
8
12
|
function _mergeNamespaces(n, m) {
|
|
9
13
|
for (var i = 0; i < m.length; i++) {
|
|
10
14
|
const e = m[i];
|
|
@@ -24,53 +28,20 @@ function _mergeNamespaces(n, m) {
|
|
|
24
28
|
}
|
|
25
29
|
return Object.freeze(Object.defineProperty(n, Symbol.toStringTag, { value: "Module" }));
|
|
26
30
|
}
|
|
27
|
-
const parseMultipartData = (ctx) => {
|
|
28
|
-
if (!ctx.is("multipart")) {
|
|
29
|
-
return { data: ctx.request.body, files: {} };
|
|
30
|
-
}
|
|
31
|
-
const { body = {}, files = {} } = ctx.request;
|
|
32
|
-
if (!body.data) {
|
|
33
|
-
return ctx.badRequest(
|
|
34
|
-
`When using multipart/form-data you need to provide your data in a JSON 'data' field.`
|
|
35
|
-
);
|
|
36
|
-
}
|
|
37
|
-
let data;
|
|
38
|
-
try {
|
|
39
|
-
data = JSON.parse(body.data);
|
|
40
|
-
} catch (error) {
|
|
41
|
-
return ctx.badRequest(`Invalid 'data' field. 'data' should be a valid JSON.`);
|
|
42
|
-
}
|
|
43
|
-
const filesToUpload = Object.keys(files).reduce((acc2, key2) => {
|
|
44
|
-
const fullPath = _$1.toPath(key2);
|
|
45
|
-
if (fullPath.length <= 1 || fullPath[0] !== "files") {
|
|
46
|
-
return ctx.badRequest(
|
|
47
|
-
`When using multipart/form-data you need to provide your files by prefixing them with the 'files'.
|
|
48
|
-
For example, when a media file is named "avatar", make sure the form key name is "files.avatar"`
|
|
49
|
-
);
|
|
50
|
-
}
|
|
51
|
-
const path = _$1.tail(fullPath);
|
|
52
|
-
acc2[path.join(".")] = files[key2];
|
|
53
|
-
return acc2;
|
|
54
|
-
}, {});
|
|
55
|
-
return {
|
|
56
|
-
data,
|
|
57
|
-
files: filesToUpload
|
|
58
|
-
};
|
|
59
|
-
};
|
|
60
31
|
const _ = require("lodash");
|
|
61
|
-
const dates = require("date-fns");
|
|
32
|
+
const dates$1 = require("date-fns");
|
|
62
33
|
const timeRegex = /^(2[0-3]|[01][0-9]):([0-5][0-9]):([0-5][0-9])(.[0-9]{1,3})?$/;
|
|
63
34
|
const isDate = (v) => {
|
|
64
|
-
return dates.isDate(v);
|
|
35
|
+
return dates$1.isDate(v);
|
|
65
36
|
};
|
|
66
|
-
const parseTime = (
|
|
67
|
-
if (isDate(
|
|
68
|
-
return dates.format(
|
|
37
|
+
const parseTime = (value) => {
|
|
38
|
+
if (isDate(value)) {
|
|
39
|
+
return dates$1.format(value, "HH:mm:ss.SSS");
|
|
69
40
|
}
|
|
70
|
-
if (typeof
|
|
71
|
-
throw new Error(`Expected a string, got a ${typeof
|
|
41
|
+
if (typeof value !== "string") {
|
|
42
|
+
throw new Error(`Expected a string, got a ${typeof value}`);
|
|
72
43
|
}
|
|
73
|
-
const result =
|
|
44
|
+
const result = value.match(timeRegex);
|
|
74
45
|
if (result === null) {
|
|
75
46
|
throw new Error("Invalid time format, expected HH:mm:ss.SSS");
|
|
76
47
|
}
|
|
@@ -78,721 +49,289 @@ const parseTime = (value2) => {
|
|
|
78
49
|
const fractionPart = _.padEnd(fraction.slice(1), 3, "0");
|
|
79
50
|
return `${hours}:${minutes}:${seconds}.${fractionPart}`;
|
|
80
51
|
};
|
|
81
|
-
const parseDate = (
|
|
82
|
-
if (isDate(
|
|
83
|
-
return dates.format(
|
|
52
|
+
const parseDate = (value) => {
|
|
53
|
+
if (isDate(value)) {
|
|
54
|
+
return dates$1.format(value, "yyyy-MM-dd");
|
|
84
55
|
}
|
|
85
|
-
if (typeof
|
|
86
|
-
throw new Error(`Expected a string, got a ${typeof
|
|
56
|
+
if (typeof value !== "string") {
|
|
57
|
+
throw new Error(`Expected a string, got a ${typeof value}`);
|
|
87
58
|
}
|
|
88
59
|
try {
|
|
89
|
-
const date = dates.parseISO(
|
|
90
|
-
if (dates.isValid(date))
|
|
91
|
-
return dates.format(date, "yyyy-MM-dd");
|
|
60
|
+
const date = dates$1.parseISO(value);
|
|
61
|
+
if (dates$1.isValid(date))
|
|
62
|
+
return dates$1.format(date, "yyyy-MM-dd");
|
|
92
63
|
throw new Error(`Invalid format, expected an ISO compatible date`);
|
|
93
64
|
} catch (error) {
|
|
94
65
|
throw new Error(`Invalid format, expected an ISO compatible date`);
|
|
95
66
|
}
|
|
96
67
|
};
|
|
97
|
-
const parseDateTimeOrTimestamp = (
|
|
98
|
-
if (isDate(
|
|
99
|
-
return
|
|
68
|
+
const parseDateTimeOrTimestamp = (value) => {
|
|
69
|
+
if (isDate(value)) {
|
|
70
|
+
return value;
|
|
100
71
|
}
|
|
101
|
-
if (typeof
|
|
102
|
-
throw new Error(`Expected a string, got a ${typeof
|
|
72
|
+
if (typeof value !== "string") {
|
|
73
|
+
throw new Error(`Expected a string, got a ${typeof value}`);
|
|
103
74
|
}
|
|
104
75
|
try {
|
|
105
|
-
const date = dates.parseISO(
|
|
106
|
-
if (dates.isValid(date))
|
|
76
|
+
const date = dates$1.parseISO(value);
|
|
77
|
+
if (dates$1.isValid(date))
|
|
107
78
|
return date;
|
|
108
|
-
const milliUnixDate = dates.parse(
|
|
109
|
-
if (dates.isValid(milliUnixDate))
|
|
79
|
+
const milliUnixDate = dates$1.parse(value, "T", /* @__PURE__ */ new Date());
|
|
80
|
+
if (dates$1.isValid(milliUnixDate))
|
|
110
81
|
return milliUnixDate;
|
|
111
82
|
throw new Error(`Invalid format, expected a timestamp or an ISO date`);
|
|
112
83
|
} catch (error) {
|
|
113
84
|
throw new Error(`Invalid format, expected a timestamp or an ISO date`);
|
|
114
85
|
}
|
|
115
86
|
};
|
|
116
|
-
const parseBoolean = (
|
|
87
|
+
const parseBoolean = (value, options) => {
|
|
117
88
|
const { forceCast = false } = options;
|
|
118
|
-
if (typeof
|
|
119
|
-
return
|
|
89
|
+
if (typeof value === "boolean") {
|
|
90
|
+
return value;
|
|
120
91
|
}
|
|
121
|
-
if (typeof
|
|
122
|
-
if (["true", "t", "1", 1].includes(
|
|
92
|
+
if (typeof value === "string" || typeof value === "number") {
|
|
93
|
+
if (["true", "t", "1", 1].includes(value)) {
|
|
123
94
|
return true;
|
|
124
95
|
}
|
|
125
|
-
if (["false", "f", "0", 0].includes(
|
|
96
|
+
if (["false", "f", "0", 0].includes(value)) {
|
|
126
97
|
return false;
|
|
127
98
|
}
|
|
128
99
|
}
|
|
129
100
|
if (forceCast) {
|
|
130
|
-
return Boolean(
|
|
101
|
+
return Boolean(value);
|
|
131
102
|
}
|
|
132
103
|
throw new Error('Invalid boolean input. Expected "t","1","true","false","0","f"');
|
|
133
104
|
};
|
|
134
105
|
const parseType = (options) => {
|
|
135
|
-
const { type, value
|
|
106
|
+
const { type, value, forceCast } = options;
|
|
136
107
|
switch (type) {
|
|
137
108
|
case "boolean":
|
|
138
|
-
return parseBoolean(
|
|
109
|
+
return parseBoolean(value, { forceCast });
|
|
139
110
|
case "integer":
|
|
140
111
|
case "biginteger":
|
|
141
112
|
case "float":
|
|
142
113
|
case "decimal": {
|
|
143
|
-
return _.toNumber(
|
|
114
|
+
return _.toNumber(value);
|
|
144
115
|
}
|
|
145
116
|
case "time": {
|
|
146
|
-
return parseTime(
|
|
117
|
+
return parseTime(value);
|
|
147
118
|
}
|
|
148
119
|
case "date": {
|
|
149
|
-
return parseDate(
|
|
120
|
+
return parseDate(value);
|
|
150
121
|
}
|
|
151
122
|
case "timestamp":
|
|
152
123
|
case "datetime": {
|
|
153
|
-
return parseDateTimeOrTimestamp(
|
|
124
|
+
return parseDateTimeOrTimestamp(value);
|
|
154
125
|
}
|
|
155
126
|
default:
|
|
156
|
-
return
|
|
157
|
-
}
|
|
158
|
-
};
|
|
159
|
-
const PLUGIN_PREFIX = "plugin::";
|
|
160
|
-
const API_PREFIX = "api::";
|
|
161
|
-
const parsePolicy = (policy2) => {
|
|
162
|
-
if (typeof policy2 === "string") {
|
|
163
|
-
return { policyName: policy2, config: {} };
|
|
127
|
+
return value;
|
|
164
128
|
}
|
|
165
|
-
const { name, config } = policy2;
|
|
166
|
-
return { policyName: name, config };
|
|
167
129
|
};
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
130
|
+
function envFn(key, defaultValue) {
|
|
131
|
+
return _$1.has(process.env, key) ? process.env[key] : defaultValue;
|
|
132
|
+
}
|
|
133
|
+
function getKey(key) {
|
|
134
|
+
return process.env[key] ?? "";
|
|
135
|
+
}
|
|
136
|
+
const utils = {
|
|
137
|
+
int(key, defaultValue) {
|
|
138
|
+
if (!_$1.has(process.env, key)) {
|
|
139
|
+
return defaultValue;
|
|
140
|
+
}
|
|
141
|
+
return parseInt(getKey(key), 10);
|
|
142
|
+
},
|
|
143
|
+
float(key, defaultValue) {
|
|
144
|
+
if (!_$1.has(process.env, key)) {
|
|
145
|
+
return defaultValue;
|
|
146
|
+
}
|
|
147
|
+
return parseFloat(getKey(key));
|
|
148
|
+
},
|
|
149
|
+
bool(key, defaultValue) {
|
|
150
|
+
if (!_$1.has(process.env, key)) {
|
|
151
|
+
return defaultValue;
|
|
152
|
+
}
|
|
153
|
+
return getKey(key) === "true";
|
|
154
|
+
},
|
|
155
|
+
json(key, defaultValue) {
|
|
156
|
+
if (!_$1.has(process.env, key)) {
|
|
157
|
+
return defaultValue;
|
|
158
|
+
}
|
|
159
|
+
try {
|
|
160
|
+
return JSON.parse(getKey(key));
|
|
161
|
+
} catch (error) {
|
|
162
|
+
if (error instanceof Error) {
|
|
163
|
+
throw new Error(`Invalid json environment variable ${key}: ${error.message}`);
|
|
164
|
+
}
|
|
165
|
+
throw error;
|
|
166
|
+
}
|
|
167
|
+
},
|
|
168
|
+
array(key, defaultValue) {
|
|
169
|
+
if (!_$1.has(process.env, key)) {
|
|
170
|
+
return defaultValue;
|
|
171
|
+
}
|
|
172
|
+
let value = getKey(key);
|
|
173
|
+
if (value.startsWith("[") && value.endsWith("]")) {
|
|
174
|
+
value = value.substring(1, value.length - 1);
|
|
175
|
+
}
|
|
176
|
+
return value.split(",").map((v) => {
|
|
177
|
+
return _$1.trim(_$1.trim(v, " "), '"');
|
|
178
|
+
});
|
|
179
|
+
},
|
|
180
|
+
date(key, defaultValue) {
|
|
181
|
+
if (!_$1.has(process.env, key)) {
|
|
182
|
+
return defaultValue;
|
|
183
|
+
}
|
|
184
|
+
return new Date(getKey(key));
|
|
185
|
+
},
|
|
186
|
+
/**
|
|
187
|
+
* Gets a value from env that matches oneOf provided values
|
|
188
|
+
* @param {string} key
|
|
189
|
+
* @param {string[]} expectedValues
|
|
190
|
+
* @param {string|undefined} defaultValue
|
|
191
|
+
* @returns {string|undefined}
|
|
192
|
+
*/
|
|
193
|
+
oneOf(key, expectedValues, defaultValue) {
|
|
194
|
+
if (!expectedValues) {
|
|
195
|
+
throw new Error(`env.oneOf requires expectedValues`);
|
|
196
|
+
}
|
|
197
|
+
if (defaultValue && !expectedValues.includes(defaultValue)) {
|
|
198
|
+
throw new Error(`env.oneOf requires defaultValue to be included in expectedValues`);
|
|
199
|
+
}
|
|
200
|
+
const rawValue = env(key, defaultValue);
|
|
201
|
+
return expectedValues.includes(rawValue) ? rawValue : defaultValue;
|
|
175
202
|
}
|
|
176
203
|
};
|
|
177
|
-
const
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
204
|
+
const env = Object.assign(envFn, utils);
|
|
205
|
+
const SINGLE_TYPE = "singleType";
|
|
206
|
+
const COLLECTION_TYPE = "collectionType";
|
|
207
|
+
const ID_ATTRIBUTE$4 = "id";
|
|
208
|
+
const DOC_ID_ATTRIBUTE$4 = "documentId";
|
|
209
|
+
const PUBLISHED_AT_ATTRIBUTE$1 = "publishedAt";
|
|
210
|
+
const CREATED_BY_ATTRIBUTE$3 = "createdBy";
|
|
211
|
+
const UPDATED_BY_ATTRIBUTE$3 = "updatedBy";
|
|
212
|
+
const CREATED_AT_ATTRIBUTE = "createdAt";
|
|
213
|
+
const UPDATED_AT_ATTRIBUTE = "updatedAt";
|
|
214
|
+
const constants$1 = {
|
|
215
|
+
ID_ATTRIBUTE: ID_ATTRIBUTE$4,
|
|
216
|
+
DOC_ID_ATTRIBUTE: DOC_ID_ATTRIBUTE$4,
|
|
217
|
+
PUBLISHED_AT_ATTRIBUTE: PUBLISHED_AT_ATTRIBUTE$1,
|
|
218
|
+
CREATED_BY_ATTRIBUTE: CREATED_BY_ATTRIBUTE$3,
|
|
219
|
+
UPDATED_BY_ATTRIBUTE: UPDATED_BY_ATTRIBUTE$3,
|
|
220
|
+
CREATED_AT_ATTRIBUTE,
|
|
221
|
+
UPDATED_AT_ATTRIBUTE,
|
|
222
|
+
SINGLE_TYPE,
|
|
223
|
+
COLLECTION_TYPE
|
|
197
224
|
};
|
|
198
|
-
const
|
|
199
|
-
const
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
return resolvedPolicy;
|
|
225
|
+
const getTimestamps = (model) => {
|
|
226
|
+
const attributes = [];
|
|
227
|
+
if (has(CREATED_AT_ATTRIBUTE, model.attributes)) {
|
|
228
|
+
attributes.push(CREATED_AT_ATTRIBUTE);
|
|
203
229
|
}
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
return localPolicy;
|
|
230
|
+
if (has(UPDATED_AT_ATTRIBUTE, model.attributes)) {
|
|
231
|
+
attributes.push(UPDATED_AT_ATTRIBUTE);
|
|
207
232
|
}
|
|
208
|
-
|
|
233
|
+
return attributes;
|
|
209
234
|
};
|
|
210
|
-
const
|
|
211
|
-
const
|
|
212
|
-
if (
|
|
213
|
-
|
|
235
|
+
const getCreatorFields = (model) => {
|
|
236
|
+
const attributes = [];
|
|
237
|
+
if (has(CREATED_BY_ATTRIBUTE$3, model.attributes)) {
|
|
238
|
+
attributes.push(CREATED_BY_ATTRIBUTE$3);
|
|
214
239
|
}
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
if (typeof policy2 === "function") {
|
|
218
|
-
return policy2;
|
|
240
|
+
if (has(UPDATED_BY_ATTRIBUTE$3, model.attributes)) {
|
|
241
|
+
attributes.push(UPDATED_BY_ATTRIBUTE$3);
|
|
219
242
|
}
|
|
220
|
-
|
|
221
|
-
|
|
243
|
+
return attributes;
|
|
244
|
+
};
|
|
245
|
+
const getNonWritableAttributes = (model) => {
|
|
246
|
+
if (!model)
|
|
247
|
+
return [];
|
|
248
|
+
const nonWritableAttributes = _$1.reduce(
|
|
249
|
+
model.attributes,
|
|
250
|
+
(acc, attr, attrName) => attr.writable === false ? acc.concat(attrName) : acc,
|
|
251
|
+
[]
|
|
252
|
+
);
|
|
253
|
+
return _$1.uniq([
|
|
254
|
+
ID_ATTRIBUTE$4,
|
|
255
|
+
DOC_ID_ATTRIBUTE$4,
|
|
256
|
+
...getTimestamps(model),
|
|
257
|
+
...nonWritableAttributes
|
|
258
|
+
]);
|
|
259
|
+
};
|
|
260
|
+
const getWritableAttributes = (model) => {
|
|
261
|
+
if (!model)
|
|
262
|
+
return [];
|
|
263
|
+
return _$1.difference(Object.keys(model.attributes), getNonWritableAttributes(model));
|
|
264
|
+
};
|
|
265
|
+
const isWritableAttribute = (model, attributeName) => {
|
|
266
|
+
return getWritableAttributes(model).includes(attributeName);
|
|
267
|
+
};
|
|
268
|
+
const getNonVisibleAttributes = (model) => {
|
|
269
|
+
const nonVisibleAttributes = _$1.reduce(
|
|
270
|
+
model.attributes,
|
|
271
|
+
(acc, attr, attrName) => attr.visible === false ? acc.concat(attrName) : acc,
|
|
272
|
+
[]
|
|
273
|
+
);
|
|
274
|
+
return _$1.uniq([ID_ATTRIBUTE$4, DOC_ID_ATTRIBUTE$4, ...getTimestamps(model), ...nonVisibleAttributes]);
|
|
275
|
+
};
|
|
276
|
+
const getVisibleAttributes = (model) => {
|
|
277
|
+
return _$1.difference(_$1.keys(model.attributes), getNonVisibleAttributes(model));
|
|
278
|
+
};
|
|
279
|
+
const isVisibleAttribute = (model, attributeName) => {
|
|
280
|
+
return getVisibleAttributes(model).includes(attributeName);
|
|
281
|
+
};
|
|
282
|
+
const getOptions = (model) => _$1.assign({ draftAndPublish: false }, _$1.get(model, "options", {}));
|
|
283
|
+
const hasDraftAndPublish = (model) => _$1.get(model, "options.draftAndPublish", false) === true;
|
|
284
|
+
const isDraft = (data, model) => hasDraftAndPublish(model) && _$1.get(data, PUBLISHED_AT_ATTRIBUTE$1) === null;
|
|
285
|
+
const isSingleType = ({ kind = COLLECTION_TYPE }) => kind === SINGLE_TYPE;
|
|
286
|
+
const isCollectionType = ({ kind = COLLECTION_TYPE }) => kind === COLLECTION_TYPE;
|
|
287
|
+
const isKind = (kind) => (model) => model.kind === kind;
|
|
288
|
+
const getStoredPrivateAttributes = (model) => union(
|
|
289
|
+
strapi?.config?.get("api.responses.privateAttributes", []) ?? [],
|
|
290
|
+
getOr([], "options.privateAttributes", model)
|
|
291
|
+
);
|
|
292
|
+
const getPrivateAttributes = (model) => {
|
|
293
|
+
return _$1.union(
|
|
294
|
+
getStoredPrivateAttributes(model),
|
|
295
|
+
_$1.keys(_$1.pickBy(model.attributes, (attr) => !!attr.private))
|
|
296
|
+
);
|
|
297
|
+
};
|
|
298
|
+
const isPrivateAttribute = (model, attributeName) => {
|
|
299
|
+
if (model?.attributes?.[attributeName]?.private === true) {
|
|
300
|
+
return true;
|
|
222
301
|
}
|
|
223
|
-
return
|
|
302
|
+
return getStoredPrivateAttributes(model).includes(attributeName);
|
|
224
303
|
};
|
|
225
|
-
const
|
|
226
|
-
|
|
227
|
-
const wrappedValidator = (config) => {
|
|
228
|
-
if (validator) {
|
|
229
|
-
try {
|
|
230
|
-
validator(config);
|
|
231
|
-
} catch (e) {
|
|
232
|
-
throw new Error(`Invalid config passed to "${name}" policy.`);
|
|
233
|
-
}
|
|
234
|
-
}
|
|
235
|
-
};
|
|
236
|
-
return {
|
|
237
|
-
name,
|
|
238
|
-
validator: wrappedValidator,
|
|
239
|
-
handler
|
|
240
|
-
};
|
|
304
|
+
const isScalarAttribute = (attribute) => {
|
|
305
|
+
return !["media", "component", "relation", "dynamiczone"].includes(attribute?.type);
|
|
241
306
|
};
|
|
242
|
-
const
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
307
|
+
const isMediaAttribute = (attribute) => attribute?.type === "media";
|
|
308
|
+
const isRelationalAttribute = (attribute) => attribute?.type === "relation";
|
|
309
|
+
const isComponentAttribute = (attribute) => ["component", "dynamiczone"].includes(attribute?.type);
|
|
310
|
+
const isDynamicZoneAttribute = (attribute) => attribute?.type === "dynamiczone";
|
|
311
|
+
const isMorphToRelationalAttribute = (attribute) => {
|
|
312
|
+
return isRelationalAttribute(attribute) && attribute?.relation?.startsWith?.("morphTo");
|
|
313
|
+
};
|
|
314
|
+
const getComponentAttributes = (schema) => {
|
|
315
|
+
return _$1.reduce(
|
|
316
|
+
schema.attributes,
|
|
317
|
+
(acc, attr, attrName) => {
|
|
318
|
+
if (isComponentAttribute(attr))
|
|
319
|
+
acc.push(attrName);
|
|
320
|
+
return acc;
|
|
249
321
|
},
|
|
250
|
-
|
|
322
|
+
[]
|
|
251
323
|
);
|
|
252
324
|
};
|
|
253
|
-
const
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
},
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
const isObj$3 = (value2) => isPlainObject$1(value2);
|
|
264
|
-
const templateConfiguration = (obj, configPath = "") => {
|
|
265
|
-
return Object.keys(obj).reduce((acc, key) => {
|
|
266
|
-
const value = obj[key];
|
|
267
|
-
if (isObj$3(value) && !isString(value)) {
|
|
268
|
-
acc[key] = templateConfiguration(value, `${configPath}.${key}`);
|
|
269
|
-
} else if (isString(value) && !excludeConfigPaths.includes(configPath.substr(1)) && value.match(regex) !== null) {
|
|
270
|
-
acc[key] = eval("`" + value + "`");
|
|
271
|
-
} else {
|
|
272
|
-
acc[key] = value;
|
|
273
|
-
}
|
|
274
|
-
return acc;
|
|
275
|
-
}, {});
|
|
276
|
-
};
|
|
277
|
-
const formatYupInnerError = (yupError) => ({
|
|
278
|
-
path: toPath(yupError.path),
|
|
279
|
-
message: yupError.message,
|
|
280
|
-
name: yupError.name
|
|
281
|
-
});
|
|
282
|
-
const formatYupErrors = (yupError) => ({
|
|
283
|
-
errors: isEmpty(yupError.inner) ? [formatYupInnerError(yupError)] : yupError.inner.map(formatYupInnerError),
|
|
284
|
-
message: yupError.message
|
|
285
|
-
});
|
|
286
|
-
class ApplicationError extends Error {
|
|
287
|
-
name;
|
|
288
|
-
details;
|
|
289
|
-
message;
|
|
290
|
-
constructor(message = "An application error occured", details = {}) {
|
|
291
|
-
super();
|
|
292
|
-
this.name = "ApplicationError";
|
|
293
|
-
this.message = message;
|
|
294
|
-
this.details = details;
|
|
295
|
-
}
|
|
296
|
-
}
|
|
297
|
-
class ValidationError extends ApplicationError {
|
|
298
|
-
constructor(message, details) {
|
|
299
|
-
super(message, details);
|
|
300
|
-
this.name = "ValidationError";
|
|
301
|
-
}
|
|
302
|
-
}
|
|
303
|
-
class YupValidationError extends ValidationError {
|
|
304
|
-
constructor(yupError, message) {
|
|
305
|
-
super("Validation");
|
|
306
|
-
const { errors: errors2, message: yupMessage } = formatYupErrors(yupError);
|
|
307
|
-
this.message = message || yupMessage;
|
|
308
|
-
this.details = { errors: errors2 };
|
|
309
|
-
}
|
|
310
|
-
}
|
|
311
|
-
class PaginationError extends ApplicationError {
|
|
312
|
-
constructor(message = "Invalid pagination", details) {
|
|
313
|
-
super(message, details);
|
|
314
|
-
this.name = "PaginationError";
|
|
315
|
-
this.message = message;
|
|
316
|
-
}
|
|
317
|
-
}
|
|
318
|
-
class NotFoundError extends ApplicationError {
|
|
319
|
-
constructor(message = "Entity not found", details) {
|
|
320
|
-
super(message, details);
|
|
321
|
-
this.name = "NotFoundError";
|
|
322
|
-
this.message = message;
|
|
323
|
-
}
|
|
324
|
-
}
|
|
325
|
-
class ForbiddenError extends ApplicationError {
|
|
326
|
-
constructor(message = "Forbidden access", details) {
|
|
327
|
-
super(message, details);
|
|
328
|
-
this.name = "ForbiddenError";
|
|
329
|
-
this.message = message;
|
|
330
|
-
}
|
|
331
|
-
}
|
|
332
|
-
class UnauthorizedError extends ApplicationError {
|
|
333
|
-
constructor(message = "Unauthorized", details) {
|
|
334
|
-
super(message, details);
|
|
335
|
-
this.name = "UnauthorizedError";
|
|
336
|
-
this.message = message;
|
|
337
|
-
}
|
|
338
|
-
}
|
|
339
|
-
class RateLimitError extends ApplicationError {
|
|
340
|
-
constructor(message = "Too many requests, please try again later.", details) {
|
|
341
|
-
super(message, details);
|
|
342
|
-
this.name = "RateLimitError";
|
|
343
|
-
this.message = message;
|
|
344
|
-
this.details = details || {};
|
|
345
|
-
}
|
|
346
|
-
}
|
|
347
|
-
class PayloadTooLargeError extends ApplicationError {
|
|
348
|
-
constructor(message = "Entity too large", details) {
|
|
349
|
-
super(message, details);
|
|
350
|
-
this.name = "PayloadTooLargeError";
|
|
351
|
-
this.message = message;
|
|
352
|
-
}
|
|
353
|
-
}
|
|
354
|
-
class PolicyError extends ForbiddenError {
|
|
355
|
-
constructor(message = "Policy Failed", details) {
|
|
356
|
-
super(message, details);
|
|
357
|
-
this.name = "PolicyError";
|
|
358
|
-
this.message = message;
|
|
359
|
-
this.details = details || {};
|
|
360
|
-
}
|
|
361
|
-
}
|
|
362
|
-
class NotImplementedError extends ApplicationError {
|
|
363
|
-
constructor(message = "This feature is not implemented yet", details) {
|
|
364
|
-
super(message, details);
|
|
365
|
-
this.name = "NotImplementedError";
|
|
366
|
-
this.message = message;
|
|
367
|
-
}
|
|
368
|
-
}
|
|
369
|
-
const errors = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
370
|
-
__proto__: null,
|
|
371
|
-
ApplicationError,
|
|
372
|
-
ForbiddenError,
|
|
373
|
-
HttpError,
|
|
374
|
-
NotFoundError,
|
|
375
|
-
NotImplementedError,
|
|
376
|
-
PaginationError,
|
|
377
|
-
PayloadTooLargeError,
|
|
378
|
-
PolicyError,
|
|
379
|
-
RateLimitError,
|
|
380
|
-
UnauthorizedError,
|
|
381
|
-
ValidationError,
|
|
382
|
-
YupValidationError
|
|
383
|
-
}, Symbol.toStringTag, { value: "Module" }));
|
|
384
|
-
const handleYupError = (error, errorMessage) => {
|
|
385
|
-
throw new YupValidationError(error, errorMessage);
|
|
386
|
-
};
|
|
387
|
-
const defaultValidationParam = { strict: true, abortEarly: false };
|
|
388
|
-
const validateYupSchema = (schema, options = {}) => async (body, errorMessage) => {
|
|
389
|
-
try {
|
|
390
|
-
const optionsWithDefaults = defaults(defaultValidationParam, options);
|
|
391
|
-
const result = await schema.validate(body, optionsWithDefaults);
|
|
392
|
-
return result;
|
|
393
|
-
} catch (e) {
|
|
394
|
-
if (e instanceof yup$1.ValidationError) {
|
|
395
|
-
handleYupError(e, errorMessage);
|
|
396
|
-
}
|
|
397
|
-
throw e;
|
|
398
|
-
}
|
|
399
|
-
};
|
|
400
|
-
const validateYupSchemaSync = (schema, options = {}) => (body, errorMessage) => {
|
|
401
|
-
try {
|
|
402
|
-
const optionsWithDefaults = defaults(defaultValidationParam, options);
|
|
403
|
-
return schema.validateSync(body, optionsWithDefaults);
|
|
404
|
-
} catch (e) {
|
|
405
|
-
if (e instanceof yup$1.ValidationError) {
|
|
406
|
-
handleYupError(e, errorMessage);
|
|
407
|
-
}
|
|
408
|
-
throw e;
|
|
409
|
-
}
|
|
410
|
-
};
|
|
411
|
-
const nameToSlug = (name, options = { separator: "-" }) => slugify(name, options);
|
|
412
|
-
const nameToCollectionName = (name) => slugify(name, { separator: "_" });
|
|
413
|
-
const toRegressedEnumValue = (value2) => slugify(value2, {
|
|
414
|
-
decamelize: false,
|
|
415
|
-
lowercase: false,
|
|
416
|
-
separator: "_"
|
|
417
|
-
});
|
|
418
|
-
const getCommonBeginning = (...strings) => _$1.takeWhile(strings[0], (char, index2) => strings.every((string) => string[index2] === char)).join(
|
|
419
|
-
""
|
|
420
|
-
);
|
|
421
|
-
const getCommonPath = (...paths) => {
|
|
422
|
-
const [segments, ...otherSegments] = paths.map((it) => _$1.split(it, "/"));
|
|
423
|
-
return _$1.join(
|
|
424
|
-
_$1.takeWhile(segments, (str, index2) => otherSegments.every((it) => it[index2] === str)),
|
|
425
|
-
"/"
|
|
426
|
-
);
|
|
427
|
-
};
|
|
428
|
-
const escapeQuery = (query, charsToEscape, escapeChar = "\\") => {
|
|
429
|
-
return query.split("").reduce(
|
|
430
|
-
(escapedQuery, char) => charsToEscape.includes(char) ? `${escapedQuery}${escapeChar}${char}` : `${escapedQuery}${char}`,
|
|
431
|
-
""
|
|
432
|
-
);
|
|
433
|
-
};
|
|
434
|
-
const stringIncludes = (arr, val) => arr.map(String).includes(String(val));
|
|
435
|
-
const stringEquals = (a, b) => String(a) === String(b);
|
|
436
|
-
const isCamelCase = (value2) => /^[a-z][a-zA-Z0-9]+$/.test(value2);
|
|
437
|
-
const isKebabCase = (value2) => /^([a-z][a-z0-9]*)(-[a-z0-9]+)*$/.test(value2);
|
|
438
|
-
const startsWithANumber = (value2) => /^[0-9]/.test(value2);
|
|
439
|
-
const joinBy = (joint, ...args) => {
|
|
440
|
-
const trim2 = trimChars(joint);
|
|
441
|
-
const trimEnd = trimCharsEnd(joint);
|
|
442
|
-
const trimStart = trimCharsStart(joint);
|
|
443
|
-
return args.reduce((url, path, index2) => {
|
|
444
|
-
if (args.length === 1)
|
|
445
|
-
return path;
|
|
446
|
-
if (index2 === 0)
|
|
447
|
-
return trimEnd(path);
|
|
448
|
-
if (index2 === args.length - 1)
|
|
449
|
-
return url + joint + trimStart(path);
|
|
450
|
-
return url + joint + trim2(path);
|
|
451
|
-
}, "");
|
|
452
|
-
};
|
|
453
|
-
const toKebabCase = (value2) => kebabCase(value2);
|
|
454
|
-
const { toString } = Object.prototype;
|
|
455
|
-
const errorToString = Error.prototype.toString;
|
|
456
|
-
const regExpToString = RegExp.prototype.toString;
|
|
457
|
-
const symbolToString = typeof Symbol !== "undefined" ? Symbol.prototype.toString : () => "";
|
|
458
|
-
const SYMBOL_REGEXP = /^Symbol\((.*)\)(.*)$/;
|
|
459
|
-
function printNumber(val) {
|
|
460
|
-
if (val != +val)
|
|
461
|
-
return "NaN";
|
|
462
|
-
const isNegativeZero = val === 0 && 1 / val < 0;
|
|
463
|
-
return isNegativeZero ? "-0" : `${val}`;
|
|
464
|
-
}
|
|
465
|
-
function printSimpleValue(val, quoteStrings = false) {
|
|
466
|
-
if (val == null || val === true || val === false)
|
|
467
|
-
return `${val}`;
|
|
468
|
-
if (typeof val === "number")
|
|
469
|
-
return printNumber(val);
|
|
470
|
-
if (typeof val === "string")
|
|
471
|
-
return quoteStrings ? `"${val}"` : val;
|
|
472
|
-
if (typeof val === "function")
|
|
473
|
-
return `[Function ${val.name || "anonymous"}]`;
|
|
474
|
-
if (typeof val === "symbol")
|
|
475
|
-
return symbolToString.call(val).replace(SYMBOL_REGEXP, "Symbol($1)");
|
|
476
|
-
const tag = toString.call(val).slice(8, -1);
|
|
477
|
-
if (tag === "Date") {
|
|
478
|
-
const v = val;
|
|
479
|
-
return Number.isNaN(v.getTime()) ? `${v}` : v.toISOString();
|
|
480
|
-
}
|
|
481
|
-
if (tag === "Error" || val instanceof Error)
|
|
482
|
-
return `[${errorToString.call(val)}]`;
|
|
483
|
-
if (tag === "RegExp")
|
|
484
|
-
return regExpToString.call(val);
|
|
485
|
-
return null;
|
|
486
|
-
}
|
|
487
|
-
function printValue(value2, quoteStrings) {
|
|
488
|
-
const result = printSimpleValue(value2, quoteStrings);
|
|
489
|
-
if (result !== null)
|
|
490
|
-
return result;
|
|
491
|
-
return JSON.stringify(
|
|
492
|
-
value2,
|
|
493
|
-
function replacer(key2, value22) {
|
|
494
|
-
const result2 = printSimpleValue(this[key2], quoteStrings);
|
|
495
|
-
if (result2 !== null)
|
|
496
|
-
return result2;
|
|
497
|
-
return value22;
|
|
498
|
-
},
|
|
499
|
-
2
|
|
500
|
-
);
|
|
501
|
-
}
|
|
502
|
-
const strapiID = () => new StrapiIDSchema();
|
|
503
|
-
const isNotNilTest = (value2) => !_$1.isNil(value2);
|
|
504
|
-
const isNotNullTest = (value2) => !_$1.isNull(value2);
|
|
505
|
-
yup$1.addMethod(yup$1.mixed, "notNil", function isNotNill(msg = "${path} must be defined.") {
|
|
506
|
-
return this.test("defined", msg, isNotNilTest);
|
|
507
|
-
});
|
|
508
|
-
yup$1.addMethod(yup$1.mixed, "notNull", function isNotNull(msg = "${path} cannot be null.") {
|
|
509
|
-
return this.test("defined", msg, isNotNullTest);
|
|
510
|
-
});
|
|
511
|
-
yup$1.addMethod(yup$1.mixed, "isFunction", function isFunction(message = "${path} is not a function") {
|
|
512
|
-
return this.test(
|
|
513
|
-
"is a function",
|
|
514
|
-
message,
|
|
515
|
-
(value2) => _$1.isUndefined(value2) || _$1.isFunction(value2)
|
|
516
|
-
);
|
|
517
|
-
});
|
|
518
|
-
yup$1.addMethod(
|
|
519
|
-
yup$1.string,
|
|
520
|
-
"isCamelCase",
|
|
521
|
-
function isCamelCase$1(message = "${path} is not in camel case (anExampleOfCamelCase)") {
|
|
522
|
-
return this.test(
|
|
523
|
-
"is in camelCase",
|
|
524
|
-
message,
|
|
525
|
-
(value2) => value2 ? isCamelCase(value2) : true
|
|
526
|
-
);
|
|
527
|
-
}
|
|
528
|
-
);
|
|
529
|
-
yup$1.addMethod(
|
|
530
|
-
yup$1.string,
|
|
531
|
-
"isKebabCase",
|
|
532
|
-
function isKebabCase$1(message = "${path} is not in kebab case (an-example-of-kebab-case)") {
|
|
533
|
-
return this.test(
|
|
534
|
-
"is in kebab-case",
|
|
535
|
-
message,
|
|
536
|
-
(value2) => value2 ? isKebabCase(value2) : true
|
|
537
|
-
);
|
|
538
|
-
}
|
|
539
|
-
);
|
|
540
|
-
yup$1.addMethod(
|
|
541
|
-
yup$1.object,
|
|
542
|
-
"onlyContainsFunctions",
|
|
543
|
-
function onlyContainsFunctions(message = "${path} contains values that are not functions") {
|
|
544
|
-
return this.test(
|
|
545
|
-
"only contains functions",
|
|
546
|
-
message,
|
|
547
|
-
(value2) => _$1.isUndefined(value2) || value2 && Object.values(value2).every(_$1.isFunction)
|
|
548
|
-
);
|
|
549
|
-
}
|
|
550
|
-
);
|
|
551
|
-
yup$1.addMethod(
|
|
552
|
-
yup$1.array,
|
|
553
|
-
"uniqueProperty",
|
|
554
|
-
function uniqueProperty(propertyName, message) {
|
|
555
|
-
return this.test("unique", message, function unique(list) {
|
|
556
|
-
const errors2 = [];
|
|
557
|
-
list?.forEach((element, index2) => {
|
|
558
|
-
const sameElements = list.filter(
|
|
559
|
-
(e) => get(propertyName, e) === get(propertyName, element)
|
|
560
|
-
);
|
|
561
|
-
if (sameElements.length > 1) {
|
|
562
|
-
errors2.push(
|
|
563
|
-
this.createError({
|
|
564
|
-
path: `${this.path}[${index2}].${propertyName}`,
|
|
565
|
-
message
|
|
566
|
-
})
|
|
567
|
-
);
|
|
568
|
-
}
|
|
569
|
-
});
|
|
570
|
-
if (errors2.length) {
|
|
571
|
-
throw new yup$1.ValidationError(errors2);
|
|
572
|
-
}
|
|
573
|
-
return true;
|
|
574
|
-
});
|
|
575
|
-
}
|
|
576
|
-
);
|
|
577
|
-
class StrapiIDSchema extends yup$1.MixedSchema {
|
|
578
|
-
constructor() {
|
|
579
|
-
super({ type: "strapiID" });
|
|
580
|
-
}
|
|
581
|
-
_typeCheck(value2) {
|
|
582
|
-
return typeof value2 === "string" || isNumber(value2) && isInteger(value2) && value2 >= 0;
|
|
583
|
-
}
|
|
584
|
-
}
|
|
585
|
-
yup$1.setLocale({
|
|
586
|
-
mixed: {
|
|
587
|
-
notType(options) {
|
|
588
|
-
const { path, type, value: value2, originalValue } = options;
|
|
589
|
-
const isCast = originalValue != null && originalValue !== value2;
|
|
590
|
-
const msg = `${path} must be a \`${type}\` type, but the final value was: \`${printValue(value2, true)}\`${isCast ? ` (cast from the value \`${printValue(originalValue, true)}\`).` : "."}`;
|
|
591
|
-
return msg;
|
|
592
|
-
}
|
|
593
|
-
}
|
|
594
|
-
});
|
|
595
|
-
const yup = /* @__PURE__ */ _mergeNamespaces({
|
|
596
|
-
__proto__: null,
|
|
597
|
-
StrapiIDSchema,
|
|
598
|
-
strapiID
|
|
599
|
-
}, [yup$1]);
|
|
600
|
-
const removeUndefined = (obj2) => _$1.pickBy(obj2, (value2) => typeof value2 !== "undefined");
|
|
601
|
-
const keysDeep = (obj2, path = []) => !_$1.isObject(obj2) ? [path.join(".")] : _$1.reduce(
|
|
602
|
-
obj2,
|
|
603
|
-
(acc2, next, key2) => _$1.concat(acc2, keysDeep(next, [...path, key2])),
|
|
604
|
-
[]
|
|
605
|
-
);
|
|
606
|
-
const getConfigUrls = (config, forAdminBuild = false) => {
|
|
607
|
-
const serverConfig = config.get("server");
|
|
608
|
-
const adminConfig = config.get("admin");
|
|
609
|
-
let serverUrl = _$1.get(serverConfig, "url", "");
|
|
610
|
-
serverUrl = _$1.trim(serverUrl, "/ ");
|
|
611
|
-
if (typeof serverUrl !== "string") {
|
|
612
|
-
throw new Error("Invalid server url config. Make sure the url is a string.");
|
|
613
|
-
}
|
|
614
|
-
if (serverUrl.startsWith("http")) {
|
|
615
|
-
try {
|
|
616
|
-
serverUrl = _$1.trim(new URL(serverConfig.url).toString(), "/");
|
|
617
|
-
} catch (e) {
|
|
618
|
-
throw new Error(
|
|
619
|
-
"Invalid server url config. Make sure the url defined in server.js is valid."
|
|
620
|
-
);
|
|
621
|
-
}
|
|
622
|
-
} else if (serverUrl !== "") {
|
|
623
|
-
serverUrl = `/${serverUrl}`;
|
|
624
|
-
}
|
|
625
|
-
let adminUrl = _$1.get(adminConfig, "url", "/admin");
|
|
626
|
-
adminUrl = _$1.trim(adminUrl, "/ ");
|
|
627
|
-
if (typeof adminUrl !== "string") {
|
|
628
|
-
throw new Error("Invalid admin url config. Make sure the url is a non-empty string.");
|
|
629
|
-
}
|
|
630
|
-
if (adminUrl.startsWith("http")) {
|
|
631
|
-
try {
|
|
632
|
-
adminUrl = _$1.trim(new URL(adminUrl).toString(), "/");
|
|
633
|
-
} catch (e) {
|
|
634
|
-
throw new Error("Invalid admin url config. Make sure the url defined in server.js is valid.");
|
|
635
|
-
}
|
|
636
|
-
} else {
|
|
637
|
-
adminUrl = `${serverUrl}/${adminUrl}`;
|
|
638
|
-
}
|
|
639
|
-
let adminPath = adminUrl;
|
|
640
|
-
if (serverUrl.startsWith("http") && adminUrl.startsWith("http") && new URL(adminUrl).origin === new URL(serverUrl).origin && !forAdminBuild) {
|
|
641
|
-
adminPath = adminUrl.replace(getCommonPath(serverUrl, adminUrl), "");
|
|
642
|
-
adminPath = `/${_$1.trim(adminPath, "/")}`;
|
|
643
|
-
} else if (adminUrl.startsWith("http")) {
|
|
644
|
-
adminPath = new URL(adminUrl).pathname;
|
|
645
|
-
}
|
|
646
|
-
return {
|
|
647
|
-
serverUrl,
|
|
648
|
-
adminUrl,
|
|
649
|
-
adminPath
|
|
650
|
-
};
|
|
651
|
-
};
|
|
652
|
-
const getAbsoluteUrl = (adminOrServer) => (config, forAdminBuild = false) => {
|
|
653
|
-
const { serverUrl, adminUrl } = getConfigUrls(config, forAdminBuild);
|
|
654
|
-
const url = adminOrServer === "server" ? serverUrl : adminUrl;
|
|
655
|
-
if (url.startsWith("http")) {
|
|
656
|
-
return url;
|
|
657
|
-
}
|
|
658
|
-
const hostname = config.get("environment") === "development" && ["127.0.0.1", "0.0.0.0"].includes(config.get("server.host")) ? "localhost" : config.get("server.host");
|
|
659
|
-
return `http://${hostname}:${config.get("server.port")}${url}`;
|
|
660
|
-
};
|
|
661
|
-
const getAbsoluteAdminUrl = getAbsoluteUrl("admin");
|
|
662
|
-
const getAbsoluteServerUrl = getAbsoluteUrl("server");
|
|
663
|
-
const generateTimestampCode = (date) => {
|
|
664
|
-
const referDate = date || /* @__PURE__ */ new Date();
|
|
665
|
-
return referDate.getTime().toString(36);
|
|
666
|
-
};
|
|
667
|
-
const SINGLE_TYPE = "singleType";
|
|
668
|
-
const COLLECTION_TYPE = "collectionType";
|
|
669
|
-
const ID_ATTRIBUTE = "id";
|
|
670
|
-
const PUBLISHED_AT_ATTRIBUTE$1 = "publishedAt";
|
|
671
|
-
const CREATED_BY_ATTRIBUTE$3 = "createdBy";
|
|
672
|
-
const UPDATED_BY_ATTRIBUTE$3 = "updatedBy";
|
|
673
|
-
const CREATED_AT_ATTRIBUTE = "createdAt";
|
|
674
|
-
const UPDATED_AT_ATTRIBUTE = "updatedAt";
|
|
675
|
-
const DP_PUB_STATE_LIVE = "live";
|
|
676
|
-
const DP_PUB_STATE_PREVIEW = "preview";
|
|
677
|
-
const DP_PUB_STATES = [DP_PUB_STATE_LIVE, DP_PUB_STATE_PREVIEW];
|
|
678
|
-
const constants$1 = {
|
|
679
|
-
ID_ATTRIBUTE,
|
|
680
|
-
PUBLISHED_AT_ATTRIBUTE: PUBLISHED_AT_ATTRIBUTE$1,
|
|
681
|
-
CREATED_BY_ATTRIBUTE: CREATED_BY_ATTRIBUTE$3,
|
|
682
|
-
UPDATED_BY_ATTRIBUTE: UPDATED_BY_ATTRIBUTE$3,
|
|
683
|
-
CREATED_AT_ATTRIBUTE,
|
|
684
|
-
UPDATED_AT_ATTRIBUTE,
|
|
685
|
-
DP_PUB_STATES,
|
|
686
|
-
DP_PUB_STATE_LIVE,
|
|
687
|
-
DP_PUB_STATE_PREVIEW,
|
|
688
|
-
SINGLE_TYPE,
|
|
689
|
-
COLLECTION_TYPE
|
|
690
|
-
};
|
|
691
|
-
const getTimestamps = (model) => {
|
|
692
|
-
const attributes = [];
|
|
693
|
-
if (has(CREATED_AT_ATTRIBUTE, model.attributes)) {
|
|
694
|
-
attributes.push(CREATED_AT_ATTRIBUTE);
|
|
695
|
-
}
|
|
696
|
-
if (has(UPDATED_AT_ATTRIBUTE, model.attributes)) {
|
|
697
|
-
attributes.push(UPDATED_AT_ATTRIBUTE);
|
|
698
|
-
}
|
|
699
|
-
return attributes;
|
|
700
|
-
};
|
|
701
|
-
const getCreatorFields = (model) => {
|
|
702
|
-
const attributes = [];
|
|
703
|
-
if (has(CREATED_BY_ATTRIBUTE$3, model.attributes)) {
|
|
704
|
-
attributes.push(CREATED_BY_ATTRIBUTE$3);
|
|
705
|
-
}
|
|
706
|
-
if (has(UPDATED_BY_ATTRIBUTE$3, model.attributes)) {
|
|
707
|
-
attributes.push(UPDATED_BY_ATTRIBUTE$3);
|
|
708
|
-
}
|
|
709
|
-
return attributes;
|
|
710
|
-
};
|
|
711
|
-
const getNonWritableAttributes = (model) => {
|
|
712
|
-
if (!model)
|
|
713
|
-
return [];
|
|
714
|
-
const nonWritableAttributes = _$1.reduce(
|
|
715
|
-
model.attributes,
|
|
716
|
-
(acc2, attr, attrName) => attr.writable === false ? acc2.concat(attrName) : acc2,
|
|
717
|
-
[]
|
|
718
|
-
);
|
|
719
|
-
return _$1.uniq([ID_ATTRIBUTE, ...getTimestamps(model), ...nonWritableAttributes]);
|
|
720
|
-
};
|
|
721
|
-
const getWritableAttributes = (model) => {
|
|
722
|
-
if (!model)
|
|
723
|
-
return [];
|
|
724
|
-
return _$1.difference(Object.keys(model.attributes), getNonWritableAttributes(model));
|
|
725
|
-
};
|
|
726
|
-
const isWritableAttribute = (model, attributeName) => {
|
|
727
|
-
return getWritableAttributes(model).includes(attributeName);
|
|
728
|
-
};
|
|
729
|
-
const getNonVisibleAttributes = (model) => {
|
|
730
|
-
const nonVisibleAttributes = _$1.reduce(
|
|
731
|
-
model.attributes,
|
|
732
|
-
(acc2, attr, attrName) => attr.visible === false ? acc2.concat(attrName) : acc2,
|
|
733
|
-
[]
|
|
734
|
-
);
|
|
735
|
-
return _$1.uniq([ID_ATTRIBUTE, ...getTimestamps(model), ...nonVisibleAttributes]);
|
|
736
|
-
};
|
|
737
|
-
const getVisibleAttributes = (model) => {
|
|
738
|
-
return _$1.difference(_$1.keys(model.attributes), getNonVisibleAttributes(model));
|
|
739
|
-
};
|
|
740
|
-
const isVisibleAttribute = (model, attributeName) => {
|
|
741
|
-
return getVisibleAttributes(model).includes(attributeName);
|
|
742
|
-
};
|
|
743
|
-
const getOptions = (model) => _$1.assign({ draftAndPublish: false }, _$1.get(model, "options", {}));
|
|
744
|
-
const hasDraftAndPublish = (model) => _$1.get(model, "options.draftAndPublish", false) === true;
|
|
745
|
-
const isDraft = (data, model) => hasDraftAndPublish(model) && _$1.get(data, PUBLISHED_AT_ATTRIBUTE$1) === null;
|
|
746
|
-
const isSingleType = ({ kind = COLLECTION_TYPE }) => kind === SINGLE_TYPE;
|
|
747
|
-
const isCollectionType = ({ kind = COLLECTION_TYPE }) => kind === COLLECTION_TYPE;
|
|
748
|
-
const isKind = (kind) => (model) => model.kind === kind;
|
|
749
|
-
const getStoredPrivateAttributes = (model) => union(
|
|
750
|
-
strapi?.config?.get("api.responses.privateAttributes", []) ?? [],
|
|
751
|
-
getOr([], "options.privateAttributes", model)
|
|
752
|
-
);
|
|
753
|
-
const getPrivateAttributes = (model) => {
|
|
754
|
-
return _$1.union(
|
|
755
|
-
getStoredPrivateAttributes(model),
|
|
756
|
-
_$1.keys(_$1.pickBy(model.attributes, (attr) => !!attr.private))
|
|
757
|
-
);
|
|
758
|
-
};
|
|
759
|
-
const isPrivateAttribute = (model, attributeName) => {
|
|
760
|
-
if (model?.attributes?.[attributeName]?.private === true) {
|
|
761
|
-
return true;
|
|
762
|
-
}
|
|
763
|
-
return getStoredPrivateAttributes(model).includes(attributeName);
|
|
764
|
-
};
|
|
765
|
-
const isScalarAttribute = (attribute) => {
|
|
766
|
-
return !["media", "component", "relation", "dynamiczone"].includes(attribute?.type);
|
|
767
|
-
};
|
|
768
|
-
const isMediaAttribute = (attribute) => attribute?.type === "media";
|
|
769
|
-
const isRelationalAttribute = (attribute) => attribute?.type === "relation";
|
|
770
|
-
const isComponentAttribute = (attribute) => ["component", "dynamiczone"].includes(attribute?.type);
|
|
771
|
-
const isDynamicZoneAttribute = (attribute) => attribute?.type === "dynamiczone";
|
|
772
|
-
const isMorphToRelationalAttribute = (attribute) => {
|
|
773
|
-
return isRelationalAttribute(attribute) && attribute?.relation?.startsWith?.("morphTo");
|
|
774
|
-
};
|
|
775
|
-
const getComponentAttributes = (schema) => {
|
|
776
|
-
return _$1.reduce(
|
|
777
|
-
schema.attributes,
|
|
778
|
-
(acc2, attr, attrName) => {
|
|
779
|
-
if (isComponentAttribute(attr))
|
|
780
|
-
acc2.push(attrName);
|
|
781
|
-
return acc2;
|
|
782
|
-
},
|
|
783
|
-
[]
|
|
784
|
-
);
|
|
785
|
-
};
|
|
786
|
-
const getScalarAttributes = (schema) => {
|
|
787
|
-
return _$1.reduce(
|
|
788
|
-
schema.attributes,
|
|
789
|
-
(acc2, attr, attrName) => {
|
|
790
|
-
if (isScalarAttribute(attr))
|
|
791
|
-
acc2.push(attrName);
|
|
792
|
-
return acc2;
|
|
793
|
-
},
|
|
794
|
-
[]
|
|
795
|
-
);
|
|
325
|
+
const getScalarAttributes = (schema) => {
|
|
326
|
+
return _$1.reduce(
|
|
327
|
+
schema.attributes,
|
|
328
|
+
(acc, attr, attrName) => {
|
|
329
|
+
if (isScalarAttribute(attr))
|
|
330
|
+
acc.push(attrName);
|
|
331
|
+
return acc;
|
|
332
|
+
},
|
|
333
|
+
[]
|
|
334
|
+
);
|
|
796
335
|
};
|
|
797
336
|
const isTypedAttribute = (attribute, type) => {
|
|
798
337
|
return _$1.has(attribute, "type") && attribute.type === type;
|
|
@@ -830,103 +369,6 @@ const contentTypes = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.define
|
|
|
830
369
|
isVisibleAttribute,
|
|
831
370
|
isWritableAttribute
|
|
832
371
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
833
|
-
function envFn(key2, defaultValue) {
|
|
834
|
-
return _$1.has(process.env, key2) ? process.env[key2] : defaultValue;
|
|
835
|
-
}
|
|
836
|
-
function getKey(key2) {
|
|
837
|
-
return process.env[key2] ?? "";
|
|
838
|
-
}
|
|
839
|
-
const utils = {
|
|
840
|
-
int(key2, defaultValue) {
|
|
841
|
-
if (!_$1.has(process.env, key2)) {
|
|
842
|
-
return defaultValue;
|
|
843
|
-
}
|
|
844
|
-
return parseInt(getKey(key2), 10);
|
|
845
|
-
},
|
|
846
|
-
float(key2, defaultValue) {
|
|
847
|
-
if (!_$1.has(process.env, key2)) {
|
|
848
|
-
return defaultValue;
|
|
849
|
-
}
|
|
850
|
-
return parseFloat(getKey(key2));
|
|
851
|
-
},
|
|
852
|
-
bool(key2, defaultValue) {
|
|
853
|
-
if (!_$1.has(process.env, key2)) {
|
|
854
|
-
return defaultValue;
|
|
855
|
-
}
|
|
856
|
-
return getKey(key2) === "true";
|
|
857
|
-
},
|
|
858
|
-
json(key2, defaultValue) {
|
|
859
|
-
if (!_$1.has(process.env, key2)) {
|
|
860
|
-
return defaultValue;
|
|
861
|
-
}
|
|
862
|
-
try {
|
|
863
|
-
return JSON.parse(getKey(key2));
|
|
864
|
-
} catch (error) {
|
|
865
|
-
if (error instanceof Error) {
|
|
866
|
-
throw new Error(`Invalid json environment variable ${key2}: ${error.message}`);
|
|
867
|
-
}
|
|
868
|
-
throw error;
|
|
869
|
-
}
|
|
870
|
-
},
|
|
871
|
-
array(key2, defaultValue) {
|
|
872
|
-
if (!_$1.has(process.env, key2)) {
|
|
873
|
-
return defaultValue;
|
|
874
|
-
}
|
|
875
|
-
let value2 = getKey(key2);
|
|
876
|
-
if (value2.startsWith("[") && value2.endsWith("]")) {
|
|
877
|
-
value2 = value2.substring(1, value2.length - 1);
|
|
878
|
-
}
|
|
879
|
-
return value2.split(",").map((v) => {
|
|
880
|
-
return _$1.trim(_$1.trim(v, " "), '"');
|
|
881
|
-
});
|
|
882
|
-
},
|
|
883
|
-
date(key2, defaultValue) {
|
|
884
|
-
if (!_$1.has(process.env, key2)) {
|
|
885
|
-
return defaultValue;
|
|
886
|
-
}
|
|
887
|
-
return new Date(getKey(key2));
|
|
888
|
-
},
|
|
889
|
-
/**
|
|
890
|
-
* Gets a value from env that matches oneOf provided values
|
|
891
|
-
* @param {string} key
|
|
892
|
-
* @param {string[]} expectedValues
|
|
893
|
-
* @param {string|undefined} defaultValue
|
|
894
|
-
* @returns {string|undefined}
|
|
895
|
-
*/
|
|
896
|
-
oneOf(key2, expectedValues, defaultValue) {
|
|
897
|
-
if (!expectedValues) {
|
|
898
|
-
throw new Error(`env.oneOf requires expectedValues`);
|
|
899
|
-
}
|
|
900
|
-
if (defaultValue && !expectedValues.includes(defaultValue)) {
|
|
901
|
-
throw new Error(`env.oneOf requires defaultValue to be included in expectedValues`);
|
|
902
|
-
}
|
|
903
|
-
const rawValue = env(key2, defaultValue);
|
|
904
|
-
return expectedValues.includes(rawValue) ? rawValue : defaultValue;
|
|
905
|
-
}
|
|
906
|
-
};
|
|
907
|
-
const env = Object.assign(envFn, utils);
|
|
908
|
-
const MANY_RELATIONS = ["oneToMany", "manyToMany"];
|
|
909
|
-
const getRelationalFields = (contentType) => {
|
|
910
|
-
return Object.keys(contentType.attributes).filter((attributeName) => {
|
|
911
|
-
return contentType.attributes[attributeName].type === "relation";
|
|
912
|
-
});
|
|
913
|
-
};
|
|
914
|
-
const isOneToAny = (attribute) => isRelationalAttribute(attribute) && ["oneToOne", "oneToMany"].includes(attribute.relation);
|
|
915
|
-
const isManyToAny = (attribute) => isRelationalAttribute(attribute) && ["manyToMany", "manyToOne"].includes(attribute.relation);
|
|
916
|
-
const isAnyToOne = (attribute) => isRelationalAttribute(attribute) && ["oneToOne", "manyToOne"].includes(attribute.relation);
|
|
917
|
-
const isAnyToMany = (attribute) => isRelationalAttribute(attribute) && ["oneToMany", "manyToMany"].includes(attribute.relation);
|
|
918
|
-
const constants = {
|
|
919
|
-
MANY_RELATIONS
|
|
920
|
-
};
|
|
921
|
-
const relations = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
922
|
-
__proto__: null,
|
|
923
|
-
constants,
|
|
924
|
-
getRelationalFields,
|
|
925
|
-
isAnyToMany,
|
|
926
|
-
isAnyToOne,
|
|
927
|
-
isManyToAny,
|
|
928
|
-
isOneToAny
|
|
929
|
-
}, Symbol.toStringTag, { value: "Module" }));
|
|
930
372
|
const { CREATED_BY_ATTRIBUTE: CREATED_BY_ATTRIBUTE$2, UPDATED_BY_ATTRIBUTE: UPDATED_BY_ATTRIBUTE$2 } = constants$1;
|
|
931
373
|
const setCreatorFields = ({ user, isEdition = false }) => (data) => {
|
|
932
374
|
if (isEdition) {
|
|
@@ -1022,26 +464,26 @@ const providerFactory = (options = {}) => {
|
|
|
1022
464
|
};
|
|
1023
465
|
return {
|
|
1024
466
|
hooks: state.hooks,
|
|
1025
|
-
async register(
|
|
1026
|
-
if (throwOnDuplicates && this.has(
|
|
1027
|
-
throw new Error(`Duplicated item key: ${
|
|
467
|
+
async register(key, item) {
|
|
468
|
+
if (throwOnDuplicates && this.has(key)) {
|
|
469
|
+
throw new Error(`Duplicated item key: ${key}`);
|
|
1028
470
|
}
|
|
1029
|
-
await state.hooks.willRegister.call({ key
|
|
1030
|
-
state.registry.set(
|
|
1031
|
-
await state.hooks.didRegister.call({ key
|
|
471
|
+
await state.hooks.willRegister.call({ key, value: item });
|
|
472
|
+
state.registry.set(key, item);
|
|
473
|
+
await state.hooks.didRegister.call({ key, value: cloneDeep(item) });
|
|
1032
474
|
return this;
|
|
1033
475
|
},
|
|
1034
|
-
async delete(
|
|
1035
|
-
if (this.has(
|
|
1036
|
-
const item = this.get(
|
|
1037
|
-
await state.hooks.willDelete.call({ key
|
|
1038
|
-
state.registry.delete(
|
|
1039
|
-
await state.hooks.didDelete.call({ key
|
|
476
|
+
async delete(key) {
|
|
477
|
+
if (this.has(key)) {
|
|
478
|
+
const item = this.get(key);
|
|
479
|
+
await state.hooks.willDelete.call({ key, value: cloneDeep(item) });
|
|
480
|
+
state.registry.delete(key);
|
|
481
|
+
await state.hooks.didDelete.call({ key, value: cloneDeep(item) });
|
|
1040
482
|
}
|
|
1041
483
|
return this;
|
|
1042
484
|
},
|
|
1043
|
-
get(
|
|
1044
|
-
return state.registry.get(
|
|
485
|
+
get(key) {
|
|
486
|
+
return state.registry.get(key);
|
|
1045
487
|
},
|
|
1046
488
|
getWhere(filters2 = {}) {
|
|
1047
489
|
const items = this.values();
|
|
@@ -1050,7 +492,7 @@ const providerFactory = (options = {}) => {
|
|
|
1050
492
|
return items;
|
|
1051
493
|
}
|
|
1052
494
|
return items.filter((item) => {
|
|
1053
|
-
return filtersEntries.every(([
|
|
495
|
+
return filtersEntries.every(([key, value]) => item[key] === value);
|
|
1054
496
|
});
|
|
1055
497
|
},
|
|
1056
498
|
values() {
|
|
@@ -1059,93 +501,22 @@ const providerFactory = (options = {}) => {
|
|
|
1059
501
|
keys() {
|
|
1060
502
|
return Array.from(state.registry.keys());
|
|
1061
503
|
},
|
|
1062
|
-
has(
|
|
1063
|
-
return state.registry.has(
|
|
504
|
+
has(key) {
|
|
505
|
+
return state.registry.has(key);
|
|
1064
506
|
},
|
|
1065
507
|
size() {
|
|
1066
508
|
return state.registry.size;
|
|
1067
509
|
},
|
|
1068
510
|
async clear() {
|
|
1069
511
|
const keys = this.keys();
|
|
1070
|
-
for (const
|
|
1071
|
-
await this.delete(
|
|
512
|
+
for (const key of keys) {
|
|
513
|
+
await this.delete(key);
|
|
1072
514
|
}
|
|
1073
515
|
return this;
|
|
1074
516
|
}
|
|
1075
517
|
};
|
|
1076
518
|
};
|
|
1077
|
-
|
|
1078
|
-
offset: {
|
|
1079
|
-
start: 0,
|
|
1080
|
-
limit: 10
|
|
1081
|
-
},
|
|
1082
|
-
page: {
|
|
1083
|
-
page: 1,
|
|
1084
|
-
pageSize: 10
|
|
1085
|
-
}
|
|
1086
|
-
};
|
|
1087
|
-
const paginationAttributes = ["start", "limit", "page", "pageSize"];
|
|
1088
|
-
const withMaxLimit = (limit, maxLimit = -1) => {
|
|
1089
|
-
if (maxLimit === -1 || limit < maxLimit) {
|
|
1090
|
-
return limit;
|
|
1091
|
-
}
|
|
1092
|
-
return maxLimit;
|
|
1093
|
-
};
|
|
1094
|
-
const ensureMinValues = ({ start, limit }) => ({
|
|
1095
|
-
start: Math.max(start, 0),
|
|
1096
|
-
limit: limit === -1 ? limit : Math.max(limit, 1)
|
|
1097
|
-
});
|
|
1098
|
-
const ensureMaxValues = (maxLimit = -1) => ({ start, limit }) => ({
|
|
1099
|
-
start,
|
|
1100
|
-
limit: withMaxLimit(limit, maxLimit)
|
|
1101
|
-
});
|
|
1102
|
-
const withNoLimit = (pagination2, maxLimit = -1) => ({
|
|
1103
|
-
...pagination2,
|
|
1104
|
-
limit: pagination2.limit === -1 ? maxLimit : pagination2.limit
|
|
1105
|
-
});
|
|
1106
|
-
const withDefaultPagination = (args, { defaults: defaults2 = {}, maxLimit = -1 } = {}) => {
|
|
1107
|
-
const defaultValues = merge(STRAPI_DEFAULTS, defaults2);
|
|
1108
|
-
const usePagePagination = !isNil(args.page) || !isNil(args.pageSize);
|
|
1109
|
-
const useOffsetPagination = !isNil(args.start) || !isNil(args.limit);
|
|
1110
|
-
const ensureValidValues = pipe(ensureMinValues, ensureMaxValues(maxLimit));
|
|
1111
|
-
if (!usePagePagination && !useOffsetPagination) {
|
|
1112
|
-
return merge(args, ensureValidValues(defaultValues.offset));
|
|
1113
|
-
}
|
|
1114
|
-
if (usePagePagination && useOffsetPagination) {
|
|
1115
|
-
throw new PaginationError("Cannot use both page & offset pagination in the same query");
|
|
1116
|
-
}
|
|
1117
|
-
const pagination2 = {
|
|
1118
|
-
start: 0,
|
|
1119
|
-
limit: 0
|
|
1120
|
-
};
|
|
1121
|
-
if (useOffsetPagination) {
|
|
1122
|
-
const { start, limit } = merge(defaultValues.offset, args);
|
|
1123
|
-
Object.assign(pagination2, { start, limit });
|
|
1124
|
-
}
|
|
1125
|
-
if (usePagePagination) {
|
|
1126
|
-
const { page, pageSize } = merge(defaultValues.page, {
|
|
1127
|
-
...args,
|
|
1128
|
-
pageSize: Math.max(1, args.pageSize ?? 0)
|
|
1129
|
-
});
|
|
1130
|
-
Object.assign(pagination2, {
|
|
1131
|
-
start: (page - 1) * pageSize,
|
|
1132
|
-
limit: pageSize
|
|
1133
|
-
});
|
|
1134
|
-
}
|
|
1135
|
-
Object.assign(pagination2, withNoLimit(pagination2, maxLimit));
|
|
1136
|
-
const replacePaginationAttributes = pipe(
|
|
1137
|
-
// Remove pagination attributes
|
|
1138
|
-
omit(paginationAttributes),
|
|
1139
|
-
// Merge the object with the new pagination + ensure minimum & maximum values
|
|
1140
|
-
merge(ensureValidValues(pagination2))
|
|
1141
|
-
);
|
|
1142
|
-
return replacePaginationAttributes(args);
|
|
1143
|
-
};
|
|
1144
|
-
const pagination = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
1145
|
-
__proto__: null,
|
|
1146
|
-
withDefaultPagination
|
|
1147
|
-
}, Symbol.toStringTag, { value: "Module" }));
|
|
1148
|
-
function pipeAsync(...fns) {
|
|
519
|
+
function pipe(...fns) {
|
|
1149
520
|
const [firstFn, ...fnRest] = fns;
|
|
1150
521
|
return async (...args) => {
|
|
1151
522
|
let res = await firstFn.apply(firstFn, args);
|
|
@@ -1155,34 +526,37 @@ function pipeAsync(...fns) {
|
|
|
1155
526
|
return res;
|
|
1156
527
|
};
|
|
1157
528
|
}
|
|
1158
|
-
const
|
|
1159
|
-
const
|
|
1160
|
-
let
|
|
529
|
+
const map = curry(pMap);
|
|
530
|
+
const reduce = (mixedArray) => async (iteratee, initialValue) => {
|
|
531
|
+
let acc = initialValue;
|
|
1161
532
|
for (let i = 0; i < mixedArray.length; i += 1) {
|
|
1162
|
-
|
|
533
|
+
acc = await iteratee(acc, await mixedArray[i], i);
|
|
1163
534
|
}
|
|
1164
|
-
return
|
|
1165
|
-
};
|
|
1166
|
-
const forEachAsync = async (array, func, options) => {
|
|
1167
|
-
await pMap(array, func, options);
|
|
535
|
+
return acc;
|
|
1168
536
|
};
|
|
1169
|
-
const
|
|
537
|
+
const async = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
538
|
+
__proto__: null,
|
|
539
|
+
map,
|
|
540
|
+
pipe,
|
|
541
|
+
reduce
|
|
542
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
543
|
+
const visitor$8 = ({ key, attribute }, { remove: remove2 }) => {
|
|
1170
544
|
if (attribute?.type === "password") {
|
|
1171
|
-
remove2(
|
|
545
|
+
remove2(key);
|
|
1172
546
|
}
|
|
1173
547
|
};
|
|
1174
|
-
const visitor$
|
|
548
|
+
const visitor$7 = ({ schema, key, attribute }, { remove: remove2 }) => {
|
|
1175
549
|
if (!attribute) {
|
|
1176
550
|
return;
|
|
1177
551
|
}
|
|
1178
|
-
const isPrivate = attribute.private === true || isPrivateAttribute(schema,
|
|
552
|
+
const isPrivate = attribute.private === true || isPrivateAttribute(schema, key);
|
|
1179
553
|
if (isPrivate) {
|
|
1180
|
-
remove2(
|
|
554
|
+
remove2(key);
|
|
1181
555
|
}
|
|
1182
556
|
};
|
|
1183
557
|
const ACTIONS_TO_VERIFY$1 = ["find"];
|
|
1184
558
|
const { CREATED_BY_ATTRIBUTE: CREATED_BY_ATTRIBUTE$1, UPDATED_BY_ATTRIBUTE: UPDATED_BY_ATTRIBUTE$1 } = constants$1;
|
|
1185
|
-
const removeRestrictedRelations = (auth) => async ({ data, key
|
|
559
|
+
const removeRestrictedRelations = (auth) => async ({ data, key, attribute, schema }, { remove: remove2, set }) => {
|
|
1186
560
|
if (!attribute) {
|
|
1187
561
|
return;
|
|
1188
562
|
}
|
|
@@ -1192,7 +566,7 @@ const removeRestrictedRelations = (auth) => async ({ data, key: key2, attribute,
|
|
|
1192
566
|
}
|
|
1193
567
|
const handleMorphRelation = async () => {
|
|
1194
568
|
const newMorphValue = [];
|
|
1195
|
-
for (const element of data[
|
|
569
|
+
for (const element of data[key]) {
|
|
1196
570
|
const scopes = ACTIONS_TO_VERIFY$1.map((action) => `${element.__type}.${action}`);
|
|
1197
571
|
const isAllowed = await hasAccessToSomeScopes$1(scopes, auth);
|
|
1198
572
|
if (isAllowed) {
|
|
@@ -1200,19 +574,19 @@ const removeRestrictedRelations = (auth) => async ({ data, key: key2, attribute,
|
|
|
1200
574
|
}
|
|
1201
575
|
}
|
|
1202
576
|
if (newMorphValue.length === 0) {
|
|
1203
|
-
remove2(
|
|
577
|
+
remove2(key);
|
|
1204
578
|
} else {
|
|
1205
|
-
set(
|
|
579
|
+
set(key, newMorphValue);
|
|
1206
580
|
}
|
|
1207
581
|
};
|
|
1208
582
|
const handleRegularRelation = async () => {
|
|
1209
583
|
const scopes = ACTIONS_TO_VERIFY$1.map((action) => `${attribute.target}.${action}`);
|
|
1210
584
|
const isAllowed = await hasAccessToSomeScopes$1(scopes, auth);
|
|
1211
585
|
if (!isAllowed) {
|
|
1212
|
-
remove2(
|
|
586
|
+
remove2(key);
|
|
1213
587
|
}
|
|
1214
588
|
};
|
|
1215
|
-
const isCreatorRelation = [CREATED_BY_ATTRIBUTE$1, UPDATED_BY_ATTRIBUTE$1].includes(
|
|
589
|
+
const isCreatorRelation = [CREATED_BY_ATTRIBUTE$1, UPDATED_BY_ATTRIBUTE$1].includes(key);
|
|
1216
590
|
if (isMorphToRelationalAttribute(attribute)) {
|
|
1217
591
|
await handleMorphRelation();
|
|
1218
592
|
return;
|
|
@@ -1233,21 +607,21 @@ const hasAccessToSomeScopes$1 = async (scopes, auth) => {
|
|
|
1233
607
|
}
|
|
1234
608
|
return false;
|
|
1235
609
|
};
|
|
1236
|
-
const visitor$
|
|
610
|
+
const visitor$6 = ({ key, attribute }, { remove: remove2 }) => {
|
|
1237
611
|
if (isMorphToRelationalAttribute(attribute)) {
|
|
1238
|
-
remove2(
|
|
612
|
+
remove2(key);
|
|
1239
613
|
}
|
|
1240
614
|
};
|
|
1241
|
-
const visitor$
|
|
615
|
+
const visitor$5 = ({ key, attribute }, { remove: remove2 }) => {
|
|
1242
616
|
if (isDynamicZoneAttribute(attribute)) {
|
|
1243
|
-
remove2(
|
|
617
|
+
remove2(key);
|
|
1244
618
|
}
|
|
1245
619
|
};
|
|
1246
|
-
const removeDisallowedFields = (allowedFields = null) => ({ key
|
|
620
|
+
const removeDisallowedFields = (allowedFields = null) => ({ key, path: { attribute: path } }, { remove: remove2 }) => {
|
|
1247
621
|
if (allowedFields === null) {
|
|
1248
622
|
return;
|
|
1249
623
|
}
|
|
1250
|
-
if (!(isArray(allowedFields) && allowedFields.every(isString
|
|
624
|
+
if (!(isArray(allowedFields) && allowedFields.every(isString))) {
|
|
1251
625
|
throw new TypeError(
|
|
1252
626
|
`Expected array of strings for allowedFields but got "${typeof allowedFields}"`
|
|
1253
627
|
);
|
|
@@ -1262,42 +636,52 @@ const removeDisallowedFields = (allowedFields = null) => ({ key: key2, path: { a
|
|
|
1262
636
|
if (isPathAllowed) {
|
|
1263
637
|
return;
|
|
1264
638
|
}
|
|
1265
|
-
remove2(
|
|
639
|
+
remove2(key);
|
|
1266
640
|
};
|
|
1267
641
|
const getContainedPaths$1 = (path) => {
|
|
1268
642
|
const parts = toPath(path);
|
|
1269
|
-
return parts.reduce((
|
|
1270
|
-
return [...
|
|
643
|
+
return parts.reduce((acc, value, index2, list) => {
|
|
644
|
+
return [...acc, list.slice(0, index2 + 1).join(".")];
|
|
1271
645
|
}, []);
|
|
1272
646
|
};
|
|
1273
|
-
const removeRestrictedFields = (restrictedFields = null) => ({ key
|
|
647
|
+
const removeRestrictedFields = (restrictedFields = null) => ({ key, path: { attribute: path } }, { remove: remove2 }) => {
|
|
1274
648
|
if (restrictedFields === null) {
|
|
1275
|
-
remove2(
|
|
649
|
+
remove2(key);
|
|
1276
650
|
return;
|
|
1277
651
|
}
|
|
1278
|
-
if (!(isArray(restrictedFields) && restrictedFields.every(isString
|
|
652
|
+
if (!(isArray(restrictedFields) && restrictedFields.every(isString))) {
|
|
1279
653
|
throw new TypeError(
|
|
1280
654
|
`Expected array of strings for restrictedFields but got "${typeof restrictedFields}"`
|
|
1281
655
|
);
|
|
1282
656
|
}
|
|
1283
657
|
if (restrictedFields.includes(path)) {
|
|
1284
|
-
remove2(
|
|
658
|
+
remove2(key);
|
|
1285
659
|
return;
|
|
1286
660
|
}
|
|
1287
661
|
const isRestrictedNested = restrictedFields.some(
|
|
1288
662
|
(allowedPath) => path?.toString().startsWith(`${allowedPath}.`)
|
|
1289
663
|
);
|
|
1290
664
|
if (isRestrictedNested) {
|
|
1291
|
-
remove2(
|
|
665
|
+
remove2(key);
|
|
666
|
+
}
|
|
667
|
+
};
|
|
668
|
+
const visitor$4 = ({ schema, key, value }, { set }) => {
|
|
669
|
+
if (key === "" && value === "*") {
|
|
670
|
+
const { attributes } = schema;
|
|
671
|
+
const newPopulateQuery = Object.entries(attributes).filter(
|
|
672
|
+
([, attribute]) => ["relation", "component", "media", "dynamiczone"].includes(attribute.type)
|
|
673
|
+
).reduce((acc, [key2]) => ({ ...acc, [key2]: true }), {});
|
|
674
|
+
set("", newPopulateQuery);
|
|
1292
675
|
}
|
|
1293
676
|
};
|
|
1294
677
|
const visitors$1 = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
1295
678
|
__proto__: null,
|
|
679
|
+
expandWildcardPopulate: visitor$4,
|
|
1296
680
|
removeDisallowedFields,
|
|
1297
|
-
removeDynamicZones: visitor$
|
|
1298
|
-
removeMorphToRelations: visitor$
|
|
1299
|
-
removePassword: visitor$
|
|
1300
|
-
removePrivate: visitor$
|
|
681
|
+
removeDynamicZones: visitor$5,
|
|
682
|
+
removeMorphToRelations: visitor$6,
|
|
683
|
+
removePassword: visitor$8,
|
|
684
|
+
removePrivate: visitor$7,
|
|
1301
685
|
removeRestrictedFields,
|
|
1302
686
|
removeRestrictedRelations
|
|
1303
687
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
@@ -1334,85 +718,85 @@ const traverseEntity = async (visitor2, options, entity) => {
|
|
|
1334
718
|
const visitorUtils = createVisitorUtils({ data: copy });
|
|
1335
719
|
const keys = Object.keys(copy);
|
|
1336
720
|
for (let i = 0; i < keys.length; i += 1) {
|
|
1337
|
-
const
|
|
1338
|
-
const attribute = schema.attributes[
|
|
721
|
+
const key = keys[i];
|
|
722
|
+
const attribute = schema.attributes[key];
|
|
1339
723
|
if (isNil(attribute)) {
|
|
1340
724
|
continue;
|
|
1341
725
|
}
|
|
1342
726
|
const newPath = { ...path };
|
|
1343
|
-
newPath.raw = isNil(path.raw) ?
|
|
727
|
+
newPath.raw = isNil(path.raw) ? key : `${path.raw}.${key}`;
|
|
1344
728
|
if (!isNil(attribute)) {
|
|
1345
|
-
newPath.attribute = isNil(path.attribute) ?
|
|
729
|
+
newPath.attribute = isNil(path.attribute) ? key : `${path.attribute}.${key}`;
|
|
1346
730
|
}
|
|
1347
731
|
const visitorOptions = {
|
|
1348
732
|
data: copy,
|
|
1349
733
|
schema,
|
|
1350
|
-
key
|
|
1351
|
-
value: copy[
|
|
734
|
+
key,
|
|
735
|
+
value: copy[key],
|
|
1352
736
|
attribute,
|
|
1353
737
|
path: newPath
|
|
1354
738
|
};
|
|
1355
739
|
await visitor2(visitorOptions, visitorUtils);
|
|
1356
|
-
const
|
|
1357
|
-
if (isNil(
|
|
740
|
+
const value = copy[key];
|
|
741
|
+
if (isNil(value)) {
|
|
1358
742
|
continue;
|
|
1359
743
|
}
|
|
1360
744
|
if (isRelationalAttribute(attribute)) {
|
|
1361
745
|
const isMorphRelation = attribute.relation.toLowerCase().startsWith("morph");
|
|
1362
746
|
const method = isMorphRelation ? traverseMorphRelationTarget : traverseRelationTarget(strapi.getModel(attribute.target));
|
|
1363
|
-
if (isArray(
|
|
1364
|
-
const res = new Array(
|
|
1365
|
-
for (let i2 = 0; i2 <
|
|
1366
|
-
res[i2] = await method(visitor2, newPath,
|
|
747
|
+
if (isArray(value)) {
|
|
748
|
+
const res = new Array(value.length);
|
|
749
|
+
for (let i2 = 0; i2 < value.length; i2 += 1) {
|
|
750
|
+
res[i2] = await method(visitor2, newPath, value[i2]);
|
|
1367
751
|
}
|
|
1368
|
-
copy[
|
|
752
|
+
copy[key] = res;
|
|
1369
753
|
} else {
|
|
1370
|
-
copy[
|
|
754
|
+
copy[key] = await method(visitor2, newPath, value);
|
|
1371
755
|
}
|
|
1372
756
|
continue;
|
|
1373
757
|
}
|
|
1374
758
|
if (isMediaAttribute(attribute)) {
|
|
1375
|
-
if (isArray(
|
|
1376
|
-
const res = new Array(
|
|
1377
|
-
for (let i2 = 0; i2 <
|
|
1378
|
-
res[i2] = await traverseMediaTarget(visitor2, newPath,
|
|
759
|
+
if (isArray(value)) {
|
|
760
|
+
const res = new Array(value.length);
|
|
761
|
+
for (let i2 = 0; i2 < value.length; i2 += 1) {
|
|
762
|
+
res[i2] = await traverseMediaTarget(visitor2, newPath, value[i2]);
|
|
1379
763
|
}
|
|
1380
|
-
copy[
|
|
764
|
+
copy[key] = res;
|
|
1381
765
|
} else {
|
|
1382
|
-
copy[
|
|
766
|
+
copy[key] = await traverseMediaTarget(visitor2, newPath, value);
|
|
1383
767
|
}
|
|
1384
768
|
continue;
|
|
1385
769
|
}
|
|
1386
770
|
if (attribute.type === "component") {
|
|
1387
771
|
const targetSchema = strapi.getModel(attribute.component);
|
|
1388
|
-
if (isArray(
|
|
1389
|
-
const res = new Array(
|
|
1390
|
-
for (let i2 = 0; i2 <
|
|
1391
|
-
res[i2] = await traverseComponent(visitor2, newPath, targetSchema,
|
|
772
|
+
if (isArray(value)) {
|
|
773
|
+
const res = new Array(value.length);
|
|
774
|
+
for (let i2 = 0; i2 < value.length; i2 += 1) {
|
|
775
|
+
res[i2] = await traverseComponent(visitor2, newPath, targetSchema, value[i2]);
|
|
1392
776
|
}
|
|
1393
|
-
copy[
|
|
777
|
+
copy[key] = res;
|
|
1394
778
|
} else {
|
|
1395
|
-
copy[
|
|
779
|
+
copy[key] = await traverseComponent(visitor2, newPath, targetSchema, value);
|
|
1396
780
|
}
|
|
1397
781
|
continue;
|
|
1398
782
|
}
|
|
1399
|
-
if (attribute.type === "dynamiczone" && isArray(
|
|
1400
|
-
const res = new Array(
|
|
1401
|
-
for (let i2 = 0; i2 <
|
|
1402
|
-
res[i2] = await visitDynamicZoneEntry(visitor2, newPath,
|
|
783
|
+
if (attribute.type === "dynamiczone" && isArray(value)) {
|
|
784
|
+
const res = new Array(value.length);
|
|
785
|
+
for (let i2 = 0; i2 < value.length; i2 += 1) {
|
|
786
|
+
res[i2] = await visitDynamicZoneEntry(visitor2, newPath, value[i2]);
|
|
1403
787
|
}
|
|
1404
|
-
copy[
|
|
788
|
+
copy[key] = res;
|
|
1405
789
|
continue;
|
|
1406
790
|
}
|
|
1407
791
|
}
|
|
1408
792
|
return copy;
|
|
1409
793
|
};
|
|
1410
794
|
const createVisitorUtils = ({ data }) => ({
|
|
1411
|
-
remove(
|
|
1412
|
-
delete data[
|
|
795
|
+
remove(key) {
|
|
796
|
+
delete data[key];
|
|
1413
797
|
},
|
|
1414
|
-
set(
|
|
1415
|
-
data[
|
|
798
|
+
set(key, value) {
|
|
799
|
+
data[key] = value;
|
|
1416
800
|
}
|
|
1417
801
|
});
|
|
1418
802
|
const traverseEntity$1 = curry(traverseEntity);
|
|
@@ -1441,37 +825,37 @@ const traverseFactory = () => {
|
|
|
1441
825
|
}
|
|
1442
826
|
let out = utils2.transform(data);
|
|
1443
827
|
const keys = utils2.keys(out);
|
|
1444
|
-
for (const
|
|
1445
|
-
const attribute = schema?.attributes?.[
|
|
828
|
+
for (const key of keys) {
|
|
829
|
+
const attribute = schema?.attributes?.[key] ?? // FIX: Needed to not break existing behavior on the API.
|
|
1446
830
|
// It looks for the attribute in the DB metadata when the key is in snake_case
|
|
1447
|
-
schema?.attributes?.[strapi.db.metadata.get(schema?.uid).columnToAttribute[
|
|
831
|
+
schema?.attributes?.[strapi.db.metadata.get(schema?.uid).columnToAttribute[key]];
|
|
1448
832
|
const newPath = { ...path };
|
|
1449
|
-
newPath.raw = isNil(path.raw) ?
|
|
833
|
+
newPath.raw = isNil(path.raw) ? key : `${path.raw}.${key}`;
|
|
1450
834
|
if (!isNil(attribute)) {
|
|
1451
|
-
newPath.attribute = isNil(path.attribute) ?
|
|
835
|
+
newPath.attribute = isNil(path.attribute) ? key : `${path.attribute}.${key}`;
|
|
1452
836
|
}
|
|
1453
837
|
const visitorOptions = {
|
|
1454
|
-
key
|
|
1455
|
-
value: utils2.get(
|
|
838
|
+
key,
|
|
839
|
+
value: utils2.get(key, out),
|
|
1456
840
|
attribute,
|
|
1457
841
|
schema,
|
|
1458
842
|
path: newPath,
|
|
1459
843
|
data: out
|
|
1460
844
|
};
|
|
1461
845
|
const transformUtils = {
|
|
1462
|
-
remove(
|
|
1463
|
-
out = utils2.remove(
|
|
846
|
+
remove(key2) {
|
|
847
|
+
out = utils2.remove(key2, out);
|
|
1464
848
|
},
|
|
1465
|
-
set(
|
|
1466
|
-
out = utils2.set(
|
|
849
|
+
set(key2, value2) {
|
|
850
|
+
out = utils2.set(key2, value2, out);
|
|
1467
851
|
},
|
|
1468
852
|
recurse: traverse
|
|
1469
853
|
};
|
|
1470
854
|
await visitor2(visitorOptions, pick(["remove", "set"], transformUtils));
|
|
1471
|
-
const
|
|
855
|
+
const value = utils2.get(key, out);
|
|
1472
856
|
const createContext = () => ({
|
|
1473
|
-
key
|
|
1474
|
-
value
|
|
857
|
+
key,
|
|
858
|
+
value,
|
|
1475
859
|
attribute,
|
|
1476
860
|
schema,
|
|
1477
861
|
path: newPath,
|
|
@@ -1530,7 +914,7 @@ const traverseFactory = () => {
|
|
|
1530
914
|
}
|
|
1531
915
|
};
|
|
1532
916
|
};
|
|
1533
|
-
const isObj$2 = (
|
|
917
|
+
const isObj$2 = (value) => isObject(value);
|
|
1534
918
|
const filters = traverseFactory().intercept(
|
|
1535
919
|
// Intercept filters arrays and apply the traversal to each one individually
|
|
1536
920
|
isArray,
|
|
@@ -1551,50 +935,50 @@ const filters = traverseFactory().intercept(
|
|
|
1551
935
|
}
|
|
1552
936
|
).parse(isObj$2, () => ({
|
|
1553
937
|
transform: cloneDeep,
|
|
1554
|
-
remove(
|
|
1555
|
-
return omit(
|
|
938
|
+
remove(key, data) {
|
|
939
|
+
return omit(key, data);
|
|
1556
940
|
},
|
|
1557
|
-
set(
|
|
1558
|
-
return { ...data, [
|
|
941
|
+
set(key, value, data) {
|
|
942
|
+
return { ...data, [key]: value };
|
|
1559
943
|
},
|
|
1560
944
|
keys(data) {
|
|
1561
945
|
return Object.keys(data);
|
|
1562
946
|
},
|
|
1563
|
-
get(
|
|
1564
|
-
return data[
|
|
947
|
+
get(key, data) {
|
|
948
|
+
return data[key];
|
|
1565
949
|
}
|
|
1566
|
-
})).ignore(({ value
|
|
950
|
+
})).ignore(({ value }) => isNil(value)).on(
|
|
1567
951
|
({ attribute }) => isNil(attribute),
|
|
1568
|
-
async ({ key
|
|
1569
|
-
set(
|
|
952
|
+
async ({ key, visitor: visitor2, path, value, schema }, { set, recurse }) => {
|
|
953
|
+
set(key, await recurse(visitor2, { schema, path }, value));
|
|
1570
954
|
}
|
|
1571
|
-
).onRelation(async ({ key
|
|
955
|
+
).onRelation(async ({ key, attribute, visitor: visitor2, path, value }, { set, recurse }) => {
|
|
1572
956
|
const isMorphRelation = attribute.relation.toLowerCase().startsWith("morph");
|
|
1573
957
|
if (isMorphRelation) {
|
|
1574
958
|
return;
|
|
1575
959
|
}
|
|
1576
960
|
const targetSchemaUID = attribute.target;
|
|
1577
961
|
const targetSchema = strapi.getModel(targetSchemaUID);
|
|
1578
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1579
|
-
set(
|
|
1580
|
-
}).onComponent(async ({ key
|
|
962
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
963
|
+
set(key, newValue);
|
|
964
|
+
}).onComponent(async ({ key, attribute, visitor: visitor2, path, value }, { set, recurse }) => {
|
|
1581
965
|
const targetSchema = strapi.getModel(attribute.component);
|
|
1582
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1583
|
-
set(
|
|
1584
|
-
}).onMedia(async ({ key
|
|
966
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
967
|
+
set(key, newValue);
|
|
968
|
+
}).onMedia(async ({ key, visitor: visitor2, path, value }, { set, recurse }) => {
|
|
1585
969
|
const targetSchemaUID = "plugin::upload.file";
|
|
1586
970
|
const targetSchema = strapi.getModel(targetSchemaUID);
|
|
1587
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1588
|
-
set(
|
|
971
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
972
|
+
set(key, newValue);
|
|
1589
973
|
});
|
|
1590
974
|
const traverseQueryFilters = curry(filters.traverse);
|
|
1591
975
|
const ORDERS = { asc: "asc", desc: "desc" };
|
|
1592
976
|
const ORDER_VALUES = Object.values(ORDERS);
|
|
1593
|
-
const isSortOrder = (
|
|
1594
|
-
const isStringArray$3 = (
|
|
1595
|
-
const isObjectArray = (
|
|
1596
|
-
const isNestedSorts = (
|
|
1597
|
-
const isObj$1 = (
|
|
977
|
+
const isSortOrder = (value) => ORDER_VALUES.includes(value.toLowerCase());
|
|
978
|
+
const isStringArray$3 = (value) => Array.isArray(value) && value.every(isString);
|
|
979
|
+
const isObjectArray = (value) => Array.isArray(value) && value.every(isObject);
|
|
980
|
+
const isNestedSorts = (value) => isString(value) && value.split(",").length > 1;
|
|
981
|
+
const isObj$1 = (value) => isObject(value);
|
|
1598
982
|
const sort = traverseFactory().intercept(
|
|
1599
983
|
// String with chained sorts (foo,bar,foobar) => split, map(recurse), then recompose
|
|
1600
984
|
isNestedSorts,
|
|
@@ -1619,221 +1003,240 @@ const sort = traverseFactory().intercept(
|
|
|
1619
1003
|
(res) => res.filter((nestedSort) => !isEmpty(nestedSort))
|
|
1620
1004
|
);
|
|
1621
1005
|
}
|
|
1622
|
-
).parse(isString
|
|
1623
|
-
const tokenize = pipe(split("."), map(split(":")), flatten);
|
|
1006
|
+
).parse(isString, () => {
|
|
1007
|
+
const tokenize = pipe$1(split("."), map$1(split(":")), flatten);
|
|
1624
1008
|
const recompose = (parts) => {
|
|
1625
1009
|
if (parts.length === 0) {
|
|
1626
1010
|
return void 0;
|
|
1627
1011
|
}
|
|
1628
|
-
return parts.reduce((
|
|
1012
|
+
return parts.reduce((acc, part) => {
|
|
1629
1013
|
if (isEmpty(part)) {
|
|
1630
|
-
return
|
|
1014
|
+
return acc;
|
|
1631
1015
|
}
|
|
1632
|
-
if (
|
|
1016
|
+
if (acc === "") {
|
|
1633
1017
|
return part;
|
|
1634
1018
|
}
|
|
1635
|
-
return isSortOrder(part) ? `${
|
|
1019
|
+
return isSortOrder(part) ? `${acc}:${part}` : `${acc}.${part}`;
|
|
1636
1020
|
}, "");
|
|
1637
1021
|
};
|
|
1638
1022
|
return {
|
|
1639
1023
|
transform: trim,
|
|
1640
|
-
remove(
|
|
1024
|
+
remove(key, data) {
|
|
1641
1025
|
const [root] = tokenize(data);
|
|
1642
|
-
return root ===
|
|
1026
|
+
return root === key ? void 0 : data;
|
|
1643
1027
|
},
|
|
1644
|
-
set(
|
|
1028
|
+
set(key, value, data) {
|
|
1645
1029
|
const [root] = tokenize(data);
|
|
1646
|
-
if (root !==
|
|
1030
|
+
if (root !== key) {
|
|
1647
1031
|
return data;
|
|
1648
1032
|
}
|
|
1649
|
-
return isNil(
|
|
1033
|
+
return isNil(value) ? root : `${root}.${value}`;
|
|
1650
1034
|
},
|
|
1651
1035
|
keys(data) {
|
|
1652
1036
|
const v = first(tokenize(data));
|
|
1653
1037
|
return v ? [v] : [];
|
|
1654
1038
|
},
|
|
1655
|
-
get(
|
|
1039
|
+
get(key, data) {
|
|
1656
1040
|
const [root, ...rest] = tokenize(data);
|
|
1657
|
-
return
|
|
1041
|
+
return key === root ? recompose(rest) : void 0;
|
|
1658
1042
|
}
|
|
1659
1043
|
};
|
|
1660
1044
|
}).parse(isObj$1, () => ({
|
|
1661
1045
|
transform: cloneDeep,
|
|
1662
|
-
remove(
|
|
1663
|
-
const { [
|
|
1046
|
+
remove(key, data) {
|
|
1047
|
+
const { [key]: ignored, ...rest } = data;
|
|
1664
1048
|
return rest;
|
|
1665
1049
|
},
|
|
1666
|
-
set(
|
|
1667
|
-
return { ...data, [
|
|
1050
|
+
set(key, value, data) {
|
|
1051
|
+
return { ...data, [key]: value };
|
|
1668
1052
|
},
|
|
1669
1053
|
keys(data) {
|
|
1670
1054
|
return Object.keys(data);
|
|
1671
1055
|
},
|
|
1672
|
-
get(
|
|
1673
|
-
return data[
|
|
1056
|
+
get(key, data) {
|
|
1057
|
+
return data[key];
|
|
1674
1058
|
}
|
|
1675
|
-
})).onRelation(async ({ key
|
|
1059
|
+
})).onRelation(async ({ key, value, attribute, visitor: visitor2, path }, { set, recurse }) => {
|
|
1676
1060
|
const isMorphRelation = attribute.relation.toLowerCase().startsWith("morph");
|
|
1677
1061
|
if (isMorphRelation) {
|
|
1678
1062
|
return;
|
|
1679
1063
|
}
|
|
1680
1064
|
const targetSchemaUID = attribute.target;
|
|
1681
1065
|
const targetSchema = strapi.getModel(targetSchemaUID);
|
|
1682
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1683
|
-
set(
|
|
1684
|
-
}).onMedia(async ({ key
|
|
1066
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
1067
|
+
set(key, newValue);
|
|
1068
|
+
}).onMedia(async ({ key, path, visitor: visitor2, value }, { recurse, set }) => {
|
|
1685
1069
|
const targetSchemaUID = "plugin::upload.file";
|
|
1686
1070
|
const targetSchema = strapi.getModel(targetSchemaUID);
|
|
1687
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1688
|
-
set(
|
|
1689
|
-
}).onComponent(async ({ key
|
|
1071
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
1072
|
+
set(key, newValue);
|
|
1073
|
+
}).onComponent(async ({ key, value, visitor: visitor2, path, attribute }, { recurse, set }) => {
|
|
1690
1074
|
const targetSchema = strapi.getModel(attribute.component);
|
|
1691
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1692
|
-
set(
|
|
1075
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
1076
|
+
set(key, newValue);
|
|
1693
1077
|
});
|
|
1694
1078
|
const traverseQuerySort = curry(sort.traverse);
|
|
1695
1079
|
const isKeyword = (keyword) => {
|
|
1696
|
-
return ({ key
|
|
1697
|
-
return !attribute && keyword ===
|
|
1080
|
+
return ({ key, attribute }) => {
|
|
1081
|
+
return !attribute && keyword === key;
|
|
1698
1082
|
};
|
|
1699
1083
|
};
|
|
1700
|
-
const isStringArray$2 = (
|
|
1701
|
-
const
|
|
1702
|
-
const isObj = (value2) => isObject(value2);
|
|
1084
|
+
const isStringArray$2 = (value) => isArray(value) && value.every(isString);
|
|
1085
|
+
const isObj = (value) => isObject(value);
|
|
1703
1086
|
const populate = traverseFactory().intercept(isStringArray$2, async (visitor2, options, populate2, { recurse }) => {
|
|
1704
1087
|
const visitedPopulate = await Promise.all(
|
|
1705
1088
|
populate2.map((nestedPopulate) => recurse(visitor2, options, nestedPopulate))
|
|
1706
1089
|
);
|
|
1707
1090
|
return visitedPopulate.filter((item) => !isNil(item));
|
|
1708
|
-
}).
|
|
1709
|
-
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
|
|
1713
|
-
|
|
1714
|
-
|
|
1715
|
-
|
|
1091
|
+
}).parse(
|
|
1092
|
+
(value) => value === "*",
|
|
1093
|
+
() => ({
|
|
1094
|
+
/**
|
|
1095
|
+
* Since value is '*', we don't need to transform it
|
|
1096
|
+
*/
|
|
1097
|
+
transform: identity,
|
|
1098
|
+
/**
|
|
1099
|
+
* '*' isn't a key/value structure, so regardless
|
|
1100
|
+
* of the given key, it returns the data ('*')
|
|
1101
|
+
*/
|
|
1102
|
+
get: (_key, data) => data,
|
|
1103
|
+
/**
|
|
1104
|
+
* '*' isn't a key/value structure, so regardless
|
|
1105
|
+
* of the given `key`, use `value` as the new `data`
|
|
1106
|
+
*/
|
|
1107
|
+
set: (_key, value) => value,
|
|
1108
|
+
/**
|
|
1109
|
+
* '*' isn't a key/value structure, but we need to simulate at least one to enable
|
|
1110
|
+
* the data traversal. We're using '' since it represents a falsy string value
|
|
1111
|
+
*/
|
|
1112
|
+
keys: constant([""]),
|
|
1113
|
+
/**
|
|
1114
|
+
* Removing '*' means setting it to undefined, regardless of the given key
|
|
1115
|
+
*/
|
|
1116
|
+
remove: constant(void 0)
|
|
1117
|
+
})
|
|
1118
|
+
).parse(isString, () => {
|
|
1716
1119
|
const tokenize = split(".");
|
|
1717
1120
|
const recompose = join(".");
|
|
1718
1121
|
return {
|
|
1719
1122
|
transform: trim,
|
|
1720
|
-
remove(
|
|
1123
|
+
remove(key, data) {
|
|
1721
1124
|
const [root] = tokenize(data);
|
|
1722
|
-
return root ===
|
|
1125
|
+
return root === key ? void 0 : data;
|
|
1723
1126
|
},
|
|
1724
|
-
set(
|
|
1127
|
+
set(key, value, data) {
|
|
1725
1128
|
const [root] = tokenize(data);
|
|
1726
|
-
if (root !==
|
|
1129
|
+
if (root !== key) {
|
|
1727
1130
|
return data;
|
|
1728
1131
|
}
|
|
1729
|
-
return isNil(
|
|
1132
|
+
return isNil(value) || isEmpty(value) ? root : `${root}.${value}`;
|
|
1730
1133
|
},
|
|
1731
1134
|
keys(data) {
|
|
1732
1135
|
const v = first(tokenize(data));
|
|
1733
1136
|
return v ? [v] : [];
|
|
1734
1137
|
},
|
|
1735
|
-
get(
|
|
1138
|
+
get(key, data) {
|
|
1736
1139
|
const [root, ...rest] = tokenize(data);
|
|
1737
|
-
return
|
|
1140
|
+
return key === root ? recompose(rest) : void 0;
|
|
1738
1141
|
}
|
|
1739
1142
|
};
|
|
1740
1143
|
}).parse(isObj, () => ({
|
|
1741
1144
|
transform: cloneDeep,
|
|
1742
|
-
remove(
|
|
1743
|
-
const { [
|
|
1145
|
+
remove(key, data) {
|
|
1146
|
+
const { [key]: ignored, ...rest } = data;
|
|
1744
1147
|
return rest;
|
|
1745
1148
|
},
|
|
1746
|
-
set(
|
|
1747
|
-
return { ...data, [
|
|
1149
|
+
set(key, value, data) {
|
|
1150
|
+
return { ...data, [key]: value };
|
|
1748
1151
|
},
|
|
1749
1152
|
keys(data) {
|
|
1750
1153
|
return Object.keys(data);
|
|
1751
1154
|
},
|
|
1752
|
-
get(
|
|
1753
|
-
return data[
|
|
1155
|
+
get(key, data) {
|
|
1156
|
+
return data[key];
|
|
1754
1157
|
}
|
|
1755
|
-
})).ignore(({ key
|
|
1756
|
-
return ["sort", "filters", "fields"].includes(
|
|
1158
|
+
})).ignore(({ key, attribute }) => {
|
|
1159
|
+
return ["sort", "filters", "fields"].includes(key) && !attribute;
|
|
1757
1160
|
}).on(
|
|
1758
1161
|
// Handle recursion on populate."populate"
|
|
1759
1162
|
isKeyword("populate"),
|
|
1760
|
-
async ({ key
|
|
1761
|
-
const newValue = await recurse(visitor2, { schema, path },
|
|
1762
|
-
set(
|
|
1163
|
+
async ({ key, visitor: visitor2, path, value, schema }, { set, recurse }) => {
|
|
1164
|
+
const newValue = await recurse(visitor2, { schema, path }, value);
|
|
1165
|
+
set(key, newValue);
|
|
1763
1166
|
}
|
|
1764
|
-
).on(isKeyword("on"), async ({ key
|
|
1167
|
+
).on(isKeyword("on"), async ({ key, visitor: visitor2, path, value }, { set, recurse }) => {
|
|
1765
1168
|
const newOn = {};
|
|
1766
|
-
if (!isObj(
|
|
1169
|
+
if (!isObj(value)) {
|
|
1767
1170
|
return;
|
|
1768
1171
|
}
|
|
1769
|
-
for (const [uid, subPopulate] of Object.entries(
|
|
1172
|
+
for (const [uid, subPopulate] of Object.entries(value)) {
|
|
1770
1173
|
const model = strapi.getModel(uid);
|
|
1771
1174
|
const newPath = { ...path, raw: `${path.raw}[${uid}]` };
|
|
1772
1175
|
newOn[uid] = await recurse(visitor2, { schema: model, path: newPath }, subPopulate);
|
|
1773
1176
|
}
|
|
1774
|
-
set(
|
|
1775
|
-
}).onRelation(async ({ key
|
|
1776
|
-
if (isNil(
|
|
1177
|
+
set(key, newOn);
|
|
1178
|
+
}).onRelation(async ({ key, value, attribute, visitor: visitor2, path, schema }, { set, recurse }) => {
|
|
1179
|
+
if (isNil(value)) {
|
|
1777
1180
|
return;
|
|
1778
1181
|
}
|
|
1779
1182
|
if (isMorphToRelationalAttribute(attribute)) {
|
|
1780
|
-
if (!isObject(
|
|
1183
|
+
if (!isObject(value) || !("on" in value && isObject(value?.on))) {
|
|
1781
1184
|
return;
|
|
1782
1185
|
}
|
|
1783
|
-
const newValue2 = await recurse(visitor2, { schema, path }, { on:
|
|
1784
|
-
set(
|
|
1186
|
+
const newValue2 = await recurse(visitor2, { schema, path }, { on: value?.on });
|
|
1187
|
+
set(key, { on: newValue2 });
|
|
1785
1188
|
}
|
|
1786
1189
|
const targetSchemaUID = attribute.target;
|
|
1787
1190
|
const targetSchema = strapi.getModel(targetSchemaUID);
|
|
1788
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1789
|
-
set(
|
|
1790
|
-
}).onMedia(async ({ key
|
|
1791
|
-
if (isNil(
|
|
1191
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
1192
|
+
set(key, newValue);
|
|
1193
|
+
}).onMedia(async ({ key, path, visitor: visitor2, value }, { recurse, set }) => {
|
|
1194
|
+
if (isNil(value)) {
|
|
1792
1195
|
return;
|
|
1793
1196
|
}
|
|
1794
1197
|
const targetSchemaUID = "plugin::upload.file";
|
|
1795
1198
|
const targetSchema = strapi.getModel(targetSchemaUID);
|
|
1796
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1797
|
-
set(
|
|
1798
|
-
}).onComponent(async ({ key
|
|
1799
|
-
if (isNil(
|
|
1199
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
1200
|
+
set(key, newValue);
|
|
1201
|
+
}).onComponent(async ({ key, value, visitor: visitor2, path, attribute }, { recurse, set }) => {
|
|
1202
|
+
if (isNil(value)) {
|
|
1800
1203
|
return;
|
|
1801
1204
|
}
|
|
1802
1205
|
const targetSchema = strapi.getModel(attribute.component);
|
|
1803
|
-
const newValue = await recurse(visitor2, { schema: targetSchema, path },
|
|
1804
|
-
set(
|
|
1805
|
-
}).onDynamicZone(async ({ key
|
|
1806
|
-
if (isNil(
|
|
1206
|
+
const newValue = await recurse(visitor2, { schema: targetSchema, path }, value);
|
|
1207
|
+
set(key, newValue);
|
|
1208
|
+
}).onDynamicZone(async ({ key, value, attribute, schema, visitor: visitor2, path }, { set, recurse }) => {
|
|
1209
|
+
if (isNil(value)) {
|
|
1807
1210
|
return;
|
|
1808
1211
|
}
|
|
1809
|
-
if (isObject(
|
|
1212
|
+
if (isObject(value)) {
|
|
1810
1213
|
const { components } = attribute;
|
|
1811
1214
|
const newValue = {};
|
|
1812
|
-
let newProperties = omit("on",
|
|
1215
|
+
let newProperties = omit("on", value);
|
|
1813
1216
|
for (const componentUID of components) {
|
|
1814
1217
|
const componentSchema = strapi.getModel(componentUID);
|
|
1815
|
-
const properties = await recurse(visitor2, { schema: componentSchema, path },
|
|
1218
|
+
const properties = await recurse(visitor2, { schema: componentSchema, path }, value);
|
|
1816
1219
|
newProperties = merge(newProperties, properties);
|
|
1817
1220
|
}
|
|
1818
1221
|
Object.assign(newValue, newProperties);
|
|
1819
|
-
if ("on" in
|
|
1820
|
-
const newOn = await recurse(visitor2, { schema, path }, { on:
|
|
1222
|
+
if ("on" in value && value.on) {
|
|
1223
|
+
const newOn = await recurse(visitor2, { schema, path }, { on: value.on });
|
|
1821
1224
|
Object.assign(newValue, newOn);
|
|
1822
1225
|
}
|
|
1823
|
-
set(
|
|
1226
|
+
set(key, newValue);
|
|
1824
1227
|
} else {
|
|
1825
|
-
const newValue = await recurse(visitor2, { schema, path },
|
|
1826
|
-
set(
|
|
1228
|
+
const newValue = await recurse(visitor2, { schema, path }, value);
|
|
1229
|
+
set(key, newValue);
|
|
1827
1230
|
}
|
|
1828
1231
|
});
|
|
1829
1232
|
const traverseQueryPopulate = curry(populate.traverse);
|
|
1830
|
-
const isStringArray$1 = (
|
|
1233
|
+
const isStringArray$1 = (value) => isArray(value) && value.every(isString);
|
|
1831
1234
|
const fields = traverseFactory().intercept(isStringArray$1, async (visitor2, options, fields2, { recurse }) => {
|
|
1832
1235
|
return Promise.all(fields2.map((field) => recurse(visitor2, options, field)));
|
|
1833
|
-
}).intercept((
|
|
1236
|
+
}).intercept((value) => eq("*", value), constant("*")).parse(isString, () => ({
|
|
1834
1237
|
transform: trim,
|
|
1835
|
-
remove(
|
|
1836
|
-
return data ===
|
|
1238
|
+
remove(key, data) {
|
|
1239
|
+
return data === key ? void 0 : data;
|
|
1837
1240
|
},
|
|
1838
1241
|
set(_key, _value, data) {
|
|
1839
1242
|
return data;
|
|
@@ -1841,8 +1244,8 @@ const fields = traverseFactory().intercept(isStringArray$1, async (visitor2, opt
|
|
|
1841
1244
|
keys(data) {
|
|
1842
1245
|
return [data];
|
|
1843
1246
|
},
|
|
1844
|
-
get(
|
|
1845
|
-
return
|
|
1247
|
+
get(key, data) {
|
|
1248
|
+
return key === data ? data : void 0;
|
|
1846
1249
|
}
|
|
1847
1250
|
}));
|
|
1848
1251
|
const traverseQueryFields = curry(fields.traverse);
|
|
@@ -1901,31 +1304,32 @@ const OPERATORS = {
|
|
|
1901
1304
|
array: ARRAY_OPERATORS
|
|
1902
1305
|
};
|
|
1903
1306
|
const OPERATORS_LOWERCASE = Object.fromEntries(
|
|
1904
|
-
Object.entries(OPERATORS).map(([
|
|
1905
|
-
|
|
1906
|
-
values.map((
|
|
1307
|
+
Object.entries(OPERATORS).map(([key, values]) => [
|
|
1308
|
+
key,
|
|
1309
|
+
values.map((value) => value.toLowerCase())
|
|
1907
1310
|
])
|
|
1908
1311
|
);
|
|
1909
|
-
const isObjKey = (
|
|
1910
|
-
return
|
|
1312
|
+
const isObjKey = (key, obj) => {
|
|
1313
|
+
return key in obj;
|
|
1911
1314
|
};
|
|
1912
|
-
const isOperatorOfType = (type,
|
|
1315
|
+
const isOperatorOfType = (type, key, ignoreCase = false) => {
|
|
1913
1316
|
if (ignoreCase) {
|
|
1914
|
-
return OPERATORS_LOWERCASE[type]?.includes(
|
|
1317
|
+
return OPERATORS_LOWERCASE[type]?.includes(key.toLowerCase()) ?? false;
|
|
1915
1318
|
}
|
|
1916
1319
|
if (isObjKey(type, OPERATORS)) {
|
|
1917
|
-
return OPERATORS[type]?.includes(
|
|
1320
|
+
return OPERATORS[type]?.includes(key) ?? false;
|
|
1918
1321
|
}
|
|
1919
1322
|
return false;
|
|
1920
1323
|
};
|
|
1921
|
-
const isOperator = (
|
|
1922
|
-
return Object.keys(OPERATORS).some((type) => isOperatorOfType(type,
|
|
1324
|
+
const isOperator = (key, ignoreCase = false) => {
|
|
1325
|
+
return Object.keys(OPERATORS).some((type) => isOperatorOfType(type, key, ignoreCase));
|
|
1923
1326
|
};
|
|
1327
|
+
const { ID_ATTRIBUTE: ID_ATTRIBUTE$3, DOC_ID_ATTRIBUTE: DOC_ID_ATTRIBUTE$3 } = constants$1;
|
|
1924
1328
|
const sanitizePasswords = (schema) => async (entity) => {
|
|
1925
1329
|
if (!schema) {
|
|
1926
1330
|
throw new Error("Missing schema in sanitizePasswords");
|
|
1927
1331
|
}
|
|
1928
|
-
return traverseEntity$1(visitor$
|
|
1332
|
+
return traverseEntity$1(visitor$8, { schema }, entity);
|
|
1929
1333
|
};
|
|
1930
1334
|
const defaultSanitizeOutput = async (schema, entity) => {
|
|
1931
1335
|
if (!schema) {
|
|
@@ -1933,8 +1337,8 @@ const defaultSanitizeOutput = async (schema, entity) => {
|
|
|
1933
1337
|
}
|
|
1934
1338
|
return traverseEntity$1(
|
|
1935
1339
|
(...args) => {
|
|
1340
|
+
visitor$8(...args);
|
|
1936
1341
|
visitor$7(...args);
|
|
1937
|
-
visitor$6(...args);
|
|
1938
1342
|
},
|
|
1939
1343
|
{ schema },
|
|
1940
1344
|
entity
|
|
@@ -1944,33 +1348,33 @@ const defaultSanitizeFilters = curry((schema, filters2) => {
|
|
|
1944
1348
|
if (!schema) {
|
|
1945
1349
|
throw new Error("Missing schema in defaultSanitizeFilters");
|
|
1946
1350
|
}
|
|
1947
|
-
return
|
|
1351
|
+
return pipe(
|
|
1948
1352
|
// Remove keys that are not attributes or valid operators
|
|
1949
1353
|
traverseQueryFilters(
|
|
1950
|
-
({ key
|
|
1354
|
+
({ key, attribute }, { remove: remove2 }) => {
|
|
1951
1355
|
const isAttribute = !!attribute;
|
|
1952
|
-
if (
|
|
1356
|
+
if ([ID_ATTRIBUTE$3, DOC_ID_ATTRIBUTE$3].includes(key)) {
|
|
1953
1357
|
return;
|
|
1954
1358
|
}
|
|
1955
|
-
if (!isAttribute && !isOperator(
|
|
1956
|
-
remove2(
|
|
1359
|
+
if (!isAttribute && !isOperator(key)) {
|
|
1360
|
+
remove2(key);
|
|
1957
1361
|
}
|
|
1958
1362
|
},
|
|
1959
1363
|
{ schema }
|
|
1960
1364
|
),
|
|
1961
1365
|
// Remove dynamic zones from filters
|
|
1962
|
-
traverseQueryFilters(visitor$4, { schema }),
|
|
1963
|
-
// Remove morpTo relations from filters
|
|
1964
1366
|
traverseQueryFilters(visitor$5, { schema }),
|
|
1367
|
+
// Remove morpTo relations from filters
|
|
1368
|
+
traverseQueryFilters(visitor$6, { schema }),
|
|
1965
1369
|
// Remove passwords from filters
|
|
1966
|
-
traverseQueryFilters(visitor$
|
|
1370
|
+
traverseQueryFilters(visitor$8, { schema }),
|
|
1967
1371
|
// Remove private from filters
|
|
1968
|
-
traverseQueryFilters(visitor$
|
|
1372
|
+
traverseQueryFilters(visitor$7, { schema }),
|
|
1969
1373
|
// Remove empty objects
|
|
1970
1374
|
traverseQueryFilters(
|
|
1971
|
-
({ key
|
|
1972
|
-
if (isObject(
|
|
1973
|
-
remove2(
|
|
1375
|
+
({ key, value }, { remove: remove2 }) => {
|
|
1376
|
+
if (isObject(value) && isEmpty(value)) {
|
|
1377
|
+
remove2(key);
|
|
1974
1378
|
}
|
|
1975
1379
|
},
|
|
1976
1380
|
{ schema }
|
|
@@ -1981,35 +1385,35 @@ const defaultSanitizeSort = curry((schema, sort2) => {
|
|
|
1981
1385
|
if (!schema) {
|
|
1982
1386
|
throw new Error("Missing schema in defaultSanitizeSort");
|
|
1983
1387
|
}
|
|
1984
|
-
return
|
|
1388
|
+
return pipe(
|
|
1985
1389
|
// Remove non attribute keys
|
|
1986
1390
|
traverseQuerySort(
|
|
1987
|
-
({ key
|
|
1988
|
-
if (
|
|
1391
|
+
({ key, attribute }, { remove: remove2 }) => {
|
|
1392
|
+
if ([ID_ATTRIBUTE$3, DOC_ID_ATTRIBUTE$3].includes(key)) {
|
|
1989
1393
|
return;
|
|
1990
1394
|
}
|
|
1991
1395
|
if (!attribute) {
|
|
1992
|
-
remove2(
|
|
1396
|
+
remove2(key);
|
|
1993
1397
|
}
|
|
1994
1398
|
},
|
|
1995
1399
|
{ schema }
|
|
1996
1400
|
),
|
|
1997
1401
|
// Remove dynamic zones from sort
|
|
1998
|
-
traverseQuerySort(visitor$4, { schema }),
|
|
1999
|
-
// Remove morpTo relations from sort
|
|
2000
1402
|
traverseQuerySort(visitor$5, { schema }),
|
|
2001
|
-
// Remove
|
|
1403
|
+
// Remove morpTo relations from sort
|
|
2002
1404
|
traverseQuerySort(visitor$6, { schema }),
|
|
2003
|
-
// Remove
|
|
1405
|
+
// Remove private from sort
|
|
2004
1406
|
traverseQuerySort(visitor$7, { schema }),
|
|
1407
|
+
// Remove passwords from filters
|
|
1408
|
+
traverseQuerySort(visitor$8, { schema }),
|
|
2005
1409
|
// Remove keys for empty non-scalar values
|
|
2006
1410
|
traverseQuerySort(
|
|
2007
|
-
({ key
|
|
2008
|
-
if (
|
|
1411
|
+
({ key, attribute, value }, { remove: remove2 }) => {
|
|
1412
|
+
if ([ID_ATTRIBUTE$3, DOC_ID_ATTRIBUTE$3].includes(key)) {
|
|
2009
1413
|
return;
|
|
2010
1414
|
}
|
|
2011
|
-
if (!isScalarAttribute(attribute) && isEmpty(
|
|
2012
|
-
remove2(
|
|
1415
|
+
if (!isScalarAttribute(attribute) && isEmpty(value)) {
|
|
1416
|
+
remove2(key);
|
|
2013
1417
|
}
|
|
2014
1418
|
},
|
|
2015
1419
|
{ schema }
|
|
@@ -2020,51 +1424,55 @@ const defaultSanitizeFields = curry((schema, fields2) => {
|
|
|
2020
1424
|
if (!schema) {
|
|
2021
1425
|
throw new Error("Missing schema in defaultSanitizeFields");
|
|
2022
1426
|
}
|
|
2023
|
-
return
|
|
1427
|
+
return pipe(
|
|
2024
1428
|
// Only keep scalar attributes
|
|
2025
1429
|
traverseQueryFields(
|
|
2026
|
-
({ key
|
|
2027
|
-
if (
|
|
1430
|
+
({ key, attribute }, { remove: remove2 }) => {
|
|
1431
|
+
if ([ID_ATTRIBUTE$3, DOC_ID_ATTRIBUTE$3].includes(key)) {
|
|
2028
1432
|
return;
|
|
2029
1433
|
}
|
|
2030
1434
|
if (isNil(attribute) || !isScalarAttribute(attribute)) {
|
|
2031
|
-
remove2(
|
|
1435
|
+
remove2(key);
|
|
2032
1436
|
}
|
|
2033
1437
|
},
|
|
2034
1438
|
{ schema }
|
|
2035
1439
|
),
|
|
2036
1440
|
// Remove private fields
|
|
2037
|
-
traverseQueryFields(visitor$6, { schema }),
|
|
2038
|
-
// Remove password fields
|
|
2039
1441
|
traverseQueryFields(visitor$7, { schema }),
|
|
1442
|
+
// Remove password fields
|
|
1443
|
+
traverseQueryFields(visitor$8, { schema }),
|
|
2040
1444
|
// Remove nil values from fields array
|
|
2041
|
-
(
|
|
1445
|
+
(value) => isArray(value) ? value.filter((field) => !isNil(field)) : value
|
|
2042
1446
|
)(fields2);
|
|
2043
1447
|
});
|
|
2044
1448
|
const defaultSanitizePopulate = curry((schema, populate2) => {
|
|
2045
1449
|
if (!schema) {
|
|
2046
1450
|
throw new Error("Missing schema in defaultSanitizePopulate");
|
|
2047
1451
|
}
|
|
2048
|
-
return
|
|
1452
|
+
return pipe(
|
|
1453
|
+
traverseQueryPopulate(visitor$4, { schema }),
|
|
2049
1454
|
traverseQueryPopulate(
|
|
2050
|
-
async ({ key
|
|
1455
|
+
async ({ key, value, schema: schema2, attribute }, { set }) => {
|
|
2051
1456
|
if (attribute) {
|
|
2052
1457
|
return;
|
|
2053
1458
|
}
|
|
2054
|
-
if (
|
|
2055
|
-
set(
|
|
1459
|
+
if (key === "sort") {
|
|
1460
|
+
set(key, await defaultSanitizeSort(schema2, value));
|
|
2056
1461
|
}
|
|
2057
|
-
if (
|
|
2058
|
-
set(
|
|
1462
|
+
if (key === "filters") {
|
|
1463
|
+
set(key, await defaultSanitizeFilters(schema2, value));
|
|
2059
1464
|
}
|
|
2060
|
-
if (
|
|
2061
|
-
set(
|
|
1465
|
+
if (key === "fields") {
|
|
1466
|
+
set(key, await defaultSanitizeFields(schema2, value));
|
|
1467
|
+
}
|
|
1468
|
+
if (key === "populate") {
|
|
1469
|
+
set(key, await defaultSanitizePopulate(schema2, value));
|
|
2062
1470
|
}
|
|
2063
1471
|
},
|
|
2064
1472
|
{ schema }
|
|
2065
1473
|
),
|
|
2066
1474
|
// Remove private fields
|
|
2067
|
-
traverseQueryPopulate(visitor$
|
|
1475
|
+
traverseQueryPopulate(visitor$7, { schema })
|
|
2068
1476
|
)(populate2);
|
|
2069
1477
|
});
|
|
2070
1478
|
const sanitizers = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
@@ -2087,7 +1495,8 @@ const createContentAPISanitizers = () => {
|
|
|
2087
1495
|
const nonWritableAttributes = getNonWritableAttributes(schema);
|
|
2088
1496
|
const transforms = [
|
|
2089
1497
|
// Remove first level ID in inputs
|
|
2090
|
-
omit(
|
|
1498
|
+
omit(constants$1.ID_ATTRIBUTE),
|
|
1499
|
+
omit(constants$1.DOC_ID_ATTRIBUTE),
|
|
2091
1500
|
// Remove non-writable attributes
|
|
2092
1501
|
traverseEntity$1(removeRestrictedFields(nonWritableAttributes), { schema })
|
|
2093
1502
|
];
|
|
@@ -2095,7 +1504,7 @@ const createContentAPISanitizers = () => {
|
|
|
2095
1504
|
transforms.push(traverseEntity$1(removeRestrictedRelations(auth), { schema }));
|
|
2096
1505
|
}
|
|
2097
1506
|
strapi.sanitizers.get("content-api.input").forEach((sanitizer) => transforms.push(sanitizer(schema)));
|
|
2098
|
-
return
|
|
1507
|
+
return pipe(...transforms)(data);
|
|
2099
1508
|
};
|
|
2100
1509
|
const sanitizeOutput = async (data, schema, { auth } = {}) => {
|
|
2101
1510
|
if (!schema) {
|
|
@@ -2113,7 +1522,7 @@ const createContentAPISanitizers = () => {
|
|
|
2113
1522
|
transforms.push(traverseEntity$1(removeRestrictedRelations(auth), { schema }));
|
|
2114
1523
|
}
|
|
2115
1524
|
strapi.sanitizers.get("content-api.output").forEach((sanitizer) => transforms.push(sanitizer(schema)));
|
|
2116
|
-
return
|
|
1525
|
+
return pipe(...transforms)(data);
|
|
2117
1526
|
};
|
|
2118
1527
|
const sanitizeQuery = async (query, schema, { auth } = {}) => {
|
|
2119
1528
|
if (!schema) {
|
|
@@ -2146,7 +1555,7 @@ const createContentAPISanitizers = () => {
|
|
|
2146
1555
|
if (auth) {
|
|
2147
1556
|
transforms.push(traverseQueryFilters(removeRestrictedRelations(auth), { schema }));
|
|
2148
1557
|
}
|
|
2149
|
-
return
|
|
1558
|
+
return pipe(...transforms)(filters2);
|
|
2150
1559
|
};
|
|
2151
1560
|
const sanitizeSort = (sort2, schema, { auth } = {}) => {
|
|
2152
1561
|
if (!schema) {
|
|
@@ -2156,14 +1565,14 @@ const createContentAPISanitizers = () => {
|
|
|
2156
1565
|
if (auth) {
|
|
2157
1566
|
transforms.push(traverseQuerySort(removeRestrictedRelations(auth), { schema }));
|
|
2158
1567
|
}
|
|
2159
|
-
return
|
|
1568
|
+
return pipe(...transforms)(sort2);
|
|
2160
1569
|
};
|
|
2161
1570
|
const sanitizeFields = (fields2, schema) => {
|
|
2162
1571
|
if (!schema) {
|
|
2163
1572
|
throw new Error("Missing schema in sanitizeFields");
|
|
2164
1573
|
}
|
|
2165
1574
|
const transforms = [defaultSanitizeFields(schema)];
|
|
2166
|
-
return
|
|
1575
|
+
return pipe(...transforms)(fields2);
|
|
2167
1576
|
};
|
|
2168
1577
|
const sanitizePopulate = (populate2, schema, { auth } = {}) => {
|
|
2169
1578
|
if (!schema) {
|
|
@@ -2173,7 +1582,7 @@ const createContentAPISanitizers = () => {
|
|
|
2173
1582
|
if (auth) {
|
|
2174
1583
|
transforms.push(traverseQueryPopulate(removeRestrictedRelations(auth), { schema }));
|
|
2175
1584
|
}
|
|
2176
|
-
return
|
|
1585
|
+
return pipe(...transforms)(populate2);
|
|
2177
1586
|
};
|
|
2178
1587
|
return {
|
|
2179
1588
|
input: sanitizeInput,
|
|
@@ -2191,26 +1600,134 @@ const index$1 = {
|
|
|
2191
1600
|
sanitizers,
|
|
2192
1601
|
visitors: visitors$1
|
|
2193
1602
|
};
|
|
2194
|
-
const
|
|
2195
|
-
|
|
1603
|
+
const formatYupInnerError = (yupError) => ({
|
|
1604
|
+
path: toPath(yupError.path),
|
|
1605
|
+
message: yupError.message,
|
|
1606
|
+
name: yupError.name
|
|
1607
|
+
});
|
|
1608
|
+
const formatYupErrors = (yupError) => ({
|
|
1609
|
+
errors: isEmpty(yupError.inner) ? [formatYupInnerError(yupError)] : yupError.inner.map(formatYupInnerError),
|
|
1610
|
+
message: yupError.message
|
|
1611
|
+
});
|
|
1612
|
+
class ApplicationError extends Error {
|
|
1613
|
+
name;
|
|
1614
|
+
details;
|
|
1615
|
+
message;
|
|
1616
|
+
constructor(message = "An application error occured", details = {}) {
|
|
1617
|
+
super();
|
|
1618
|
+
this.name = "ApplicationError";
|
|
1619
|
+
this.message = message;
|
|
1620
|
+
this.details = details;
|
|
1621
|
+
}
|
|
1622
|
+
}
|
|
1623
|
+
class ValidationError extends ApplicationError {
|
|
1624
|
+
constructor(message, details) {
|
|
1625
|
+
super(message, details);
|
|
1626
|
+
this.name = "ValidationError";
|
|
1627
|
+
}
|
|
1628
|
+
}
|
|
1629
|
+
class YupValidationError extends ValidationError {
|
|
1630
|
+
constructor(yupError, message) {
|
|
1631
|
+
super("Validation");
|
|
1632
|
+
const { errors: errors2, message: yupMessage } = formatYupErrors(yupError);
|
|
1633
|
+
this.message = message || yupMessage;
|
|
1634
|
+
this.details = { errors: errors2 };
|
|
1635
|
+
}
|
|
1636
|
+
}
|
|
1637
|
+
class PaginationError extends ApplicationError {
|
|
1638
|
+
constructor(message = "Invalid pagination", details) {
|
|
1639
|
+
super(message, details);
|
|
1640
|
+
this.name = "PaginationError";
|
|
1641
|
+
this.message = message;
|
|
1642
|
+
}
|
|
1643
|
+
}
|
|
1644
|
+
class NotFoundError extends ApplicationError {
|
|
1645
|
+
constructor(message = "Entity not found", details) {
|
|
1646
|
+
super(message, details);
|
|
1647
|
+
this.name = "NotFoundError";
|
|
1648
|
+
this.message = message;
|
|
1649
|
+
}
|
|
1650
|
+
}
|
|
1651
|
+
class ForbiddenError extends ApplicationError {
|
|
1652
|
+
constructor(message = "Forbidden access", details) {
|
|
1653
|
+
super(message, details);
|
|
1654
|
+
this.name = "ForbiddenError";
|
|
1655
|
+
this.message = message;
|
|
1656
|
+
}
|
|
1657
|
+
}
|
|
1658
|
+
class UnauthorizedError extends ApplicationError {
|
|
1659
|
+
constructor(message = "Unauthorized", details) {
|
|
1660
|
+
super(message, details);
|
|
1661
|
+
this.name = "UnauthorizedError";
|
|
1662
|
+
this.message = message;
|
|
1663
|
+
}
|
|
1664
|
+
}
|
|
1665
|
+
class RateLimitError extends ApplicationError {
|
|
1666
|
+
constructor(message = "Too many requests, please try again later.", details) {
|
|
1667
|
+
super(message, details);
|
|
1668
|
+
this.name = "RateLimitError";
|
|
1669
|
+
this.message = message;
|
|
1670
|
+
this.details = details || {};
|
|
1671
|
+
}
|
|
1672
|
+
}
|
|
1673
|
+
class PayloadTooLargeError extends ApplicationError {
|
|
1674
|
+
constructor(message = "Entity too large", details) {
|
|
1675
|
+
super(message, details);
|
|
1676
|
+
this.name = "PayloadTooLargeError";
|
|
1677
|
+
this.message = message;
|
|
1678
|
+
}
|
|
1679
|
+
}
|
|
1680
|
+
class PolicyError extends ForbiddenError {
|
|
1681
|
+
constructor(message = "Policy Failed", details) {
|
|
1682
|
+
super(message, details);
|
|
1683
|
+
this.name = "PolicyError";
|
|
1684
|
+
this.message = message;
|
|
1685
|
+
this.details = details || {};
|
|
1686
|
+
}
|
|
1687
|
+
}
|
|
1688
|
+
class NotImplementedError extends ApplicationError {
|
|
1689
|
+
constructor(message = "This feature is not implemented yet", details) {
|
|
1690
|
+
super(message, details);
|
|
1691
|
+
this.name = "NotImplementedError";
|
|
1692
|
+
this.message = message;
|
|
1693
|
+
}
|
|
1694
|
+
}
|
|
1695
|
+
const errors = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
1696
|
+
__proto__: null,
|
|
1697
|
+
ApplicationError,
|
|
1698
|
+
ForbiddenError,
|
|
1699
|
+
HttpError,
|
|
1700
|
+
NotFoundError,
|
|
1701
|
+
NotImplementedError,
|
|
1702
|
+
PaginationError,
|
|
1703
|
+
PayloadTooLargeError,
|
|
1704
|
+
PolicyError,
|
|
1705
|
+
RateLimitError,
|
|
1706
|
+
UnauthorizedError,
|
|
1707
|
+
ValidationError,
|
|
1708
|
+
YupValidationError
|
|
1709
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
1710
|
+
const throwInvalidParam = ({ key, path }) => {
|
|
1711
|
+
const msg = path && path !== key ? `Invalid parameter ${key} at ${path}` : `Invalid parameter ${key}`;
|
|
1712
|
+
throw new ValidationError(msg);
|
|
2196
1713
|
};
|
|
2197
|
-
const visitor$3 = ({ key
|
|
1714
|
+
const visitor$3 = ({ key, attribute, path }) => {
|
|
2198
1715
|
if (attribute?.type === "password") {
|
|
2199
|
-
throwInvalidParam({ key:
|
|
1716
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2200
1717
|
}
|
|
2201
1718
|
};
|
|
2202
|
-
const visitor$2 = ({ schema, key
|
|
1719
|
+
const visitor$2 = ({ schema, key, attribute, path }) => {
|
|
2203
1720
|
if (!attribute) {
|
|
2204
1721
|
return;
|
|
2205
1722
|
}
|
|
2206
|
-
const isPrivate = attribute.private === true || isPrivateAttribute(schema,
|
|
1723
|
+
const isPrivate = attribute.private === true || isPrivateAttribute(schema, key);
|
|
2207
1724
|
if (isPrivate) {
|
|
2208
|
-
throwInvalidParam({ key:
|
|
1725
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2209
1726
|
}
|
|
2210
1727
|
};
|
|
2211
1728
|
const ACTIONS_TO_VERIFY = ["find"];
|
|
2212
1729
|
const { CREATED_BY_ATTRIBUTE, UPDATED_BY_ATTRIBUTE } = constants$1;
|
|
2213
|
-
const throwRestrictedRelations = (auth) => async ({ data, key
|
|
1730
|
+
const throwRestrictedRelations = (auth) => async ({ data, key, attribute, schema, path }) => {
|
|
2214
1731
|
if (!attribute) {
|
|
2215
1732
|
return;
|
|
2216
1733
|
}
|
|
@@ -2219,11 +1736,11 @@ const throwRestrictedRelations = (auth) => async ({ data, key: key2, attribute,
|
|
|
2219
1736
|
return;
|
|
2220
1737
|
}
|
|
2221
1738
|
const handleMorphRelation = async () => {
|
|
2222
|
-
for (const element of data[
|
|
1739
|
+
for (const element of data[key]) {
|
|
2223
1740
|
const scopes = ACTIONS_TO_VERIFY.map((action) => `${element.__type}.${action}`);
|
|
2224
1741
|
const isAllowed = await hasAccessToSomeScopes(scopes, auth);
|
|
2225
1742
|
if (!isAllowed) {
|
|
2226
|
-
throwInvalidParam({ key:
|
|
1743
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2227
1744
|
}
|
|
2228
1745
|
}
|
|
2229
1746
|
};
|
|
@@ -2231,10 +1748,10 @@ const throwRestrictedRelations = (auth) => async ({ data, key: key2, attribute,
|
|
|
2231
1748
|
const scopes = ACTIONS_TO_VERIFY.map((action) => `${attribute.target}.${action}`);
|
|
2232
1749
|
const isAllowed = await hasAccessToSomeScopes(scopes, auth);
|
|
2233
1750
|
if (!isAllowed) {
|
|
2234
|
-
throwInvalidParam({ key:
|
|
1751
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2235
1752
|
}
|
|
2236
1753
|
};
|
|
2237
|
-
const isCreatorRelation = [CREATED_BY_ATTRIBUTE, UPDATED_BY_ATTRIBUTE].includes(
|
|
1754
|
+
const isCreatorRelation = [CREATED_BY_ATTRIBUTE, UPDATED_BY_ATTRIBUTE].includes(key);
|
|
2238
1755
|
if (isMorphToRelationalAttribute(attribute)) {
|
|
2239
1756
|
await handleMorphRelation();
|
|
2240
1757
|
return;
|
|
@@ -2255,21 +1772,21 @@ const hasAccessToSomeScopes = async (scopes, auth) => {
|
|
|
2255
1772
|
}
|
|
2256
1773
|
return false;
|
|
2257
1774
|
};
|
|
2258
|
-
const visitor$1 = ({ key
|
|
1775
|
+
const visitor$1 = ({ key, attribute, path }) => {
|
|
2259
1776
|
if (isMorphToRelationalAttribute(attribute)) {
|
|
2260
|
-
throwInvalidParam({ key:
|
|
1777
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2261
1778
|
}
|
|
2262
1779
|
};
|
|
2263
|
-
const visitor = ({ key
|
|
1780
|
+
const visitor = ({ key, attribute, path }) => {
|
|
2264
1781
|
if (isDynamicZoneAttribute(attribute)) {
|
|
2265
|
-
throwInvalidParam({ key:
|
|
1782
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2266
1783
|
}
|
|
2267
1784
|
};
|
|
2268
|
-
const throwDisallowedFields = (allowedFields = null) => ({ key
|
|
1785
|
+
const throwDisallowedFields = (allowedFields = null) => ({ key, path: { attribute: path } }) => {
|
|
2269
1786
|
if (allowedFields === null) {
|
|
2270
1787
|
return;
|
|
2271
1788
|
}
|
|
2272
|
-
if (!(isArray(allowedFields) && allowedFields.every(isString
|
|
1789
|
+
if (!(isArray(allowedFields) && allowedFields.every(isString))) {
|
|
2273
1790
|
throw new TypeError(
|
|
2274
1791
|
`Expected array of strings for allowedFields but got "${typeof allowedFields}"`
|
|
2275
1792
|
);
|
|
@@ -2284,31 +1801,31 @@ const throwDisallowedFields = (allowedFields = null) => ({ key: key2, path: { at
|
|
|
2284
1801
|
if (isPathAllowed) {
|
|
2285
1802
|
return;
|
|
2286
1803
|
}
|
|
2287
|
-
throwInvalidParam({ key
|
|
1804
|
+
throwInvalidParam({ key, path });
|
|
2288
1805
|
};
|
|
2289
1806
|
const getContainedPaths = (path) => {
|
|
2290
1807
|
const parts = toPath(path);
|
|
2291
|
-
return parts.reduce((
|
|
2292
|
-
return [...
|
|
1808
|
+
return parts.reduce((acc, value, index2, list) => {
|
|
1809
|
+
return [...acc, list.slice(0, index2 + 1).join(".")];
|
|
2293
1810
|
}, []);
|
|
2294
1811
|
};
|
|
2295
|
-
const throwRestrictedFields = (restrictedFields = null) => ({ key
|
|
1812
|
+
const throwRestrictedFields = (restrictedFields = null) => ({ key, path: { attribute: path } }) => {
|
|
2296
1813
|
if (restrictedFields === null) {
|
|
2297
|
-
throwInvalidParam({ key
|
|
1814
|
+
throwInvalidParam({ key, path });
|
|
2298
1815
|
}
|
|
2299
|
-
if (!(isArray(restrictedFields) && restrictedFields.every(isString
|
|
1816
|
+
if (!(isArray(restrictedFields) && restrictedFields.every(isString))) {
|
|
2300
1817
|
throw new TypeError(
|
|
2301
1818
|
`Expected array of strings for restrictedFields but got "${typeof restrictedFields}"`
|
|
2302
1819
|
);
|
|
2303
1820
|
}
|
|
2304
1821
|
if (restrictedFields.includes(path)) {
|
|
2305
|
-
throwInvalidParam({ key
|
|
1822
|
+
throwInvalidParam({ key, path });
|
|
2306
1823
|
}
|
|
2307
1824
|
const isRestrictedNested = restrictedFields.some(
|
|
2308
1825
|
(allowedPath) => path?.toString().startsWith(`${allowedPath}.`)
|
|
2309
1826
|
);
|
|
2310
1827
|
if (isRestrictedNested) {
|
|
2311
|
-
throwInvalidParam({ key
|
|
1828
|
+
throwInvalidParam({ key, path });
|
|
2312
1829
|
}
|
|
2313
1830
|
};
|
|
2314
1831
|
const visitors = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
@@ -2321,6 +1838,7 @@ const visitors = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProp
|
|
|
2321
1838
|
throwRestrictedFields,
|
|
2322
1839
|
throwRestrictedRelations
|
|
2323
1840
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
1841
|
+
const { ID_ATTRIBUTE: ID_ATTRIBUTE$2, DOC_ID_ATTRIBUTE: DOC_ID_ATTRIBUTE$2 } = constants$1;
|
|
2324
1842
|
const throwPasswords = (schema) => async (entity) => {
|
|
2325
1843
|
if (!schema) {
|
|
2326
1844
|
throw new Error("Missing schema in throwPasswords");
|
|
@@ -2331,16 +1849,16 @@ const defaultValidateFilters = curry((schema, filters2) => {
|
|
|
2331
1849
|
if (!schema) {
|
|
2332
1850
|
throw new Error("Missing schema in defaultValidateFilters");
|
|
2333
1851
|
}
|
|
2334
|
-
return
|
|
1852
|
+
return pipe(
|
|
2335
1853
|
// keys that are not attributes or valid operators
|
|
2336
1854
|
traverseQueryFilters(
|
|
2337
|
-
({ key
|
|
2338
|
-
if (
|
|
1855
|
+
({ key, attribute, path }) => {
|
|
1856
|
+
if ([ID_ATTRIBUTE$2, DOC_ID_ATTRIBUTE$2].includes(key)) {
|
|
2339
1857
|
return;
|
|
2340
1858
|
}
|
|
2341
1859
|
const isAttribute = !!attribute;
|
|
2342
|
-
if (!isAttribute && !isOperator(
|
|
2343
|
-
throwInvalidParam({ key:
|
|
1860
|
+
if (!isAttribute && !isOperator(key)) {
|
|
1861
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2344
1862
|
}
|
|
2345
1863
|
},
|
|
2346
1864
|
{ schema }
|
|
@@ -2360,15 +1878,15 @@ const defaultValidateSort = curry((schema, sort2) => {
|
|
|
2360
1878
|
if (!schema) {
|
|
2361
1879
|
throw new Error("Missing schema in defaultValidateSort");
|
|
2362
1880
|
}
|
|
2363
|
-
return
|
|
1881
|
+
return pipe(
|
|
2364
1882
|
// non attribute keys
|
|
2365
1883
|
traverseQuerySort(
|
|
2366
|
-
({ key
|
|
2367
|
-
if (
|
|
1884
|
+
({ key, attribute, path }) => {
|
|
1885
|
+
if ([ID_ATTRIBUTE$2, DOC_ID_ATTRIBUTE$2].includes(key)) {
|
|
2368
1886
|
return;
|
|
2369
1887
|
}
|
|
2370
1888
|
if (!attribute) {
|
|
2371
|
-
throwInvalidParam({ key:
|
|
1889
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2372
1890
|
}
|
|
2373
1891
|
},
|
|
2374
1892
|
{ schema }
|
|
@@ -2383,12 +1901,12 @@ const defaultValidateSort = curry((schema, sort2) => {
|
|
|
2383
1901
|
traverseQuerySort(visitor$3, { schema }),
|
|
2384
1902
|
// keys for empty non-scalar values
|
|
2385
1903
|
traverseQuerySort(
|
|
2386
|
-
({ key
|
|
2387
|
-
if (
|
|
1904
|
+
({ key, attribute, value, path }) => {
|
|
1905
|
+
if ([ID_ATTRIBUTE$2, DOC_ID_ATTRIBUTE$2].includes(key)) {
|
|
2388
1906
|
return;
|
|
2389
1907
|
}
|
|
2390
|
-
if (!isScalarAttribute(attribute) && isEmpty(
|
|
2391
|
-
throwInvalidParam({ key:
|
|
1908
|
+
if (!isScalarAttribute(attribute) && isEmpty(value)) {
|
|
1909
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2392
1910
|
}
|
|
2393
1911
|
},
|
|
2394
1912
|
{ schema }
|
|
@@ -2399,15 +1917,15 @@ const defaultValidateFields = curry((schema, fields2) => {
|
|
|
2399
1917
|
if (!schema) {
|
|
2400
1918
|
throw new Error("Missing schema in defaultValidateFields");
|
|
2401
1919
|
}
|
|
2402
|
-
return
|
|
1920
|
+
return pipe(
|
|
2403
1921
|
// Only allow scalar attributes
|
|
2404
1922
|
traverseQueryFields(
|
|
2405
|
-
({ key
|
|
2406
|
-
if (
|
|
1923
|
+
({ key, attribute, path }) => {
|
|
1924
|
+
if ([ID_ATTRIBUTE$2, DOC_ID_ATTRIBUTE$2].includes(key)) {
|
|
2407
1925
|
return;
|
|
2408
1926
|
}
|
|
2409
1927
|
if (isNil(attribute) || !isScalarAttribute(attribute)) {
|
|
2410
|
-
throwInvalidParam({ key:
|
|
1928
|
+
throwInvalidParam({ key, path: path.attribute });
|
|
2411
1929
|
}
|
|
2412
1930
|
},
|
|
2413
1931
|
{ schema }
|
|
@@ -2418,13 +1936,44 @@ const defaultValidateFields = curry((schema, fields2) => {
|
|
|
2418
1936
|
traverseQueryFields(visitor$3, { schema })
|
|
2419
1937
|
)(fields2);
|
|
2420
1938
|
});
|
|
1939
|
+
const defaultValidatePopulate = curry((schema, populate2) => {
|
|
1940
|
+
if (!schema) {
|
|
1941
|
+
throw new Error("Missing schema in defaultValidatePopulate");
|
|
1942
|
+
}
|
|
1943
|
+
return pipe(
|
|
1944
|
+
traverseQueryPopulate(
|
|
1945
|
+
async ({ key, value, schema: schema2, attribute }, { set }) => {
|
|
1946
|
+
if (attribute) {
|
|
1947
|
+
return;
|
|
1948
|
+
}
|
|
1949
|
+
if (key === "sort") {
|
|
1950
|
+
set(key, await defaultValidateSort(schema2, value));
|
|
1951
|
+
}
|
|
1952
|
+
if (key === "filters") {
|
|
1953
|
+
set(key, await defaultValidateFilters(schema2, value));
|
|
1954
|
+
}
|
|
1955
|
+
if (key === "fields") {
|
|
1956
|
+
set(key, await defaultValidateFields(schema2, value));
|
|
1957
|
+
}
|
|
1958
|
+
if (key === "populate") {
|
|
1959
|
+
set(key, await defaultValidatePopulate(schema2, value));
|
|
1960
|
+
}
|
|
1961
|
+
},
|
|
1962
|
+
{ schema }
|
|
1963
|
+
),
|
|
1964
|
+
// Remove private fields
|
|
1965
|
+
traverseQueryPopulate(visitor$2, { schema })
|
|
1966
|
+
)(populate2);
|
|
1967
|
+
});
|
|
2421
1968
|
const validators = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2422
1969
|
__proto__: null,
|
|
2423
1970
|
defaultValidateFields,
|
|
2424
1971
|
defaultValidateFilters,
|
|
1972
|
+
defaultValidatePopulate,
|
|
2425
1973
|
defaultValidateSort,
|
|
2426
1974
|
throwPasswords
|
|
2427
1975
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
1976
|
+
const { ID_ATTRIBUTE: ID_ATTRIBUTE$1, DOC_ID_ATTRIBUTE: DOC_ID_ATTRIBUTE$1 } = constants$1;
|
|
2428
1977
|
const createContentAPIValidators = () => {
|
|
2429
1978
|
const validateInput = async (data, schema, { auth } = {}) => {
|
|
2430
1979
|
if (!schema) {
|
|
@@ -2437,8 +1986,13 @@ const createContentAPIValidators = () => {
|
|
|
2437
1986
|
const nonWritableAttributes = getNonWritableAttributes(schema);
|
|
2438
1987
|
const transforms = [
|
|
2439
1988
|
(data2) => {
|
|
2440
|
-
if (isObject(data2)
|
|
2441
|
-
|
|
1989
|
+
if (isObject(data2)) {
|
|
1990
|
+
if (ID_ATTRIBUTE$1 in data2) {
|
|
1991
|
+
throwInvalidParam({ key: ID_ATTRIBUTE$1 });
|
|
1992
|
+
}
|
|
1993
|
+
if (DOC_ID_ATTRIBUTE$1 in data2) {
|
|
1994
|
+
throwInvalidParam({ key: DOC_ID_ATTRIBUTE$1 });
|
|
1995
|
+
}
|
|
2442
1996
|
}
|
|
2443
1997
|
},
|
|
2444
1998
|
// non-writable attributes
|
|
@@ -2448,13 +2002,13 @@ const createContentAPIValidators = () => {
|
|
|
2448
2002
|
transforms.push(traverseEntity$1(throwRestrictedRelations(auth), { schema }));
|
|
2449
2003
|
}
|
|
2450
2004
|
strapi.validators.get("content-api.input").forEach((validator) => transforms.push(validator(schema)));
|
|
2451
|
-
|
|
2005
|
+
await pipe(...transforms)(data);
|
|
2452
2006
|
};
|
|
2453
2007
|
const validateQuery = async (query, schema, { auth } = {}) => {
|
|
2454
2008
|
if (!schema) {
|
|
2455
2009
|
throw new Error("Missing schema in validateQuery");
|
|
2456
2010
|
}
|
|
2457
|
-
const { filters: filters2, sort: sort2, fields: fields2 } = query;
|
|
2011
|
+
const { filters: filters2, sort: sort2, fields: fields2, populate: populate2 } = query;
|
|
2458
2012
|
if (filters2) {
|
|
2459
2013
|
await validateFilters(filters2, schema, { auth });
|
|
2460
2014
|
}
|
|
@@ -2464,6 +2018,9 @@ const createContentAPIValidators = () => {
|
|
|
2464
2018
|
if (fields2) {
|
|
2465
2019
|
await validateFields(fields2, schema);
|
|
2466
2020
|
}
|
|
2021
|
+
if (populate2 && populate2 !== "*") {
|
|
2022
|
+
await validatePopulate(populate2, schema);
|
|
2023
|
+
}
|
|
2467
2024
|
};
|
|
2468
2025
|
const validateFilters = async (filters2, schema, { auth } = {}) => {
|
|
2469
2026
|
if (!schema) {
|
|
@@ -2477,7 +2034,7 @@ const createContentAPIValidators = () => {
|
|
|
2477
2034
|
if (auth) {
|
|
2478
2035
|
transforms.push(traverseQueryFilters(throwRestrictedRelations(auth), { schema }));
|
|
2479
2036
|
}
|
|
2480
|
-
|
|
2037
|
+
await pipe(...transforms)(filters2);
|
|
2481
2038
|
};
|
|
2482
2039
|
const validateSort = async (sort2, schema, { auth } = {}) => {
|
|
2483
2040
|
if (!schema) {
|
|
@@ -2487,21 +2044,32 @@ const createContentAPIValidators = () => {
|
|
|
2487
2044
|
if (auth) {
|
|
2488
2045
|
transforms.push(traverseQuerySort(throwRestrictedRelations(auth), { schema }));
|
|
2489
2046
|
}
|
|
2490
|
-
|
|
2047
|
+
await pipe(...transforms)(sort2);
|
|
2491
2048
|
};
|
|
2492
|
-
const validateFields = (fields2, schema) => {
|
|
2049
|
+
const validateFields = async (fields2, schema) => {
|
|
2493
2050
|
if (!schema) {
|
|
2494
2051
|
throw new Error("Missing schema in validateFields");
|
|
2495
2052
|
}
|
|
2496
2053
|
const transforms = [defaultValidateFields(schema)];
|
|
2497
|
-
|
|
2054
|
+
await pipe(...transforms)(fields2);
|
|
2055
|
+
};
|
|
2056
|
+
const validatePopulate = async (populate2, schema, { auth } = {}) => {
|
|
2057
|
+
if (!schema) {
|
|
2058
|
+
throw new Error("Missing schema in sanitizePopulate");
|
|
2059
|
+
}
|
|
2060
|
+
const transforms = [defaultValidatePopulate(schema)];
|
|
2061
|
+
if (auth) {
|
|
2062
|
+
transforms.push(traverseQueryPopulate(throwRestrictedRelations(auth), { schema }));
|
|
2063
|
+
}
|
|
2064
|
+
await pipe(...transforms)(populate2);
|
|
2498
2065
|
};
|
|
2499
2066
|
return {
|
|
2500
2067
|
input: validateInput,
|
|
2501
2068
|
query: validateQuery,
|
|
2502
2069
|
filters: validateFilters,
|
|
2503
2070
|
sort: validateSort,
|
|
2504
|
-
fields: validateFields
|
|
2071
|
+
fields: validateFields,
|
|
2072
|
+
populate: validatePopulate
|
|
2505
2073
|
};
|
|
2506
2074
|
};
|
|
2507
2075
|
const contentAPI = createContentAPIValidators();
|
|
@@ -2510,7 +2078,7 @@ const index = {
|
|
|
2510
2078
|
validators,
|
|
2511
2079
|
visitors
|
|
2512
2080
|
};
|
|
2513
|
-
const { PUBLISHED_AT_ATTRIBUTE } = constants$1;
|
|
2081
|
+
const { ID_ATTRIBUTE, DOC_ID_ATTRIBUTE, PUBLISHED_AT_ATTRIBUTE } = constants$1;
|
|
2514
2082
|
class InvalidOrderError extends Error {
|
|
2515
2083
|
constructor() {
|
|
2516
2084
|
super();
|
|
@@ -2524,7 +2092,7 @@ class InvalidSortError extends Error {
|
|
|
2524
2092
|
}
|
|
2525
2093
|
}
|
|
2526
2094
|
function validateOrder(order) {
|
|
2527
|
-
if (!isString
|
|
2095
|
+
if (!isString(order) || !["asc", "desc"].includes(order.toLocaleLowerCase())) {
|
|
2528
2096
|
throw new InvalidOrderError();
|
|
2529
2097
|
}
|
|
2530
2098
|
}
|
|
@@ -2534,8 +2102,8 @@ const convertCountQueryParams = (countQuery) => {
|
|
|
2534
2102
|
const convertOrderingQueryParams = (ordering) => {
|
|
2535
2103
|
return ordering;
|
|
2536
2104
|
};
|
|
2537
|
-
const isPlainObject = (
|
|
2538
|
-
const isStringArray = (
|
|
2105
|
+
const isPlainObject = (value) => _$1.isPlainObject(value);
|
|
2106
|
+
const isStringArray = (value) => isArray(value) && value.every(isString);
|
|
2539
2107
|
const convertSortQueryParams = (sortQuery) => {
|
|
2540
2108
|
if (typeof sortQuery === "string") {
|
|
2541
2109
|
return convertStringSortQueryParam(sortQuery);
|
|
@@ -2552,13 +2120,13 @@ const convertSortQueryParams = (sortQuery) => {
|
|
|
2552
2120
|
throw new InvalidSortError();
|
|
2553
2121
|
};
|
|
2554
2122
|
const convertStringSortQueryParam = (sortQuery) => {
|
|
2555
|
-
return sortQuery.split(",").map((
|
|
2123
|
+
return sortQuery.split(",").map((value) => convertSingleSortQueryParam(value));
|
|
2556
2124
|
};
|
|
2557
2125
|
const convertSingleSortQueryParam = (sortQuery) => {
|
|
2558
2126
|
if (!sortQuery) {
|
|
2559
2127
|
return {};
|
|
2560
2128
|
}
|
|
2561
|
-
if (!isString
|
|
2129
|
+
if (!isString(sortQuery)) {
|
|
2562
2130
|
throw new Error("Invalid sort query");
|
|
2563
2131
|
}
|
|
2564
2132
|
const [field, order = "asc"] = sortQuery.split(":");
|
|
@@ -2638,15 +2206,15 @@ const convertPopulateQueryParams = (populate2, schema, depth = 0) => {
|
|
|
2638
2206
|
return true;
|
|
2639
2207
|
}
|
|
2640
2208
|
if (typeof populate2 === "string") {
|
|
2641
|
-
return populate2.split(",").map((
|
|
2209
|
+
return populate2.split(",").map((value) => _$1.trim(value));
|
|
2642
2210
|
}
|
|
2643
2211
|
if (Array.isArray(populate2)) {
|
|
2644
2212
|
return _$1.uniq(
|
|
2645
|
-
populate2.flatMap((
|
|
2646
|
-
if (typeof
|
|
2213
|
+
populate2.flatMap((value) => {
|
|
2214
|
+
if (typeof value !== "string") {
|
|
2647
2215
|
throw new InvalidPopulateError();
|
|
2648
2216
|
}
|
|
2649
|
-
return
|
|
2217
|
+
return value.split(",").map((value2) => _$1.trim(value2));
|
|
2650
2218
|
})
|
|
2651
2219
|
);
|
|
2652
2220
|
}
|
|
@@ -2655,25 +2223,30 @@ const convertPopulateQueryParams = (populate2, schema, depth = 0) => {
|
|
|
2655
2223
|
}
|
|
2656
2224
|
throw new InvalidPopulateError();
|
|
2657
2225
|
};
|
|
2226
|
+
const hasFragmentPopulateDefined = (populate2) => {
|
|
2227
|
+
return typeof populate2 === "object" && "on" in populate2 && !isNil(populate2.on);
|
|
2228
|
+
};
|
|
2658
2229
|
const convertPopulateObject = (populate2, schema) => {
|
|
2659
2230
|
if (!schema) {
|
|
2660
2231
|
return {};
|
|
2661
2232
|
}
|
|
2662
2233
|
const { attributes } = schema;
|
|
2663
|
-
return Object.entries(populate2).reduce((
|
|
2664
|
-
|
|
2234
|
+
return Object.entries(populate2).reduce((acc, [key, subPopulate]) => {
|
|
2235
|
+
if (_$1.isBoolean(subPopulate)) {
|
|
2236
|
+
return { ...acc, [key]: subPopulate };
|
|
2237
|
+
}
|
|
2238
|
+
const attribute = attributes[key];
|
|
2665
2239
|
if (!attribute) {
|
|
2666
|
-
return
|
|
2240
|
+
return acc;
|
|
2667
2241
|
}
|
|
2668
2242
|
const isAllowedAttributeForFragmentPopulate = isDynamicZoneAttribute(attribute) || isMorphToRelationalAttribute(attribute);
|
|
2669
|
-
|
|
2670
|
-
if (isAllowedAttributeForFragmentPopulate && hasFragmentPopulateDefined) {
|
|
2243
|
+
if (isAllowedAttributeForFragmentPopulate && hasFragmentPopulateDefined(subPopulate)) {
|
|
2671
2244
|
return {
|
|
2672
|
-
...
|
|
2673
|
-
[
|
|
2245
|
+
...acc,
|
|
2246
|
+
[key]: {
|
|
2674
2247
|
on: Object.entries(subPopulate.on).reduce(
|
|
2675
|
-
(
|
|
2676
|
-
...
|
|
2248
|
+
(acc2, [type, typeSubPopulate]) => ({
|
|
2249
|
+
...acc2,
|
|
2677
2250
|
[type]: convertNestedPopulate(typeSubPopulate, strapi.getModel(type))
|
|
2678
2251
|
}),
|
|
2679
2252
|
{}
|
|
@@ -2684,15 +2257,15 @@ const convertPopulateObject = (populate2, schema) => {
|
|
|
2684
2257
|
if (isDynamicZoneAttribute(attribute)) {
|
|
2685
2258
|
const populates = attribute.components.map((uid) => strapi.getModel(uid)).map((schema2) => convertNestedPopulate(subPopulate, schema2)).map((populate22) => populate22 === true ? {} : populate22).filter((populate22) => populate22 !== false);
|
|
2686
2259
|
if (isEmpty(populates)) {
|
|
2687
|
-
return
|
|
2260
|
+
return acc;
|
|
2688
2261
|
}
|
|
2689
2262
|
return {
|
|
2690
|
-
...
|
|
2691
|
-
[
|
|
2263
|
+
...acc,
|
|
2264
|
+
[key]: mergeAll(populates)
|
|
2692
2265
|
};
|
|
2693
2266
|
}
|
|
2694
2267
|
if (isMorphToRelationalAttribute(attribute)) {
|
|
2695
|
-
return { ...
|
|
2268
|
+
return { ...acc, [key]: convertNestedPopulate(subPopulate, void 0) };
|
|
2696
2269
|
}
|
|
2697
2270
|
let targetSchemaUID;
|
|
2698
2271
|
if (attribute.type === "relation") {
|
|
@@ -2702,19 +2275,19 @@ const convertPopulateObject = (populate2, schema) => {
|
|
|
2702
2275
|
} else if (attribute.type === "media") {
|
|
2703
2276
|
targetSchemaUID = "plugin::upload.file";
|
|
2704
2277
|
} else {
|
|
2705
|
-
return
|
|
2278
|
+
return acc;
|
|
2706
2279
|
}
|
|
2707
2280
|
const targetSchema = strapi.getModel(targetSchemaUID);
|
|
2708
2281
|
if (!targetSchema) {
|
|
2709
|
-
return
|
|
2282
|
+
return acc;
|
|
2710
2283
|
}
|
|
2711
2284
|
const populateObject = convertNestedPopulate(subPopulate, targetSchema);
|
|
2712
2285
|
if (!populateObject) {
|
|
2713
|
-
return
|
|
2286
|
+
return acc;
|
|
2714
2287
|
}
|
|
2715
2288
|
return {
|
|
2716
|
-
...
|
|
2717
|
-
[
|
|
2289
|
+
...acc,
|
|
2290
|
+
[key]: populateObject
|
|
2718
2291
|
};
|
|
2719
2292
|
}, {});
|
|
2720
2293
|
};
|
|
@@ -2748,282 +2321,707 @@ const convertNestedPopulate = (subPopulate, schema) => {
|
|
|
2748
2321
|
if (ordering) {
|
|
2749
2322
|
query.ordering = convertOrderingQueryParams(ordering);
|
|
2750
2323
|
}
|
|
2751
|
-
validatePaginationParams(page, pageSize, start, limit);
|
|
2752
|
-
if (!isNil(page)) {
|
|
2753
|
-
query.page = convertPageQueryParams(page);
|
|
2324
|
+
validatePaginationParams(page, pageSize, start, limit);
|
|
2325
|
+
if (!isNil(page)) {
|
|
2326
|
+
query.page = convertPageQueryParams(page);
|
|
2327
|
+
}
|
|
2328
|
+
if (!isNil(pageSize)) {
|
|
2329
|
+
query.pageSize = convertPageSizeQueryParams(pageSize, page);
|
|
2330
|
+
}
|
|
2331
|
+
if (!isNil(start)) {
|
|
2332
|
+
query.offset = convertStartQueryParams(start);
|
|
2333
|
+
}
|
|
2334
|
+
if (!isNil(limit)) {
|
|
2335
|
+
query.limit = convertLimitQueryParams(limit);
|
|
2336
|
+
}
|
|
2337
|
+
return query;
|
|
2338
|
+
};
|
|
2339
|
+
const convertFieldsQueryParams = (fields2, depth = 0) => {
|
|
2340
|
+
if (depth === 0 && fields2 === "*") {
|
|
2341
|
+
return void 0;
|
|
2342
|
+
}
|
|
2343
|
+
if (typeof fields2 === "string") {
|
|
2344
|
+
const fieldsValues = fields2.split(",").map((value) => _$1.trim(value));
|
|
2345
|
+
return _$1.uniq([ID_ATTRIBUTE, DOC_ID_ATTRIBUTE, ...fieldsValues]);
|
|
2346
|
+
}
|
|
2347
|
+
if (isStringArray(fields2)) {
|
|
2348
|
+
const fieldsValues = fields2.flatMap((value) => convertFieldsQueryParams(value, depth + 1)).filter((v) => !isNil(v));
|
|
2349
|
+
return _$1.uniq([ID_ATTRIBUTE, DOC_ID_ATTRIBUTE, ...fieldsValues]);
|
|
2350
|
+
}
|
|
2351
|
+
throw new Error("Invalid fields parameter. Expected a string or an array of strings");
|
|
2352
|
+
};
|
|
2353
|
+
const isValidSchemaAttribute = (key, schema) => {
|
|
2354
|
+
if ([DOC_ID_ATTRIBUTE, ID_ATTRIBUTE].includes(key)) {
|
|
2355
|
+
return true;
|
|
2356
|
+
}
|
|
2357
|
+
if (!schema) {
|
|
2358
|
+
return false;
|
|
2359
|
+
}
|
|
2360
|
+
return Object.keys(schema.attributes).includes(key);
|
|
2361
|
+
};
|
|
2362
|
+
const convertFiltersQueryParams = (filters2, schema) => {
|
|
2363
|
+
if (!isObject(filters2)) {
|
|
2364
|
+
throw new Error("The filters parameter must be an object or an array");
|
|
2365
|
+
}
|
|
2366
|
+
const filtersCopy = cloneDeep(filters2);
|
|
2367
|
+
return convertAndSanitizeFilters(filtersCopy, schema);
|
|
2368
|
+
};
|
|
2369
|
+
const convertAndSanitizeFilters = (filters2, schema) => {
|
|
2370
|
+
if (Array.isArray(filters2)) {
|
|
2371
|
+
return filters2.map((filter) => convertAndSanitizeFilters(filter, schema)).filter((filter) => !isPlainObject(filter) || !isEmpty(filter));
|
|
2372
|
+
}
|
|
2373
|
+
if (!isPlainObject(filters2)) {
|
|
2374
|
+
return filters2;
|
|
2375
|
+
}
|
|
2376
|
+
const removeOperator = (operator) => delete filters2[operator];
|
|
2377
|
+
for (const [key, value] of Object.entries(filters2)) {
|
|
2378
|
+
const attribute = get(key, schema?.attributes);
|
|
2379
|
+
const validKey = isOperator(key) || isValidSchemaAttribute(key, schema);
|
|
2380
|
+
if (!validKey) {
|
|
2381
|
+
removeOperator(key);
|
|
2382
|
+
} else if (attribute) {
|
|
2383
|
+
if (attribute.type === "relation") {
|
|
2384
|
+
filters2[key] = convertAndSanitizeFilters(value, strapi.getModel(attribute.target));
|
|
2385
|
+
} else if (attribute.type === "component") {
|
|
2386
|
+
filters2[key] = convertAndSanitizeFilters(value, strapi.getModel(attribute.component));
|
|
2387
|
+
} else if (attribute.type === "media") {
|
|
2388
|
+
filters2[key] = convertAndSanitizeFilters(value, strapi.getModel("plugin::upload.file"));
|
|
2389
|
+
} else if (attribute.type === "dynamiczone") {
|
|
2390
|
+
removeOperator(key);
|
|
2391
|
+
} else if (attribute.type === "password") {
|
|
2392
|
+
removeOperator(key);
|
|
2393
|
+
} else {
|
|
2394
|
+
filters2[key] = convertAndSanitizeFilters(value, schema);
|
|
2395
|
+
}
|
|
2396
|
+
} else if (["$null", "$notNull"].includes(key)) {
|
|
2397
|
+
filters2[key] = parseType({ type: "boolean", value: filters2[key], forceCast: true });
|
|
2398
|
+
} else if (isObject(value)) {
|
|
2399
|
+
filters2[key] = convertAndSanitizeFilters(value, schema);
|
|
2400
|
+
}
|
|
2401
|
+
if (isPlainObject(filters2[key]) && isEmpty(filters2[key])) {
|
|
2402
|
+
removeOperator(key);
|
|
2403
|
+
}
|
|
2404
|
+
}
|
|
2405
|
+
return filters2;
|
|
2406
|
+
};
|
|
2407
|
+
const convertStatusParams = (status, query = {}) => {
|
|
2408
|
+
query.filters = ({ meta }) => {
|
|
2409
|
+
const contentType = strapi.contentTypes[meta.uid];
|
|
2410
|
+
if (!contentType || !hasDraftAndPublish(contentType)) {
|
|
2411
|
+
return {};
|
|
2412
|
+
}
|
|
2413
|
+
return { [PUBLISHED_AT_ATTRIBUTE]: { $null: status === "draft" } };
|
|
2414
|
+
};
|
|
2415
|
+
};
|
|
2416
|
+
const transformParamsToQuery = (uid, params) => {
|
|
2417
|
+
const schema = strapi.getModel(uid);
|
|
2418
|
+
const query = {};
|
|
2419
|
+
const { _q, sort: sort2, filters: filters2, fields: fields2, populate: populate2, page, pageSize, start, limit, status, ...rest } = params;
|
|
2420
|
+
if (!isNil(status)) {
|
|
2421
|
+
convertStatusParams(status, query);
|
|
2422
|
+
}
|
|
2423
|
+
if (!isNil(_q)) {
|
|
2424
|
+
query._q = _q;
|
|
2425
|
+
}
|
|
2426
|
+
if (!isNil(sort2)) {
|
|
2427
|
+
query.orderBy = convertSortQueryParams(sort2);
|
|
2428
|
+
}
|
|
2429
|
+
if (!isNil(filters2)) {
|
|
2430
|
+
query.where = convertFiltersQueryParams(filters2, schema);
|
|
2431
|
+
}
|
|
2432
|
+
if (!isNil(fields2)) {
|
|
2433
|
+
query.select = convertFieldsQueryParams(fields2);
|
|
2434
|
+
}
|
|
2435
|
+
if (!isNil(populate2)) {
|
|
2436
|
+
query.populate = convertPopulateQueryParams(populate2, schema);
|
|
2437
|
+
}
|
|
2438
|
+
validatePaginationParams(page, pageSize, start, limit);
|
|
2439
|
+
if (!isNil(page)) {
|
|
2440
|
+
query.page = convertPageQueryParams(page);
|
|
2441
|
+
}
|
|
2442
|
+
if (!isNil(pageSize)) {
|
|
2443
|
+
query.pageSize = convertPageSizeQueryParams(pageSize, page);
|
|
2444
|
+
}
|
|
2445
|
+
if (!isNil(start)) {
|
|
2446
|
+
query.offset = convertStartQueryParams(start);
|
|
2447
|
+
}
|
|
2448
|
+
if (!isNil(limit)) {
|
|
2449
|
+
query.limit = convertLimitQueryParams(limit);
|
|
2450
|
+
}
|
|
2451
|
+
return {
|
|
2452
|
+
...rest,
|
|
2453
|
+
...query
|
|
2454
|
+
};
|
|
2455
|
+
};
|
|
2456
|
+
const convertQueryParams = {
|
|
2457
|
+
convertSortQueryParams,
|
|
2458
|
+
convertStartQueryParams,
|
|
2459
|
+
convertLimitQueryParams,
|
|
2460
|
+
convertPopulateQueryParams,
|
|
2461
|
+
convertFiltersQueryParams,
|
|
2462
|
+
convertFieldsQueryParams,
|
|
2463
|
+
transformParamsToQuery
|
|
2464
|
+
};
|
|
2465
|
+
function importDefault(modName) {
|
|
2466
|
+
const mod = require(modName);
|
|
2467
|
+
return mod && mod.__esModule ? mod.default : mod;
|
|
2468
|
+
}
|
|
2469
|
+
const machineId = () => {
|
|
2470
|
+
try {
|
|
2471
|
+
const deviceId = machineIdSync();
|
|
2472
|
+
return deviceId;
|
|
2473
|
+
} catch (error) {
|
|
2474
|
+
const deviceId = randomUUID();
|
|
2475
|
+
return deviceId;
|
|
2476
|
+
}
|
|
2477
|
+
};
|
|
2478
|
+
const handleYupError = (error, errorMessage) => {
|
|
2479
|
+
throw new YupValidationError(error, errorMessage);
|
|
2480
|
+
};
|
|
2481
|
+
const defaultValidationParam = { strict: true, abortEarly: false };
|
|
2482
|
+
const validateYupSchema = (schema, options = {}) => async (body, errorMessage) => {
|
|
2483
|
+
try {
|
|
2484
|
+
const optionsWithDefaults = defaults(defaultValidationParam, options);
|
|
2485
|
+
const result = await schema.validate(body, optionsWithDefaults);
|
|
2486
|
+
return result;
|
|
2487
|
+
} catch (e) {
|
|
2488
|
+
if (e instanceof yup$1.ValidationError) {
|
|
2489
|
+
handleYupError(e, errorMessage);
|
|
2490
|
+
}
|
|
2491
|
+
throw e;
|
|
2492
|
+
}
|
|
2493
|
+
};
|
|
2494
|
+
const validateYupSchemaSync = (schema, options = {}) => (body, errorMessage) => {
|
|
2495
|
+
try {
|
|
2496
|
+
const optionsWithDefaults = defaults(defaultValidationParam, options);
|
|
2497
|
+
return schema.validateSync(body, optionsWithDefaults);
|
|
2498
|
+
} catch (e) {
|
|
2499
|
+
if (e instanceof yup$1.ValidationError) {
|
|
2500
|
+
handleYupError(e, errorMessage);
|
|
2501
|
+
}
|
|
2502
|
+
throw e;
|
|
2503
|
+
}
|
|
2504
|
+
};
|
|
2505
|
+
const STRAPI_DEFAULTS = {
|
|
2506
|
+
offset: {
|
|
2507
|
+
start: 0,
|
|
2508
|
+
limit: 10
|
|
2509
|
+
},
|
|
2510
|
+
page: {
|
|
2511
|
+
page: 1,
|
|
2512
|
+
pageSize: 10
|
|
2513
|
+
}
|
|
2514
|
+
};
|
|
2515
|
+
const paginationAttributes = ["start", "limit", "page", "pageSize"];
|
|
2516
|
+
const withMaxLimit = (limit, maxLimit = -1) => {
|
|
2517
|
+
if (maxLimit === -1 || limit < maxLimit) {
|
|
2518
|
+
return limit;
|
|
2519
|
+
}
|
|
2520
|
+
return maxLimit;
|
|
2521
|
+
};
|
|
2522
|
+
const ensureMinValues = ({ start, limit }) => ({
|
|
2523
|
+
start: Math.max(start, 0),
|
|
2524
|
+
limit: limit === -1 ? limit : Math.max(limit, 1)
|
|
2525
|
+
});
|
|
2526
|
+
const ensureMaxValues = (maxLimit = -1) => ({ start, limit }) => ({
|
|
2527
|
+
start,
|
|
2528
|
+
limit: withMaxLimit(limit, maxLimit)
|
|
2529
|
+
});
|
|
2530
|
+
const withNoLimit = (pagination2, maxLimit = -1) => ({
|
|
2531
|
+
...pagination2,
|
|
2532
|
+
limit: pagination2.limit === -1 ? maxLimit : pagination2.limit
|
|
2533
|
+
});
|
|
2534
|
+
const withDefaultPagination = (args, { defaults: defaults2 = {}, maxLimit = -1 } = {}) => {
|
|
2535
|
+
const defaultValues = merge(STRAPI_DEFAULTS, defaults2);
|
|
2536
|
+
const usePagePagination = !isNil(args.page) || !isNil(args.pageSize);
|
|
2537
|
+
const useOffsetPagination = !isNil(args.start) || !isNil(args.limit);
|
|
2538
|
+
const ensureValidValues = pipe$1(ensureMinValues, ensureMaxValues(maxLimit));
|
|
2539
|
+
if (!usePagePagination && !useOffsetPagination) {
|
|
2540
|
+
return merge(args, ensureValidValues(defaultValues.offset));
|
|
2541
|
+
}
|
|
2542
|
+
if (usePagePagination && useOffsetPagination) {
|
|
2543
|
+
throw new PaginationError("Cannot use both page & offset pagination in the same query");
|
|
2754
2544
|
}
|
|
2755
|
-
|
|
2756
|
-
|
|
2545
|
+
const pagination2 = {
|
|
2546
|
+
start: 0,
|
|
2547
|
+
limit: 0
|
|
2548
|
+
};
|
|
2549
|
+
if (useOffsetPagination) {
|
|
2550
|
+
const { start, limit } = merge(defaultValues.offset, args);
|
|
2551
|
+
Object.assign(pagination2, { start, limit });
|
|
2757
2552
|
}
|
|
2758
|
-
if (
|
|
2759
|
-
|
|
2553
|
+
if (usePagePagination) {
|
|
2554
|
+
const { page, pageSize } = merge(defaultValues.page, {
|
|
2555
|
+
...args,
|
|
2556
|
+
pageSize: Math.max(1, args.pageSize ?? 0)
|
|
2557
|
+
});
|
|
2558
|
+
Object.assign(pagination2, {
|
|
2559
|
+
start: (page - 1) * pageSize,
|
|
2560
|
+
limit: pageSize
|
|
2561
|
+
});
|
|
2760
2562
|
}
|
|
2761
|
-
|
|
2762
|
-
|
|
2563
|
+
Object.assign(pagination2, withNoLimit(pagination2, maxLimit));
|
|
2564
|
+
const replacePaginationAttributes = pipe$1(
|
|
2565
|
+
// Remove pagination attributes
|
|
2566
|
+
omit(paginationAttributes),
|
|
2567
|
+
// Merge the object with the new pagination + ensure minimum & maximum values
|
|
2568
|
+
merge(ensureValidValues(pagination2))
|
|
2569
|
+
);
|
|
2570
|
+
return replacePaginationAttributes(args);
|
|
2571
|
+
};
|
|
2572
|
+
const pagination = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2573
|
+
__proto__: null,
|
|
2574
|
+
withDefaultPagination
|
|
2575
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2576
|
+
const SUPPORTED_PACKAGE_MANAGERS = ["npm", "yarn"];
|
|
2577
|
+
const DEFAULT_PACKAGE_MANAGER = "npm";
|
|
2578
|
+
const getPreferred = async (pkgPath) => {
|
|
2579
|
+
const pm = await preferredPM(pkgPath);
|
|
2580
|
+
const hasPackageManager = pm !== void 0;
|
|
2581
|
+
if (!hasPackageManager) {
|
|
2582
|
+
throw new Error(`Couldn't find a package manager in your project.`);
|
|
2583
|
+
}
|
|
2584
|
+
const isPackageManagerSupported = SUPPORTED_PACKAGE_MANAGERS.includes(pm.name);
|
|
2585
|
+
if (!isPackageManagerSupported) {
|
|
2586
|
+
process.emitWarning(
|
|
2587
|
+
`We detected your package manager (${pm.name} v${pm.version}), but it's not officially supported by Strapi yet. Defaulting to npm instead.`
|
|
2588
|
+
);
|
|
2589
|
+
return DEFAULT_PACKAGE_MANAGER;
|
|
2763
2590
|
}
|
|
2764
|
-
|
|
2765
|
-
return query;
|
|
2591
|
+
return pm.name;
|
|
2766
2592
|
};
|
|
2767
|
-
const
|
|
2768
|
-
|
|
2769
|
-
|
|
2593
|
+
const installDependencies = (path, packageManager2, options = {}) => {
|
|
2594
|
+
return execa(packageManager2, ["install"], { ...options, cwd: path, stdin: "ignore" });
|
|
2595
|
+
};
|
|
2596
|
+
const packageManager = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2597
|
+
__proto__: null,
|
|
2598
|
+
getPreferred,
|
|
2599
|
+
installDependencies
|
|
2600
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2601
|
+
const createStrictInterpolationRegExp = (allowedVariableNames, flags) => {
|
|
2602
|
+
const oneOfVariables = allowedVariableNames.join("|");
|
|
2603
|
+
return new RegExp(`<%=\\s*(${oneOfVariables})\\s*%>`, flags);
|
|
2604
|
+
};
|
|
2605
|
+
const createLooseInterpolationRegExp = (flags) => new RegExp(/<%=([\s\S]+?)%>/, flags);
|
|
2606
|
+
const template = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2607
|
+
__proto__: null,
|
|
2608
|
+
createLooseInterpolationRegExp,
|
|
2609
|
+
createStrictInterpolationRegExp
|
|
2610
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2611
|
+
const kbytesToBytes = (kbytes) => kbytes * 1e3;
|
|
2612
|
+
const bytesToKbytes = (bytes) => Math.round(bytes / 1e3 * 100) / 100;
|
|
2613
|
+
const bytesToHumanReadable = (bytes) => {
|
|
2614
|
+
const sizes = ["Bytes", "KB", "MB", "GB", "TB", "PB"];
|
|
2615
|
+
if (bytes === 0)
|
|
2616
|
+
return "0 Bytes";
|
|
2617
|
+
const i = parseInt(`${Math.floor(Math.log(bytes) / Math.log(1e3))}`, 10);
|
|
2618
|
+
return `${Math.round(bytes / 1e3 ** i)} ${sizes[i]}`;
|
|
2619
|
+
};
|
|
2620
|
+
const streamToBuffer = (stream) => new Promise((resolve, reject) => {
|
|
2621
|
+
const chunks = [];
|
|
2622
|
+
stream.on("data", (chunk) => {
|
|
2623
|
+
chunks.push(chunk);
|
|
2624
|
+
});
|
|
2625
|
+
stream.on("end", () => {
|
|
2626
|
+
resolve(Buffer.concat(chunks));
|
|
2627
|
+
});
|
|
2628
|
+
stream.on("error", reject);
|
|
2629
|
+
});
|
|
2630
|
+
const getStreamSize = (stream) => new Promise((resolve, reject) => {
|
|
2631
|
+
let size = 0;
|
|
2632
|
+
stream.on("data", (chunk) => {
|
|
2633
|
+
size += Buffer.byteLength(chunk);
|
|
2634
|
+
});
|
|
2635
|
+
stream.on("close", () => resolve(size));
|
|
2636
|
+
stream.on("error", reject);
|
|
2637
|
+
stream.resume();
|
|
2638
|
+
});
|
|
2639
|
+
function writableDiscardStream(options) {
|
|
2640
|
+
return new Writable({
|
|
2641
|
+
...options,
|
|
2642
|
+
write(chunk, encding, callback) {
|
|
2643
|
+
setImmediate(callback);
|
|
2644
|
+
}
|
|
2645
|
+
});
|
|
2646
|
+
}
|
|
2647
|
+
const file = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2648
|
+
__proto__: null,
|
|
2649
|
+
bytesToHumanReadable,
|
|
2650
|
+
bytesToKbytes,
|
|
2651
|
+
getStreamSize,
|
|
2652
|
+
kbytesToBytes,
|
|
2653
|
+
streamToBuffer,
|
|
2654
|
+
writableDiscardStream
|
|
2655
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2656
|
+
const PLUGIN_PREFIX = "plugin::";
|
|
2657
|
+
const API_PREFIX = "api::";
|
|
2658
|
+
const parsePolicy = (policy2) => {
|
|
2659
|
+
if (typeof policy2 === "string") {
|
|
2660
|
+
return { policyName: policy2, config: {} };
|
|
2770
2661
|
}
|
|
2771
|
-
|
|
2772
|
-
|
|
2773
|
-
|
|
2662
|
+
const { name, config } = policy2;
|
|
2663
|
+
return { policyName: name, config };
|
|
2664
|
+
};
|
|
2665
|
+
const searchLocalPolicy = (policyName, policyContext) => {
|
|
2666
|
+
const { pluginName, apiName } = policyContext ?? {};
|
|
2667
|
+
if (pluginName) {
|
|
2668
|
+
return strapi.policy(`${PLUGIN_PREFIX}${pluginName}.${policyName}`);
|
|
2774
2669
|
}
|
|
2775
|
-
if (
|
|
2776
|
-
|
|
2777
|
-
return _$1.uniq(["id", ...fieldsValues]);
|
|
2670
|
+
if (apiName) {
|
|
2671
|
+
return strapi.policy(`${API_PREFIX}${apiName}.${policyName}`);
|
|
2778
2672
|
}
|
|
2779
|
-
throw new Error("Invalid fields parameter. Expected a string or an array of strings");
|
|
2780
2673
|
};
|
|
2781
|
-
const
|
|
2782
|
-
|
|
2783
|
-
|
|
2674
|
+
const globalPolicy = ({ method, endpoint, controller, action, plugin }) => {
|
|
2675
|
+
return async (ctx, next) => {
|
|
2676
|
+
ctx.request.route = {
|
|
2677
|
+
endpoint: `${method} ${endpoint}`,
|
|
2678
|
+
controller: _$1.toLower(controller),
|
|
2679
|
+
action: _$1.toLower(action),
|
|
2680
|
+
verb: _$1.toLower(method),
|
|
2681
|
+
plugin
|
|
2682
|
+
};
|
|
2683
|
+
await next();
|
|
2684
|
+
};
|
|
2685
|
+
};
|
|
2686
|
+
const resolvePolicies = (config, policyContext) => {
|
|
2687
|
+
const { pluginName, apiName } = policyContext ?? {};
|
|
2688
|
+
return config.map((policyConfig) => {
|
|
2689
|
+
return {
|
|
2690
|
+
handler: getPolicy(policyConfig, { pluginName, apiName }),
|
|
2691
|
+
config: typeof policyConfig === "object" && policyConfig.config || {}
|
|
2692
|
+
};
|
|
2693
|
+
});
|
|
2694
|
+
};
|
|
2695
|
+
const findPolicy = (name, policyContext) => {
|
|
2696
|
+
const { pluginName, apiName } = policyContext ?? {};
|
|
2697
|
+
const resolvedPolicy = strapi.policy(name);
|
|
2698
|
+
if (resolvedPolicy !== void 0) {
|
|
2699
|
+
return resolvedPolicy;
|
|
2784
2700
|
}
|
|
2785
|
-
|
|
2786
|
-
|
|
2701
|
+
const localPolicy = searchLocalPolicy(name, { pluginName, apiName });
|
|
2702
|
+
if (localPolicy !== void 0) {
|
|
2703
|
+
return localPolicy;
|
|
2787
2704
|
}
|
|
2788
|
-
|
|
2705
|
+
throw new Error(`Could not find policy "${name}"`);
|
|
2789
2706
|
};
|
|
2790
|
-
const
|
|
2791
|
-
|
|
2792
|
-
|
|
2707
|
+
const getPolicy = (policyConfig, policyContext) => {
|
|
2708
|
+
const { pluginName, apiName } = policyContext ?? {};
|
|
2709
|
+
if (typeof policyConfig === "function") {
|
|
2710
|
+
return policyConfig;
|
|
2793
2711
|
}
|
|
2794
|
-
const
|
|
2795
|
-
|
|
2796
|
-
|
|
2797
|
-
|
|
2798
|
-
if (Array.isArray(filters2)) {
|
|
2799
|
-
return filters2.map((filter) => convertAndSanitizeFilters(filter, schema)).filter((filter) => !isPlainObject(filter) || !isEmpty(filter));
|
|
2712
|
+
const { policyName, config } = parsePolicy(policyConfig);
|
|
2713
|
+
const policy2 = findPolicy(policyName, { pluginName, apiName });
|
|
2714
|
+
if (typeof policy2 === "function") {
|
|
2715
|
+
return policy2;
|
|
2800
2716
|
}
|
|
2801
|
-
if (
|
|
2802
|
-
|
|
2717
|
+
if (policy2.validator) {
|
|
2718
|
+
policy2.validator(config);
|
|
2803
2719
|
}
|
|
2804
|
-
|
|
2805
|
-
|
|
2806
|
-
|
|
2807
|
-
|
|
2808
|
-
|
|
2809
|
-
|
|
2810
|
-
|
|
2811
|
-
|
|
2812
|
-
|
|
2813
|
-
|
|
2814
|
-
filters2[key2] = convertAndSanitizeFilters(value2, strapi.getModel(attribute.component));
|
|
2815
|
-
} else if (attribute.type === "media") {
|
|
2816
|
-
filters2[key2] = convertAndSanitizeFilters(value2, strapi.getModel("plugin::upload.file"));
|
|
2817
|
-
} else if (attribute.type === "dynamiczone") {
|
|
2818
|
-
removeOperator(key2);
|
|
2819
|
-
} else if (attribute.type === "password") {
|
|
2820
|
-
removeOperator(key2);
|
|
2821
|
-
} else {
|
|
2822
|
-
filters2[key2] = convertAndSanitizeFilters(value2, schema);
|
|
2720
|
+
return policy2.handler;
|
|
2721
|
+
};
|
|
2722
|
+
const createPolicy = (options) => {
|
|
2723
|
+
const { name = "unnamed", validator, handler } = options;
|
|
2724
|
+
const wrappedValidator = (config) => {
|
|
2725
|
+
if (validator) {
|
|
2726
|
+
try {
|
|
2727
|
+
validator(config);
|
|
2728
|
+
} catch (e) {
|
|
2729
|
+
throw new Error(`Invalid config passed to "${name}" policy.`);
|
|
2823
2730
|
}
|
|
2824
|
-
} else if (["$null", "$notNull"].includes(key2)) {
|
|
2825
|
-
filters2[key2] = parseType({ type: "boolean", value: filters2[key2], forceCast: true });
|
|
2826
|
-
} else if (isObject(value2)) {
|
|
2827
|
-
filters2[key2] = convertAndSanitizeFilters(value2, schema);
|
|
2828
2731
|
}
|
|
2829
|
-
|
|
2830
|
-
|
|
2831
|
-
|
|
2832
|
-
|
|
2833
|
-
|
|
2732
|
+
};
|
|
2733
|
+
return {
|
|
2734
|
+
name,
|
|
2735
|
+
validator: wrappedValidator,
|
|
2736
|
+
handler
|
|
2737
|
+
};
|
|
2834
2738
|
};
|
|
2835
|
-
const
|
|
2836
|
-
|
|
2837
|
-
|
|
2838
|
-
|
|
2839
|
-
|
|
2840
|
-
|
|
2841
|
-
if (!constants$1.DP_PUB_STATES.includes(publicationState)) {
|
|
2842
|
-
throw new Error(
|
|
2843
|
-
`Invalid publicationState. Expected one of 'preview','live' received: ${publicationState}.`
|
|
2844
|
-
);
|
|
2845
|
-
}
|
|
2846
|
-
query.filters = ({ meta }) => {
|
|
2847
|
-
if (publicationState === "live" && has(PUBLISHED_AT_ATTRIBUTE, meta.attributes)) {
|
|
2848
|
-
return { [PUBLISHED_AT_ATTRIBUTE]: { $notNull: true } };
|
|
2739
|
+
const createPolicyContext = (type, ctx) => {
|
|
2740
|
+
return Object.assign(
|
|
2741
|
+
{
|
|
2742
|
+
is: eq(type),
|
|
2743
|
+
get type() {
|
|
2744
|
+
return type;
|
|
2849
2745
|
}
|
|
2850
|
-
}
|
|
2851
|
-
|
|
2746
|
+
},
|
|
2747
|
+
ctx
|
|
2748
|
+
);
|
|
2749
|
+
};
|
|
2750
|
+
const policy = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2751
|
+
__proto__: null,
|
|
2752
|
+
createPolicy,
|
|
2753
|
+
createPolicyContext,
|
|
2754
|
+
get: getPolicy,
|
|
2755
|
+
globalPolicy,
|
|
2756
|
+
resolve: resolvePolicies
|
|
2757
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2758
|
+
const nameToSlug = (name, options = { separator: "-" }) => slugify(name, options);
|
|
2759
|
+
const nameToCollectionName = (name) => slugify(name, { separator: "_" });
|
|
2760
|
+
const toRegressedEnumValue = (value) => slugify(value, {
|
|
2761
|
+
decamelize: false,
|
|
2762
|
+
lowercase: false,
|
|
2763
|
+
separator: "_"
|
|
2764
|
+
});
|
|
2765
|
+
const getCommonPath = (...paths) => {
|
|
2766
|
+
const [segments, ...otherSegments] = paths.map((it) => _$1.split(it, "/"));
|
|
2767
|
+
return _$1.join(
|
|
2768
|
+
_$1.takeWhile(segments, (str, index2) => otherSegments.every((it) => it[index2] === str)),
|
|
2769
|
+
"/"
|
|
2770
|
+
);
|
|
2771
|
+
};
|
|
2772
|
+
const isEqual = (a, b) => String(a) === String(b);
|
|
2773
|
+
const isCamelCase = (value) => /^[a-z][a-zA-Z0-9]+$/.test(value);
|
|
2774
|
+
const isKebabCase = (value) => /^([a-z][a-z0-9]*)(-[a-z0-9]+)*$/.test(value);
|
|
2775
|
+
const startsWithANumber = (value) => /^[0-9]/.test(value);
|
|
2776
|
+
const joinBy = (joint, ...args) => {
|
|
2777
|
+
const trim2 = trimChars(joint);
|
|
2778
|
+
const trimEnd = trimCharsEnd(joint);
|
|
2779
|
+
const trimStart = trimCharsStart(joint);
|
|
2780
|
+
return args.reduce((url, path, index2) => {
|
|
2781
|
+
if (args.length === 1)
|
|
2782
|
+
return path;
|
|
2783
|
+
if (index2 === 0)
|
|
2784
|
+
return trimEnd(path);
|
|
2785
|
+
if (index2 === args.length - 1)
|
|
2786
|
+
return url + joint + trimStart(path);
|
|
2787
|
+
return url + joint + trim2(path);
|
|
2788
|
+
}, "");
|
|
2789
|
+
};
|
|
2790
|
+
const toKebabCase = (value) => kebabCase(value);
|
|
2791
|
+
const strings = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2792
|
+
__proto__: null,
|
|
2793
|
+
getCommonPath,
|
|
2794
|
+
isCamelCase,
|
|
2795
|
+
isEqual,
|
|
2796
|
+
isKebabCase,
|
|
2797
|
+
joinBy,
|
|
2798
|
+
nameToCollectionName,
|
|
2799
|
+
nameToSlug,
|
|
2800
|
+
startsWithANumber,
|
|
2801
|
+
toKebabCase,
|
|
2802
|
+
toRegressedEnumValue
|
|
2803
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2804
|
+
const castIncludes = (arr, val, cast) => arr.map((val2) => cast(val2)).includes(cast(val));
|
|
2805
|
+
const includesString = (arr, val) => castIncludes(arr, val, String);
|
|
2806
|
+
const arrays = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2807
|
+
__proto__: null,
|
|
2808
|
+
includesString
|
|
2809
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2810
|
+
const keysDeep = (obj, path = []) => !_$1.isObject(obj) ? [path.join(".")] : _$1.reduce(
|
|
2811
|
+
obj,
|
|
2812
|
+
(acc, next, key) => _$1.concat(acc, keysDeep(next, [...path, key])),
|
|
2813
|
+
[]
|
|
2814
|
+
);
|
|
2815
|
+
const objects = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2816
|
+
__proto__: null,
|
|
2817
|
+
keysDeep
|
|
2818
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2819
|
+
const timestampCode = (date) => {
|
|
2820
|
+
const referDate = date ?? /* @__PURE__ */ new Date();
|
|
2821
|
+
return referDate.getTime().toString(36);
|
|
2852
2822
|
};
|
|
2853
|
-
const
|
|
2854
|
-
|
|
2855
|
-
|
|
2856
|
-
|
|
2857
|
-
|
|
2858
|
-
|
|
2859
|
-
|
|
2860
|
-
|
|
2861
|
-
|
|
2862
|
-
|
|
2863
|
-
if (
|
|
2864
|
-
|
|
2823
|
+
const dates = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2824
|
+
__proto__: null,
|
|
2825
|
+
timestampCode
|
|
2826
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2827
|
+
const { toString } = Object.prototype;
|
|
2828
|
+
const errorToString = Error.prototype.toString;
|
|
2829
|
+
const regExpToString = RegExp.prototype.toString;
|
|
2830
|
+
const symbolToString = typeof Symbol !== "undefined" ? Symbol.prototype.toString : () => "";
|
|
2831
|
+
const SYMBOL_REGEXP = /^Symbol\((.*)\)(.*)$/;
|
|
2832
|
+
function printNumber(val) {
|
|
2833
|
+
if (val != +val)
|
|
2834
|
+
return "NaN";
|
|
2835
|
+
const isNegativeZero = val === 0 && 1 / val < 0;
|
|
2836
|
+
return isNegativeZero ? "-0" : `${val}`;
|
|
2837
|
+
}
|
|
2838
|
+
function printSimpleValue(val, quoteStrings = false) {
|
|
2839
|
+
if (val == null || val === true || val === false)
|
|
2840
|
+
return `${val}`;
|
|
2841
|
+
if (typeof val === "number")
|
|
2842
|
+
return printNumber(val);
|
|
2843
|
+
if (typeof val === "string")
|
|
2844
|
+
return quoteStrings ? `"${val}"` : val;
|
|
2845
|
+
if (typeof val === "function")
|
|
2846
|
+
return `[Function ${val.name || "anonymous"}]`;
|
|
2847
|
+
if (typeof val === "symbol")
|
|
2848
|
+
return symbolToString.call(val).replace(SYMBOL_REGEXP, "Symbol($1)");
|
|
2849
|
+
const tag = toString.call(val).slice(8, -1);
|
|
2850
|
+
if (tag === "Date") {
|
|
2851
|
+
const v = val;
|
|
2852
|
+
return Number.isNaN(v.getTime()) ? `${v}` : v.toISOString();
|
|
2865
2853
|
}
|
|
2866
|
-
if (
|
|
2867
|
-
|
|
2854
|
+
if (tag === "Error" || val instanceof Error)
|
|
2855
|
+
return `[${errorToString.call(val)}]`;
|
|
2856
|
+
if (tag === "RegExp")
|
|
2857
|
+
return regExpToString.call(val);
|
|
2858
|
+
return null;
|
|
2859
|
+
}
|
|
2860
|
+
function printValue(value, quoteStrings) {
|
|
2861
|
+
const result = printSimpleValue(value, quoteStrings);
|
|
2862
|
+
if (result !== null)
|
|
2863
|
+
return result;
|
|
2864
|
+
return JSON.stringify(
|
|
2865
|
+
value,
|
|
2866
|
+
function replacer(key, value2) {
|
|
2867
|
+
const result2 = printSimpleValue(this[key], quoteStrings);
|
|
2868
|
+
if (result2 !== null)
|
|
2869
|
+
return result2;
|
|
2870
|
+
return value2;
|
|
2871
|
+
},
|
|
2872
|
+
2
|
|
2873
|
+
);
|
|
2874
|
+
}
|
|
2875
|
+
const strapiID = () => new StrapiIDSchema();
|
|
2876
|
+
const isNotNilTest = (value) => !_$1.isNil(value);
|
|
2877
|
+
const isNotNullTest = (value) => !_$1.isNull(value);
|
|
2878
|
+
yup$1.addMethod(yup$1.mixed, "notNil", function isNotNill(msg = "${path} must be defined.") {
|
|
2879
|
+
return this.test("defined", msg, isNotNilTest);
|
|
2880
|
+
});
|
|
2881
|
+
yup$1.addMethod(yup$1.mixed, "notNull", function isNotNull(msg = "${path} cannot be null.") {
|
|
2882
|
+
return this.test("defined", msg, isNotNullTest);
|
|
2883
|
+
});
|
|
2884
|
+
yup$1.addMethod(yup$1.mixed, "isFunction", function isFunction(message = "${path} is not a function") {
|
|
2885
|
+
return this.test(
|
|
2886
|
+
"is a function",
|
|
2887
|
+
message,
|
|
2888
|
+
(value) => _$1.isUndefined(value) || _$1.isFunction(value)
|
|
2889
|
+
);
|
|
2890
|
+
});
|
|
2891
|
+
yup$1.addMethod(
|
|
2892
|
+
yup$1.string,
|
|
2893
|
+
"isCamelCase",
|
|
2894
|
+
function isCamelCase$1(message = "${path} is not in camel case (anExampleOfCamelCase)") {
|
|
2895
|
+
return this.test(
|
|
2896
|
+
"is in camelCase",
|
|
2897
|
+
message,
|
|
2898
|
+
(value) => value ? isCamelCase(value) : true
|
|
2899
|
+
);
|
|
2868
2900
|
}
|
|
2869
|
-
|
|
2870
|
-
|
|
2901
|
+
);
|
|
2902
|
+
yup$1.addMethod(
|
|
2903
|
+
yup$1.string,
|
|
2904
|
+
"isKebabCase",
|
|
2905
|
+
function isKebabCase$1(message = "${path} is not in kebab case (an-example-of-kebab-case)") {
|
|
2906
|
+
return this.test(
|
|
2907
|
+
"is in kebab-case",
|
|
2908
|
+
message,
|
|
2909
|
+
(value) => value ? isKebabCase(value) : true
|
|
2910
|
+
);
|
|
2871
2911
|
}
|
|
2872
|
-
|
|
2873
|
-
|
|
2874
|
-
|
|
2912
|
+
);
|
|
2913
|
+
yup$1.addMethod(
|
|
2914
|
+
yup$1.object,
|
|
2915
|
+
"onlyContainsFunctions",
|
|
2916
|
+
function onlyContainsFunctions(message = "${path} contains values that are not functions") {
|
|
2917
|
+
return this.test(
|
|
2918
|
+
"only contains functions",
|
|
2919
|
+
message,
|
|
2920
|
+
(value) => _$1.isUndefined(value) || value && Object.values(value).every(_$1.isFunction)
|
|
2921
|
+
);
|
|
2875
2922
|
}
|
|
2876
|
-
|
|
2877
|
-
|
|
2923
|
+
);
|
|
2924
|
+
yup$1.addMethod(
|
|
2925
|
+
yup$1.array,
|
|
2926
|
+
"uniqueProperty",
|
|
2927
|
+
function uniqueProperty(propertyName, message) {
|
|
2928
|
+
return this.test("unique", message, function unique(list) {
|
|
2929
|
+
const errors2 = [];
|
|
2930
|
+
list?.forEach((element, index2) => {
|
|
2931
|
+
const sameElements = list.filter(
|
|
2932
|
+
(e) => get(propertyName, e) === get(propertyName, element)
|
|
2933
|
+
);
|
|
2934
|
+
if (sameElements.length > 1) {
|
|
2935
|
+
errors2.push(
|
|
2936
|
+
this.createError({
|
|
2937
|
+
path: `${this.path}[${index2}].${propertyName}`,
|
|
2938
|
+
message
|
|
2939
|
+
})
|
|
2940
|
+
);
|
|
2941
|
+
}
|
|
2942
|
+
});
|
|
2943
|
+
if (errors2.length) {
|
|
2944
|
+
throw new yup$1.ValidationError(errors2);
|
|
2945
|
+
}
|
|
2946
|
+
return true;
|
|
2947
|
+
});
|
|
2878
2948
|
}
|
|
2879
|
-
|
|
2880
|
-
|
|
2949
|
+
);
|
|
2950
|
+
class StrapiIDSchema extends yup$1.MixedSchema {
|
|
2951
|
+
constructor() {
|
|
2952
|
+
super({ type: "strapiID" });
|
|
2881
2953
|
}
|
|
2882
|
-
|
|
2883
|
-
|
|
2954
|
+
_typeCheck(value) {
|
|
2955
|
+
return typeof value === "string" || isNumber(value) && isInteger(value) && value >= 0;
|
|
2884
2956
|
}
|
|
2885
|
-
convertPublicationStateParams(schema, params, query);
|
|
2886
|
-
return query;
|
|
2887
|
-
};
|
|
2888
|
-
const convertQueryParams = {
|
|
2889
|
-
convertSortQueryParams,
|
|
2890
|
-
convertStartQueryParams,
|
|
2891
|
-
convertLimitQueryParams,
|
|
2892
|
-
convertPopulateQueryParams,
|
|
2893
|
-
convertFiltersQueryParams,
|
|
2894
|
-
convertFieldsQueryParams,
|
|
2895
|
-
convertPublicationStateParams,
|
|
2896
|
-
transformParamsToQuery
|
|
2897
|
-
};
|
|
2898
|
-
function importDefault(modName) {
|
|
2899
|
-
const mod = require(modName);
|
|
2900
|
-
return mod && mod.__esModule ? mod.default : mod;
|
|
2901
2957
|
}
|
|
2902
|
-
|
|
2903
|
-
|
|
2904
|
-
|
|
2905
|
-
};
|
|
2906
|
-
const
|
|
2907
|
-
const
|
|
2908
|
-
|
|
2909
|
-
createLooseInterpolationRegExp,
|
|
2910
|
-
createStrictInterpolationRegExp
|
|
2911
|
-
}, Symbol.toStringTag, { value: "Module" }));
|
|
2912
|
-
const kbytesToBytes = (kbytes) => kbytes * 1e3;
|
|
2913
|
-
const bytesToKbytes = (bytes) => Math.round(bytes / 1e3 * 100) / 100;
|
|
2914
|
-
const bytesToHumanReadable = (bytes) => {
|
|
2915
|
-
const sizes = ["Bytes", "KB", "MB", "GB", "TB", "PB"];
|
|
2916
|
-
if (bytes === 0)
|
|
2917
|
-
return "0 Bytes";
|
|
2918
|
-
const i = parseInt(`${Math.floor(Math.log(bytes) / Math.log(1e3))}`, 10);
|
|
2919
|
-
return `${Math.round(bytes / 1e3 ** i)} ${sizes[i]}`;
|
|
2920
|
-
};
|
|
2921
|
-
const streamToBuffer = (stream) => new Promise((resolve, reject) => {
|
|
2922
|
-
const chunks = [];
|
|
2923
|
-
stream.on("data", (chunk) => {
|
|
2924
|
-
chunks.push(chunk);
|
|
2925
|
-
});
|
|
2926
|
-
stream.on("end", () => {
|
|
2927
|
-
resolve(Buffer.concat(chunks));
|
|
2928
|
-
});
|
|
2929
|
-
stream.on("error", reject);
|
|
2930
|
-
});
|
|
2931
|
-
const getStreamSize = (stream) => new Promise((resolve, reject) => {
|
|
2932
|
-
let size = 0;
|
|
2933
|
-
stream.on("data", (chunk) => {
|
|
2934
|
-
size += Buffer.byteLength(chunk);
|
|
2935
|
-
});
|
|
2936
|
-
stream.on("close", () => resolve(size));
|
|
2937
|
-
stream.on("error", reject);
|
|
2938
|
-
stream.resume();
|
|
2939
|
-
});
|
|
2940
|
-
function writableDiscardStream(options) {
|
|
2941
|
-
return new Writable({
|
|
2942
|
-
...options,
|
|
2943
|
-
write(chunk, encding, callback) {
|
|
2944
|
-
setImmediate(callback);
|
|
2958
|
+
yup$1.setLocale({
|
|
2959
|
+
mixed: {
|
|
2960
|
+
notType(options) {
|
|
2961
|
+
const { path, type, value, originalValue } = options;
|
|
2962
|
+
const isCast = originalValue != null && originalValue !== value;
|
|
2963
|
+
const msg = `${path} must be a \`${type}\` type, but the final value was: \`${printValue(value, true)}\`${isCast ? ` (cast from the value \`${printValue(originalValue, true)}\`).` : "."}`;
|
|
2964
|
+
return msg;
|
|
2945
2965
|
}
|
|
2946
|
-
});
|
|
2947
|
-
}
|
|
2948
|
-
const file = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2949
|
-
__proto__: null,
|
|
2950
|
-
bytesToHumanReadable,
|
|
2951
|
-
bytesToKbytes,
|
|
2952
|
-
getStreamSize,
|
|
2953
|
-
kbytesToBytes,
|
|
2954
|
-
streamToBuffer,
|
|
2955
|
-
writableDiscardStream
|
|
2956
|
-
}, Symbol.toStringTag, { value: "Module" }));
|
|
2957
|
-
const webhookEvents = {
|
|
2958
|
-
ENTRY_CREATE: "entry.create",
|
|
2959
|
-
ENTRY_UPDATE: "entry.update",
|
|
2960
|
-
ENTRY_DELETE: "entry.delete",
|
|
2961
|
-
ENTRY_PUBLISH: "entry.publish",
|
|
2962
|
-
ENTRY_UNPUBLISH: "entry.unpublish",
|
|
2963
|
-
MEDIA_CREATE: "media.create",
|
|
2964
|
-
MEDIA_UPDATE: "media.update",
|
|
2965
|
-
MEDIA_DELETE: "media.delete"
|
|
2966
|
-
};
|
|
2967
|
-
const deprecatedWebhookEvents = new Proxy(webhookEvents, {
|
|
2968
|
-
get(target, prop) {
|
|
2969
|
-
console.warn(
|
|
2970
|
-
"[deprecated] @strapi/utils/webhook will no longer exist in the next major release of Strapi. Instead, the webhookEvents object can be retrieved from strapi.webhookStore.allowedEvents"
|
|
2971
|
-
);
|
|
2972
|
-
return target[prop];
|
|
2973
2966
|
}
|
|
2974
2967
|
});
|
|
2975
|
-
const
|
|
2976
|
-
|
|
2968
|
+
const yup = /* @__PURE__ */ _mergeNamespaces({
|
|
2969
|
+
__proto__: null,
|
|
2970
|
+
StrapiIDSchema,
|
|
2971
|
+
strapiID
|
|
2972
|
+
}, [yup$1]);
|
|
2973
|
+
const MANY_RELATIONS = ["oneToMany", "manyToMany"];
|
|
2974
|
+
const getRelationalFields = (contentType) => {
|
|
2975
|
+
return Object.keys(contentType.attributes).filter((attributeName) => {
|
|
2976
|
+
return contentType.attributes[attributeName].type === "relation";
|
|
2977
|
+
});
|
|
2978
|
+
};
|
|
2979
|
+
const isOneToAny = (attribute) => isRelationalAttribute(attribute) && ["oneToOne", "oneToMany"].includes(attribute.relation);
|
|
2980
|
+
const isManyToAny = (attribute) => isRelationalAttribute(attribute) && ["manyToMany", "manyToOne"].includes(attribute.relation);
|
|
2981
|
+
const isAnyToOne = (attribute) => isRelationalAttribute(attribute) && ["oneToOne", "manyToOne"].includes(attribute.relation);
|
|
2982
|
+
const isAnyToMany = (attribute) => isRelationalAttribute(attribute) && ["oneToMany", "manyToMany"].includes(attribute.relation);
|
|
2983
|
+
const constants = {
|
|
2984
|
+
MANY_RELATIONS
|
|
2977
2985
|
};
|
|
2986
|
+
const relations = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2987
|
+
__proto__: null,
|
|
2988
|
+
constants,
|
|
2989
|
+
getRelationalFields,
|
|
2990
|
+
isAnyToMany,
|
|
2991
|
+
isAnyToOne,
|
|
2992
|
+
isManyToAny,
|
|
2993
|
+
isOneToAny
|
|
2994
|
+
}, Symbol.toStringTag, { value: "Module" }));
|
|
2978
2995
|
export {
|
|
2996
|
+
arrays,
|
|
2997
|
+
async,
|
|
2979
2998
|
contentTypes,
|
|
2980
2999
|
convertQueryParams,
|
|
3000
|
+
dates,
|
|
2981
3001
|
env,
|
|
2982
3002
|
errors,
|
|
2983
|
-
escapeQuery,
|
|
2984
3003
|
file,
|
|
2985
|
-
forEachAsync,
|
|
2986
|
-
generateTimestampCode,
|
|
2987
|
-
getAbsoluteAdminUrl,
|
|
2988
|
-
getAbsoluteServerUrl,
|
|
2989
|
-
getCommonBeginning,
|
|
2990
|
-
getConfigUrls,
|
|
2991
|
-
handleYupError,
|
|
2992
3004
|
hooks,
|
|
2993
3005
|
importDefault,
|
|
2994
|
-
isCamelCase,
|
|
2995
|
-
isKebabCase,
|
|
2996
3006
|
isOperator,
|
|
2997
3007
|
isOperatorOfType,
|
|
2998
|
-
|
|
2999
|
-
|
|
3000
|
-
|
|
3001
|
-
nameToCollectionName,
|
|
3002
|
-
nameToSlug,
|
|
3008
|
+
machineId as machineID,
|
|
3009
|
+
objects,
|
|
3010
|
+
packageManager,
|
|
3003
3011
|
pagination,
|
|
3004
|
-
parseMultipartData,
|
|
3005
3012
|
parseType,
|
|
3006
|
-
pipeAsync,
|
|
3007
3013
|
policy,
|
|
3008
3014
|
providerFactory,
|
|
3009
|
-
reduceAsync,
|
|
3010
3015
|
relations,
|
|
3011
|
-
removeUndefined,
|
|
3012
3016
|
index$1 as sanitize,
|
|
3013
3017
|
setCreatorFields,
|
|
3014
|
-
|
|
3015
|
-
stringEquals,
|
|
3016
|
-
stringIncludes,
|
|
3018
|
+
strings,
|
|
3017
3019
|
template,
|
|
3018
|
-
templateConfiguration,
|
|
3019
|
-
toKebabCase,
|
|
3020
|
-
toRegressedEnumValue,
|
|
3021
3020
|
index$2 as traverse,
|
|
3022
3021
|
traverseEntity$1 as traverseEntity,
|
|
3023
3022
|
index as validate,
|
|
3024
3023
|
validateYupSchema,
|
|
3025
3024
|
validateYupSchemaSync,
|
|
3026
|
-
webhook,
|
|
3027
3025
|
yup
|
|
3028
3026
|
};
|
|
3029
3027
|
//# sourceMappingURL=index.mjs.map
|