mirror of
https://github.com/ComfortablyCoding/strapi-plugin-slugify.git
synced 2025-12-18 00:02:40 -05:00
101 lines
3.0 KiB
JavaScript
101 lines
3.0 KiB
JavaScript
const _ = require('lodash');
|
|
const { getPluginService } = require('../utils/getPluginService');
|
|
const { isValidFindSlugParams } = require('../utils/isValidFindSlugParams');
|
|
const { hasRequiredModelScopes } = require('../utils/hasRequiredModelScopes');
|
|
const { sanitizeOutput } = require('../utils/sanitizeOutput');
|
|
const { ForbiddenError, ValidationError } = require('@strapi/utils').errors;
|
|
|
|
const getCustomTypes = (strapi, nexus) => {
|
|
const { naming } = getPluginService('utils', 'graphql');
|
|
const { toEntityResponse } = getPluginService('format', 'graphql').returnTypes;
|
|
const { modelsByUID } = getPluginService('settingsService').get();
|
|
const { getEntityResponseName } = naming;
|
|
|
|
// get all types required for findSlug query
|
|
let findSlugTypes = {
|
|
response: [],
|
|
};
|
|
_.forEach(strapi.contentTypes, (contentType, uid) => {
|
|
if (modelsByUID[uid]) {
|
|
findSlugTypes.response.push(getEntityResponseName(contentType));
|
|
}
|
|
});
|
|
|
|
// ensure we have at least one type before attempting to register
|
|
if (!findSlugTypes.response.length) {
|
|
return [];
|
|
}
|
|
|
|
// build custom union type based on defined models
|
|
const FindSlugResponse = nexus.unionType({
|
|
name: 'FindSlugResponse',
|
|
description: 'Union Type of all registered slug content types',
|
|
definition(t) {
|
|
t.members(...findSlugTypes.response);
|
|
},
|
|
resolveType: (ctx) => {
|
|
return getEntityResponseName(modelsByUID[ctx.info.resourceUID].contentType);
|
|
},
|
|
});
|
|
|
|
return [
|
|
FindSlugResponse,
|
|
nexus.extendType({
|
|
type: 'Query',
|
|
definition: (t) => {
|
|
t.field('findSlug', {
|
|
type: FindSlugResponse,
|
|
args: {
|
|
modelName: nexus.stringArg('The model name of the content type'),
|
|
slug: nexus.stringArg('The slug to query for'),
|
|
publicationState: nexus.stringArg('The publication state of the entry'),
|
|
},
|
|
resolve: async (_parent, args, ctx) => {
|
|
const { modelsByName } = getPluginService('settingsService').get();
|
|
const { modelName, slug, publicationState } = args;
|
|
const { auth } = ctx.state;
|
|
|
|
try {
|
|
isValidFindSlugParams({
|
|
modelName,
|
|
slug,
|
|
modelsByName,
|
|
publicationState,
|
|
});
|
|
} catch (error) {
|
|
throw new ValidationError(error.message);
|
|
}
|
|
const { uid, field, contentType } = modelsByName[modelName];
|
|
|
|
try {
|
|
await hasRequiredModelScopes(strapi, uid, auth);
|
|
} catch (error) {
|
|
throw new ForbiddenError();
|
|
}
|
|
|
|
// build query
|
|
let query = {
|
|
filters: {
|
|
[field]: slug,
|
|
},
|
|
};
|
|
|
|
// only return published entries by default if content type has draftAndPublish enabled
|
|
if (_.get(contentType, ['options', 'draftAndPublish'], false)) {
|
|
query.publicationState = publicationState || 'live';
|
|
}
|
|
|
|
const data = await getPluginService('slugService').findOne(uid, query);
|
|
const sanitizedEntity = await sanitizeOutput(data, contentType, auth);
|
|
return toEntityResponse(sanitizedEntity, { resourceUID: uid });
|
|
},
|
|
});
|
|
},
|
|
}),
|
|
];
|
|
};
|
|
|
|
module.exports = {
|
|
getCustomTypes,
|
|
};
|