strapi-plugin-navigation
Version:
Strapi - Navigation plugin
1,813 lines • 354 kB
JavaScript
import de, { uniqBy as lu, isNil as Ke, find as Gn, includes as fu, last as qn, capitalize as pu, once as li, omit as yn, isEmpty as Ye, get as ln, toString as du, pick as Fa, differenceBy as hu, upperFirst as Zi, isObject as dr, isArray as Mr, isString as Ji, zipWith as mu, first as hr, cloneDeep as gu, isNaN as yu } from "lodash";
import * as y from "zod";
import { z as $a } from "zod";
import { union as vu, getOr as wu, curry as De, isObject as $e, isNil as X, clone as Eu, isArray as We, pick as eo, isEmpty as ze, cloneDeep as fi, omit as bu, isString as Ue, trim as vn, pipe as Su, split as jr, map as xu, flatten as _u, first as Ia, constant as Hr, identity as Au, join as Tu, eq as Cu, get as to } from "lodash/fp";
import no from "crypto";
import wn from "child_process";
import En from "lodash/has";
import Oa from "lodash/mapValues";
import ro from "lodash/snakeCase";
import Ru from "lodash/camelCase";
import Fu from "lodash/mapKeys";
import Kn from "os";
import Ee from "path";
import Xe from "fs";
import Na from "assert";
import $u from "events";
import Iu from "buffer";
import Wn from "stream";
import ut from "util";
import Ou from "constants";
import "node:stream";
import Nu from "@sindresorhus/slugify";
import * as K from "zod/v4";
import Pu from "pluralize";
const pi = y.object({
name: y.string({ required_error: "requiredError" }).nonempty("requiredError").refine((e) => !e.includes(" "), { message: "noSpaceError" }),
label: y.string({ required_error: "requiredError" }).nonempty("requiredError"),
description: y.string().optional(),
placeholder: y.string().optional(),
required: y.boolean().optional(),
enabled: y.boolean().optional()
}), Lu = pi.extend({
type: y.literal("select"),
multi: y.boolean(),
options: y.array(y.string(), { required_error: "requiredError" }).min(1, { message: "requiredError" })
}), ku = pi.extend({
type: y.enum(["boolean", "string"]),
multi: y.literal(!1).optional(),
options: y.array(y.string()).max(0).optional()
}), Du = pi.extend({
type: y.literal("media"),
multi: y.literal(!1).optional(),
options: y.array(y.string()).max(0).optional()
}), Pa = y.discriminatedUnion("type", [
ku,
Du,
Lu
]), La = y.union([
y.literal("audience"),
Pa
]), Mu = y.object({
additionalFields: y.array(La),
allowedLevels: y.number(),
contentTypes: y.array(y.string()),
defaultContentType: y.string().optional(),
contentTypesNameFields: y.record(y.string(), y.array(y.string())),
contentTypesPopulate: y.record(y.string(), y.array(y.string())),
gql: y.object({
navigationItemRelated: y.array(y.string())
}),
pathDefaultFields: y.record(y.string(), y.any()),
cascadeMenuAttached: y.boolean(),
preferCustomContentTypes: y.boolean(),
isCacheEnabled: y.boolean().optional()
}), ka = y.object({
id: y.number(),
documentId: y.string(),
name: y.string(),
key: y.string()
}), ju = y.enum(["INTERNAL", "EXTERNAL", "WRAPPER"]), di = y.object({
id: y.number(),
documentId: y.string(),
title: y.string(),
type: ju,
path: y.string().or(y.null()).optional(),
slug: y.string().or(y.null()).optional(),
externalPath: y.string().or(y.null()).optional(),
uiRouterKey: y.string(),
menuAttached: y.boolean(),
order: y.number().int(),
collapsed: y.boolean(),
related: y.object({ documentId: y.string().optional(), __type: y.string() }).catchall(y.unknown()).nullish().optional(),
additionalFields: y.record(y.string(), y.unknown()).or(y.null()).optional(),
audience: y.array(ka).or(y.null()).optional(),
autoSync: y.boolean().or(y.null()).optional()
}), Hu = di.omit({
related: !0
}).pick({
path: !0,
type: !0,
uiRouterKey: !0,
title: !0,
externalPath: !0
}).extend({ related: y.unknown().optional() }), Ht = di.extend({
parent: y.lazy(() => Ht.or(y.null())).optional(),
items: y.lazy(() => Ht.array()).optional(),
master: y.lazy(() => tt(!1)).optional()
}), io = y.array(Ht), tt = (e) => y.object({
id: y.number(),
documentId: y.string(),
name: y.string(),
slug: y.string(),
locale: y.string(),
visible: y.boolean(),
items: e ? y.array(Ht) : Ht.array().optional()
}), Bu = tt(!1).omit({
items: !0,
id: !0,
documentId: !0,
slug: !0,
locale: !0
}).extend({
documentId: y.string().optional(),
id: y.undefined().optional()
}), Uu = di.omit({ id: !0, documentId: !0 }).extend({
id: y.number().optional(),
documentId: y.string().optional(),
items: y.lazy(() => Da).or(y.null()).optional(),
updated: y.boolean().optional(),
removed: y.boolean().optional()
}), Da = y.array(Uu), Gu = tt(!1).extend({
items: Da
}).partial().required({
id: !0,
documentId: !0
}), qu = y.enum(["collectionType", "singleType"]), Ku = y.object({
singularName: y.string(),
pluralName: y.string(),
displayName: y.string(),
description: y.string().optional(),
name: y.string().optional()
}), Ma = y.object({
required: y.boolean().optional(),
max: y.number().optional(),
min: y.number().optional(),
minLength: y.number().optional(),
maxLength: y.number().optional(),
private: y.boolean().optional(),
configurable: y.boolean().optional(),
default: y.any().optional()
}), Wu = y.enum([
"string",
"text",
"richtext",
"blocks",
"email",
"password",
"date",
"time",
"datetime",
"timestamp",
"boolean",
"integer",
"biginteger",
"float",
"decimal",
"json",
"relation",
"media"
]), zu = Ma.extend({
type: Wu
}), Yu = Ma.extend({
type: y.literal("enumeration"),
enum: y.string().array()
}), Qu = y.object({
type: y.literal("component"),
component: y.string(),
repeatable: y.boolean().optional()
}), Vu = y.object({
type: y.literal("dynamiczone"),
components: y.string().array()
}), Xu = y.object({
type: y.literal("uid")
}), Zu = y.object({
type: y.literal("media"),
allowedTypes: y.enum(["images", "videos", "audios", "files"]).array(),
required: y.boolean().optional()
}), Ju = y.enum([
"oneToOne",
"oneToMany",
"manyToOne",
"manyToMany",
"morphToMany",
"manyToMorph"
]), el = y.object({
type: y.literal("relation"),
relation: Ju,
target: y.string(),
mappedBy: y.string().optional(),
inversedBy: y.string().optional()
}), tl = y.record(
y.string(),
y.union([
zu,
Yu,
Qu,
Vu,
el,
Zu,
Xu
])
), Br = y.object({
kind: qu,
collectionName: y.string(),
info: Ku,
options: y.object({
draftAndPublish: y.boolean().optional(),
hidden: y.boolean().optional(),
templateName: y.string().optional()
}).optional(),
attributes: tl,
actions: y.record(y.string(), y.any()).optional(),
lifecycles: y.record(y.string(), y.any()).optional(),
uid: y.string(),
apiName: y.string().optional(),
// TODO?: remove
associations: y.object({
model: y.string(),
alias: y.string()
}).array().optional(),
modelName: y.string().optional(),
plugin: y.string().optional(),
pluginOptions: y.record(y.string(), y.any()).optional(),
isSingle: y.boolean().optional()
});
Br.pick({
info: !0,
kind: !0,
attributes: !0,
options: !0
});
const qt = (e, t) => (n) => {
t(n(e()));
};
let Ur = Mu;
const nl = qt(
() => Ur,
(e) => {
Ur = e;
}
);
let Gr = La;
const rl = qt(
() => Gr,
(e) => {
Gr = e;
}
);
let qr = Pa;
const il = qt(
() => qr,
(e) => {
qr = e;
}
);
let Kr = Bu;
const ol = qt(
() => Kr,
(e) => {
Kr = e;
}
);
let Wr = Gu;
const al = qt(
() => Wr,
(e) => {
Wr = e;
}
), Ce = {
get configSchema() {
return Ur;
},
get navigationItemAdditionalField() {
return Gr;
},
get navigationItemCustomField() {
return qr;
},
get createNavigationSchema() {
return Kr;
},
get updateNavigationSchema() {
return Wr;
}
}, sl = /^(?<type>[a-z0-9-]+)\:{2}(?<api>[a-z0-9-]+)\.{1}(?<contentType>[a-z0-9-]+)$/i, cl = [
"beforeCreate",
"beforeCreateMany",
"afterCreate",
"afterCreateMany",
"beforeUpdate",
"beforeUpdateMany",
"afterUpdate",
"afterUpdateMany",
"beforeDelete",
"beforeDeleteMany",
"afterDelete",
"afterDeleteMany",
"beforeCount",
"afterCount",
"beforeFindOne",
"afterFindOne",
"beforeFindMany",
"afterFindMany"
], ul = "$", ja = ["api::", "plugin::"], Ha = [
"admin::",
"plugin::content-releases",
"plugin::i18n.locale",
"plugin::navigation",
"plugin::review-workflows",
"plugin::users-permissions",
"plugin::upload.folder"
], ll = ["title", "subject", "name"], oo = { SINGLE: "singleType" }, ao = [
"title",
"type",
"path",
"externalPath",
"uiRouterKey",
"menuAttached",
"order",
"collapsed",
"related",
"parent",
"master",
"audience",
"additionalFields"
], fl = (e) => e.filter((t) => t !== "audience"), Ba = (e) => {
const t = fl(e);
if (t.length !== lu(t, "name").length)
throw new Error("All names of custom fields must be unique.");
if (!Ke(
Gn(
t,
(n) => typeof n == "object" && fu(ao, n.name)
)
))
throw new Error(
`Name of custom field cannot be one of: ${ao.join(", ")}`
);
}, Ua = (e, t) => {
if (e == null)
throw t ?? new Error("Non-empty value expected, empty given");
}, pl = (e = "") => {
const t = (a) => a.split("-").map((o) => pu(o)).join(""), [n, r, i] = dl(e);
return n === "api" ? t(i) : `${t(r)}${t(i)}`;
}, dl = (e = "") => e.split(sl).filter((t) => t && t.length > 0), hl = (e, t) => (n) => [
n,
async (r) => {
await te(t, "common").runLifeCycleHook({
contentTypeName: e,
hookName: n,
event: r
});
}
], Ga = (e, t) => Object.fromEntries(cl.map(hl(e, t))), ye = ({
strapi: e
}) => {
const t = e.plugin("navigation");
return {
masterModel: t.contentType("navigation"),
itemModel: t.contentType("navigation-item"),
relatedModel: t.contentType("navigations-items-related"),
audienceModel: t.contentType("audience")
};
};
function te({ strapi: e }, t) {
return e.plugin("navigation").service(t);
}
const en = (e) => e === "*" ? "*" : typeof e == "string" ? [e] : e === !1 ? [] : e === !0 ? "*" : e, ml = (e = "") => {
const t = !!ja.find((r) => e.includes(r)), n = !Ha.find((r) => e.includes(r) || e === r);
return !!e && t && n;
}, gl = (e = "") => qn(e) === "s" ? e.substr(0, e.length - 1) : e, yl = li((e) => ({
find(t, n) {
const {
audienceModel: { uid: r }
} = ye(e);
return e.strapi.query(r).findMany({ where: t, limit: n }).then(ka.array().parse);
}
})), Bt = (e, t) => ({
findFirst(n, r, i = {}) {
return e.strapi.documents(t).findFirst({ populate: en(n), status: r, ...i });
},
findById(n, r, i, a = {}) {
return e.strapi.documents(t).findOne({ documentId: n, populate: en(r), status: i, ...a });
},
findManyById(n, r, i) {
return e.strapi.documents(t).findMany({
where: { documentId: { $in: n } },
populate: en(r),
status: i
});
},
findMany(n, r, i, a) {
return e.strapi.documents(t).findMany({ where: n, populate: en(r), status: i, locale: a });
},
count(n, r) {
return e.strapi.documents(t).count({
where: n,
status: r
});
}
}), Pe = li((e) => ({
async save({ item: t, locale: n }) {
const { itemModel: r } = ye(e), { __type: i, documentId: a } = t?.related ?? {}, o = i ? Bt(e, i) : void 0, s = i && o ? a ? await o.findById(a, void 0, void 0, { locale: n }) : await o.findFirst(void 0, void 0, { locale: n }) : void 0;
if (typeof t.documentId == "string") {
const { documentId: c, ...f } = t;
return e.strapi.documents(r.uid).update({
documentId: t.documentId,
data: {
...f,
related: s ? { ...s, __type: i } : void 0
},
locale: n
});
} else
return e.strapi.documents(r.uid).create({
data: {
...t,
related: s ? { ...s, __type: i } : void 0
},
locale: n
});
},
find({ filters: t, locale: n, limit: r, order: i, populate: a }) {
const { itemModel: o } = ye(e);
return e.strapi.documents(o.uid).findMany({ filters: t, locale: n, limit: r, populate: a, orderBy: i }).then((s) => s.map(zr)).then(io.parse).then((s) => s.map(bn));
},
findV4({ filters: t, locale: n, limit: r, order: i, populate: a }) {
const { itemModel: o } = ye(e);
return e.strapi.documents(o.uid).findMany({ filters: t, locale: n, limit: r, populate: a, orderBy: i });
},
count(t) {
const { itemModel: n } = ye(e);
return e.strapi.query(n.uid).count({ where: t });
},
remove(t) {
const { itemModel: n } = ye(e);
return e.strapi.documents(n.uid).delete({
documentId: t.documentId,
populate: "*"
});
},
removeForIds(t) {
const { itemModel: n } = ye(e);
return t.map(
(r) => e.strapi.documents(n.uid).delete({ documentId: r, populate: "*" })
);
},
findForMasterIds(t) {
const { itemModel: n } = ye(e);
return e.strapi.query(n.uid).findMany({
where: {
$or: t.map((r) => ({ master: r }))
},
limit: Number.MAX_SAFE_INTEGER
}).then(io.parse);
}
})), vl = ["id", "publishedAt", "createdAt", "updatedAt", "locale"], bn = ({
related: e,
items: t = [],
...n
}) => ({
...n,
items: t.map(bn),
related: e ? yn(e, vl) : void 0
}), zr = ({ related: e, ...t }) => ({
...t,
related: e?.[0]
});
class Ct extends Error {
constructor(t, n) {
super(t), this.additionalInfo = n, this.type = "NavigationError";
}
}
class mr extends Ct {
constructor() {
super(...arguments), this.type = "FillNavigationError";
}
}
class wl extends Ct {
constructor() {
super(...arguments), this.type = "InvalidParamNavigationError";
}
}
const so = (e) => e === !0 ? !0 : Array.isArray(e) ? e.includes("items") : !1, Se = li((e) => ({
find({ filters: t, locale: n, limit: r, orderBy: i, populate: a }) {
const { masterModel: o } = ye(e);
return e.strapi.documents(o.uid).findMany({ filters: t, locale: n, limit: r, populate: a, orderBy: i }).then(
(s) => s.map(({ items: c, ...f }) => ({
...f,
items: c?.map(zr)
}))
).then(
(s) => s.map(({ items: c, ...f }) => ({
...f,
items: c?.map(bn)
}))
).then((s) => tt(so(a)).array().parse(s));
},
findOne({ locale: t, filters: n, populate: r }) {
const { masterModel: i } = ye(e);
return e.strapi.documents(i.uid).findOne({ documentId: n.documentId, locale: t, populate: r }).then((a) => a && { ...a, items: a.items?.map(zr) }).then((a) => tt(so(r)).parse(a)).then((a) => ({
...a,
items: a.items?.map(bn)
}));
},
async save(t) {
const { masterModel: n } = ye(e), { documentId: r, locale: i, ...a } = t;
return r ? e.strapi.documents(n.uid).update({
locale: i,
documentId: r,
data: yn(a, ["id", "documentId"]),
populate: ["items"]
}).then(tt(!1).parse) : e.strapi.documents(n.uid).create({
locale: i,
data: {
...a,
populate: ["items"]
}
}).then(tt(!1).parse);
},
remove(t) {
const { masterModel: n } = ye(e);
if (!t.documentId)
throw new Ct("Document id is required.");
return e.strapi.documents(n.uid).delete({ documentId: t.documentId, locale: t.locale });
}
})), El = async (e) => {
const t = await Se(e).find({
locale: "*",
limit: Number.MAX_SAFE_INTEGER
}), n = await e.strapi.plugin("i18n").service("locales").getDefaultLocale();
await Promise.all(
t.map(async (r) => {
t.find(
({ documentId: a, locale: o }) => a === r.documentId && o === n
) || await Se(e).remove({
documentId: r.documentId,
locale: r.locale
});
})
);
}, qa = async ({
strapi: e,
forceDefault: t = !1
}) => {
const n = e.store({
type: "plugin",
name: "navigation"
}), r = await e.plugin("navigation").config, i = t ? {} : {
...Yr.default,
...await n.get({
key: "config"
}) ?? Yr.default
};
let a = Ye(i) ? i : Ce.configSchema.parse(i);
const o = bl(a, r);
return a = {
additionalFields: o("additionalFields"),
contentTypes: o("contentTypes"),
contentTypesNameFields: o("contentTypesNameFields"),
contentTypesPopulate: o("contentTypesPopulate"),
defaultContentType: o("defaultContentType"),
allowedLevels: o("allowedLevels"),
gql: o("gql"),
pathDefaultFields: o("pathDefaultFields"),
cascadeMenuAttached: o("cascadeMenuAttached"),
preferCustomContentTypes: o("preferCustomContentTypes"),
isCacheEnabled: o("isCacheEnabled")
}, Sl(a, { strapi: e }), Ba(a.additionalFields), await n.set({
key: "config",
value: a
}), a;
}, bl = (e, t) => (n) => {
const r = e?.[n] ?? t(n);
return Ua(r, new Error(`[Navigation] Config "${n}" is undefined`)), r;
}, Sl = (e, { strapi: t }) => {
const n = e.contentTypes.filter(
(i) => !t.contentTypes[i]
);
if (n.length === 0)
return;
const r = n.map(pl);
e.contentTypes = e.contentTypes.filter(
(i) => !n.includes(i)
), e.contentTypesNameFields = Object.fromEntries(
Object.entries(e.contentTypesNameFields).filter(
([i]) => !n.includes(i)
)
), e.gql.navigationItemRelated = e.gql.navigationItemRelated.filter(
(i) => !r.includes(i)
);
}, Yr = {
default: {
additionalFields: [],
allowedLevels: 2,
contentTypes: [],
defaultContentType: "",
contentTypesNameFields: {},
contentTypesPopulate: {},
gql: {
navigationItemRelated: []
},
pathDefaultFields: {},
pruneObsoleteI18nNavigations: !1,
cascadeMenuAttached: !0,
preferCustomContentTypes: !1,
isCacheEnabled: !1
}
}, xl = "Navigation", _l = "navigation", Al = async (e) => {
const t = te(e, "common"), { defaultLocale: n, restLocale: r = [] } = await t.readLocale(), i = Se(e), a = await i.find({
limit: Number.MAX_SAFE_INTEGER,
filters: {},
locale: "*"
});
a.length === 0 && a.push(
await i.save({
name: xl,
visible: !0,
locale: n,
slug: _l
})
);
const o = a.filter(({ locale: s }) => s === n);
for (const s of o)
for (const c of r)
!a.find(
({ locale: u, documentId: l }) => l === s.documentId && c === u
) && await i.save({
documentId: s.documentId,
name: s.name,
locale: c,
visible: s.visible,
slug: s.slug
});
}, pe = {
render: function(e) {
return `plugin::navigation.${e}`;
},
navigation: {
read: "read",
update: "update",
settings: "settings"
}
}, Tl = async ({ strapi: e }) => {
const t = [
{
section: "plugins",
displayName: "Read",
uid: pe.navigation.read,
pluginName: "navigation"
},
{
section: "plugins",
displayName: "Update",
uid: pe.navigation.update,
pluginName: "navigation"
},
{
section: "plugins",
displayName: "Settings",
uid: pe.navigation.settings,
pluginName: "navigation"
}
];
await e.admin.services.permission.actionProvider.registerMany(t);
}, Cl = "I18NLocaleCode", Rl = ({ strapi: e, nexus: t }) => {
const { nonNull: n, list: r, stringArg: i, booleanArg: a } = t;
return {
args: {
navigationIdOrSlug: n(i()),
type: "NavigationRenderType",
menuOnly: a(),
path: i(),
locale: t.arg({ type: Cl })
},
type: n(r("NavigationItem")),
resolve(c, { navigationIdOrSlug: f, type: u, menuOnly: l, path: p, locale: d }) {
const h = $a.string().parse(f);
return te({ strapi: e }, "client").render({
idOrSlug: h,
type: u,
rootPath: p,
locale: d,
menuOnly: l,
wrapRelated: !0
});
}
};
}, Fl = ({ strapi: e, nexus: t }) => {
const { nonNull: n, list: r, stringArg: i, booleanArg: a } = t;
return {
type: n(r("NavigationItem")),
args: {
documentId: n(i()),
childUiKey: n(i()),
type: "NavigationRenderType",
menuOnly: a()
},
resolve(o, s) {
const { documentId: c, childUIKey: f, type: u, menuOnly: l } = s, p = $a.string().parse(c);
return te({ strapi: e }, "client").renderChildren({
idOrSlug: p,
childUIKey: f,
type: u,
menuOnly: l,
wrapRelated: !0
});
}
};
}, $l = (e) => {
const t = {
renderNavigationChild: Fl,
renderNavigation: Rl
};
return e.nexus.extendType({
type: "Query",
definition(n) {
for (const [r, i] of Object.entries(t)) {
const a = i(e);
n.field(r, a);
}
}
});
}, Il = () => ({
"Query.renderNavigationChild": { auth: !1 },
"Query.renderNavigation": { auth: !1 }
}), Ol = ({ nexus: e }) => e.objectType({
name: "ContentTypes",
definition(t) {
t.nonNull.string("uid"), t.nonNull.string("name"), t.nonNull.boolean("isSingle"), t.nonNull.string("collectionName"), t.nonNull.string("contentTypeName"), t.nonNull.string("label"), t.nonNull.string("relatedField"), t.nonNull.string("labelSingular"), t.nonNull.string("endpoint"), t.nonNull.boolean("available"), t.nonNull.boolean("visible");
}
}), Nl = ({ nexus: e, strapi: t }) => e.objectType({
name: "ContentTypesNameFields",
async definition(n) {
n.nonNull.list.nonNull.string("default");
const i = await te({ strapi: t }, "common").getPluginStore(), o = Ce.configSchema.parse(await i.get({ key: "config" })).contentTypesNameFields;
Object.keys(o || {}).forEach((s) => n.nonNull.list.string(s));
}
}), Pl = ({ nexus: e }) => e.inputObjectType({
name: "CreateNavigation",
definition(t) {
t.nonNull.string("name"), t.nonNull.list.field("items", { type: "CreateNavigationItem" });
}
}), Ll = ({ nexus: e }) => e.inputObjectType({
name: "CreateNavigationItem",
definition(t) {
t.nonNull.string("title"), t.nonNull.field("type", { type: "NavigationItemType" }), t.string("path"), t.string("externalPath"), t.nonNull.string("uiRouterKey"), t.nonNull.boolean("menuAttached"), t.nonNull.int("order"), t.string("parent"), t.string("master"), t.list.field("items", { type: "CreateNavigationItem" }), t.list.string("audience"), t.field("related", { type: "CreateNavigationRelated" });
}
}), kl = ({ nexus: e }) => e.inputObjectType({
name: "CreateNavigationRelated",
definition(t) {
t.nonNull.string("ref"), t.nonNull.string("field"), t.nonNull.string("refId");
}
}), Dl = ({ nexus: e }) => e.objectType({
name: "Navigation",
definition(t) {
t.nonNull.string("id"), t.nonNull.string("documentId"), t.nonNull.string("name"), t.nonNull.string("slug"), t.nonNull.boolean("visible");
}
}), Ml = ({ nexus: e }) => e.objectType({
name: "NavigationConfig",
definition(t) {
t.int("allowedLevels"), t.nonNull.list.string("additionalFields"), t.field("contentTypesNameFields", { type: "ContentTypesNameFields" }), t.list.field("contentTypes", { type: "ContentTypes" });
}
}), jl = ({ nexus: e }) => e.objectType({
name: "NavigationDetails",
definition(t) {
t.nonNull.string("id"), t.nonNull.string("documentId"), t.nonNull.string("name"), t.nonNull.string("slug"), t.nonNull.boolean("visible"), t.nonNull.list.field("items", { type: "NavigationItem" });
}
}), Hl = ({ nexus: e, config: t }) => e.objectType({
name: "NavigationItem",
definition(n) {
n.nonNull.int("id"), n.nonNull.string("documentId"), n.nonNull.string("title"), n.nonNull.field("type", { type: "NavigationItemType" }), n.string("path"), n.string("externalPath"), n.nonNull.string("uiRouterKey"), n.nonNull.boolean("menuAttached"), n.nonNull.int("order"), n.field("parent", { type: "NavigationItem" }), n.string("master"), n.list.field("items", { type: "NavigationItem" }), n.field("related", { type: "NavigationItemRelated" }), t.additionalFields.find((r) => r === "audience") && n.list.string("audience"), n.field("additionalFields", { type: "NavigationItemAdditionalFields" }), n.string("created_at"), n.string("updated_at"), n.string("created_by"), n.string("updated_by"), n.string("createdAt"), n.string("updatedAt"), n.string("createdBy"), n.string("updatedBy");
}
}), Bl = ({ nexus: e, config: t }) => e.objectType({
name: "NavigationItemAdditionalFields",
definition(n) {
t.additionalFields.forEach((r) => {
if (r !== "audience" && r.enabled)
switch (r.type) {
case "media":
n.field(r.name, { type: "UploadFile" });
break;
case "string":
n.string(r.name);
break;
case "boolean":
n.boolean(r.name);
break;
case "select":
r.multi ? n.list.string(r.name) : n.string(r.name);
break;
default:
throw new Error(
`Type "${JSON.stringify(r.type)}" is unsupported by custom fields`
);
}
});
}
}), Ul = ({ strapi: e, nexus: t, config: n }) => {
const r = n.gql?.navigationItemRelated, i = "NavigationItemRelated";
return r?.length ? t.unionType({
name: i,
definition(a) {
a.members(...r);
},
resolveType: (a) => e.contentTypes[a.__type]?.globalId
}) : t.objectType({
name: i,
definition(a) {
a.int("id"), a.string("documentId"), a.string("title"), a.string("name");
}
});
}, Gl = ({ nexus: e }) => e.enumType({
name: "NavigationItemType",
members: ["INTERNAL", "EXTERNAL", "WRAPPER"]
}), ql = ({ nexus: e }) => e.enumType({
name: "NavigationRenderType",
members: ["FLAT", "TREE"]
}), Kl = [
Bl,
Ul,
Hl,
ql,
Dl,
jl,
Nl,
Ol,
Ml,
kl,
Ll,
Pl,
Gl
], Wl = (e) => Kl.map((t) => t(e)), zl = async ({ strapi: e }) => {
const t = e.plugin("graphql").service("extension");
t.shadowCRUD("plugin::navigation.audience").disable(), t.shadowCRUD("plugin::navigation.navigation").disable(), t.shadowCRUD("plugin::navigation.navigation-item").disable(), t.shadowCRUD("plugin::navigation.navigations-items-related").disable();
const r = await te({ strapi: e }, "common").getPluginStore(), i = Ce.configSchema.parse(await r.get({ key: "config" }));
t.use(({ strapi: a, nexus: o }) => {
const s = Wl({ strapi: a, nexus: o, config: i }), c = $l({ strapi: a, nexus: o }), f = Il();
return {
types: [s, c],
resolversConfig: f
};
});
}, Yl = async ({ strapi: e }) => {
!!e.plugin("graphql") && await zl({ strapi: e });
}, Ql = async (e) => {
await El(e), await qa(e), await Al(e), await Tl(e), await Yl(e), await strapi.service("plugin::navigation.migrate").migrateRelatedIdToDocumentId(), strapi.db.lifecycles.subscribe({
models: ["plugin::i18n.locale"],
async afterCreate(t) {
await te(e, "admin").refreshNavigationLocale(t.result?.code);
}
});
}, Vl = ({ strapi: e }) => {
}, Xl = ({ strapi: e }) => {
}, Zl = {
collectionName: "audience",
info: {
singularName: "audience",
pluralName: "audiences",
displayName: "Audience",
name: "audience"
},
options: {
increments: !0,
comment: "Audience"
},
attributes: {
name: {
type: "string",
required: !0
},
key: {
type: "uid",
targetField: "name"
}
}
}, Jl = {
schema: Zl
}, ef = Ga("navigation", {
strapi
}), tf = {
collectionName: "navigations",
info: {
singularName: "navigation",
pluralName: "navigations",
displayName: "Navigation",
name: "navigation"
},
options: {
comment: ""
},
pluginOptions: {
"content-manager": {
visible: !1
},
"content-type-builder": {
visible: !1
},
i18n: {
localized: !0
}
},
attributes: {
name: {
type: "text",
configurable: !1,
required: !0
},
slug: {
type: "uid",
target: "name",
configurable: !1,
required: !0
},
visible: {
type: "boolean",
default: !1,
configurable: !1
},
items: {
type: "relation",
relation: "oneToMany",
target: "plugin::navigation.navigation-item",
configurable: !1,
mappedBy: "master"
}
}
}, nf = {
schema: tf,
lifecycles: ef
}, rf = Ga("navigation-item", {
strapi
}), of = {
collectionName: "navigations_items",
info: {
singularName: "navigation-item",
pluralName: "navigation-items",
displayName: "Navigation Item",
name: "navigation-item"
},
options: {
increments: !0,
timestamps: !0,
comment: "Navigation Item"
},
pluginOptions: {
"content-manager": {
visible: !1
},
"content-type-builder": {
visible: !1
},
i18n: {
localized: !1
}
},
attributes: {
title: {
type: "text",
configurable: !1,
required: !0,
pluginOptions: {
i18n: {
localized: !1
}
}
},
type: {
type: "enumeration",
enum: ["INTERNAL", "EXTERNAL", "WRAPPER"],
default: "INTERNAL",
configurable: !1
},
path: {
type: "text",
targetField: "title",
configurable: !1
},
externalPath: {
type: "text",
configurable: !1
},
uiRouterKey: {
type: "string",
configurable: !1
},
menuAttached: {
type: "boolean",
default: !1,
configurable: !1
},
order: {
type: "integer",
default: 0,
configurable: !1
},
collapsed: {
type: "boolean",
default: !1,
configurable: !1
},
autoSync: {
type: "boolean",
default: !0,
configurable: !1
},
related: {
type: "relation",
relation: "morphToMany",
required: !0,
configurable: !1
},
parent: {
type: "relation",
relation: "oneToOne",
target: "plugin::navigation.navigation-item",
configurable: !1,
default: null
},
master: {
type: "relation",
relation: "manyToOne",
target: "plugin::navigation.navigation",
configurable: !1,
inversedBy: "items"
},
audience: {
type: "relation",
relation: "oneToMany",
target: "plugin::navigation.audience"
},
additionalFields: {
type: "json",
require: !1,
default: {}
}
}
}, af = {
schema: of,
lifecycles: rf
}, sf = {
audience: Jl,
navigation: nf,
"navigation-item": af
}, Ka = y.enum(["true", "false"]), tn = y.string(), cf = y.object({
locale: y.string().optional(),
orderBy: y.string().optional(),
orderDirection: y.enum(["DESC", "ASC"]).optional()
}), Wa = y.enum(["FLAT", "TREE", "RFR"]), za = y.enum(["draft", "published"]), Ya = y.union([y.boolean(), y.string(), y.string().array(), y.undefined()]), uf = y.object({
type: Wa.optional(),
menu: Ka.optional(),
path: y.string().optional(),
locale: y.string().optional(),
populate: Ya.optional(),
status: za.optional()
}), lf = y.object({
type: Wa.optional(),
menu: Ka.optional(),
locale: y.string().optional(),
status: za.optional()
}), ff = y.object({
source: y.string().min(1),
target: y.string().min(1),
documentId: y.string().min(1)
});
function pf(e) {
return {
getAdminService() {
return te(e, "admin");
},
getCommonService() {
return te(e, "common");
},
async get() {
return await this.getAdminService().get({});
},
async post(t) {
const { auditLog: n } = t;
try {
return await this.getAdminService().post({
payload: Ce.createNavigationSchema.parse(t.request.body),
auditLog: n
});
} catch (r) {
const i = r instanceof Error ? {
name: r.name,
message: r.message
} : {};
return t.internalServerError("Unable to create", { originalError: i });
}
},
async put(t) {
const {
params: { documentId: n },
auditLog: r
} = t, i = y.record(y.string(), y.unknown()).parse(t.request.body);
try {
return await this.getAdminService().put({
auditLog: r,
payload: Ce.updateNavigationSchema.parse({
...i,
documentId: n
})
});
} catch (a) {
const o = a instanceof Error ? {
name: a.name,
message: a.message
} : {};
return t.internalServerError("Unable to update", { originalError: o });
}
},
async delete(t) {
const {
auditLog: n,
params: { documentId: r }
} = t;
return await this.getAdminService().delete({
documentId: tn.parse(r),
auditLog: n
}), {};
},
config() {
return this.getAdminService().config({ viaSettingsPage: !1 });
},
async updateConfig(t) {
return await this.getAdminService().updateConfig({
config: Ce.configSchema.parse(t.request.body)
}), {};
},
async restoreConfig() {
return await this.getAdminService().restoreConfig(), {};
},
settingsConfig() {
return this.getAdminService().config({ viaSettingsPage: !0 });
},
async settingsRestart() {
return await this.getAdminService().restart(), {};
},
getById(t) {
const {
params: { documentId: n }
} = t;
return this.getAdminService().getById({ documentId: tn.parse(n) });
},
getContentTypeItems(t) {
const {
params: { model: n },
query: r = {}
} = t;
return this.getAdminService().getContentTypeItems({
query: y.record(y.string(), y.unknown()).parse(r),
uid: y.string().parse(n)
});
},
async fillFromOtherLocale(t) {
const { params: n, auditLog: r } = t, { source: i, target: a, documentId: o } = ff.parse(n);
return await this.getAdminService().fillFromOtherLocale({
source: i,
target: a,
documentId: o,
auditLog: r
});
},
readNavigationItemFromLocale(t) {
const {
params: { source: n, target: r },
query: { path: i }
} = t;
return this.getAdminService().readNavigationItemFromLocale({
path: y.string().parse(i),
source: tn.parse(n),
target: tn.parse(r)
});
},
getSlug(t) {
const {
query: { q: n }
} = t;
return this.getCommonService().getSlug({ query: y.string().parse(n) }).then((r) => ({ slug: r }));
},
settingsLocale() {
return this.getCommonService().readLocale();
}
};
}
const df = (e) => {
if (!(!e || e === !0 || e === "*") && typeof e != "object")
return Array.isArray(e), e;
};
function hf(e) {
return {
getService() {
return te(e, "client");
},
async readAll(t) {
try {
const { query: n = {} } = t, { locale: r, orderBy: i, orderDirection: a } = cf.parse(n);
return await this.getService().readAll({
locale: r,
orderBy: i,
orderDirection: a
});
} catch (n) {
if (n instanceof Error)
return t.badRequest(n.message);
throw n;
}
},
async render(t) {
const { params: n, query: r = {} } = t, {
type: i,
menu: a,
path: o,
locale: s,
populate: c,
status: f = "published"
} = uf.parse(r), u = y.string().parse(n.idOrSlug);
return await this.getService().render({
idOrSlug: u,
type: i,
menuOnly: a === "true",
rootPath: o,
locale: s,
populate: df(
Ya.parse(
c === "true" ? !0 : c === "false" ? !1 : Array.isArray(c) ? c.map((l) => l === "true" ? !0 : l === "false" ? !1 : c) : c
)
),
status: f
});
},
async renderChild(t) {
const { params: n, query: r = {} } = t, {
type: i,
menu: a,
locale: o,
status: s = "published"
} = lf.parse(r), c = y.string().parse(n.idOrSlug), f = y.string().parse(n.childUIKey);
return await this.getService().renderChildren({
idOrSlug: c,
childUIKey: f,
type: i,
menuOnly: a === "true",
locale: o,
status: s
});
}
};
}
const mf = {
admin: pf,
client: hf
}, gf = {}, yf = {}, vf = {
type: "admin",
routes: [
{
method: "GET",
path: "/",
handler: "admin.get",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("read")]
}
}
]
}
},
{
method: "POST",
path: "/",
handler: "admin.post",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("update")]
}
}
]
}
},
{
method: "GET",
path: "/config",
handler: "admin.config",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("read")]
}
}
]
}
},
{
method: "PUT",
path: "/config",
handler: "admin.updateConfig",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("settings")]
}
}
]
}
},
{
method: "DELETE",
path: "/config",
handler: "admin.restoreConfig",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("settings")]
}
}
]
}
},
{
method: "GET",
path: "/slug",
handler: "admin.getSlug",
config: {
policies: ["admin::isAuthenticatedAdmin"]
}
},
{
method: "GET",
path: "/:documentId",
handler: "admin.getById",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("read")]
}
}
]
}
},
{
method: "PUT",
path: "/:documentId",
handler: "admin.put",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("update")]
}
}
]
}
},
{
method: "DELETE",
path: "/:documentId",
handler: "admin.delete",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("update")]
}
}
]
}
},
{
method: "GET",
path: "/content-type-items/:model",
handler: "admin.getContentTypeItems",
config: {
policies: ["admin::isAuthenticatedAdmin"]
}
},
{
method: "GET",
path: "/settings/locale",
handler: "admin.settingsLocale",
config: {
policies: ["admin::isAuthenticatedAdmin"]
}
},
{
method: "GET",
path: "/settings/config",
handler: "admin.settingsConfig",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("settings")]
}
}
]
}
},
{
method: "GET",
path: "/settings/restart",
handler: "admin.settingsRestart",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("settings")]
}
}
]
}
},
{
method: "PUT",
path: "/i18n/copy/:documentId/:source/:target",
handler: "admin.fillFromOtherLocale",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("update")]
}
}
]
}
},
{
method: "GET",
path: "/i18n/item/read/:source/:target",
handler: "admin.readNavigationItemFromLocale",
config: {
policies: [
{
name: "admin::hasPermissions",
config: {
actions: [pe.render("read")]
}
}
]
}
}
]
}, wf = {
type: "content-api",
routes: [
{
method: "GET",
path: "/render/:idOrSlug",
handler: "client.render",
config: {
policies: []
}
},
{
method: "GET",
path: "/render/:idOrSlug/:childUIKey",
handler: "client.renderChild",
config: {
policies: []
}
},
{
method: "GET",
path: "/",
handler: "client.readAll",
config: {
policies: []
}
}
]
}, Ef = {
admin: vf,
"content-api": wf
};
function bf(e, t) {
return de.has(process.env, e) ? process.env[e] : t;
}
function pt(e) {
return process.env[e] ?? "";
}
const Sf = {
int(e, t) {
return de.has(process.env, e) ? parseInt(pt(e), 10) : t;
},
float(e, t) {
return de.has(process.env, e) ? parseFloat(pt(e)) : t;
},
bool(e, t) {
return de.has(process.env, e) ? pt(e) === "true" : t;
},
json(e, t) {
if (!de.has(process.env, e))
return t;
try {
return JSON.parse(pt(e));
} catch (n) {
throw n instanceof Error ? new Error(`Invalid json environment variable ${e}: ${n.message}`) : n;
}
},
array(e, t) {
if (!de.has(process.env, e))
return t;
let n = pt(e);
return n.startsWith("[") && n.endsWith("]") && (n = n.substring(1, n.length - 1)), n.split(",").map((r) => de.trim(de.trim(r, " "), '"'));
},
date(e, t) {
return de.has(process.env, e) ? new Date(pt(e)) : t;
},
/**
* Gets a value from env that matches oneOf provided values
* @param {string} key
* @param {string[]} expectedValues
* @param {string|undefined} defaultValue
* @returns {string|undefined}
*/
oneOf(e, t, n) {
if (!t)
throw new Error("env.oneOf requires expectedValues");
if (n && !t.includes(n))
throw new Error("env.oneOf requires defaultValue to be included in expectedValues");
const r = xf(e, n);
return t.includes(r) ? r : n;
}
}, xf = Object.assign(bf, Sf), _f = "id", Af = "documentId", Tf = {
ID_ATTRIBUTE: _f,
DOC_ID_ATTRIBUTE: Af
}, Cf = (e) => vu(strapi?.config?.get("api.responses.privateAttributes", []) ?? [], wu([], "options.privateAttributes", e)), Rf = (e, t) => e?.attributes?.[t]?.private === !0 ? !0 : Cf(e).includes(t), Qa = (e) => e && ![
"media",
"component",
"relation",
"dynamiczone"
].includes(e.type), Ff = (e) => e?.type === "media", Va = (e) => e?.type === "relation", $f = (e) => !!e && e.type === "dynamiczone", Xa = (e) => !!e && Va(e) && e.relation?.startsWith?.("morphTo"), wt = async (e, t, n) => {
const { path: r = {
raw: null,
attribute: null,
rawWithIndices: null
}, schema: i, getModel: a } = t;
let o = t.parent;
const s = async (m, g, E) => {
const T = {
schema: a(E.__type),
path: g,
getModel: a,
parent: o
};
return wt(m, T, E);
}, c = (m) => async (g, E, S) => wt(g, {
schema: m,
path: E,
getModel: a,
parent: o
}, S), f = async (m, g, E) => {
const A = {
schema: a("plugin::upload.file"),
path: g,
getModel: a,
parent: o
};
return wt(m, A, E);
}, u = async (m, g, E, S) => wt(m, {
schema: E,
path: g,
getModel: a,
parent: o
}, S), l = async (m, g, E) => {
const T = {
schema: a(E.__component),
path: g,
getModel: a,
parent: o
};
return wt(m, T, E);
};
if (!$e(n) || X(i))
return n;
const p = Eu(n), d = If({
data: p
}), h = Object.keys(p);
for (let m = 0; m < h.length; m += 1) {
const g = h[m], E = i.attributes[g], S = {
...r
};
S.raw = X(r.raw) ? g : `${r.raw}.${g}`, S.rawWithIndices = X(r.rawWithIndices) ? g : `${r.rawWithIndices}.${g}`, X(E) || (S.attribute = X(r.attribute) ? g : `${r.attribute}.${g}`);
const T = {
data: p,
schema: i,
key: g,
value: p[g],
attribute: E,
path: S,
getModel: a,
parent: o
};
await e(T, d);
const A = p[g];
if (!(X(A) || X(E))) {
if (Va(E)) {
o = {
schema: i,
key: g,
attribute: E,
path: S
};
const R = E.relation.toLowerCase().startsWith("morph") ? s : c(a(E.target));
if (We(A)) {
const k = new Array(A.length);
for (let x = 0; x < A.length; x += 1) {
const _ = {
...S,
rawWithIndices: X(S.rawWithIndices) ? `${x}` : `${S.rawWithIndices}.${x}`
};
k[x] = await R(e, _, A[x]);
}
p[g] = k;
} else
p[g] = await R(e, S, A);
continue;
}
if (Ff(E)) {
if (o = {
schema: i,
key: g,
attribute: E,
path: S
}, We(A)) {
const C = new Array(A.length);
for (let R = 0; R < A.length; R += 1) {
const k = {
...S,
rawWithIndices: X(S.rawWithIndices) ? `${R}` : `${S.rawWithIndices}.${R}`
};
C[R] = await f(e, k, A[R]);
}
p[g] = C;
} else
p[g] = await f(e, S, A);
continue;
}
if (E.type === "component") {
o = {
schema: i,
key: g,
attribute: E,
path: S
};
const C = a(E.component);
if (We(A)) {
const R = new Array(A.length);
for (let k = 0; k < A.length; k += 1) {
const x = {
...S,
rawWithIndices: X(S.rawWithIndices) ? `${k}` : `${S.rawWithIndices}.${k}`
};
R[k] = await u(e, x, C, A[k]);
}
p[g] = R;
} else
p[g] = await u(e, S, C, A);
continue;
}
if (E.type === "dynamiczone" && We(A)) {
o = {
schema: i,
key: g,
attribute: E,
path: S
};
const C = new Array(A.length);
for (let R = 0; R < A.length; R += 1) {
const k = {
...S,
rawWithIndices: X(S.rawWithIndices) ? `${R}` : `${S.rawWithIndices}.${R}`
};
C[R] = await l(e, k, A[R]);
}
p[g] = C;
continue;
}
}
}
return p;
}, If = ({ data: e }) => ({
remove(t) {
delete e[t];
},
set(t, n) {
e[t] = n;
}
});
var Of = De(wt), ve = typeof globalThis < "u" ? globalThis : typeof window < "u" ? window : typeof global < "u" ? global : typeof self < "u" ? self : {};
function Za(e) {
return e && e.__esModule && Object.prototype.hasOwnProperty.call(e, "default") ? e.default : e;
}
var Nf = { exports: {} };
(function(e, t) {
(function(n, r) {
e.exports = r(wn, no);
})(ve, function(n, r) {
return (function(i) {
function a(s) {
if (o[s]) return o[s].exports;
var c = o[s] = { exports: {}, id: s, loaded: !1 };
return i[s].call(c.exports, c, c.exports, a), c.loaded = !0, c.exports;
}
var o = {};
return a.m = i, a.c = o, a.p = "", a(0);
})([function(i, a, o) {
i.exports = o(34);
}, function(i, a, o) {
var s = o(29)("wks"), c = o(33), f = o(2).Symbol, u = typeof f == "function", l = i.exports = function(p) {
return s[p] || (s[p] = u && f[p] || (u ? f : c)("Symbol." + p));
};
l.store = s;
}, function(i, a) {
var o = i.exports = typeof window < "u" && window.Math == Math ? window : typeof self < "u" && self.Math == Math ? self : Function("return this")();
typeof __g == "number" && (__g = o);
}, function(i, a, o) {
var s = o(9);
i.exports = function(c) {
if (!s(c)) throw TypeError(c + " is not an object!");
return c;
};
}, function(i, a, o) {
i.exports = !o(24)(function() {
return Object.defineProperty({}, "a", { get: function() {
return 7;
} }).a != 7;
});
}, function(i, a, o) {
var s = o(12), c = o(17);
i.exports = o(4) ? function(f, u, l) {
return s.f(f, u, c(1, l));
} : function(f, u, l) {
return f[u] = l, f;
};
}, function(i, a) {
var o = i.exports = { version: "2.4.0" };
typeof __e == "number" && (__e = o);
}, function(i, a, o) {
var s = o(14);
i.exports = function(c, f, u) {
if (s(c), f === void 0) return c;
switch (u) {
case 1:
return function(l) {
return c.call(f, l);
};
case 2:
return function(l, p) {
return c.call(f, l, p);
};
case 3:
return function(l, p, d) {
return c.call(f, l, p, d);
};
}
return function() {
return c.apply(f, arguments);
};
};
}, function(i, a) {
var o = {}.hasOwnProperty;
i.exports = function(s, c) {
return o.call(s, c);
};
}, function(i, a) {
i.exports = function(o) {
return typeof o == "object" ? o !== null : typeof o == "function";
};
}, function(i, a) {
i.exports = {};
}, function(i, a) {
var o = {}.toString;
i.exports = function(s) {
return o.call(s).slice(8, -1);
};
}, function(i, a, o) {
var s = o(3), c = o(26), f = o(32), u = Object.defineProperty;
a.f = o(4) ? Object.defineProperty : function(l, p, d) {
if (s(l), p = f(p, !0), s(d), c) try {
return u(l, p, d);
} catch {
}
if ("get" in d || "set" in d) throw TypeError("Accessors not supported!");
return "value" in d && (l[p] = d.value), l;
};
}, function(i, a, o) {
var s = o(42), c = o(15);
i.exports = function(f) {
return s(c(f));
};
}, function(i, a) {
i.exports = function(o) {
if (typeof o != "fun