convex-cms 0.0.1 → 0.0.3
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/LICENSE +190 -0
- package/README.md +99 -0
- package/admin-dist/nitro.json +15 -0
- package/admin-dist/public/assets/CmsEmptyState-CRswfTzk.js +5 -0
- package/admin-dist/public/assets/CmsPageHeader-CirpXndm.js +1 -0
- package/admin-dist/public/assets/CmsStatusBadge-CbEUpQu-.js +1 -0
- package/admin-dist/public/assets/CmsToolbar-BI2nZOXp.js +1 -0
- package/admin-dist/public/assets/ContentEntryEditor-CBeCyK_m.js +4 -0
- package/admin-dist/public/assets/ErrorState-BIVaWmom.js +1 -0
- package/admin-dist/public/assets/TaxonomyFilter-ChaY6Y_x.js +1 -0
- package/admin-dist/public/assets/_contentTypeId-DQ8k_Rvw.js +1 -0
- package/admin-dist/public/assets/_entryId-CKU_glsK.js +1 -0
- package/admin-dist/public/assets/alert-BXjTqrwQ.js +1 -0
- package/admin-dist/public/assets/badge-hvUOzpVZ.js +1 -0
- package/admin-dist/public/assets/circle-check-big-CF_pR17r.js +1 -0
- package/admin-dist/public/assets/command-DU82cJlt.js +1 -0
- package/admin-dist/public/assets/content-_LXl3pp7.js +1 -0
- package/admin-dist/public/assets/content-types-KjxaXGxY.js +2 -0
- package/admin-dist/public/assets/globals-CS6BZ0zp.css +1 -0
- package/admin-dist/public/assets/index-DNGIZHL-.js +1 -0
- package/admin-dist/public/assets/label-KNtpL71g.js +1 -0
- package/admin-dist/public/assets/link-2-Bw2aI4V4.js +1 -0
- package/admin-dist/public/assets/list-sYepHjt_.js +1 -0
- package/admin-dist/public/assets/main-CKj5yfEi.js +97 -0
- package/admin-dist/public/assets/media-Bkrkffm7.js +1 -0
- package/admin-dist/public/assets/new._contentTypeId-C3LstjNs.js +1 -0
- package/admin-dist/public/assets/plus-DUn8v_Xf.js +1 -0
- package/admin-dist/public/assets/rotate-ccw-DJEoHcRI.js +1 -0
- package/admin-dist/public/assets/scroll-area-DfIlT0in.js +1 -0
- package/admin-dist/public/assets/search-MuAUDJKR.js +1 -0
- package/admin-dist/public/assets/select-BD29IXCI.js +1 -0
- package/admin-dist/public/assets/settings-DmMyn_6A.js +1 -0
- package/admin-dist/public/assets/switch-h3Rrnl5i.js +1 -0
- package/admin-dist/public/assets/tabs-imc8h-Dp.js +1 -0
- package/admin-dist/public/assets/taxonomies-dAsrT65H.js +1 -0
- package/admin-dist/public/assets/textarea-BTy7nwzR.js +1 -0
- package/admin-dist/public/assets/trash-SAWKZZHv.js +1 -0
- package/admin-dist/public/assets/triangle-alert-E52Vfeuh.js +1 -0
- package/admin-dist/public/assets/useBreadcrumbLabel-BECBMCzM.js +1 -0
- package/admin-dist/public/assets/usePermissions-Basjs9BT.js +1 -0
- package/admin-dist/public/favicon.ico +0 -0
- package/admin-dist/server/_chunks/_libs/@date-fns/tz.mjs +217 -0
- package/admin-dist/server/_chunks/_libs/@floating-ui/core.mjs +719 -0
- package/admin-dist/server/_chunks/_libs/@floating-ui/dom.mjs +622 -0
- package/admin-dist/server/_chunks/_libs/@floating-ui/react-dom.mjs +292 -0
- package/admin-dist/server/_chunks/_libs/@floating-ui/utils.mjs +320 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/number.mjs +6 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/primitive.mjs +11 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-arrow.mjs +23 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-avatar.mjs +119 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-checkbox.mjs +270 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-collection.mjs +69 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-compose-refs.mjs +39 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-context.mjs +137 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-dialog.mjs +325 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-direction.mjs +9 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-dismissable-layer.mjs +210 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-dropdown-menu.mjs +253 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-focus-guards.mjs +29 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-focus-scope.mjs +206 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-id.mjs +14 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-label.mjs +23 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-menu.mjs +812 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-popover.mjs +300 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-popper.mjs +286 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-portal.mjs +16 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-presence.mjs +128 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-primitive.mjs +141 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-roving-focus.mjs +224 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-scroll-area.mjs +721 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-select.mjs +1163 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-separator.mjs +28 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-slot.mjs +601 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-switch.mjs +152 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-tabs.mjs +189 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-callback-ref.mjs +11 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-controllable-state.mjs +69 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-effect-event.mjs +1 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-escape-keydown.mjs +17 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-is-hydrated.mjs +15 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-layout-effect.mjs +6 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-previous.mjs +14 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-use-size.mjs +39 -0
- package/admin-dist/server/_chunks/_libs/@radix-ui/react-visually-hidden.mjs +33 -0
- package/admin-dist/server/_chunks/_libs/@tanstack/history.mjs +409 -0
- package/admin-dist/server/_chunks/_libs/@tanstack/react-router.mjs +1711 -0
- package/admin-dist/server/_chunks/_libs/@tanstack/react-store.mjs +56 -0
- package/admin-dist/server/_chunks/_libs/@tanstack/router-core.mjs +4829 -0
- package/admin-dist/server/_chunks/_libs/@tanstack/store.mjs +134 -0
- package/admin-dist/server/_chunks/_libs/react-dom.mjs +10781 -0
- package/admin-dist/server/_chunks/_libs/react.mjs +513 -0
- package/admin-dist/server/_libs/aria-hidden.mjs +122 -0
- package/admin-dist/server/_libs/class-variance-authority.mjs +44 -0
- package/admin-dist/server/_libs/clsx.mjs +16 -0
- package/admin-dist/server/_libs/cmdk.mjs +315 -0
- package/admin-dist/server/_libs/convex.mjs +4841 -0
- package/admin-dist/server/_libs/cookie-es.mjs +58 -0
- package/admin-dist/server/_libs/croner.mjs +1 -0
- package/admin-dist/server/_libs/crossws.mjs +1 -0
- package/admin-dist/server/_libs/date-fns.mjs +1716 -0
- package/admin-dist/server/_libs/detect-node-es.mjs +1 -0
- package/admin-dist/server/_libs/get-nonce.mjs +9 -0
- package/admin-dist/server/_libs/h3-v2.mjs +277 -0
- package/admin-dist/server/_libs/h3.mjs +401 -0
- package/admin-dist/server/_libs/hookable.mjs +1 -0
- package/admin-dist/server/_libs/isbot.mjs +20 -0
- package/admin-dist/server/_libs/lucide-react.mjs +850 -0
- package/admin-dist/server/_libs/ohash.mjs +1 -0
- package/admin-dist/server/_libs/react-day-picker.mjs +2201 -0
- package/admin-dist/server/_libs/react-remove-scroll-bar.mjs +82 -0
- package/admin-dist/server/_libs/react-remove-scroll.mjs +328 -0
- package/admin-dist/server/_libs/react-style-singleton.mjs +69 -0
- package/admin-dist/server/_libs/rou3.mjs +8 -0
- package/admin-dist/server/_libs/seroval-plugins.mjs +58 -0
- package/admin-dist/server/_libs/seroval.mjs +1765 -0
- package/admin-dist/server/_libs/srvx.mjs +719 -0
- package/admin-dist/server/_libs/tailwind-merge.mjs +3010 -0
- package/admin-dist/server/_libs/tiny-invariant.mjs +12 -0
- package/admin-dist/server/_libs/tiny-warning.mjs +5 -0
- package/admin-dist/server/_libs/tslib.mjs +39 -0
- package/admin-dist/server/_libs/ufo.mjs +54 -0
- package/admin-dist/server/_libs/unctx.mjs +1 -0
- package/admin-dist/server/_libs/unstorage.mjs +1 -0
- package/admin-dist/server/_libs/use-callback-ref.mjs +66 -0
- package/admin-dist/server/_libs/use-sidecar.mjs +106 -0
- package/admin-dist/server/_libs/use-sync-external-store.mjs +139 -0
- package/admin-dist/server/_libs/zod.mjs +4223 -0
- package/admin-dist/server/_ssr/CmsEmptyState-DU7-7-mV.mjs +290 -0
- package/admin-dist/server/_ssr/CmsPageHeader-CseW0AHm.mjs +24 -0
- package/admin-dist/server/_ssr/CmsStatusBadge-B_pi4KCp.mjs +127 -0
- package/admin-dist/server/_ssr/CmsToolbar-X75ex6ek.mjs +49 -0
- package/admin-dist/server/_ssr/ContentEntryEditor-CepusRsA.mjs +3720 -0
- package/admin-dist/server/_ssr/ErrorState-cI-bKLez.mjs +89 -0
- package/admin-dist/server/_ssr/TaxonomyFilter-Bwrq0-cz.mjs +188 -0
- package/admin-dist/server/_ssr/_contentTypeId-BqYKEcLr.mjs +379 -0
- package/admin-dist/server/_ssr/_entryId-CRfnqeDf.mjs +161 -0
- package/admin-dist/server/_ssr/_tanstack-start-manifest_v-BwDlABVk.mjs +4 -0
- package/admin-dist/server/_ssr/alert-CVt45UUP.mjs +92 -0
- package/admin-dist/server/_ssr/badge-6BsP37vG.mjs +125 -0
- package/admin-dist/server/_ssr/command-fy8epIKf.mjs +128 -0
- package/admin-dist/server/_ssr/config.server-D7JHDcDv.mjs +117 -0
- package/admin-dist/server/_ssr/content-B5RhL7uW.mjs +532 -0
- package/admin-dist/server/_ssr/content-types-BIOqCQYN.mjs +1166 -0
- package/admin-dist/server/_ssr/index-DHSHDPt1.mjs +193 -0
- package/admin-dist/server/_ssr/index.mjs +1275 -0
- package/admin-dist/server/_ssr/label-C8Dko1j7.mjs +22 -0
- package/admin-dist/server/_ssr/media-CSx3XttC.mjs +1832 -0
- package/admin-dist/server/_ssr/new._contentTypeId-DzanEZQM.mjs +144 -0
- package/admin-dist/server/_ssr/router-DDWcF-kt.mjs +1556 -0
- package/admin-dist/server/_ssr/scroll-area-bjPYwhXN.mjs +59 -0
- package/admin-dist/server/_ssr/select-BUhDDf4T.mjs +142 -0
- package/admin-dist/server/_ssr/settings-DAsxnw2q.mjs +348 -0
- package/admin-dist/server/_ssr/start-HYkvq4Ni.mjs +4 -0
- package/admin-dist/server/_ssr/switch-BgyRtQ1Z.mjs +31 -0
- package/admin-dist/server/_ssr/tabs-DzMdRB1A.mjs +628 -0
- package/admin-dist/server/_ssr/taxonomies-C8j8g5Q5.mjs +915 -0
- package/admin-dist/server/_ssr/textarea-9jNeYJSc.mjs +18 -0
- package/admin-dist/server/_ssr/trash-DYMxwhZB.mjs +291 -0
- package/admin-dist/server/_ssr/useBreadcrumbLabel-FNSAr2Ha.mjs +16 -0
- package/admin-dist/server/_ssr/usePermissions-BJGGahrJ.mjs +68 -0
- package/admin-dist/server/favicon.ico +0 -0
- package/admin-dist/server/index.mjs +627 -0
- package/dist/cli/index.js +0 -0
- package/dist/client/admin-config.d.ts +0 -1
- package/dist/client/admin-config.d.ts.map +1 -1
- package/dist/client/admin-config.js +0 -1
- package/dist/client/admin-config.js.map +1 -1
- package/dist/client/adminApi.d.ts.map +1 -1
- package/dist/client/agentTools.d.ts +1237 -135
- package/dist/client/agentTools.d.ts.map +1 -1
- package/dist/client/agentTools.js +33 -9
- package/dist/client/agentTools.js.map +1 -1
- package/dist/client/index.d.ts +1 -1
- package/dist/client/index.d.ts.map +1 -1
- package/dist/client/index.js.map +1 -1
- package/dist/component/_generated/component.d.ts +9 -0
- package/dist/component/_generated/component.d.ts.map +1 -1
- package/dist/component/mediaAssets.d.ts +35 -0
- package/dist/component/mediaAssets.d.ts.map +1 -1
- package/dist/component/mediaAssets.js +81 -0
- package/dist/component/mediaAssets.js.map +1 -1
- package/dist/test.d.ts.map +1 -1
- package/dist/test.js +2 -1
- package/dist/test.js.map +1 -1
- package/package.json +24 -9
- package/dist/component/auditLog.d.ts +0 -410
- package/dist/component/auditLog.d.ts.map +0 -1
- package/dist/component/auditLog.js +0 -607
- package/dist/component/auditLog.js.map +0 -1
- package/dist/component/types.d.ts +0 -4
- package/dist/component/types.d.ts.map +0 -1
- package/dist/component/types.js +0 -2
- package/dist/component/types.js.map +0 -1
- package/src/cli/commands/admin.ts +0 -104
- package/src/cli/index.ts +0 -21
- package/src/cli/utils/detectConvexUrl.ts +0 -54
- package/src/cli/utils/openBrowser.ts +0 -16
- package/src/client/admin-config.ts +0 -138
- package/src/client/adminApi.ts +0 -942
- package/src/client/agentTools.ts +0 -1311
- package/src/client/argTypes.ts +0 -316
- package/src/client/field-types.ts +0 -187
- package/src/client/index.ts +0 -1301
- package/src/client/queryBuilder.ts +0 -1100
- package/src/client/schema/codegen.ts +0 -500
- package/src/client/schema/defineContentType.ts +0 -501
- package/src/client/schema/index.ts +0 -169
- package/src/client/schema/schemaDrift.ts +0 -574
- package/src/client/schema/typedClient.ts +0 -688
- package/src/client/schema/types.ts +0 -666
- package/src/client/types.ts +0 -723
- package/src/client/workflows.ts +0 -141
- package/src/client/wrapper.ts +0 -4304
- package/src/component/_generated/api.ts +0 -140
- package/src/component/_generated/component.ts +0 -5029
- package/src/component/_generated/dataModel.ts +0 -60
- package/src/component/_generated/server.ts +0 -156
- package/src/component/authorization.ts +0 -647
- package/src/component/authorizationHooks.ts +0 -668
- package/src/component/bulkOperations.ts +0 -687
- package/src/component/contentEntries.ts +0 -1976
- package/src/component/contentEntryMutations.ts +0 -1223
- package/src/component/contentEntryValidation.ts +0 -707
- package/src/component/contentLock.ts +0 -550
- package/src/component/contentTypeMigration.ts +0 -1064
- package/src/component/contentTypeMutations.ts +0 -969
- package/src/component/contentTypes.ts +0 -346
- package/src/component/convex.config.ts +0 -44
- package/src/component/documentTypes.ts +0 -240
- package/src/component/eventEmitter.ts +0 -485
- package/src/component/exportImport.ts +0 -1169
- package/src/component/index.ts +0 -491
- package/src/component/lib/deepReferenceResolver.ts +0 -999
- package/src/component/lib/errors.ts +0 -816
- package/src/component/lib/index.ts +0 -145
- package/src/component/lib/mediaReferenceResolver.ts +0 -495
- package/src/component/lib/metadataExtractor.ts +0 -792
- package/src/component/lib/mutationAuth.ts +0 -199
- package/src/component/lib/queries.ts +0 -79
- package/src/component/lib/ragContentChunker.ts +0 -1371
- package/src/component/lib/referenceResolver.ts +0 -430
- package/src/component/lib/slugGenerator.ts +0 -262
- package/src/component/lib/slugUniqueness.ts +0 -333
- package/src/component/lib/softDelete.ts +0 -44
- package/src/component/localeFallbackChain.ts +0 -673
- package/src/component/localeFields.ts +0 -896
- package/src/component/mediaAssetMutations.ts +0 -725
- package/src/component/mediaAssets.ts +0 -932
- package/src/component/mediaFolderMutations.ts +0 -1046
- package/src/component/mediaUploadMutations.ts +0 -224
- package/src/component/mediaVariantMutations.ts +0 -900
- package/src/component/mediaVariants.ts +0 -793
- package/src/component/ragContentIndexer.ts +0 -1067
- package/src/component/rateLimitHooks.ts +0 -572
- package/src/component/roles.ts +0 -1360
- package/src/component/scheduledPublish.ts +0 -358
- package/src/component/schema.ts +0 -617
- package/src/component/taxonomies.ts +0 -949
- package/src/component/taxonomyMutations.ts +0 -1210
- package/src/component/trash.ts +0 -724
- package/src/component/userContext.ts +0 -898
- package/src/component/validation.ts +0 -1388
- package/src/component/validators.ts +0 -949
- package/src/component/versionMutations.ts +0 -392
- package/src/component/webhookTrigger.ts +0 -1922
- package/src/react/index.ts +0 -898
- package/src/test.ts +0 -1580
package/src/client/agentTools.ts
DELETED
|
@@ -1,1311 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* @convex-cms/core Agent Tools
|
|
3
|
-
*
|
|
4
|
-
* Tool-compatible function wrappers for @convex-dev/agent integration.
|
|
5
|
-
* Provides structured tool definitions with clear parameter schemas for
|
|
6
|
-
* content creation, querying, and management.
|
|
7
|
-
*
|
|
8
|
-
* @example
|
|
9
|
-
* ```typescript
|
|
10
|
-
* import { Agent } from "@convex-dev/agent";
|
|
11
|
-
* import { createCmsTools } from "@convex-cms/core";
|
|
12
|
-
* import { components } from "./_generated/api";
|
|
13
|
-
*
|
|
14
|
-
* const cmsTools = createCmsTools(components.convexCms);
|
|
15
|
-
*
|
|
16
|
-
* const contentAgent = new Agent(components.agent, {
|
|
17
|
-
* name: "Content Manager",
|
|
18
|
-
* languageModel: openai.chat("gpt-4o"),
|
|
19
|
-
* tools: cmsTools,
|
|
20
|
-
* });
|
|
21
|
-
* ```
|
|
22
|
-
*
|
|
23
|
-
* @example
|
|
24
|
-
* ```typescript
|
|
25
|
-
* // Use individual tools
|
|
26
|
-
* import { createCmsTools } from "@convex-cms/core";
|
|
27
|
-
*
|
|
28
|
-
* const { createContentEntry, listContentEntries, publishEntry } = createCmsTools(api);
|
|
29
|
-
*
|
|
30
|
-
* const agent = new Agent(components.agent, {
|
|
31
|
-
* tools: { createContentEntry, publishEntry },
|
|
32
|
-
* });
|
|
33
|
-
* ```
|
|
34
|
-
*/
|
|
35
|
-
|
|
36
|
-
import { createTool } from "@convex-dev/agent";
|
|
37
|
-
import { z } from "zod";
|
|
38
|
-
|
|
39
|
-
// =============================================================================
|
|
40
|
-
// Component API Type
|
|
41
|
-
// =============================================================================
|
|
42
|
-
|
|
43
|
-
/**
|
|
44
|
-
* The component API type for agent tools.
|
|
45
|
-
* This represents the actual structure of `components.convexCms` from the generated API.
|
|
46
|
-
*
|
|
47
|
-
* Uses `any` for internal function references since the exact types depend on
|
|
48
|
-
* the generated Convex types which vary per project.
|
|
49
|
-
*
|
|
50
|
-
* Note: This matches the actual Convex component module structure:
|
|
51
|
-
* - contentTypes: queries in contentTypes.ts (get handles both ID and name lookup via args)
|
|
52
|
-
* - contentTypeMutations: mutations in contentTypeMutations.ts
|
|
53
|
-
* - contentEntries: queries in contentEntries.ts
|
|
54
|
-
* - contentEntryMutations: mutations in contentEntryMutations.ts
|
|
55
|
-
* - scheduledPublish: schedule-related mutations in scheduledPublish.ts (separate module)
|
|
56
|
-
* - mediaAssets: queries in mediaAssets.ts
|
|
57
|
-
* - mediaAssetMutations: mutations in mediaAssetMutations.ts
|
|
58
|
-
* - bulkOperations: bulk mutations in bulkOperations.ts
|
|
59
|
-
*
|
|
60
|
-
* IMPORTANT: This type represents the raw component API shape as exported from
|
|
61
|
-
* `components.convexCms`. It differs from the wrapper API (createCmsClient) which
|
|
62
|
-
* provides a different, more ergonomic namespace structure.
|
|
63
|
-
*/
|
|
64
|
-
export type AgentComponentApi = {
|
|
65
|
-
/**
|
|
66
|
-
* Content type queries (contentTypes.ts module)
|
|
67
|
-
* @see src/component/contentTypes.ts
|
|
68
|
-
*/
|
|
69
|
-
contentTypes: {
|
|
70
|
-
/**
|
|
71
|
-
* Get content type by ID or name.
|
|
72
|
-
* Supports lookup by either `id` OR `name` argument (not both).
|
|
73
|
-
* @example { id: "..." } or { name: "blog_post" }
|
|
74
|
-
*/
|
|
75
|
-
get: any;
|
|
76
|
-
/** List content types with filtering and pagination */
|
|
77
|
-
list: any;
|
|
78
|
-
};
|
|
79
|
-
/**
|
|
80
|
-
* Content type mutations (contentTypeMutations.ts module)
|
|
81
|
-
* @see src/component/contentTypeMutations.ts
|
|
82
|
-
*/
|
|
83
|
-
contentTypeMutations: {
|
|
84
|
-
createContentType: any;
|
|
85
|
-
updateContentType: any;
|
|
86
|
-
deleteContentType: any;
|
|
87
|
-
};
|
|
88
|
-
/**
|
|
89
|
-
* Content entry queries (contentEntries.ts module)
|
|
90
|
-
* @see src/component/contentEntries.ts
|
|
91
|
-
*/
|
|
92
|
-
contentEntries: {
|
|
93
|
-
/** Get content entry by ID */
|
|
94
|
-
get: any;
|
|
95
|
-
/** Get content entry by slug and content type ID */
|
|
96
|
-
getBySlug: any;
|
|
97
|
-
/** Get content entry by slug and content type name */
|
|
98
|
-
getBySlugAndTypeName: any;
|
|
99
|
-
/** List content entries with filtering and pagination */
|
|
100
|
-
list: any;
|
|
101
|
-
};
|
|
102
|
-
/**
|
|
103
|
-
* Content entry mutations (contentEntryMutations.ts module)
|
|
104
|
-
* @see src/component/contentEntryMutations.ts
|
|
105
|
-
*/
|
|
106
|
-
contentEntryMutations: {
|
|
107
|
-
createEntry: any;
|
|
108
|
-
updateEntry: any;
|
|
109
|
-
publishEntry: any;
|
|
110
|
-
unpublishEntry: any;
|
|
111
|
-
deleteEntry: any;
|
|
112
|
-
duplicateEntry: any;
|
|
113
|
-
restoreEntry: any;
|
|
114
|
-
};
|
|
115
|
-
/**
|
|
116
|
-
* Scheduling-related mutations (scheduledPublish.ts module - SEPARATE from contentEntryMutations)
|
|
117
|
-
* @see src/component/scheduledPublish.ts
|
|
118
|
-
*/
|
|
119
|
-
scheduledPublish: {
|
|
120
|
-
/** Schedule an entry for future publication */
|
|
121
|
-
scheduleEntry: any;
|
|
122
|
-
/** Cancel a scheduled publication */
|
|
123
|
-
cancelScheduledPublish: any;
|
|
124
|
-
};
|
|
125
|
-
/**
|
|
126
|
-
* Media asset queries (mediaAssets.ts module)
|
|
127
|
-
* @see src/component/mediaAssets.ts
|
|
128
|
-
*/
|
|
129
|
-
mediaAssets: {
|
|
130
|
-
get: any;
|
|
131
|
-
list: any;
|
|
132
|
-
};
|
|
133
|
-
/**
|
|
134
|
-
* Media asset mutations (mediaAssetMutations.ts module)
|
|
135
|
-
* @see src/component/mediaAssetMutations.ts
|
|
136
|
-
*/
|
|
137
|
-
mediaAssetMutations: {
|
|
138
|
-
createMediaAsset: any;
|
|
139
|
-
updateMediaAsset: any;
|
|
140
|
-
deleteMediaAsset: any;
|
|
141
|
-
};
|
|
142
|
-
/**
|
|
143
|
-
* Bulk operations (bulkOperations.ts module)
|
|
144
|
-
* @see src/component/bulkOperations.ts
|
|
145
|
-
*/
|
|
146
|
-
bulkOperations: {
|
|
147
|
-
bulkPublish: any;
|
|
148
|
-
bulkUnpublish: any;
|
|
149
|
-
bulkDelete: any;
|
|
150
|
-
bulkUpdate: any;
|
|
151
|
-
bulkRestore: any;
|
|
152
|
-
};
|
|
153
|
-
};
|
|
154
|
-
|
|
155
|
-
// =============================================================================
|
|
156
|
-
// Zod Schemas for Tool Arguments
|
|
157
|
-
// =============================================================================
|
|
158
|
-
|
|
159
|
-
/**
|
|
160
|
-
* Supported field types in the CMS.
|
|
161
|
-
*/
|
|
162
|
-
export const fieldTypeSchema = z.enum([
|
|
163
|
-
"text",
|
|
164
|
-
"richText",
|
|
165
|
-
"number",
|
|
166
|
-
"boolean",
|
|
167
|
-
"date",
|
|
168
|
-
"datetime",
|
|
169
|
-
"reference",
|
|
170
|
-
"media",
|
|
171
|
-
"json",
|
|
172
|
-
"select",
|
|
173
|
-
"multiSelect",
|
|
174
|
-
]);
|
|
175
|
-
|
|
176
|
-
/**
|
|
177
|
-
* Content entry status values.
|
|
178
|
-
*/
|
|
179
|
-
export const contentStatusSchema = z.enum([
|
|
180
|
-
"draft",
|
|
181
|
-
"published",
|
|
182
|
-
"archived",
|
|
183
|
-
"scheduled",
|
|
184
|
-
]);
|
|
185
|
-
|
|
186
|
-
/**
|
|
187
|
-
* Media type classification.
|
|
188
|
-
*/
|
|
189
|
-
export const mediaTypeSchema = z.enum([
|
|
190
|
-
"image",
|
|
191
|
-
"video",
|
|
192
|
-
"audio",
|
|
193
|
-
"document",
|
|
194
|
-
"other",
|
|
195
|
-
]);
|
|
196
|
-
|
|
197
|
-
/**
|
|
198
|
-
* Field-specific configuration options.
|
|
199
|
-
*/
|
|
200
|
-
export const fieldOptionsSchema = z.object({
|
|
201
|
-
// Text fields
|
|
202
|
-
minLength: z.number().optional().describe("Minimum text length"),
|
|
203
|
-
maxLength: z.number().optional().describe("Maximum text length"),
|
|
204
|
-
pattern: z.string().optional().describe("Regex pattern for validation"),
|
|
205
|
-
|
|
206
|
-
// Number fields
|
|
207
|
-
min: z.number().optional().describe("Minimum numeric value"),
|
|
208
|
-
max: z.number().optional().describe("Maximum numeric value"),
|
|
209
|
-
step: z.number().optional().describe("Step increment for numeric input"),
|
|
210
|
-
precision: z.number().optional().describe("Decimal precision"),
|
|
211
|
-
|
|
212
|
-
// Reference fields
|
|
213
|
-
allowedContentTypes: z
|
|
214
|
-
.array(z.string())
|
|
215
|
-
.optional()
|
|
216
|
-
.describe("Content type names that can be referenced"),
|
|
217
|
-
multiple: z
|
|
218
|
-
.boolean()
|
|
219
|
-
.optional()
|
|
220
|
-
.describe("Allow multiple references"),
|
|
221
|
-
minItems: z
|
|
222
|
-
.number()
|
|
223
|
-
.optional()
|
|
224
|
-
.describe("Minimum number of references when multiple is true"),
|
|
225
|
-
|
|
226
|
-
// Media fields
|
|
227
|
-
allowedMimeTypes: z
|
|
228
|
-
.array(z.string())
|
|
229
|
-
.optional()
|
|
230
|
-
.describe("Allowed MIME types (e.g., 'image/*', 'application/pdf')"),
|
|
231
|
-
maxFileSize: z
|
|
232
|
-
.number()
|
|
233
|
-
.optional()
|
|
234
|
-
.describe("Maximum file size in bytes"),
|
|
235
|
-
|
|
236
|
-
// Select fields
|
|
237
|
-
options: z
|
|
238
|
-
.array(
|
|
239
|
-
z.object({
|
|
240
|
-
value: z.string().describe("Option value"),
|
|
241
|
-
label: z.string().describe("Display label"),
|
|
242
|
-
})
|
|
243
|
-
)
|
|
244
|
-
.optional()
|
|
245
|
-
.describe("Options for select/multiSelect fields"),
|
|
246
|
-
|
|
247
|
-
// Rich text fields
|
|
248
|
-
allowedBlocks: z
|
|
249
|
-
.array(z.string())
|
|
250
|
-
.optional()
|
|
251
|
-
.describe("Allowed block types in rich text"),
|
|
252
|
-
allowedMarks: z
|
|
253
|
-
.array(z.string())
|
|
254
|
-
.optional()
|
|
255
|
-
.describe("Allowed inline marks in rich text"),
|
|
256
|
-
}).strict();
|
|
257
|
-
|
|
258
|
-
/**
|
|
259
|
-
* Field definition schema for content types.
|
|
260
|
-
*/
|
|
261
|
-
export const fieldDefinitionSchema = z.object({
|
|
262
|
-
name: z
|
|
263
|
-
.string()
|
|
264
|
-
.describe("Unique machine-readable field name (e.g., 'author_name')"),
|
|
265
|
-
label: z.string().describe("Human-readable label for the field"),
|
|
266
|
-
type: fieldTypeSchema.describe("The field data type"),
|
|
267
|
-
required: z.boolean().describe("Whether the field is required"),
|
|
268
|
-
searchable: z
|
|
269
|
-
.boolean()
|
|
270
|
-
.optional()
|
|
271
|
-
.describe("Index this field for full-text search"),
|
|
272
|
-
localized: z
|
|
273
|
-
.boolean()
|
|
274
|
-
.optional()
|
|
275
|
-
.describe("Enable per-locale values for this field"),
|
|
276
|
-
description: z
|
|
277
|
-
.string()
|
|
278
|
-
.optional()
|
|
279
|
-
.describe("Help text shown in the editor"),
|
|
280
|
-
defaultValue: z.any().optional().describe("Default value for new entries"),
|
|
281
|
-
options: fieldOptionsSchema.optional().describe("Field-specific options"),
|
|
282
|
-
});
|
|
283
|
-
|
|
284
|
-
/**
|
|
285
|
-
* Filter operators for content queries.
|
|
286
|
-
*/
|
|
287
|
-
export const filterOperatorSchema = z.enum([
|
|
288
|
-
"eq",
|
|
289
|
-
"ne",
|
|
290
|
-
"gt",
|
|
291
|
-
"gte",
|
|
292
|
-
"lt",
|
|
293
|
-
"lte",
|
|
294
|
-
"contains",
|
|
295
|
-
"startsWith",
|
|
296
|
-
"endsWith",
|
|
297
|
-
"in",
|
|
298
|
-
"notIn",
|
|
299
|
-
]);
|
|
300
|
-
|
|
301
|
-
/**
|
|
302
|
-
* Field filter for content queries.
|
|
303
|
-
*/
|
|
304
|
-
export const fieldFilterSchema = z.object({
|
|
305
|
-
field: z.string().describe("Field name to filter on"),
|
|
306
|
-
operator: filterOperatorSchema.describe("Comparison operator"),
|
|
307
|
-
value: z.any().describe("Value to compare against"),
|
|
308
|
-
});
|
|
309
|
-
|
|
310
|
-
// =============================================================================
|
|
311
|
-
// Content Type Tool Schemas
|
|
312
|
-
// =============================================================================
|
|
313
|
-
|
|
314
|
-
/**
|
|
315
|
-
* Arguments for creating a content type.
|
|
316
|
-
*/
|
|
317
|
-
export const createContentTypeArgsSchema = z.object({
|
|
318
|
-
name: z
|
|
319
|
-
.string()
|
|
320
|
-
.describe(
|
|
321
|
-
"Unique machine-readable name (e.g., 'blog_post'). Use snake_case."
|
|
322
|
-
),
|
|
323
|
-
displayName: z
|
|
324
|
-
.string()
|
|
325
|
-
.describe("Human-readable name shown in the admin UI (e.g., 'Blog Post')"),
|
|
326
|
-
description: z
|
|
327
|
-
.string()
|
|
328
|
-
.optional()
|
|
329
|
-
.describe("Description of what this content type is for"),
|
|
330
|
-
fields: z
|
|
331
|
-
.array(fieldDefinitionSchema)
|
|
332
|
-
.describe("Array of field definitions that make up this content type"),
|
|
333
|
-
icon: z
|
|
334
|
-
.string()
|
|
335
|
-
.optional()
|
|
336
|
-
.describe("Icon identifier for the admin UI (e.g., 'document', 'image')"),
|
|
337
|
-
singleton: z
|
|
338
|
-
.boolean()
|
|
339
|
-
.optional()
|
|
340
|
-
.describe(
|
|
341
|
-
"If true, only one entry of this type can exist (e.g., for settings pages)"
|
|
342
|
-
),
|
|
343
|
-
slugField: z
|
|
344
|
-
.string()
|
|
345
|
-
.optional()
|
|
346
|
-
.describe("Field name to auto-generate URL slugs from (e.g., 'title')"),
|
|
347
|
-
titleField: z
|
|
348
|
-
.string()
|
|
349
|
-
.optional()
|
|
350
|
-
.describe("Field name to use as the display title in lists"),
|
|
351
|
-
sortOrder: z
|
|
352
|
-
.number()
|
|
353
|
-
.optional()
|
|
354
|
-
.describe("Custom sort order in the admin sidebar"),
|
|
355
|
-
createdBy: z
|
|
356
|
-
.string()
|
|
357
|
-
.optional()
|
|
358
|
-
.describe("User ID of who created this type"),
|
|
359
|
-
});
|
|
360
|
-
|
|
361
|
-
/**
|
|
362
|
-
* Arguments for updating a content type.
|
|
363
|
-
*/
|
|
364
|
-
export const updateContentTypeArgsSchema = z.object({
|
|
365
|
-
id: z.string().describe("The content type ID to update"),
|
|
366
|
-
displayName: z.string().optional().describe("New display name"),
|
|
367
|
-
description: z.string().optional().describe("New description"),
|
|
368
|
-
fields: z
|
|
369
|
-
.array(fieldDefinitionSchema)
|
|
370
|
-
.optional()
|
|
371
|
-
.describe("Updated field definitions (replaces all fields)"),
|
|
372
|
-
icon: z.string().optional().describe("New icon identifier"),
|
|
373
|
-
singleton: z.boolean().optional().describe("Update singleton setting"),
|
|
374
|
-
slugField: z.string().optional().describe("New slug field"),
|
|
375
|
-
titleField: z.string().optional().describe("New title field"),
|
|
376
|
-
sortOrder: z.number().optional().describe("New sort order"),
|
|
377
|
-
isActive: z.boolean().optional().describe("Whether the type is active"),
|
|
378
|
-
updatedBy: z.string().optional().describe("User ID performing the update"),
|
|
379
|
-
});
|
|
380
|
-
|
|
381
|
-
/**
|
|
382
|
-
* Arguments for listing content types.
|
|
383
|
-
*/
|
|
384
|
-
export const listContentTypesArgsSchema = z.object({
|
|
385
|
-
includeInactive: z
|
|
386
|
-
.boolean()
|
|
387
|
-
.optional()
|
|
388
|
-
.describe("Include inactive content types in results"),
|
|
389
|
-
});
|
|
390
|
-
|
|
391
|
-
/**
|
|
392
|
-
* Arguments for getting a single content type.
|
|
393
|
-
*/
|
|
394
|
-
export const getContentTypeArgsSchema = z.object({
|
|
395
|
-
id: z.string().optional().describe("Get content type by ID"),
|
|
396
|
-
name: z
|
|
397
|
-
.string()
|
|
398
|
-
.optional()
|
|
399
|
-
.describe("Get content type by name (alternative to ID)"),
|
|
400
|
-
});
|
|
401
|
-
|
|
402
|
-
// =============================================================================
|
|
403
|
-
// Content Entry Tool Schemas
|
|
404
|
-
// =============================================================================
|
|
405
|
-
|
|
406
|
-
/**
|
|
407
|
-
* Arguments for creating a content entry.
|
|
408
|
-
*/
|
|
409
|
-
export const createContentEntryArgsSchema = z.object({
|
|
410
|
-
contentTypeId: z
|
|
411
|
-
.string()
|
|
412
|
-
.describe("The content type ID this entry belongs to"),
|
|
413
|
-
slug: z
|
|
414
|
-
.string()
|
|
415
|
-
.optional()
|
|
416
|
-
.describe(
|
|
417
|
-
"URL-friendly slug (auto-generated from slugField if not provided)"
|
|
418
|
-
),
|
|
419
|
-
data: z
|
|
420
|
-
.record(z.string(), z.any())
|
|
421
|
-
.describe("The entry's field values as key-value pairs"),
|
|
422
|
-
locale: z
|
|
423
|
-
.string()
|
|
424
|
-
.optional()
|
|
425
|
-
.describe("Locale code for localized content (e.g., 'en-US')"),
|
|
426
|
-
status: contentStatusSchema
|
|
427
|
-
.optional()
|
|
428
|
-
.describe("Initial status (defaults to 'draft')"),
|
|
429
|
-
createdBy: z.string().optional().describe("User ID of the creator"),
|
|
430
|
-
});
|
|
431
|
-
|
|
432
|
-
/**
|
|
433
|
-
* Arguments for updating a content entry.
|
|
434
|
-
*/
|
|
435
|
-
export const updateContentEntryArgsSchema = z.object({
|
|
436
|
-
id: z.string().describe("The content entry ID to update"),
|
|
437
|
-
slug: z.string().optional().describe("New URL slug"),
|
|
438
|
-
data: z.record(z.string(), z.any()).optional().describe("Updated field values to merge"),
|
|
439
|
-
status: contentStatusSchema.optional().describe("New status"),
|
|
440
|
-
scheduledPublishAt: z
|
|
441
|
-
.number()
|
|
442
|
-
.optional()
|
|
443
|
-
.describe("Unix timestamp for scheduled publishing"),
|
|
444
|
-
updatedBy: z.string().optional().describe("User ID performing the update"),
|
|
445
|
-
regenerateSlug: z
|
|
446
|
-
.boolean()
|
|
447
|
-
.optional()
|
|
448
|
-
.describe("Regenerate slug from slugField after update"),
|
|
449
|
-
});
|
|
450
|
-
|
|
451
|
-
/**
|
|
452
|
-
* Arguments for publishing a content entry.
|
|
453
|
-
*/
|
|
454
|
-
export const publishEntryArgsSchema = z.object({
|
|
455
|
-
id: z.string().describe("The content entry ID to publish"),
|
|
456
|
-
changeDescription: z
|
|
457
|
-
.string()
|
|
458
|
-
.optional()
|
|
459
|
-
.describe("Description of changes for version history"),
|
|
460
|
-
updatedBy: z.string().optional().describe("User ID performing the publish"),
|
|
461
|
-
});
|
|
462
|
-
|
|
463
|
-
/**
|
|
464
|
-
* Arguments for unpublishing a content entry.
|
|
465
|
-
*/
|
|
466
|
-
export const unpublishEntryArgsSchema = z.object({
|
|
467
|
-
id: z.string().describe("The content entry ID to unpublish (revert to draft)"),
|
|
468
|
-
updatedBy: z.string().optional().describe("User ID performing the unpublish"),
|
|
469
|
-
});
|
|
470
|
-
|
|
471
|
-
/**
|
|
472
|
-
* Arguments for scheduling a content entry.
|
|
473
|
-
*/
|
|
474
|
-
export const scheduleEntryArgsSchema = z.object({
|
|
475
|
-
id: z.string().describe("The content entry ID to schedule"),
|
|
476
|
-
publishAt: z.number().describe("Unix timestamp for when to publish"),
|
|
477
|
-
updatedBy: z.string().optional().describe("User ID performing the schedule"),
|
|
478
|
-
});
|
|
479
|
-
|
|
480
|
-
/**
|
|
481
|
-
* Arguments for deleting a content entry.
|
|
482
|
-
*/
|
|
483
|
-
export const deleteContentEntryArgsSchema = z.object({
|
|
484
|
-
id: z.string().describe("The content entry ID to delete"),
|
|
485
|
-
deletedBy: z.string().optional().describe("User ID performing the deletion"),
|
|
486
|
-
hardDelete: z
|
|
487
|
-
.boolean()
|
|
488
|
-
.optional()
|
|
489
|
-
.describe("If true, permanently delete. Otherwise soft delete (default)."),
|
|
490
|
-
});
|
|
491
|
-
|
|
492
|
-
/**
|
|
493
|
-
* Arguments for duplicating a content entry.
|
|
494
|
-
*/
|
|
495
|
-
export const duplicateContentEntryArgsSchema = z.object({
|
|
496
|
-
sourceEntryId: z.string().describe("The content entry ID to duplicate"),
|
|
497
|
-
slug: z
|
|
498
|
-
.string()
|
|
499
|
-
.optional()
|
|
500
|
-
.describe("Custom slug for the duplicate (auto-generated if not provided)"),
|
|
501
|
-
copyMediaReferences: z
|
|
502
|
-
.boolean()
|
|
503
|
-
.optional()
|
|
504
|
-
.describe("Whether to copy media references (default: true)"),
|
|
505
|
-
locale: z.string().optional().describe("Locale for the duplicated entry"),
|
|
506
|
-
createdBy: z
|
|
507
|
-
.string()
|
|
508
|
-
.optional()
|
|
509
|
-
.describe("User ID performing the duplication"),
|
|
510
|
-
});
|
|
511
|
-
|
|
512
|
-
/**
|
|
513
|
-
* Arguments for listing content entries.
|
|
514
|
-
*/
|
|
515
|
-
export const listContentEntriesArgsSchema = z.object({
|
|
516
|
-
contentTypeId: z.string().optional().describe("Filter by content type ID"),
|
|
517
|
-
contentTypeName: z
|
|
518
|
-
.string()
|
|
519
|
-
.optional()
|
|
520
|
-
.describe("Filter by content type name (alternative to ID)"),
|
|
521
|
-
status: contentStatusSchema.optional().describe("Filter by single status"),
|
|
522
|
-
statusIn: z
|
|
523
|
-
.array(contentStatusSchema)
|
|
524
|
-
.optional()
|
|
525
|
-
.describe("Filter by multiple statuses"),
|
|
526
|
-
locale: z.string().optional().describe("Filter by locale"),
|
|
527
|
-
search: z.string().optional().describe("Full-text search query"),
|
|
528
|
-
includeDeleted: z
|
|
529
|
-
.boolean()
|
|
530
|
-
.optional()
|
|
531
|
-
.describe("Include soft-deleted entries"),
|
|
532
|
-
fieldFilters: z
|
|
533
|
-
.array(fieldFilterSchema)
|
|
534
|
-
.optional()
|
|
535
|
-
.describe("Field-level filters"),
|
|
536
|
-
limit: z
|
|
537
|
-
.number()
|
|
538
|
-
.optional()
|
|
539
|
-
.describe("Maximum number of entries to return (default: 50)"),
|
|
540
|
-
cursor: z.string().optional().describe("Pagination cursor from previous page"),
|
|
541
|
-
});
|
|
542
|
-
|
|
543
|
-
/**
|
|
544
|
-
* Arguments for getting a single content entry.
|
|
545
|
-
*/
|
|
546
|
-
export const getContentEntryArgsSchema = z.object({
|
|
547
|
-
id: z.string().optional().describe("Get entry by ID"),
|
|
548
|
-
slug: z.string().optional().describe("Get entry by slug (requires contentTypeId or contentTypeName)"),
|
|
549
|
-
contentTypeId: z.string().optional().describe("Content type ID (required when using slug)"),
|
|
550
|
-
contentTypeName: z.string().optional().describe("Content type name (alternative to contentTypeId when using slug)"),
|
|
551
|
-
});
|
|
552
|
-
|
|
553
|
-
/**
|
|
554
|
-
* Arguments for restoring a soft-deleted content entry.
|
|
555
|
-
*/
|
|
556
|
-
export const restoreContentEntryArgsSchema = z.object({
|
|
557
|
-
id: z.string().describe("The content entry ID to restore from trash"),
|
|
558
|
-
updatedBy: z.string().optional().describe("User ID performing the restore"),
|
|
559
|
-
});
|
|
560
|
-
|
|
561
|
-
// =============================================================================
|
|
562
|
-
// Media Asset Tool Schemas
|
|
563
|
-
// =============================================================================
|
|
564
|
-
|
|
565
|
-
/**
|
|
566
|
-
* Arguments for creating a media asset.
|
|
567
|
-
*/
|
|
568
|
-
export const createMediaAssetArgsSchema = z.object({
|
|
569
|
-
storageId: z.string().describe("Convex storage ID from file upload"),
|
|
570
|
-
filename: z.string().describe("Original filename"),
|
|
571
|
-
mimeType: z.string().describe("MIME type (e.g., 'image/jpeg')"),
|
|
572
|
-
size: z.number().describe("File size in bytes"),
|
|
573
|
-
type: mediaTypeSchema.describe("Classified media type"),
|
|
574
|
-
title: z.string().optional().describe("Human-readable title"),
|
|
575
|
-
description: z.string().optional().describe("Description or caption"),
|
|
576
|
-
altText: z.string().optional().describe("Alt text for accessibility"),
|
|
577
|
-
folderId: z.string().optional().describe("Parent folder ID"),
|
|
578
|
-
width: z.number().optional().describe("Image/video width in pixels"),
|
|
579
|
-
height: z.number().optional().describe("Image/video height in pixels"),
|
|
580
|
-
duration: z.number().optional().describe("Audio/video duration in seconds"),
|
|
581
|
-
metadata: z.record(z.string(), z.any()).optional().describe("Additional metadata"),
|
|
582
|
-
tags: z.array(z.string()).optional().describe("Tags for organization"),
|
|
583
|
-
createdBy: z.string().optional().describe("User ID of the uploader"),
|
|
584
|
-
});
|
|
585
|
-
|
|
586
|
-
/**
|
|
587
|
-
* Arguments for updating a media asset.
|
|
588
|
-
*/
|
|
589
|
-
export const updateMediaAssetArgsSchema = z.object({
|
|
590
|
-
id: z.string().describe("The media asset ID to update"),
|
|
591
|
-
title: z.string().optional().describe("New title"),
|
|
592
|
-
description: z.string().optional().describe("New description"),
|
|
593
|
-
altText: z.string().optional().describe("New alt text"),
|
|
594
|
-
folderId: z.string().optional().describe("Move to new folder"),
|
|
595
|
-
tags: z.array(z.string()).optional().describe("New tags (replaces existing)"),
|
|
596
|
-
});
|
|
597
|
-
|
|
598
|
-
/**
|
|
599
|
-
* Arguments for listing media assets.
|
|
600
|
-
*/
|
|
601
|
-
export const listMediaAssetsArgsSchema = z.object({
|
|
602
|
-
folderId: z.string().optional().describe("Filter by folder ID"),
|
|
603
|
-
type: mediaTypeSchema.optional().describe("Filter by media type"),
|
|
604
|
-
mimeType: z.string().optional().describe("Filter by MIME type"),
|
|
605
|
-
search: z.string().optional().describe("Search in filename, title, description"),
|
|
606
|
-
tags: z.array(z.string()).optional().describe("Filter by tags (any match)"),
|
|
607
|
-
includeDeleted: z.boolean().optional().describe("Include soft-deleted assets"),
|
|
608
|
-
limit: z.number().optional().describe("Maximum number of assets to return"),
|
|
609
|
-
cursor: z.string().optional().describe("Pagination cursor"),
|
|
610
|
-
});
|
|
611
|
-
|
|
612
|
-
/**
|
|
613
|
-
* Arguments for getting a single media asset.
|
|
614
|
-
*/
|
|
615
|
-
export const getMediaAssetArgsSchema = z.object({
|
|
616
|
-
id: z.string().describe("The media asset ID to retrieve"),
|
|
617
|
-
});
|
|
618
|
-
|
|
619
|
-
/**
|
|
620
|
-
* Arguments for deleting a media asset.
|
|
621
|
-
*/
|
|
622
|
-
export const deleteMediaAssetArgsSchema = z.object({
|
|
623
|
-
id: z.string().describe("The media asset ID to delete"),
|
|
624
|
-
deletedBy: z.string().optional().describe("User ID performing the deletion"),
|
|
625
|
-
hardDelete: z.boolean().optional().describe("If true, permanently delete"),
|
|
626
|
-
});
|
|
627
|
-
|
|
628
|
-
// =============================================================================
|
|
629
|
-
// Bulk Operation Tool Schemas
|
|
630
|
-
// =============================================================================
|
|
631
|
-
|
|
632
|
-
/**
|
|
633
|
-
* Arguments for bulk publishing content entries.
|
|
634
|
-
*/
|
|
635
|
-
export const bulkPublishArgsSchema = z.object({
|
|
636
|
-
ids: z.array(z.string()).describe("Array of content entry IDs to publish"),
|
|
637
|
-
changeDescription: z
|
|
638
|
-
.string()
|
|
639
|
-
.optional()
|
|
640
|
-
.describe("Version history description"),
|
|
641
|
-
updatedBy: z.string().optional().describe("User ID performing the operation"),
|
|
642
|
-
});
|
|
643
|
-
|
|
644
|
-
/**
|
|
645
|
-
* Arguments for bulk unpublishing content entries.
|
|
646
|
-
*/
|
|
647
|
-
export const bulkUnpublishArgsSchema = z.object({
|
|
648
|
-
ids: z.array(z.string()).describe("Array of content entry IDs to unpublish"),
|
|
649
|
-
updatedBy: z.string().optional().describe("User ID performing the operation"),
|
|
650
|
-
});
|
|
651
|
-
|
|
652
|
-
/**
|
|
653
|
-
* Arguments for bulk deleting content entries.
|
|
654
|
-
*/
|
|
655
|
-
export const bulkDeleteArgsSchema = z.object({
|
|
656
|
-
ids: z.array(z.string()).describe("Array of content entry IDs to delete"),
|
|
657
|
-
deletedBy: z.string().optional().describe("User ID performing the deletion"),
|
|
658
|
-
hardDelete: z.boolean().optional().describe("If true, permanently delete"),
|
|
659
|
-
});
|
|
660
|
-
|
|
661
|
-
// =============================================================================
|
|
662
|
-
// Search Tool Schema
|
|
663
|
-
// =============================================================================
|
|
664
|
-
|
|
665
|
-
/**
|
|
666
|
-
* Arguments for searching content.
|
|
667
|
-
*/
|
|
668
|
-
export const searchContentArgsSchema = z.object({
|
|
669
|
-
query: z.string().describe("Search query string"),
|
|
670
|
-
contentTypeId: z.string().optional().describe("Limit search to content type"),
|
|
671
|
-
contentTypeName: z.string().optional().describe("Limit search to content type by name"),
|
|
672
|
-
status: contentStatusSchema.optional().describe("Filter by status"),
|
|
673
|
-
limit: z.number().optional().describe("Maximum results to return"),
|
|
674
|
-
});
|
|
675
|
-
|
|
676
|
-
// =============================================================================
|
|
677
|
-
// Tool Factory Function
|
|
678
|
-
// =============================================================================
|
|
679
|
-
|
|
680
|
-
/**
|
|
681
|
-
* Options for creating CMS tools.
|
|
682
|
-
*/
|
|
683
|
-
export interface CreateCmsToolsOptions {
|
|
684
|
-
/**
|
|
685
|
-
* Optional user ID to use as the creator/updater for all operations.
|
|
686
|
-
* If not provided, tools will not set createdBy/updatedBy fields.
|
|
687
|
-
*/
|
|
688
|
-
defaultUserId?: string;
|
|
689
|
-
}
|
|
690
|
-
|
|
691
|
-
/**
|
|
692
|
-
* Creates a set of CMS tools compatible with @convex-dev/agent.
|
|
693
|
-
*
|
|
694
|
-
* These tools provide AI agents with structured access to CMS operations
|
|
695
|
-
* including content type management, content entry CRUD, publishing workflows,
|
|
696
|
-
* and media asset management.
|
|
697
|
-
*
|
|
698
|
-
* @param componentApi - The CMS component API from `components.convexCms`
|
|
699
|
-
* @param options - Optional configuration for the tools
|
|
700
|
-
* @returns An object containing all CMS tools
|
|
701
|
-
*
|
|
702
|
-
* @example
|
|
703
|
-
* ```typescript
|
|
704
|
-
* import { Agent } from "@convex-dev/agent";
|
|
705
|
-
* import { createCmsTools } from "@convex-cms/core";
|
|
706
|
-
* import { components } from "./_generated/api";
|
|
707
|
-
*
|
|
708
|
-
* // Create all CMS tools
|
|
709
|
-
* const cmsTools = createCmsTools(components.convexCms);
|
|
710
|
-
*
|
|
711
|
-
* // Use with an agent
|
|
712
|
-
* const contentAgent = new Agent(components.agent, {
|
|
713
|
-
* name: "Content Manager",
|
|
714
|
-
* languageModel: openai.chat("gpt-4o"),
|
|
715
|
-
* tools: cmsTools,
|
|
716
|
-
* });
|
|
717
|
-
* ```
|
|
718
|
-
*
|
|
719
|
-
* @example
|
|
720
|
-
* ```typescript
|
|
721
|
-
* // Use selected tools with a specialized agent
|
|
722
|
-
* const { listContentEntries, searchContent, getContentEntry } = createCmsTools(api);
|
|
723
|
-
*
|
|
724
|
-
* const researchAgent = new Agent(components.agent, {
|
|
725
|
-
* name: "Content Researcher",
|
|
726
|
-
* tools: { listContentEntries, searchContent, getContentEntry },
|
|
727
|
-
* });
|
|
728
|
-
* ```
|
|
729
|
-
*/
|
|
730
|
-
export function createCmsTools(
|
|
731
|
-
componentApi: AgentComponentApi,
|
|
732
|
-
options: CreateCmsToolsOptions = {}
|
|
733
|
-
) {
|
|
734
|
-
const { defaultUserId } = options;
|
|
735
|
-
|
|
736
|
-
// ==========================================================================
|
|
737
|
-
// Content Type Tools
|
|
738
|
-
// ==========================================================================
|
|
739
|
-
|
|
740
|
-
/**
|
|
741
|
-
* Create a new content type with field definitions.
|
|
742
|
-
*/
|
|
743
|
-
const createContentType = createTool({
|
|
744
|
-
description:
|
|
745
|
-
"Create a new content type (schema) that defines the structure for content entries. " +
|
|
746
|
-
"Content types have a name, display name, and array of field definitions. " +
|
|
747
|
-
"Each field has a name, label, type, and validation options.",
|
|
748
|
-
args: createContentTypeArgsSchema,
|
|
749
|
-
handler: async (ctx, args) => {
|
|
750
|
-
const result = await ctx.runMutation(
|
|
751
|
-
componentApi.contentTypeMutations.createContentType,
|
|
752
|
-
{
|
|
753
|
-
...args,
|
|
754
|
-
createdBy: args.createdBy ?? defaultUserId,
|
|
755
|
-
}
|
|
756
|
-
);
|
|
757
|
-
return result;
|
|
758
|
-
},
|
|
759
|
-
});
|
|
760
|
-
|
|
761
|
-
/**
|
|
762
|
-
* Update an existing content type.
|
|
763
|
-
*/
|
|
764
|
-
const updateContentType = createTool({
|
|
765
|
-
description:
|
|
766
|
-
"Update an existing content type's properties or field definitions. " +
|
|
767
|
-
"Can modify display name, description, fields, and other settings.",
|
|
768
|
-
args: updateContentTypeArgsSchema,
|
|
769
|
-
handler: async (ctx, args) => {
|
|
770
|
-
const result = await ctx.runMutation(
|
|
771
|
-
componentApi.contentTypeMutations.updateContentType,
|
|
772
|
-
{
|
|
773
|
-
...args,
|
|
774
|
-
id: args.id ,
|
|
775
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
776
|
-
}
|
|
777
|
-
);
|
|
778
|
-
return result;
|
|
779
|
-
},
|
|
780
|
-
});
|
|
781
|
-
|
|
782
|
-
/**
|
|
783
|
-
* List all content types.
|
|
784
|
-
*/
|
|
785
|
-
const listContentTypes = createTool({
|
|
786
|
-
description:
|
|
787
|
-
"List all content types defined in the CMS. " +
|
|
788
|
-
"Returns an array of content type definitions with their field schemas.",
|
|
789
|
-
args: listContentTypesArgsSchema,
|
|
790
|
-
handler: async (ctx, args) => {
|
|
791
|
-
const result = await ctx.runQuery(
|
|
792
|
-
componentApi.contentTypes.list,
|
|
793
|
-
args
|
|
794
|
-
);
|
|
795
|
-
return result;
|
|
796
|
-
},
|
|
797
|
-
});
|
|
798
|
-
|
|
799
|
-
/**
|
|
800
|
-
* Get a single content type by ID or name.
|
|
801
|
-
*/
|
|
802
|
-
const getContentType = createTool({
|
|
803
|
-
description:
|
|
804
|
-
"Get a single content type by ID or by name. " +
|
|
805
|
-
"Returns the full content type definition including all field schemas.",
|
|
806
|
-
args: getContentTypeArgsSchema,
|
|
807
|
-
handler: async (ctx, args) => {
|
|
808
|
-
// The contentTypes.get query supports both id and name lookup via args
|
|
809
|
-
if (args.id) {
|
|
810
|
-
const result = await ctx.runQuery(componentApi.contentTypes.get, {
|
|
811
|
-
id: args.id ,
|
|
812
|
-
});
|
|
813
|
-
return result;
|
|
814
|
-
} else if (args.name) {
|
|
815
|
-
// Use the same get query with name argument (not a separate getByName)
|
|
816
|
-
const result = await ctx.runQuery(componentApi.contentTypes.get, {
|
|
817
|
-
name: args.name,
|
|
818
|
-
});
|
|
819
|
-
return result;
|
|
820
|
-
}
|
|
821
|
-
throw new Error("Either id or name must be provided");
|
|
822
|
-
},
|
|
823
|
-
});
|
|
824
|
-
|
|
825
|
-
// ==========================================================================
|
|
826
|
-
// Content Entry Tools
|
|
827
|
-
// ==========================================================================
|
|
828
|
-
|
|
829
|
-
/**
|
|
830
|
-
* Create a new content entry.
|
|
831
|
-
*/
|
|
832
|
-
const createContentEntry = createTool({
|
|
833
|
-
description:
|
|
834
|
-
"Create a new content entry for a specific content type. " +
|
|
835
|
-
"Entries start as drafts by default. " +
|
|
836
|
-
"Provide field values in the 'data' object matching the content type's field definitions.",
|
|
837
|
-
args: createContentEntryArgsSchema,
|
|
838
|
-
handler: async (ctx, args) => {
|
|
839
|
-
const result = await ctx.runMutation(
|
|
840
|
-
componentApi.contentEntryMutations.createEntry,
|
|
841
|
-
{
|
|
842
|
-
...args,
|
|
843
|
-
contentTypeId: args.contentTypeId ,
|
|
844
|
-
createdBy: args.createdBy ?? defaultUserId,
|
|
845
|
-
}
|
|
846
|
-
);
|
|
847
|
-
return result;
|
|
848
|
-
},
|
|
849
|
-
});
|
|
850
|
-
|
|
851
|
-
/**
|
|
852
|
-
* Update an existing content entry.
|
|
853
|
-
*/
|
|
854
|
-
const updateContentEntry = createTool({
|
|
855
|
-
description:
|
|
856
|
-
"Update an existing content entry's data, status, or slug. " +
|
|
857
|
-
"Only provide the fields you want to update.",
|
|
858
|
-
args: updateContentEntryArgsSchema,
|
|
859
|
-
handler: async (ctx, args) => {
|
|
860
|
-
const result = await ctx.runMutation(
|
|
861
|
-
componentApi.contentEntryMutations.updateEntry,
|
|
862
|
-
{
|
|
863
|
-
...args,
|
|
864
|
-
id: args.id ,
|
|
865
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
866
|
-
}
|
|
867
|
-
);
|
|
868
|
-
return result;
|
|
869
|
-
},
|
|
870
|
-
});
|
|
871
|
-
|
|
872
|
-
/**
|
|
873
|
-
* Publish a content entry.
|
|
874
|
-
*/
|
|
875
|
-
const publishEntry = createTool({
|
|
876
|
-
description:
|
|
877
|
-
"Publish a draft content entry, making it publicly visible. " +
|
|
878
|
-
"Creates a version snapshot for history tracking.",
|
|
879
|
-
args: publishEntryArgsSchema,
|
|
880
|
-
handler: async (ctx, args) => {
|
|
881
|
-
const result = await ctx.runMutation(
|
|
882
|
-
componentApi.contentEntryMutations.publishEntry,
|
|
883
|
-
{
|
|
884
|
-
...args,
|
|
885
|
-
id: args.id ,
|
|
886
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
887
|
-
}
|
|
888
|
-
);
|
|
889
|
-
return result;
|
|
890
|
-
},
|
|
891
|
-
});
|
|
892
|
-
|
|
893
|
-
/**
|
|
894
|
-
* Unpublish a content entry.
|
|
895
|
-
*/
|
|
896
|
-
const unpublishEntry = createTool({
|
|
897
|
-
description:
|
|
898
|
-
"Unpublish a published content entry, reverting it to draft status. " +
|
|
899
|
-
"The entry will no longer be publicly visible.",
|
|
900
|
-
args: unpublishEntryArgsSchema,
|
|
901
|
-
handler: async (ctx, args) => {
|
|
902
|
-
const result = await ctx.runMutation(
|
|
903
|
-
componentApi.contentEntryMutations.unpublishEntry,
|
|
904
|
-
{
|
|
905
|
-
...args,
|
|
906
|
-
id: args.id ,
|
|
907
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
908
|
-
}
|
|
909
|
-
);
|
|
910
|
-
return result;
|
|
911
|
-
},
|
|
912
|
-
});
|
|
913
|
-
|
|
914
|
-
/**
|
|
915
|
-
* Schedule a content entry for future publishing.
|
|
916
|
-
*/
|
|
917
|
-
const scheduleEntry = createTool({
|
|
918
|
-
description:
|
|
919
|
-
"Schedule a content entry to be published at a specific time. " +
|
|
920
|
-
"The entry will automatically be published at the scheduled time.",
|
|
921
|
-
args: scheduleEntryArgsSchema,
|
|
922
|
-
handler: async (ctx, args) => {
|
|
923
|
-
// Note: scheduleEntry is in the scheduledPublish module, NOT contentEntryMutations
|
|
924
|
-
const result = await ctx.runMutation(
|
|
925
|
-
componentApi.scheduledPublish.scheduleEntry,
|
|
926
|
-
{
|
|
927
|
-
...args,
|
|
928
|
-
id: args.id ,
|
|
929
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
930
|
-
}
|
|
931
|
-
);
|
|
932
|
-
return result;
|
|
933
|
-
},
|
|
934
|
-
});
|
|
935
|
-
|
|
936
|
-
/**
|
|
937
|
-
* Delete a content entry.
|
|
938
|
-
*/
|
|
939
|
-
const deleteContentEntry = createTool({
|
|
940
|
-
description:
|
|
941
|
-
"Delete a content entry. By default performs soft delete (recoverable). " +
|
|
942
|
-
"Set hardDelete to true for permanent deletion.",
|
|
943
|
-
args: deleteContentEntryArgsSchema,
|
|
944
|
-
handler: async (ctx, args) => {
|
|
945
|
-
const result = await ctx.runMutation(
|
|
946
|
-
componentApi.contentEntryMutations.deleteEntry,
|
|
947
|
-
{
|
|
948
|
-
...args,
|
|
949
|
-
id: args.id ,
|
|
950
|
-
deletedBy: args.deletedBy ?? defaultUserId,
|
|
951
|
-
}
|
|
952
|
-
);
|
|
953
|
-
return result;
|
|
954
|
-
},
|
|
955
|
-
});
|
|
956
|
-
|
|
957
|
-
/**
|
|
958
|
-
* Duplicate a content entry.
|
|
959
|
-
*/
|
|
960
|
-
const duplicateContentEntry = createTool({
|
|
961
|
-
description:
|
|
962
|
-
"Create a copy of an existing content entry with a new unique slug. " +
|
|
963
|
-
"Useful for creating templates or variations.",
|
|
964
|
-
args: duplicateContentEntryArgsSchema,
|
|
965
|
-
handler: async (ctx, args) => {
|
|
966
|
-
const result = await ctx.runMutation(
|
|
967
|
-
componentApi.contentEntryMutations.duplicateEntry,
|
|
968
|
-
{
|
|
969
|
-
...args,
|
|
970
|
-
sourceEntryId: args.sourceEntryId ,
|
|
971
|
-
createdBy: args.createdBy ?? defaultUserId,
|
|
972
|
-
}
|
|
973
|
-
);
|
|
974
|
-
return result;
|
|
975
|
-
},
|
|
976
|
-
});
|
|
977
|
-
|
|
978
|
-
/**
|
|
979
|
-
* List content entries with filtering and pagination.
|
|
980
|
-
*/
|
|
981
|
-
const listContentEntries = createTool({
|
|
982
|
-
description:
|
|
983
|
-
"List content entries with optional filtering by content type, status, locale, and more. " +
|
|
984
|
-
"Supports pagination through cursor and limit parameters. " +
|
|
985
|
-
"Use fieldFilters for advanced filtering on entry data fields.",
|
|
986
|
-
args: listContentEntriesArgsSchema,
|
|
987
|
-
handler: async (ctx, args) => {
|
|
988
|
-
const result = await ctx.runQuery(componentApi.contentEntries.list, {
|
|
989
|
-
contentTypeId: args.contentTypeId ,
|
|
990
|
-
contentTypeName: args.contentTypeName,
|
|
991
|
-
status: args.status,
|
|
992
|
-
statusIn: args.statusIn,
|
|
993
|
-
locale: args.locale,
|
|
994
|
-
search: args.search,
|
|
995
|
-
includeDeleted: args.includeDeleted,
|
|
996
|
-
fieldFilters: args.fieldFilters,
|
|
997
|
-
paginationOpts: {
|
|
998
|
-
numItems: args.limit ?? 50,
|
|
999
|
-
cursor: args.cursor ?? null,
|
|
1000
|
-
},
|
|
1001
|
-
});
|
|
1002
|
-
return result;
|
|
1003
|
-
},
|
|
1004
|
-
});
|
|
1005
|
-
|
|
1006
|
-
/**
|
|
1007
|
-
* Get a single content entry.
|
|
1008
|
-
*/
|
|
1009
|
-
const getContentEntry = createTool({
|
|
1010
|
-
description:
|
|
1011
|
-
"Get a single content entry by ID or by slug. " +
|
|
1012
|
-
"When using slug, you must also provide contentTypeId or contentTypeName.",
|
|
1013
|
-
args: getContentEntryArgsSchema,
|
|
1014
|
-
handler: async (ctx, args) => {
|
|
1015
|
-
if (args.id) {
|
|
1016
|
-
const result = await ctx.runQuery(componentApi.contentEntries.get, {
|
|
1017
|
-
id: args.id ,
|
|
1018
|
-
});
|
|
1019
|
-
return result;
|
|
1020
|
-
} else if (args.slug) {
|
|
1021
|
-
if (args.contentTypeId) {
|
|
1022
|
-
const result = await ctx.runQuery(
|
|
1023
|
-
componentApi.contentEntries.getBySlug,
|
|
1024
|
-
{
|
|
1025
|
-
slug: args.slug,
|
|
1026
|
-
contentTypeId: args.contentTypeId ,
|
|
1027
|
-
}
|
|
1028
|
-
);
|
|
1029
|
-
return result;
|
|
1030
|
-
} else if (args.contentTypeName) {
|
|
1031
|
-
const result = await ctx.runQuery(
|
|
1032
|
-
componentApi.contentEntries.getBySlugAndTypeName,
|
|
1033
|
-
{
|
|
1034
|
-
slug: args.slug,
|
|
1035
|
-
contentTypeName: args.contentTypeName,
|
|
1036
|
-
}
|
|
1037
|
-
);
|
|
1038
|
-
return result;
|
|
1039
|
-
}
|
|
1040
|
-
throw new Error(
|
|
1041
|
-
"When using slug, contentTypeId or contentTypeName must be provided"
|
|
1042
|
-
);
|
|
1043
|
-
}
|
|
1044
|
-
throw new Error("Either id or slug must be provided");
|
|
1045
|
-
},
|
|
1046
|
-
});
|
|
1047
|
-
|
|
1048
|
-
/**
|
|
1049
|
-
* Restore a soft-deleted content entry.
|
|
1050
|
-
*/
|
|
1051
|
-
const restoreContentEntry = createTool({
|
|
1052
|
-
description:
|
|
1053
|
-
"Restore a soft-deleted content entry from the trash. " +
|
|
1054
|
-
"Only works on entries that were soft-deleted, not hard-deleted.",
|
|
1055
|
-
args: restoreContentEntryArgsSchema,
|
|
1056
|
-
handler: async (ctx, args) => {
|
|
1057
|
-
const result = await ctx.runMutation(
|
|
1058
|
-
componentApi.contentEntryMutations.restoreEntry,
|
|
1059
|
-
{
|
|
1060
|
-
id: args.id ,
|
|
1061
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
1062
|
-
}
|
|
1063
|
-
);
|
|
1064
|
-
return result;
|
|
1065
|
-
},
|
|
1066
|
-
});
|
|
1067
|
-
|
|
1068
|
-
// ==========================================================================
|
|
1069
|
-
// Media Asset Tools
|
|
1070
|
-
// ==========================================================================
|
|
1071
|
-
|
|
1072
|
-
/**
|
|
1073
|
-
* Create a media asset record.
|
|
1074
|
-
*/
|
|
1075
|
-
const createMediaAsset = createTool({
|
|
1076
|
-
description:
|
|
1077
|
-
"Create a media asset record after uploading a file to Convex storage. " +
|
|
1078
|
-
"Requires the storageId from the upload, along with file metadata.",
|
|
1079
|
-
args: createMediaAssetArgsSchema,
|
|
1080
|
-
handler: async (ctx, args) => {
|
|
1081
|
-
const result = await ctx.runMutation(
|
|
1082
|
-
componentApi.mediaAssetMutations.createMediaAsset,
|
|
1083
|
-
{
|
|
1084
|
-
...args,
|
|
1085
|
-
storageId: args.storageId ,
|
|
1086
|
-
folderId: args.folderId ,
|
|
1087
|
-
createdBy: args.createdBy ?? defaultUserId,
|
|
1088
|
-
}
|
|
1089
|
-
);
|
|
1090
|
-
return result;
|
|
1091
|
-
},
|
|
1092
|
-
});
|
|
1093
|
-
|
|
1094
|
-
/**
|
|
1095
|
-
* Update a media asset.
|
|
1096
|
-
*/
|
|
1097
|
-
const updateMediaAsset = createTool({
|
|
1098
|
-
description:
|
|
1099
|
-
"Update a media asset's metadata (title, description, alt text, tags, folder).",
|
|
1100
|
-
args: updateMediaAssetArgsSchema,
|
|
1101
|
-
handler: async (ctx, args) => {
|
|
1102
|
-
const result = await ctx.runMutation(
|
|
1103
|
-
componentApi.mediaAssetMutations.updateMediaAsset,
|
|
1104
|
-
{
|
|
1105
|
-
...args,
|
|
1106
|
-
id: args.id ,
|
|
1107
|
-
folderId: args.folderId ,
|
|
1108
|
-
}
|
|
1109
|
-
);
|
|
1110
|
-
return result;
|
|
1111
|
-
},
|
|
1112
|
-
});
|
|
1113
|
-
|
|
1114
|
-
/**
|
|
1115
|
-
* List media assets.
|
|
1116
|
-
*/
|
|
1117
|
-
const listMediaAssets = createTool({
|
|
1118
|
-
description:
|
|
1119
|
-
"List media assets with optional filtering by folder, type, MIME type, tags, and search.",
|
|
1120
|
-
args: listMediaAssetsArgsSchema,
|
|
1121
|
-
handler: async (ctx, args) => {
|
|
1122
|
-
const result = await ctx.runQuery(componentApi.mediaAssets.list, {
|
|
1123
|
-
folderId: args.folderId ,
|
|
1124
|
-
type: args.type,
|
|
1125
|
-
mimeType: args.mimeType,
|
|
1126
|
-
search: args.search,
|
|
1127
|
-
tags: args.tags,
|
|
1128
|
-
includeDeleted: args.includeDeleted,
|
|
1129
|
-
cursor: args.cursor,
|
|
1130
|
-
limit: args.limit,
|
|
1131
|
-
});
|
|
1132
|
-
return result;
|
|
1133
|
-
},
|
|
1134
|
-
});
|
|
1135
|
-
|
|
1136
|
-
/**
|
|
1137
|
-
* Get a single media asset.
|
|
1138
|
-
*/
|
|
1139
|
-
const getMediaAsset = createTool({
|
|
1140
|
-
description:
|
|
1141
|
-
"Get a single media asset by ID, including its download URL.",
|
|
1142
|
-
args: getMediaAssetArgsSchema,
|
|
1143
|
-
handler: async (ctx, args) => {
|
|
1144
|
-
const result = await ctx.runQuery(componentApi.mediaAssets.get, {
|
|
1145
|
-
id: args.id ,
|
|
1146
|
-
});
|
|
1147
|
-
return result;
|
|
1148
|
-
},
|
|
1149
|
-
});
|
|
1150
|
-
|
|
1151
|
-
/**
|
|
1152
|
-
* Delete a media asset.
|
|
1153
|
-
*/
|
|
1154
|
-
const deleteMediaAsset = createTool({
|
|
1155
|
-
description:
|
|
1156
|
-
"Delete a media asset. By default performs soft delete (recoverable).",
|
|
1157
|
-
args: deleteMediaAssetArgsSchema,
|
|
1158
|
-
handler: async (ctx, args) => {
|
|
1159
|
-
const result = await ctx.runMutation(
|
|
1160
|
-
componentApi.mediaAssetMutations.deleteMediaAsset,
|
|
1161
|
-
{
|
|
1162
|
-
id: args.id ,
|
|
1163
|
-
deletedBy: args.deletedBy ?? defaultUserId,
|
|
1164
|
-
hardDelete: args.hardDelete,
|
|
1165
|
-
}
|
|
1166
|
-
);
|
|
1167
|
-
return result;
|
|
1168
|
-
},
|
|
1169
|
-
});
|
|
1170
|
-
|
|
1171
|
-
// ==========================================================================
|
|
1172
|
-
// Bulk Operation Tools
|
|
1173
|
-
// ==========================================================================
|
|
1174
|
-
|
|
1175
|
-
/**
|
|
1176
|
-
* Bulk publish multiple content entries.
|
|
1177
|
-
*/
|
|
1178
|
-
const bulkPublish = createTool({
|
|
1179
|
-
description:
|
|
1180
|
-
"Publish multiple content entries at once. " +
|
|
1181
|
-
"More efficient than publishing entries one by one.",
|
|
1182
|
-
args: bulkPublishArgsSchema,
|
|
1183
|
-
handler: async (ctx, args) => {
|
|
1184
|
-
const result = await ctx.runMutation(
|
|
1185
|
-
componentApi.bulkOperations.bulkPublish,
|
|
1186
|
-
{
|
|
1187
|
-
ids: args.ids,
|
|
1188
|
-
changeDescription: args.changeDescription,
|
|
1189
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
1190
|
-
}
|
|
1191
|
-
);
|
|
1192
|
-
return result;
|
|
1193
|
-
},
|
|
1194
|
-
});
|
|
1195
|
-
|
|
1196
|
-
/**
|
|
1197
|
-
* Bulk unpublish multiple content entries.
|
|
1198
|
-
*/
|
|
1199
|
-
const bulkUnpublish = createTool({
|
|
1200
|
-
description:
|
|
1201
|
-
"Unpublish multiple content entries at once, reverting them to draft status.",
|
|
1202
|
-
args: bulkUnpublishArgsSchema,
|
|
1203
|
-
handler: async (ctx, args) => {
|
|
1204
|
-
const result = await ctx.runMutation(
|
|
1205
|
-
componentApi.bulkOperations.bulkUnpublish,
|
|
1206
|
-
{
|
|
1207
|
-
ids: args.ids,
|
|
1208
|
-
updatedBy: args.updatedBy ?? defaultUserId,
|
|
1209
|
-
}
|
|
1210
|
-
);
|
|
1211
|
-
return result;
|
|
1212
|
-
},
|
|
1213
|
-
});
|
|
1214
|
-
|
|
1215
|
-
/**
|
|
1216
|
-
* Bulk delete multiple content entries.
|
|
1217
|
-
*/
|
|
1218
|
-
const bulkDelete = createTool({
|
|
1219
|
-
description:
|
|
1220
|
-
"Delete multiple content entries at once. " +
|
|
1221
|
-
"By default performs soft delete. Set hardDelete for permanent deletion.",
|
|
1222
|
-
args: bulkDeleteArgsSchema,
|
|
1223
|
-
handler: async (ctx, args) => {
|
|
1224
|
-
const result = await ctx.runMutation(
|
|
1225
|
-
componentApi.bulkOperations.bulkDelete,
|
|
1226
|
-
{
|
|
1227
|
-
ids: args.ids,
|
|
1228
|
-
deletedBy: args.deletedBy ?? defaultUserId,
|
|
1229
|
-
hardDelete: args.hardDelete,
|
|
1230
|
-
}
|
|
1231
|
-
);
|
|
1232
|
-
return result;
|
|
1233
|
-
},
|
|
1234
|
-
});
|
|
1235
|
-
|
|
1236
|
-
// ==========================================================================
|
|
1237
|
-
// Search Tool
|
|
1238
|
-
// ==========================================================================
|
|
1239
|
-
|
|
1240
|
-
/**
|
|
1241
|
-
* Search content entries.
|
|
1242
|
-
*/
|
|
1243
|
-
const searchContent = createTool({
|
|
1244
|
-
description:
|
|
1245
|
-
"Search content entries by text query across all searchable fields. " +
|
|
1246
|
-
"Optionally filter by content type and status.",
|
|
1247
|
-
args: searchContentArgsSchema,
|
|
1248
|
-
handler: async (ctx, args) => {
|
|
1249
|
-
const result = await ctx.runQuery(componentApi.contentEntries.list, {
|
|
1250
|
-
contentTypeId: args.contentTypeId ,
|
|
1251
|
-
contentTypeName: args.contentTypeName,
|
|
1252
|
-
status: args.status,
|
|
1253
|
-
search: args.query,
|
|
1254
|
-
paginationOpts: {
|
|
1255
|
-
numItems: args.limit ?? 20,
|
|
1256
|
-
cursor: null,
|
|
1257
|
-
},
|
|
1258
|
-
});
|
|
1259
|
-
return result;
|
|
1260
|
-
},
|
|
1261
|
-
});
|
|
1262
|
-
|
|
1263
|
-
// ==========================================================================
|
|
1264
|
-
// Return all tools
|
|
1265
|
-
// ==========================================================================
|
|
1266
|
-
|
|
1267
|
-
return {
|
|
1268
|
-
// Content Type Tools
|
|
1269
|
-
createContentType,
|
|
1270
|
-
updateContentType,
|
|
1271
|
-
listContentTypes,
|
|
1272
|
-
getContentType,
|
|
1273
|
-
|
|
1274
|
-
// Content Entry Tools
|
|
1275
|
-
createContentEntry,
|
|
1276
|
-
updateContentEntry,
|
|
1277
|
-
publishEntry,
|
|
1278
|
-
unpublishEntry,
|
|
1279
|
-
scheduleEntry,
|
|
1280
|
-
deleteContentEntry,
|
|
1281
|
-
duplicateContentEntry,
|
|
1282
|
-
listContentEntries,
|
|
1283
|
-
getContentEntry,
|
|
1284
|
-
restoreContentEntry,
|
|
1285
|
-
|
|
1286
|
-
// Media Asset Tools
|
|
1287
|
-
createMediaAsset,
|
|
1288
|
-
updateMediaAsset,
|
|
1289
|
-
listMediaAssets,
|
|
1290
|
-
getMediaAsset,
|
|
1291
|
-
deleteMediaAsset,
|
|
1292
|
-
|
|
1293
|
-
// Bulk Operations
|
|
1294
|
-
bulkPublish,
|
|
1295
|
-
bulkUnpublish,
|
|
1296
|
-
bulkDelete,
|
|
1297
|
-
|
|
1298
|
-
// Search
|
|
1299
|
-
searchContent,
|
|
1300
|
-
};
|
|
1301
|
-
}
|
|
1302
|
-
|
|
1303
|
-
/**
|
|
1304
|
-
* Type representing all available CMS tools.
|
|
1305
|
-
*/
|
|
1306
|
-
export type CmsTools = ReturnType<typeof createCmsTools>;
|
|
1307
|
-
|
|
1308
|
-
/**
|
|
1309
|
-
* Tool names available in the CMS tools object.
|
|
1310
|
-
*/
|
|
1311
|
-
export type CmsToolName = keyof CmsTools;
|