@ai-stack/payloadcms 3.2.18-beta → 3.2.20-beta

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.
Files changed (38) hide show
  1. package/README.md +15 -0
  2. package/dist/ai/prompts.js +1 -1
  3. package/dist/ai/prompts.js.map +1 -1
  4. package/dist/collections/Instructions.d.ts +1 -1
  5. package/dist/collections/Instructions.js +18 -9
  6. package/dist/collections/Instructions.js.map +1 -1
  7. package/dist/endpoints/fetchFields.js +2 -0
  8. package/dist/endpoints/fetchFields.js.map +1 -1
  9. package/dist/endpoints/index.js +10 -6
  10. package/dist/endpoints/index.js.map +1 -1
  11. package/dist/exports/types.d.ts +1 -1
  12. package/dist/exports/types.js.map +1 -1
  13. package/dist/fields/ComposeField/ComposeField.js +23 -15
  14. package/dist/fields/ComposeField/ComposeField.js.map +1 -1
  15. package/dist/fields/LexicalEditor/ComposeFeatureComponent.d.ts +1 -1
  16. package/dist/fields/LexicalEditor/ComposeFeatureComponent.js +4 -1
  17. package/dist/fields/LexicalEditor/ComposeFeatureComponent.js.map +1 -1
  18. package/dist/index.d.ts +1 -1
  19. package/dist/index.js +1 -1
  20. package/dist/index.js.map +1 -1
  21. package/dist/init.js +61 -30
  22. package/dist/init.js.map +1 -1
  23. package/dist/plugin.js +3 -3
  24. package/dist/plugin.js.map +1 -1
  25. package/dist/providers/InstructionsProvider/InstructionsProvider.js +8 -4
  26. package/dist/providers/InstructionsProvider/InstructionsProvider.js.map +1 -1
  27. package/dist/providers/InstructionsProvider/context.d.ts +2 -0
  28. package/dist/providers/InstructionsProvider/context.js +2 -0
  29. package/dist/providers/InstructionsProvider/context.js.map +1 -1
  30. package/dist/providers/InstructionsProvider/useInstructions.js +15 -3
  31. package/dist/providers/InstructionsProvider/useInstructions.js.map +1 -1
  32. package/dist/types.d.ts +10 -3
  33. package/dist/types.js.map +1 -1
  34. package/dist/ui/Compose/Compose.js +21 -30
  35. package/dist/ui/Compose/Compose.js.map +1 -1
  36. package/dist/utilities/extractImageData.js +1 -1
  37. package/dist/utilities/extractImageData.js.map +1 -1
  38. package/package.json +1 -1
package/dist/init.js CHANGED
@@ -3,57 +3,78 @@ import { systemGenerate } from './ai/utils/systemGenerate.js';
3
3
  import { PLUGIN_INSTRUCTIONS_TABLE } from './defaults.js';
4
4
  import { getGenerationModels } from './utilities/getGenerationModels.js';
5
5
  export const init = async (payload, fieldSchemaPaths, pluginConfig)=>{
6
+ if (!pluginConfig.generatePromptOnInit) {
7
+ return;
8
+ }
6
9
  if (pluginConfig.debugging) {
7
10
  payload.logger.info(`— AI Plugin: Initializing...`);
8
11
  }
9
12
  const paths = Object.keys(fieldSchemaPaths);
13
+ // Get all instructions for faster initialization
14
+ const { docs: allInstructions } = await payload.find({
15
+ collection: PLUGIN_INSTRUCTIONS_TABLE,
16
+ depth: 0,
17
+ pagination: false,
18
+ select: {
19
+ 'field-type': true,
20
+ 'schema-path': true
21
+ }
22
+ });
10
23
  const fieldInstructionsMap = {};
11
24
  for(let i = 0; i < paths.length; i++){
12
25
  const path = paths[i];
13
26
  const { type: fieldType, label: fieldLabel, relationTo } = fieldSchemaPaths[path];
14
- const entry = await payload.find({
15
- collection: PLUGIN_INSTRUCTIONS_TABLE,
16
- pagination: false,
17
- where: {
18
- 'field-type': {
19
- equals: fieldType
20
- },
21
- 'schema-path': {
22
- equals: path
23
- }
24
- }
25
- });
26
- if (!entry?.docs?.length) {
27
- const seedPrompts = pluginConfig.seedPrompts || defaultSeedPrompts;
28
- const { prompt, system } = seedPrompts({
27
+ let instructions = allInstructions.find((entry)=>entry['schema-path'] === path);
28
+ if (!instructions) {
29
+ let seed;
30
+ const seedOptions = {
29
31
  fieldLabel,
30
32
  fieldSchemaPaths,
31
33
  fieldType,
32
34
  path
33
- });
35
+ };
36
+ if (pluginConfig.seedPrompts) {
37
+ seed = await pluginConfig.seedPrompts(seedOptions);
38
+ }
39
+ if (seed === undefined) {
40
+ seed = await defaultSeedPrompts(seedOptions);
41
+ }
42
+ // Field should be ignored
43
+ if (!seed) {
44
+ if (pluginConfig.debugging) {
45
+ payload.logger.info(`— AI Plugin: No seed prompt for ${path}, ignoring...`);
46
+ }
47
+ continue;
48
+ }
34
49
  let generatedPrompt = '{{ title }}';
35
- if (pluginConfig.generatePromptOnInit) {
50
+ if ('prompt' in seed) {
36
51
  // find the model that has the generateText function
37
52
  const models = getGenerationModels(pluginConfig);
38
53
  const model = models && Array.isArray(models) ? models.find((model)=>model.generateText) : undefined;
39
54
  generatedPrompt = await systemGenerate({
40
- prompt,
41
- system
55
+ prompt: seed.prompt,
56
+ system: seed.system
42
57
  }, model?.generateText);
43
- payload.logger.info(`\nPrompt generated for "${fieldLabel}" field:\nprompt: ${generatedPrompt}\n\n`);
44
58
  }
45
59
  const modelsForId = getGenerationModels(pluginConfig);
46
60
  const modelForId = modelsForId && Array.isArray(modelsForId) ? modelsForId.find((a)=>a.fields.includes(fieldType)) : undefined;
47
- const instructions = await payload.create({
61
+ const data = {
62
+ 'model-id': modelForId?.id,
63
+ prompt: generatedPrompt,
64
+ ...seed.data,
65
+ 'field-type': fieldType,
66
+ 'relation-to': relationTo,
67
+ 'schema-path': path
68
+ };
69
+ payload.logger.info({
70
+ 'model-id': data['model-id'],
71
+ prompt: generatedPrompt,
72
+ ...seed.data
73
+ }, `Prompt seeded for "${path}" field`);
74
+ instructions = await payload.create({
48
75
  collection: PLUGIN_INSTRUCTIONS_TABLE,
49
- data: {
50
- 'field-type': fieldType,
51
- 'model-id': modelForId?.id,
52
- prompt: generatedPrompt,
53
- 'relation-to': relationTo,
54
- 'schema-path': path
55
- }
56
- }).then((a)=>a).catch((err)=>{
76
+ data
77
+ }).catch((err)=>{
57
78
  payload.logger.error(err, '— AI Plugin: Error creating Compose settings-');
58
79
  });
59
80
  if (instructions?.id) {
@@ -63,7 +84,17 @@ export const init = async (payload, fieldSchemaPaths, pluginConfig)=>{
63
84
  };
64
85
  }
65
86
  } else {
66
- const [instructions] = entry.docs;
87
+ if (instructions['field-type'] !== fieldType) {
88
+ payload.logger.warn(`— AI Plugin: Field type mismatch for ${path}! Was "${fieldType}", it is "${instructions['field-type']}" now. Updating...`);
89
+ await payload.update({
90
+ id: instructions.id,
91
+ collection: PLUGIN_INSTRUCTIONS_TABLE,
92
+ data: {
93
+ 'field-type': fieldType
94
+ }
95
+ });
96
+ instructions['field-type'] = fieldType;
97
+ }
67
98
  fieldInstructionsMap[path] = {
68
99
  id: instructions.id,
69
100
  fieldType
package/dist/init.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/init.ts"],"sourcesContent":["import type { Payload } from 'payload'\n\nimport type { PluginConfig } from './types.js'\n\nimport { defaultSeedPrompts } from './ai/prompts.js'\nimport { systemGenerate } from './ai/utils/systemGenerate.js'\nimport { PLUGIN_INSTRUCTIONS_TABLE } from './defaults.js'\nimport { getGenerationModels } from './utilities/getGenerationModels.js'\n\nexport const init = async (\n payload: Payload,\n fieldSchemaPaths: Record<string, { label: string; relationTo?: string; type: string }>,\n pluginConfig: PluginConfig,\n) => {\n if (pluginConfig.debugging) {\n payload.logger.info(`— AI Plugin: Initializing...`)\n }\n\n const paths = Object.keys(fieldSchemaPaths)\n\n const fieldInstructionsMap: Record<string, { fieldType: any; id: any }> = {}\n for (let i = 0; i < paths.length; i++) {\n const path = paths[i]\n const { type: fieldType, label: fieldLabel, relationTo } = fieldSchemaPaths[path]\n const entry = await payload.find({\n collection: PLUGIN_INSTRUCTIONS_TABLE,\n pagination: false,\n where: {\n 'field-type': {\n equals: fieldType,\n },\n 'schema-path': {\n equals: path,\n },\n },\n })\n\n if (!entry?.docs?.length) {\n const seedPrompts = pluginConfig.seedPrompts || defaultSeedPrompts\n const { prompt, system } = seedPrompts({\n fieldLabel,\n fieldSchemaPaths,\n fieldType,\n path,\n })\n\n let generatedPrompt = '{{ title }}'\n if (pluginConfig.generatePromptOnInit) {\n // find the model that has the generateText function\n const models = getGenerationModels(pluginConfig)\n const model =\n models && Array.isArray(models) ? models.find((model) => model.generateText) : undefined\n generatedPrompt = await systemGenerate(\n {\n prompt,\n system,\n },\n model?.generateText,\n )\n payload.logger.info(\n `\\nPrompt generated for \"${fieldLabel}\" field:\\nprompt: ${generatedPrompt}\\n\\n`,\n )\n }\n\n const modelsForId = getGenerationModels(pluginConfig)\n const modelForId =\n modelsForId && Array.isArray(modelsForId)\n ? modelsForId.find((a) => a.fields.includes(fieldType))\n : undefined\n\n const instructions = await payload\n .create({\n collection: PLUGIN_INSTRUCTIONS_TABLE,\n data: {\n 'field-type': fieldType,\n 'model-id': modelForId?.id,\n prompt: generatedPrompt,\n 'relation-to': relationTo,\n 'schema-path': path,\n },\n })\n .then((a) => a)\n .catch((err) => {\n payload.logger.error(err, '— AI Plugin: Error creating Compose settings-')\n })\n\n if (instructions?.id) {\n fieldInstructionsMap[path] = {\n id: instructions.id,\n fieldType,\n }\n }\n } else {\n const [instructions] = entry.docs\n fieldInstructionsMap[path] = {\n id: instructions.id,\n fieldType,\n }\n }\n }\n\n if (pluginConfig.debugging) {\n payload.logger.info(\n `— AI Plugin: Enabled fields map: ${JSON.stringify(fieldInstructionsMap, null, 2)}`,\n )\n payload.logger.info(`— AI Plugin: Initialized!`)\n }\n\n if (pluginConfig.generatePromptOnInit) {\n payload.logger.info(\n '\\n\\n-AI Plugin: Example prompts are added to get you started, Now go break some code 🚀🚀🚀\\n\\n',\n )\n }\n}\n"],"names":["defaultSeedPrompts","systemGenerate","PLUGIN_INSTRUCTIONS_TABLE","getGenerationModels","init","payload","fieldSchemaPaths","pluginConfig","debugging","logger","info","paths","Object","keys","fieldInstructionsMap","i","length","path","type","fieldType","label","fieldLabel","relationTo","entry","find","collection","pagination","where","equals","docs","seedPrompts","prompt","system","generatedPrompt","generatePromptOnInit","models","model","Array","isArray","generateText","undefined","modelsForId","modelForId","a","fields","includes","instructions","create","data","id","then","catch","err","error","JSON","stringify"],"mappings":"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"}
1
+ {"version":3,"sources":["../src/init.ts"],"sourcesContent":["import type { Payload } from 'payload'\n\nimport type { PluginConfig } from './types.js'\n\nimport { defaultSeedPrompts } from './ai/prompts.js'\nimport { systemGenerate } from './ai/utils/systemGenerate.js'\nimport { PLUGIN_INSTRUCTIONS_TABLE } from './defaults.js'\nimport { getGenerationModels } from './utilities/getGenerationModels.js'\n\nexport const init = async (\n payload: Payload,\n fieldSchemaPaths: Record<string, { label: string; relationTo?: string; type: string }>,\n pluginConfig: PluginConfig,\n) => {\n if (!pluginConfig.generatePromptOnInit) {\n return\n }\n\n if (pluginConfig.debugging) {\n payload.logger.info(`— AI Plugin: Initializing...`)\n }\n\n const paths = Object.keys(fieldSchemaPaths)\n\n // Get all instructions for faster initialization\n const { docs: allInstructions } = await payload.find({\n collection: PLUGIN_INSTRUCTIONS_TABLE,\n depth: 0,\n pagination: false,\n select: {\n 'field-type': true,\n 'schema-path': true,\n },\n })\n\n const fieldInstructionsMap: Record<string, { fieldType: any; id: any }> = {}\n\n for (let i = 0; i < paths.length; i++) {\n const path = paths[i]\n const { type: fieldType, label: fieldLabel, relationTo } = fieldSchemaPaths[path]\n let instructions = allInstructions.find((entry) => entry['schema-path'] === path)\n\n if (!instructions) {\n let seed\n const seedOptions = {\n fieldLabel,\n fieldSchemaPaths,\n fieldType,\n path,\n }\n\n if (pluginConfig.seedPrompts) {seed = await pluginConfig.seedPrompts(seedOptions)}\n if (seed === undefined) {seed = await defaultSeedPrompts(seedOptions)}\n // Field should be ignored\n if (!seed) {\n if (pluginConfig.debugging) {\n payload.logger.info(`— AI Plugin: No seed prompt for ${path}, ignoring...`)\n }\n continue\n }\n\n let generatedPrompt = '{{ title }}'\n if ('prompt' in seed) {\n // find the model that has the generateText function\n const models = getGenerationModels(pluginConfig)\n const model =\n models && Array.isArray(models) ? models.find((model) => model.generateText) : undefined\n generatedPrompt = await systemGenerate(\n {\n prompt: seed.prompt,\n system: seed.system,\n },\n model?.generateText,\n )\n }\n\n const modelsForId = getGenerationModels(pluginConfig)\n const modelForId =\n modelsForId && Array.isArray(modelsForId)\n ? modelsForId.find((a) => a.fields.includes(fieldType))\n : undefined\n\n const data = {\n 'model-id': modelForId?.id,\n prompt: generatedPrompt,\n ...seed.data, // allow to override data, but not the one below\n 'field-type': fieldType,\n 'relation-to': relationTo,\n 'schema-path': path,\n }\n\n payload.logger.info(\n {\n 'model-id': data['model-id'],\n prompt: generatedPrompt,\n ...seed.data,\n },\n `Prompt seeded for \"${path}\" field`,\n )\n\n instructions = (await payload\n .create({\n collection: PLUGIN_INSTRUCTIONS_TABLE,\n data,\n })\n .catch((err) => {\n payload.logger.error(err, '— AI Plugin: Error creating Compose settings-')\n })) as (typeof allInstructions)[0]\n\n if (instructions?.id) {\n fieldInstructionsMap[path] = {\n id: instructions.id,\n fieldType,\n }\n }\n } else {\n if (instructions['field-type'] !== fieldType) {\n payload.logger.warn(\n `— AI Plugin: Field type mismatch for ${path}! Was \"${fieldType}\", it is \"${instructions['field-type']}\" now. Updating...`,\n )\n await payload.update({\n id: instructions.id,\n collection: PLUGIN_INSTRUCTIONS_TABLE,\n data: {\n 'field-type': fieldType,\n },\n })\n instructions['field-type'] = fieldType\n }\n\n fieldInstructionsMap[path] = {\n id: instructions.id,\n fieldType,\n }\n }\n }\n\n if (pluginConfig.debugging) {\n payload.logger.info(\n `— AI Plugin: Enabled fields map: ${JSON.stringify(fieldInstructionsMap, null, 2)}`,\n )\n payload.logger.info(`— AI Plugin: Initialized!`)\n }\n\n if (pluginConfig.generatePromptOnInit) {\n payload.logger.info(\n '\\n\\n-AI Plugin: Example prompts are added to get you started, Now go break some code 🚀🚀🚀\\n\\n',\n )\n }\n}\n"],"names":["defaultSeedPrompts","systemGenerate","PLUGIN_INSTRUCTIONS_TABLE","getGenerationModels","init","payload","fieldSchemaPaths","pluginConfig","generatePromptOnInit","debugging","logger","info","paths","Object","keys","docs","allInstructions","find","collection","depth","pagination","select","fieldInstructionsMap","i","length","path","type","fieldType","label","fieldLabel","relationTo","instructions","entry","seed","seedOptions","seedPrompts","undefined","generatedPrompt","models","model","Array","isArray","generateText","prompt","system","modelsForId","modelForId","a","fields","includes","data","id","create","catch","err","error","warn","update","JSON","stringify"],"mappings":"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"}
package/dist/plugin.js CHANGED
@@ -157,10 +157,10 @@ const payloadAiPlugin = (pluginConfig)=>(incomingConfig)=>{
157
157
  await init(payload, collectionsFieldPathMap, pluginConfig).catch((error)=>{
158
158
  payload.logger.error(error, `— AI Plugin: Initialization Error`);
159
159
  }).finally(()=>{
160
- setTimeout(()=>{
161
- payload.logger.info(securityMessage);
162
- }, 1000);
163
160
  if (!pluginConfig.disableSponsorMessage) {
161
+ setTimeout(()=>{
162
+ payload.logger.info(securityMessage);
163
+ }, 1000);
164
164
  setTimeout(()=>{
165
165
  payload.logger.info(sponsorMessage);
166
166
  }, 3000);
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/plugin.ts"],"sourcesContent":["import type { CollectionConfig, Config, GlobalConfig } from 'payload'\n\nimport { deepMerge } from 'payload/shared'\n\nimport type { PluginConfig } from './types.js'\n\nimport { defaultGenerationModels } from './ai/models/index.js'\nimport { lexicalJsonSchema } from './ai/schemas/lexicalJsonSchema.js'\nimport { instructionsCollection } from './collections/Instructions.js'\nimport { PLUGIN_NAME } from './defaults.js'\nimport { fetchFields } from './endpoints/fetchFields.js'\nimport { endpoints } from './endpoints/index.js'\nimport { init } from './init.js'\nimport { translations } from './translations/index.js'\nimport { getGenerationModels } from './utilities/getGenerationModels.js'\nimport { isPluginActivated } from './utilities/isPluginActivated.js'\nimport { updateFieldsConfig } from './utilities/updateFieldsConfig.js'\n\nconst defaultPluginConfig: PluginConfig = {\n access: {\n generate: ({ req }) => !!req.user,\n settings: ({ req }) => !!req.user,\n },\n collections: {},\n disableSponsorMessage: false,\n generatePromptOnInit: true,\n generationModels: defaultGenerationModels,\n}\n\nconst sponsorMessage = `\n╔═══════════════════════════════════════════════════════════════╗\n║ THANK YOU FOR USING THE PAYLOAD AI PLUGIN! ║\n║ ║\n║ If this plugin makes your life easier, please ║\n║ consider supporting its development and maintenance: ║\n║ ║\n║ • Buy me a coffee: https://buymeacoffee.com/ashbuilds ║\n║ • Sponsor on GitHub: https://github.com/sponsors/ashbuilds ║\n║ ║\n║ Your support fuels continued improvements, ║\n║ new features, and more caffeinated coding sessions! ☕ ║\n║ ║\n║ Got feedback or need help? Submit an issue here: ║\n║ • https://github.com/ashbuilds/payload-ai/issues/new ║\n║ ║\n║ Thank you again, and happy building! ║\n╚═══════════════════════════════════════════════════════════════╝\n`\n\nconst securityMessage = `\n╔═══════════════════════════════════════════════════════════════╗\n║ SECURITY NOTICE ║\n║ ║\n║ The AI Plugin now requires authentication by default. ║\n║ All AI features are restricted to authenticated users. ║\n║ ║\n║ To customize access control, configure the 'access' option ║\n║ in your plugin settings. See documentation for details. ║\n║ ║\n║ If you need different access patterns, please configure ║\n║ them explicitly in your plugin configuration. ║\n╚═══════════════════════════════════════════════════════════════╝\n`\n\nconst payloadAiPlugin =\n (pluginConfig: PluginConfig) =>\n (incomingConfig: Config): Config => {\n pluginConfig = {\n ...defaultPluginConfig,\n ...pluginConfig,\n access: {\n ...defaultPluginConfig.access,\n ...pluginConfig.access,\n },\n }\n\n pluginConfig.generationModels = getGenerationModels(pluginConfig)\n\n const isActivated = isPluginActivated(pluginConfig)\n let updatedConfig: Config = { ...incomingConfig }\n let collectionsFieldPathMap = {}\n\n if (isActivated) {\n const Instructions = instructionsCollection(pluginConfig)\n // Inject editor schema to config, so that it can be accessed when /textarea endpoint will hit\n const lexicalSchema = lexicalJsonSchema(pluginConfig.editorConfig?.nodes)\n\n Instructions.admin = {\n ...Instructions.admin,\n }\n\n if (pluginConfig.debugging) {\n Instructions.admin.hidden = false\n }\n\n Instructions.admin.custom = {\n ...(Instructions.admin.custom || {}),\n [PLUGIN_NAME]: {\n editorConfig: {\n // Used in admin client for useObject hook\n schema: lexicalSchema,\n },\n },\n }\n\n const collections = [...(incomingConfig.collections ?? []), Instructions]\n const globals = [...(incomingConfig.globals ?? [])]\n const { collections: collectionSlugs, globals: globalsSlugs } = pluginConfig\n\n const { components: { providers = [] } = {} } = incomingConfig.admin || {}\n const updatedProviders = [\n ...(providers ?? []),\n {\n path: '@ai-stack/payloadcms/client#InstructionsProvider',\n },\n ]\n\n incomingConfig.admin = {\n ...(incomingConfig.admin || {}),\n components: {\n ...(incomingConfig.admin?.components ?? {}),\n providers: updatedProviders,\n },\n }\n\n const pluginEndpoints = endpoints(pluginConfig)\n updatedConfig = {\n ...incomingConfig,\n collections: collections.map((collection) => {\n if (collectionSlugs[collection.slug]) {\n const { schemaPathMap, updatedCollectionConfig } = updateFieldsConfig(collection)\n collectionsFieldPathMap = {\n ...collectionsFieldPathMap,\n ...schemaPathMap,\n }\n return updatedCollectionConfig as CollectionConfig\n }\n\n return collection\n }),\n endpoints: [\n ...(incomingConfig.endpoints ?? []),\n pluginEndpoints.textarea,\n pluginEndpoints.upload,\n fetchFields(pluginConfig),\n ],\n globals: globals.map((global) => {\n if (globalsSlugs && globalsSlugs[global.slug]) {\n const { schemaPathMap, updatedCollectionConfig } = updateFieldsConfig(global)\n collectionsFieldPathMap = {\n ...collectionsFieldPathMap,\n ...schemaPathMap,\n }\n return updatedCollectionConfig as GlobalConfig\n }\n\n return global\n }),\n i18n: {\n ...(incomingConfig.i18n || {}),\n translations: {\n ...deepMerge(translations, incomingConfig.i18n?.translations ?? {}),\n },\n },\n }\n }\n\n updatedConfig.onInit = async (payload) => {\n if (incomingConfig.onInit) await incomingConfig.onInit(payload)\n\n if (!isActivated) {\n payload.logger.warn(`— AI Plugin: Not activated. Please verify your environment keys.`)\n return\n }\n\n await init(payload, collectionsFieldPathMap, pluginConfig)\n .catch((error) => {\n payload.logger.error(error, `— AI Plugin: Initialization Error`)\n })\n .finally(() => {\n setTimeout(() => {\n payload.logger.info(securityMessage)\n }, 1000)\n\n if (!pluginConfig.disableSponsorMessage) {\n setTimeout(() => {\n payload.logger.info(sponsorMessage)\n }, 3000)\n }\n })\n }\n\n return updatedConfig\n }\n\nexport { payloadAiPlugin }\n"],"names":["deepMerge","defaultGenerationModels","lexicalJsonSchema","instructionsCollection","PLUGIN_NAME","fetchFields","endpoints","init","translations","getGenerationModels","isPluginActivated","updateFieldsConfig","defaultPluginConfig","access","generate","req","user","settings","collections","disableSponsorMessage","generatePromptOnInit","generationModels","sponsorMessage","securityMessage","payloadAiPlugin","pluginConfig","incomingConfig","isActivated","updatedConfig","collectionsFieldPathMap","Instructions","lexicalSchema","editorConfig","nodes","admin","debugging","hidden","custom","schema","globals","collectionSlugs","globalsSlugs","components","providers","updatedProviders","path","pluginEndpoints","map","collection","slug","schemaPathMap","updatedCollectionConfig","textarea","upload","global","i18n","onInit","payload","logger","warn","catch","error","finally","setTimeout","info"],"mappings":"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"}
1
+ {"version":3,"sources":["../src/plugin.ts"],"sourcesContent":["import type { CollectionConfig, Config, GlobalConfig } from 'payload'\n\nimport { deepMerge } from 'payload/shared'\n\nimport type { PluginConfig } from './types.js'\n\nimport { defaultGenerationModels } from './ai/models/index.js'\nimport { lexicalJsonSchema } from './ai/schemas/lexicalJsonSchema.js'\nimport { instructionsCollection } from './collections/Instructions.js'\nimport { PLUGIN_NAME } from './defaults.js'\nimport { fetchFields } from './endpoints/fetchFields.js'\nimport { endpoints } from './endpoints/index.js'\nimport { init } from './init.js'\nimport { translations } from './translations/index.js'\nimport { getGenerationModels } from './utilities/getGenerationModels.js'\nimport { isPluginActivated } from './utilities/isPluginActivated.js'\nimport { updateFieldsConfig } from './utilities/updateFieldsConfig.js'\n\nconst defaultPluginConfig: PluginConfig = {\n access: {\n generate: ({ req }) => !!req.user,\n settings: ({ req }) => !!req.user,\n },\n collections: {},\n disableSponsorMessage: false,\n generatePromptOnInit: true,\n generationModels: defaultGenerationModels,\n}\n\nconst sponsorMessage = `\n╔═══════════════════════════════════════════════════════════════╗\n║ THANK YOU FOR USING THE PAYLOAD AI PLUGIN! ║\n║ ║\n║ If this plugin makes your life easier, please ║\n║ consider supporting its development and maintenance: ║\n║ ║\n║ • Buy me a coffee: https://buymeacoffee.com/ashbuilds ║\n║ • Sponsor on GitHub: https://github.com/sponsors/ashbuilds ║\n║ ║\n║ Your support fuels continued improvements, ║\n║ new features, and more caffeinated coding sessions! ☕ ║\n║ ║\n║ Got feedback or need help? Submit an issue here: ║\n║ • https://github.com/ashbuilds/payload-ai/issues/new ║\n║ ║\n║ Thank you again, and happy building! ║\n╚═══════════════════════════════════════════════════════════════╝\n`\n\nconst securityMessage = `\n╔═══════════════════════════════════════════════════════════════╗\n║ SECURITY NOTICE ║\n║ ║\n║ The AI Plugin now requires authentication by default. ║\n║ All AI features are restricted to authenticated users. ║\n║ ║\n║ To customize access control, configure the 'access' option ║\n║ in your plugin settings. See documentation for details. ║\n║ ║\n║ If you need different access patterns, please configure ║\n║ them explicitly in your plugin configuration. ║\n╚═══════════════════════════════════════════════════════════════╝\n`\n\nconst payloadAiPlugin =\n (pluginConfig: PluginConfig) =>\n (incomingConfig: Config): Config => {\n pluginConfig = {\n ...defaultPluginConfig,\n ...pluginConfig,\n access: {\n ...defaultPluginConfig.access,\n ...pluginConfig.access,\n },\n }\n\n pluginConfig.generationModels = getGenerationModels(pluginConfig)\n\n const isActivated = isPluginActivated(pluginConfig)\n let updatedConfig: Config = { ...incomingConfig }\n let collectionsFieldPathMap = {}\n\n if (isActivated) {\n const Instructions = instructionsCollection(pluginConfig)\n // Inject editor schema to config, so that it can be accessed when /textarea endpoint will hit\n const lexicalSchema = lexicalJsonSchema(pluginConfig.editorConfig?.nodes)\n\n Instructions.admin = {\n ...Instructions.admin,\n }\n\n if (pluginConfig.debugging) {\n Instructions.admin.hidden = false\n }\n\n Instructions.admin.custom = {\n ...(Instructions.admin.custom || {}),\n [PLUGIN_NAME]: {\n editorConfig: {\n // Used in admin client for useObject hook\n schema: lexicalSchema,\n },\n },\n }\n\n const collections = [...(incomingConfig.collections ?? []), Instructions]\n const globals = [...(incomingConfig.globals ?? [])]\n const { collections: collectionSlugs, globals: globalsSlugs } = pluginConfig\n\n const { components: { providers = [] } = {} } = incomingConfig.admin || {}\n const updatedProviders = [\n ...(providers ?? []),\n {\n path: '@ai-stack/payloadcms/client#InstructionsProvider',\n },\n ]\n\n incomingConfig.admin = {\n ...(incomingConfig.admin || {}),\n components: {\n ...(incomingConfig.admin?.components ?? {}),\n providers: updatedProviders,\n },\n }\n\n const pluginEndpoints = endpoints(pluginConfig)\n updatedConfig = {\n ...incomingConfig,\n collections: collections.map((collection) => {\n if (collectionSlugs[collection.slug]) {\n const { schemaPathMap, updatedCollectionConfig } = updateFieldsConfig(collection)\n collectionsFieldPathMap = {\n ...collectionsFieldPathMap,\n ...schemaPathMap,\n }\n return updatedCollectionConfig as CollectionConfig\n }\n\n return collection\n }),\n endpoints: [\n ...(incomingConfig.endpoints ?? []),\n pluginEndpoints.textarea,\n pluginEndpoints.upload,\n fetchFields(pluginConfig),\n ],\n globals: globals.map((global) => {\n if (globalsSlugs && globalsSlugs[global.slug]) {\n const { schemaPathMap, updatedCollectionConfig } = updateFieldsConfig(global)\n collectionsFieldPathMap = {\n ...collectionsFieldPathMap,\n ...schemaPathMap,\n }\n return updatedCollectionConfig as GlobalConfig\n }\n\n return global\n }),\n i18n: {\n ...(incomingConfig.i18n || {}),\n translations: {\n ...deepMerge(translations, incomingConfig.i18n?.translations ?? {}),\n },\n },\n }\n }\n\n updatedConfig.onInit = async (payload) => {\n if (incomingConfig.onInit) await incomingConfig.onInit(payload)\n\n if (!isActivated) {\n payload.logger.warn(`— AI Plugin: Not activated. Please verify your environment keys.`)\n return\n }\n\n await init(payload, collectionsFieldPathMap, pluginConfig)\n .catch((error) => {\n payload.logger.error(error, `— AI Plugin: Initialization Error`)\n })\n .finally(() => {\n if (!pluginConfig.disableSponsorMessage) {\n setTimeout(() => {\n payload.logger.info(securityMessage)\n }, 1000)\n setTimeout(() => {\n payload.logger.info(sponsorMessage)\n }, 3000)\n }\n })\n }\n\n return updatedConfig\n }\n\nexport { payloadAiPlugin }\n"],"names":["deepMerge","defaultGenerationModels","lexicalJsonSchema","instructionsCollection","PLUGIN_NAME","fetchFields","endpoints","init","translations","getGenerationModels","isPluginActivated","updateFieldsConfig","defaultPluginConfig","access","generate","req","user","settings","collections","disableSponsorMessage","generatePromptOnInit","generationModels","sponsorMessage","securityMessage","payloadAiPlugin","pluginConfig","incomingConfig","isActivated","updatedConfig","collectionsFieldPathMap","Instructions","lexicalSchema","editorConfig","nodes","admin","debugging","hidden","custom","schema","globals","collectionSlugs","globalsSlugs","components","providers","updatedProviders","path","pluginEndpoints","map","collection","slug","schemaPathMap","updatedCollectionConfig","textarea","upload","global","i18n","onInit","payload","logger","warn","catch","error","finally","setTimeout","info"],"mappings":"AAEA,SAASA,SAAS,QAAQ,iBAAgB;AAI1C,SAASC,uBAAuB,QAAQ,uBAAsB;AAC9D,SAASC,iBAAiB,QAAQ,oCAAmC;AACrE,SAASC,sBAAsB,QAAQ,gCAA+B;AACtE,SAASC,WAAW,QAAQ,gBAAe;AAC3C,SAASC,WAAW,QAAQ,6BAA4B;AACxD,SAASC,SAAS,QAAQ,uBAAsB;AAChD,SAASC,IAAI,QAAQ,YAAW;AAChC,SAASC,YAAY,QAAQ,0BAAyB;AACtD,SAASC,mBAAmB,QAAQ,qCAAoC;AACxE,SAASC,iBAAiB,QAAQ,mCAAkC;AACpE,SAASC,kBAAkB,QAAQ,oCAAmC;AAEtE,MAAMC,sBAAoC;IACxCC,QAAQ;QACNC,UAAU,CAAC,EAAEC,GAAG,EAAE,GAAK,CAAC,CAACA,IAAIC,IAAI;QACjCC,UAAU,CAAC,EAAEF,GAAG,EAAE,GAAK,CAAC,CAACA,IAAIC,IAAI;IACnC;IACAE,aAAa,CAAC;IACdC,uBAAuB;IACvBC,sBAAsB;IACtBC,kBAAkBpB;AACpB;AAEA,MAAMqB,iBAAiB,CAAC;;;;;;;;;;;;;;;;;;AAkBxB,CAAC;AAED,MAAMC,kBAAkB,CAAC;;;;;;;;;;;;;AAazB,CAAC;AAED,MAAMC,kBACJ,CAACC,eACD,CAACC;QACCD,eAAe;YACb,GAAGb,mBAAmB;YACtB,GAAGa,YAAY;YACfZ,QAAQ;gBACN,GAAGD,oBAAoBC,MAAM;gBAC7B,GAAGY,aAAaZ,MAAM;YACxB;QACF;QAEAY,aAAaJ,gBAAgB,GAAGZ,oBAAoBgB;QAEpD,MAAME,cAAcjB,kBAAkBe;QACtC,IAAIG,gBAAwB;YAAE,GAAGF,cAAc;QAAC;QAChD,IAAIG,0BAA0B,CAAC;QAE/B,IAAIF,aAAa;YACf,MAAMG,eAAe3B,uBAAuBsB;YAC5C,8FAA8F;YAC9F,MAAMM,gBAAgB7B,kBAAkBuB,aAAaO,YAAY,EAAEC;YAEnEH,aAAaI,KAAK,GAAG;gBACnB,GAAGJ,aAAaI,KAAK;YACvB;YAEA,IAAIT,aAAaU,SAAS,EAAE;gBAC1BL,aAAaI,KAAK,CAACE,MAAM,GAAG;YAC9B;YAEAN,aAAaI,KAAK,CAACG,MAAM,GAAG;gBAC1B,GAAIP,aAAaI,KAAK,CAACG,MAAM,IAAI,CAAC,CAAC;gBACnC,CAACjC,YAAY,EAAE;oBACb4B,cAAc;wBACZ,0CAA0C;wBAC1CM,QAAQP;oBACV;gBACF;YACF;YAEA,MAAMb,cAAc;mBAAKQ,eAAeR,WAAW,IAAI,EAAE;gBAAGY;aAAa;YACzE,MAAMS,UAAU;mBAAKb,eAAea,OAAO,IAAI,EAAE;aAAE;YACnD,MAAM,EAAErB,aAAasB,eAAe,EAAED,SAASE,YAAY,EAAE,GAAGhB;YAEhE,MAAM,EAAEiB,YAAY,EAAEC,YAAY,EAAE,EAAE,GAAG,CAAC,CAAC,EAAE,GAAGjB,eAAeQ,KAAK,IAAI,CAAC;YACzE,MAAMU,mBAAmB;mBACnBD,aAAa,EAAE;gBACnB;oBACEE,MAAM;gBACR;aACD;YAEDnB,eAAeQ,KAAK,GAAG;gBACrB,GAAIR,eAAeQ,KAAK,IAAI,CAAC,CAAC;gBAC9BQ,YAAY;oBACV,GAAIhB,eAAeQ,KAAK,EAAEQ,cAAc,CAAC,CAAC;oBAC1CC,WAAWC;gBACb;YACF;YAEA,MAAME,kBAAkBxC,UAAUmB;YAClCG,gBAAgB;gBACd,GAAGF,cAAc;gBACjBR,aAAaA,YAAY6B,GAAG,CAAC,CAACC;oBAC5B,IAAIR,eAAe,CAACQ,WAAWC,IAAI,CAAC,EAAE;wBACpC,MAAM,EAAEC,aAAa,EAAEC,uBAAuB,EAAE,GAAGxC,mBAAmBqC;wBACtEnB,0BAA0B;4BACxB,GAAGA,uBAAuB;4BAC1B,GAAGqB,aAAa;wBAClB;wBACA,OAAOC;oBACT;oBAEA,OAAOH;gBACT;gBACA1C,WAAW;uBACLoB,eAAepB,SAAS,IAAI,EAAE;oBAClCwC,gBAAgBM,QAAQ;oBACxBN,gBAAgBO,MAAM;oBACtBhD,YAAYoB;iBACb;gBACDc,SAASA,QAAQQ,GAAG,CAAC,CAACO;oBACpB,IAAIb,gBAAgBA,YAAY,CAACa,OAAOL,IAAI,CAAC,EAAE;wBAC7C,MAAM,EAAEC,aAAa,EAAEC,uBAAuB,EAAE,GAAGxC,mBAAmB2C;wBACtEzB,0BAA0B;4BACxB,GAAGA,uBAAuB;4BAC1B,GAAGqB,aAAa;wBAClB;wBACA,OAAOC;oBACT;oBAEA,OAAOG;gBACT;gBACAC,MAAM;oBACJ,GAAI7B,eAAe6B,IAAI,IAAI,CAAC,CAAC;oBAC7B/C,cAAc;wBACZ,GAAGR,UAAUQ,cAAckB,eAAe6B,IAAI,EAAE/C,gBAAgB,CAAC,EAAE;oBACrE;gBACF;YACF;QACF;QAEAoB,cAAc4B,MAAM,GAAG,OAAOC;YAC5B,IAAI/B,eAAe8B,MAAM,EAAE,MAAM9B,eAAe8B,MAAM,CAACC;YAEvD,IAAI,CAAC9B,aAAa;gBAChB8B,QAAQC,MAAM,CAACC,IAAI,CAAC,CAAC,gEAAgE,CAAC;gBACtF;YACF;YAEE,MAAMpD,KAAKkD,SAAS5B,yBAAyBJ,cAC1CmC,KAAK,CAAC,CAACC;gBACNJ,QAAQC,MAAM,CAACG,KAAK,CAACA,OAAO,CAAC,iCAAiC,CAAC;YACjE,GACCC,OAAO,CAAC;gBACP,IAAI,CAACrC,aAAaN,qBAAqB,EAAE;oBACvC4C,WAAW;wBACTN,QAAQC,MAAM,CAACM,IAAI,CAACzC;oBACtB,GAAG;oBACHwC,WAAW;wBACTN,QAAQC,MAAM,CAACM,IAAI,CAAC1C;oBACtB,GAAG;gBACL;YACF;QACJ;QAEF,OAAOM;IACT;AAEF,SAASJ,eAAe,GAAE"}
@@ -10,6 +10,7 @@ export const InstructionsProvider = ({ children })=>{
10
10
  const [activeCollection, setActiveCollection] = useState('');
11
11
  const [isConfigAllowed, setIsConfigAllowed] = useState(false);
12
12
  const [enabledLanguages, setEnabledLanguages] = useState();
13
+ const [debugging, setDebugging] = useState(false);
13
14
  const { user } = useAuth();
14
15
  const { config } = useConfig();
15
16
  const { routes: { api }, serverURL } = config;
@@ -18,10 +19,11 @@ export const InstructionsProvider = ({ children })=>{
18
19
  useEffect(()=>{
19
20
  fetch(`${serverURL}${api}${PLUGIN_FETCH_FIELDS_ENDPOINT}`).then(async (res)=>{
20
21
  await res.json().then((data)=>{
21
- setIsConfigAllowed(data?.isConfigAllowed);
22
- setEnabledLanguages(data?.enabledLanguages);
23
- setInstructionsState(data?.fields);
24
- setPromptFields(data?.promptFields);
22
+ setIsConfigAllowed(data?.isConfigAllowed || false);
23
+ setEnabledLanguages(data?.enabledLanguages || []);
24
+ setInstructionsState(data?.fields || {});
25
+ setPromptFields(data?.promptFields || []);
26
+ setDebugging(data?.debugging || false);
25
27
  });
26
28
  }).catch((err)=>{
27
29
  console.error('InstructionsProvider:', err);
@@ -34,7 +36,9 @@ export const InstructionsProvider = ({ children })=>{
34
36
  return /*#__PURE__*/ _jsx(InstructionsContext.Provider, {
35
37
  value: {
36
38
  activeCollection,
39
+ debugging,
37
40
  enabledLanguages,
41
+ hasInstructions: instructions && Object.keys(instructions).length > 0,
38
42
  instructions,
39
43
  isConfigAllowed,
40
44
  promptFields,
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/providers/InstructionsProvider/InstructionsProvider.tsx"],"sourcesContent":["'use client'\n\n\nimport { useAuth, useConfig } from '@payloadcms/ui'\nimport React, { useEffect, useState } from 'react'\n\nimport type { SerializedPromptField } from '../../types.js'\n\nimport { PLUGIN_FETCH_FIELDS_ENDPOINT } from '../../defaults.js'\nimport { InstructionsContext } from './context.js'\n\n\nexport const InstructionsProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n const [instructions, setInstructionsState] = useState({})\n const [promptFields, setPromptFields] = useState<SerializedPromptField[]>([])\n const [activeCollection, setActiveCollection] = useState('')\n const [isConfigAllowed, setIsConfigAllowed] = useState(false)\n const [enabledLanguages, setEnabledLanguages] = useState<string[]>()\n const { user } = useAuth()\n\n const { config } = useConfig()\n const {\n routes: { api },\n serverURL,\n } = config\n\n // This is here because each field have separate instructions and\n // their ID is needed to edit them for Drawer\n useEffect(() => {\n fetch(`${serverURL}${api}${PLUGIN_FETCH_FIELDS_ENDPOINT}`)\n .then(async (res) => {\n await res.json().then((data) => {\n setIsConfigAllowed(data?.isConfigAllowed)\n setEnabledLanguages(data?.enabledLanguages)\n setInstructionsState(data?.fields)\n setPromptFields(data?.promptFields)\n })\n })\n .catch((err) => {\n console.error('InstructionsProvider:', err)\n })\n }, [api, serverURL, user])\n\n return (\n <InstructionsContext.Provider\n value={{\n activeCollection,\n enabledLanguages,\n instructions,\n isConfigAllowed,\n promptFields,\n setActiveCollection,\n }}\n >\n {children}\n </InstructionsContext.Provider>\n )\n}\n"],"names":["useAuth","useConfig","React","useEffect","useState","PLUGIN_FETCH_FIELDS_ENDPOINT","InstructionsContext","InstructionsProvider","children","instructions","setInstructionsState","promptFields","setPromptFields","activeCollection","setActiveCollection","isConfigAllowed","setIsConfigAllowed","enabledLanguages","setEnabledLanguages","user","config","routes","api","serverURL","fetch","then","res","json","data","fields","catch","err","console","error","Provider","value"],"mappings":"AAAA;;AAGA,SAASA,OAAO,EAAEC,SAAS,QAAQ,iBAAgB;AACnD,OAAOC,SAASC,SAAS,EAAEC,QAAQ,QAAQ,QAAO;AAIlD,SAASC,4BAA4B,QAAQ,oBAAmB;AAChE,SAASC,mBAAmB,QAAQ,eAAc;AAGlD,OAAO,MAAMC,uBAAgE,CAAC,EAAEC,QAAQ,EAAE;IACxF,MAAM,CAACC,cAAcC,qBAAqB,GAAGN,SAAS,CAAC;IACvD,MAAM,CAACO,cAAcC,gBAAgB,GAAGR,SAAkC,EAAE;IAC5E,MAAM,CAACS,kBAAkBC,oBAAoB,GAAGV,SAAS;IACzD,MAAM,CAACW,iBAAiBC,mBAAmB,GAAGZ,SAAS;IACvD,MAAM,CAACa,kBAAkBC,oBAAoB,GAAGd;IAChD,MAAM,EAAEe,IAAI,EAAE,GAAGnB;IAEjB,MAAM,EAAEoB,MAAM,EAAE,GAAGnB;IACnB,MAAM,EACJoB,QAAQ,EAAEC,GAAG,EAAE,EACfC,SAAS,EACV,GAAGH;IAEJ,iEAAiE;IACjE,6CAA6C;IAC7CjB,UAAU;QACRqB,MAAM,GAAGD,YAAYD,MAAMjB,8BAA8B,EACtDoB,IAAI,CAAC,OAAOC;YACX,MAAMA,IAAIC,IAAI,GAAGF,IAAI,CAAC,CAACG;gBACrBZ,mBAAmBY,MAAMb;gBACzBG,oBAAoBU,MAAMX;gBAC1BP,qBAAqBkB,MAAMC;gBAC3BjB,gBAAgBgB,MAAMjB;YACxB;QACF,GACCmB,KAAK,CAAC,CAACC;YACNC,QAAQC,KAAK,CAAC,yBAAyBF;QACzC;IACJ,GAAG;QAACT;QAAKC;QAAWJ;KAAK;IAEzB,qBACE,KAACb,oBAAoB4B,QAAQ;QAC3BC,OAAO;YACLtB;YACAI;YACAR;YACAM;YACAJ;YACAG;QACF;kBAECN;;AAGP,EAAC"}
1
+ {"version":3,"sources":["../../../src/providers/InstructionsProvider/InstructionsProvider.tsx"],"sourcesContent":["'use client'\n\n\nimport { useAuth, useConfig } from '@payloadcms/ui'\nimport React, { useEffect, useState } from 'react'\n\nimport type { SerializedPromptField } from '../../types.js'\n\nimport { PLUGIN_FETCH_FIELDS_ENDPOINT } from '../../defaults.js'\nimport { InstructionsContext } from './context.js'\n\n\nexport const InstructionsProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n const [instructions, setInstructionsState] = useState({})\n const [promptFields, setPromptFields] = useState<SerializedPromptField[]>([])\n const [activeCollection, setActiveCollection] = useState('')\n const [isConfigAllowed, setIsConfigAllowed] = useState(false)\n const [enabledLanguages, setEnabledLanguages] = useState<string[]>()\n const [debugging, setDebugging] = useState(false)\n const { user } = useAuth()\n\n const { config } = useConfig()\n const {\n routes: { api },\n serverURL,\n } = config\n\n // This is here because each field have separate instructions and\n // their ID is needed to edit them for Drawer\n useEffect(() => {\n fetch(`${serverURL}${api}${PLUGIN_FETCH_FIELDS_ENDPOINT}`)\n .then(async (res) => {\n await res.json().then((data) => {\n setIsConfigAllowed(data?.isConfigAllowed || false)\n setEnabledLanguages(data?.enabledLanguages || [])\n setInstructionsState(data?.fields || {})\n setPromptFields(data?.promptFields || [])\n setDebugging(data?.debugging || false)\n })\n })\n .catch((err) => {\n console.error('InstructionsProvider:', err)\n })\n }, [api, serverURL, user])\n\n return (\n <InstructionsContext.Provider\n value={{\n activeCollection,\n debugging,\n enabledLanguages,\n hasInstructions: instructions && Object.keys(instructions).length > 0,\n instructions,\n isConfigAllowed,\n promptFields,\n setActiveCollection,\n }}\n >\n {children}\n </InstructionsContext.Provider>\n )\n}\n"],"names":["useAuth","useConfig","React","useEffect","useState","PLUGIN_FETCH_FIELDS_ENDPOINT","InstructionsContext","InstructionsProvider","children","instructions","setInstructionsState","promptFields","setPromptFields","activeCollection","setActiveCollection","isConfigAllowed","setIsConfigAllowed","enabledLanguages","setEnabledLanguages","debugging","setDebugging","user","config","routes","api","serverURL","fetch","then","res","json","data","fields","catch","err","console","error","Provider","value","hasInstructions","Object","keys","length"],"mappings":"AAAA;;AAGA,SAASA,OAAO,EAAEC,SAAS,QAAQ,iBAAgB;AACnD,OAAOC,SAASC,SAAS,EAAEC,QAAQ,QAAQ,QAAO;AAIlD,SAASC,4BAA4B,QAAQ,oBAAmB;AAChE,SAASC,mBAAmB,QAAQ,eAAc;AAGlD,OAAO,MAAMC,uBAAgE,CAAC,EAAEC,QAAQ,EAAE;IACxF,MAAM,CAACC,cAAcC,qBAAqB,GAAGN,SAAS,CAAC;IACvD,MAAM,CAACO,cAAcC,gBAAgB,GAAGR,SAAkC,EAAE;IAC5E,MAAM,CAACS,kBAAkBC,oBAAoB,GAAGV,SAAS;IACzD,MAAM,CAACW,iBAAiBC,mBAAmB,GAAGZ,SAAS;IACvD,MAAM,CAACa,kBAAkBC,oBAAoB,GAAGd;IAChD,MAAM,CAACe,WAAWC,aAAa,GAAGhB,SAAS;IAC3C,MAAM,EAAEiB,IAAI,EAAE,GAAGrB;IAEjB,MAAM,EAAEsB,MAAM,EAAE,GAAGrB;IACnB,MAAM,EACJsB,QAAQ,EAAEC,GAAG,EAAE,EACfC,SAAS,EACV,GAAGH;IAEJ,iEAAiE;IACjE,6CAA6C;IAC7CnB,UAAU;QACRuB,MAAM,GAAGD,YAAYD,MAAMnB,8BAA8B,EACtDsB,IAAI,CAAC,OAAOC;YACX,MAAMA,IAAIC,IAAI,GAAGF,IAAI,CAAC,CAACG;gBACrBd,mBAAmBc,MAAMf,mBAAmB;gBAC5CG,oBAAoBY,MAAMb,oBAAoB,EAAE;gBAChDP,qBAAqBoB,MAAMC,UAAU,CAAC;gBACtCnB,gBAAgBkB,MAAMnB,gBAAgB,EAAE;gBACxCS,aAAaU,MAAMX,aAAa;YAClC;QACF,GACCa,KAAK,CAAC,CAACC;YACNC,QAAQC,KAAK,CAAC,yBAAyBF;QACzC;IACJ,GAAG;QAACT;QAAKC;QAAWJ;KAAK;IAEzB,qBACE,KAACf,oBAAoB8B,QAAQ;QAC3BC,OAAO;YACLxB;YACAM;YACAF;YACAqB,iBAAiB7B,gBAAgB8B,OAAOC,IAAI,CAAC/B,cAAcgC,MAAM,GAAG;YACpEhC;YACAM;YACAJ;YACAG;QACF;kBAECN;;AAGP,EAAC"}
@@ -3,8 +3,10 @@ import type React from 'react';
3
3
  import type { SerializedPromptField } from '../../types.js';
4
4
  export type InstructionsContextValue = {
5
5
  activeCollection?: string;
6
+ debugging?: boolean;
6
7
  enabledLanguages?: string[];
7
8
  field?: Field;
9
+ hasInstructions: boolean;
8
10
  instructions: Record<string, any>;
9
11
  isConfigAllowed: boolean;
10
12
  path?: string;
@@ -1,7 +1,9 @@
1
1
  'use client';
2
2
  import { createContext } from 'react';
3
3
  export const initialContext = {
4
+ debugging: false,
4
5
  field: undefined,
6
+ hasInstructions: false,
5
7
  instructions: {},
6
8
  isConfigAllowed: true,
7
9
  path: '',
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/providers/InstructionsProvider/context.ts"],"sourcesContent":["'use client'\n\nimport type { Field } from 'payload'\nimport type React from 'react';\n\nimport { createContext } from 'react'\n\nimport type { SerializedPromptField } from '../../types.js'\n\nexport type InstructionsContextValue = {\n activeCollection?: string\n enabledLanguages?: string[]\n field?: Field\n instructions: Record<string, any>\n isConfigAllowed: boolean\n path?: string\n promptFields: SerializedPromptField[]\n schemaPath?: unknown\n setActiveCollection?: React.Dispatch<React.SetStateAction<string>>\n}\n\nexport const initialContext: InstructionsContextValue = {\n field: undefined,\n instructions: {},\n isConfigAllowed: true,\n path: '',\n promptFields: [],\n schemaPath: '',\n}\n\nexport const InstructionsContext = createContext<InstructionsContextValue>(initialContext)\n"],"names":["createContext","initialContext","field","undefined","instructions","isConfigAllowed","path","promptFields","schemaPath","InstructionsContext"],"mappings":"AAAA;AAKA,SAASA,aAAa,QAAQ,QAAO;AAgBrC,OAAO,MAAMC,iBAA2C;IACtDC,OAAOC;IACPC,cAAc,CAAC;IACfC,iBAAiB;IACjBC,MAAM;IACNC,cAAc,EAAE;IAChBC,YAAY;AACd,EAAC;AAED,OAAO,MAAMC,sBAAsBT,cAAwCC,gBAAe"}
1
+ {"version":3,"sources":["../../../src/providers/InstructionsProvider/context.ts"],"sourcesContent":["'use client'\n\nimport type { Field } from 'payload'\nimport type React from 'react';\n\nimport { createContext } from 'react'\n\nimport type { SerializedPromptField } from '../../types.js'\n\nexport type InstructionsContextValue = {\n activeCollection?: string\n debugging?: boolean\n enabledLanguages?: string[]\n field?: Field\n hasInstructions: boolean\n instructions: Record<string, any>\n isConfigAllowed: boolean\n path?: string\n promptFields: SerializedPromptField[]\n schemaPath?: unknown\n setActiveCollection?: React.Dispatch<React.SetStateAction<string>>\n}\n\nexport const initialContext: InstructionsContextValue = {\n debugging: false,\n field: undefined,\n hasInstructions: false,\n instructions: {},\n isConfigAllowed: true,\n path: '',\n promptFields: [],\n schemaPath: '',\n}\n\nexport const InstructionsContext = createContext<InstructionsContextValue>(initialContext)\n"],"names":["createContext","initialContext","debugging","field","undefined","hasInstructions","instructions","isConfigAllowed","path","promptFields","schemaPath","InstructionsContext"],"mappings":"AAAA;AAKA,SAASA,aAAa,QAAQ,QAAO;AAkBrC,OAAO,MAAMC,iBAA2C;IACtDC,WAAW;IACXC,OAAOC;IACPC,iBAAiB;IACjBC,cAAc,CAAC;IACfC,iBAAiB;IACjBC,MAAM;IACNC,cAAc,EAAE;IAChBC,YAAY;AACd,EAAC;AAED,OAAO,MAAMC,sBAAsBX,cAAwCC,gBAAe"}
@@ -3,10 +3,18 @@ import { useDocumentInfo } from '@payloadcms/ui';
3
3
  import { useContext, useEffect, useMemo, useState } from 'react';
4
4
  import { PLUGIN_INSTRUCTIONS_TABLE } from '../../defaults.js';
5
5
  import { handlebarsHelpers, handlebarsHelpersMap } from '../../libraries/handlebars/helpersMap.js';
6
+ const warnedOnceOnNoInstructionId = new Set();
7
+ const warnOnceOnMissingInstructions = (path)=>{
8
+ if (!warnedOnceOnNoInstructionId.has(path)) {
9
+ warnedOnceOnNoInstructionId.add(path);
10
+ // eslint-disable-next-line no-console
11
+ console.info(`[AI Plugin] There are no AI instructions for this field: ${path}. Enable "generatePromptOnInit" option to enable them.`);
12
+ }
13
+ };
6
14
  export const useInstructions = (update = {})=>{
7
15
  const context = useContext(InstructionsContext);
8
16
  const { collectionSlug } = useDocumentInfo();
9
- const { activeCollection, instructions, promptFields, setActiveCollection } = context;
17
+ const { activeCollection, hasInstructions, instructions, promptFields, setActiveCollection, debugging } = context;
10
18
  const [schemaPath, setSchemaPath] = useState(update.schemaPath);
11
19
  useEffect(()=>{
12
20
  if (update.schemaPath !== schemaPath) {
@@ -26,7 +34,7 @@ export const useInstructions = (update = {})=>{
26
34
  ]);
27
35
  const groupedFields = useMemo(()=>{
28
36
  const result = {};
29
- for (const fullKey of Object.keys(instructions)){
37
+ for (const fullKey of Object.keys(instructions || {})){
30
38
  const [collection, ...pathParts] = fullKey.split('.');
31
39
  const path = pathParts.join('.');
32
40
  if (!result[collection]) {
@@ -76,9 +84,13 @@ export const useInstructions = (update = {})=>{
76
84
  instructions,
77
85
  promptFields
78
86
  ]);
87
+ const pathInstructions = instructions[schemaPath];
88
+ if (debugging && !pathInstructions && schemaPath && hasInstructions) {
89
+ warnOnceOnMissingInstructions(schemaPath);
90
+ }
79
91
  return {
80
92
  ...context,
81
- ...instructions[schemaPath] || {},
93
+ ...pathInstructions || {},
82
94
  promptEditorSuggestions
83
95
  };
84
96
  };
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/providers/InstructionsProvider/useInstructions.ts"],"sourcesContent":["import { InstructionsContext } from '@ai-stack/payloadcms/client'\nimport { useDocumentInfo } from '@payloadcms/ui'\nimport { useContext, useEffect, useMemo, useState } from 'react'\n\nimport { PLUGIN_INSTRUCTIONS_TABLE } from '../../defaults.js'\nimport { handlebarsHelpers, handlebarsHelpersMap } from '../../libraries/handlebars/helpersMap.js'\n\nexport const useInstructions = (\n update: {\n schemaPath?: unknown\n } = {},\n) => {\n const context = useContext(InstructionsContext)\n const { collectionSlug } = useDocumentInfo()\n const { activeCollection, instructions, promptFields, setActiveCollection } = context\n\n const [schemaPath, setSchemaPath] = useState(update.schemaPath as string)\n\n useEffect(() => {\n if (update.schemaPath !== schemaPath) {\n setSchemaPath((update.schemaPath as string) ?? '')\n }\n }, [update.schemaPath])\n\n useEffect(() => {\n if (\n activeCollection !== collectionSlug &&\n collectionSlug !== PLUGIN_INSTRUCTIONS_TABLE &&\n typeof setActiveCollection === 'function'\n ) {\n setActiveCollection(collectionSlug ?? '')\n }\n }, [activeCollection, collectionSlug, setActiveCollection])\n\n const groupedFields = useMemo(() => {\n const result: Record<string, string[]> = {}\n\n for (const fullKey of Object.keys(instructions)) {\n const [collection, ...pathParts] = fullKey.split('.')\n const path = pathParts.join('.')\n if (!result[collection]) {\n result[collection] = []\n }\n result[collection].push(path)\n }\n\n return result\n }, [instructions])\n\n // Suggestions for prompt editor\n const promptEditorSuggestions = useMemo(() => {\n const activeFields = groupedFields[activeCollection as string] || []\n\n const suggestions: string[] = []\n\n activeFields.forEach((f) => {\n const fieldKey = Object.keys(instructions).find((k) => k.endsWith(f))\n const fieldInfo = fieldKey ? instructions[fieldKey] : undefined\n\n if (!fieldInfo) {return}\n\n if (fieldInfo.fieldType === 'upload') {\n suggestions.push(`${f}.url`)\n return\n }\n\n const helpers = handlebarsHelpers.filter(\n (h) => (handlebarsHelpersMap as Record<string, any>)[h]?.field === fieldInfo.fieldType,\n )\n\n if (helpers.length) {\n for (const helper of helpers) {\n suggestions.push(`${helper} ${f}`)\n }\n } else {\n suggestions.push(f)\n }\n }, [])\n\n promptFields.forEach(({ name, collections }) => {\n if (!activeCollection) {return}\n\n if (!collections || collections.includes(activeCollection)) {\n suggestions.push(name)\n }\n })\n\n return suggestions\n }, [groupedFields, activeCollection, instructions, promptFields])\n\n return {\n ...context,\n ...(instructions[schemaPath] || {}),\n promptEditorSuggestions,\n }\n}\n"],"names":["InstructionsContext","useDocumentInfo","useContext","useEffect","useMemo","useState","PLUGIN_INSTRUCTIONS_TABLE","handlebarsHelpers","handlebarsHelpersMap","useInstructions","update","context","collectionSlug","activeCollection","instructions","promptFields","setActiveCollection","schemaPath","setSchemaPath","groupedFields","result","fullKey","Object","keys","collection","pathParts","split","path","join","push","promptEditorSuggestions","activeFields","suggestions","forEach","f","fieldKey","find","k","endsWith","fieldInfo","undefined","fieldType","helpers","filter","h","field","length","helper","name","collections","includes"],"mappings":"AAAA,SAASA,mBAAmB,QAAQ,8BAA6B;AACjE,SAASC,eAAe,QAAQ,iBAAgB;AAChD,SAASC,UAAU,EAAEC,SAAS,EAAEC,OAAO,EAAEC,QAAQ,QAAQ,QAAO;AAEhE,SAASC,yBAAyB,QAAQ,oBAAmB;AAC7D,SAASC,iBAAiB,EAAEC,oBAAoB,QAAQ,2CAA0C;AAElG,OAAO,MAAMC,kBAAkB,CAC7BC,SAEI,CAAC,CAAC;IAEN,MAAMC,UAAUT,WAAWF;IAC3B,MAAM,EAAEY,cAAc,EAAE,GAAGX;IAC3B,MAAM,EAAEY,gBAAgB,EAAEC,YAAY,EAAEC,YAAY,EAAEC,mBAAmB,EAAE,GAAGL;IAE9E,MAAM,CAACM,YAAYC,cAAc,GAAGb,SAASK,OAAOO,UAAU;IAE9Dd,UAAU;QACR,IAAIO,OAAOO,UAAU,KAAKA,YAAY;YACpCC,cAAc,AAACR,OAAOO,UAAU,IAAe;QACjD;IACF,GAAG;QAACP,OAAOO,UAAU;KAAC;IAEtBd,UAAU;QACR,IACEU,qBAAqBD,kBACrBA,mBAAmBN,6BACnB,OAAOU,wBAAwB,YAC/B;YACAA,oBAAoBJ,kBAAkB;QACxC;IACF,GAAG;QAACC;QAAkBD;QAAgBI;KAAoB;IAE1D,MAAMG,gBAAgBf,QAAQ;QAC5B,MAAMgB,SAAmC,CAAC;QAE1C,KAAK,MAAMC,WAAWC,OAAOC,IAAI,CAACT,cAAe;YAC/C,MAAM,CAACU,YAAY,GAAGC,UAAU,GAAGJ,QAAQK,KAAK,CAAC;YACjD,MAAMC,OAAOF,UAAUG,IAAI,CAAC;YAC5B,IAAI,CAACR,MAAM,CAACI,WAAW,EAAE;gBACvBJ,MAAM,CAACI,WAAW,GAAG,EAAE;YACzB;YACAJ,MAAM,CAACI,WAAW,CAACK,IAAI,CAACF;QAC1B;QAEA,OAAOP;IACT,GAAG;QAACN;KAAa;IAEjB,gCAAgC;IAChC,MAAMgB,0BAA0B1B,QAAQ;QACtC,MAAM2B,eAAeZ,aAAa,CAACN,iBAA2B,IAAI,EAAE;QAEpE,MAAMmB,cAAwB,EAAE;QAEhCD,aAAaE,OAAO,CAAC,CAACC;YACpB,MAAMC,WAAWb,OAAOC,IAAI,CAACT,cAAcsB,IAAI,CAAC,CAACC,IAAMA,EAAEC,QAAQ,CAACJ;YAClE,MAAMK,YAAYJ,WAAWrB,YAAY,CAACqB,SAAS,GAAGK;YAEtD,IAAI,CAACD,WAAW;gBAAC;YAAM;YAEvB,IAAIA,UAAUE,SAAS,KAAK,UAAU;gBACpCT,YAAYH,IAAI,CAAC,GAAGK,EAAE,IAAI,CAAC;gBAC3B;YACF;YAEA,MAAMQ,UAAUnC,kBAAkBoC,MAAM,CACtC,CAACC,IAAM,AAACpC,oBAA4C,CAACoC,EAAE,EAAEC,UAAUN,UAAUE,SAAS;YAGxF,IAAIC,QAAQI,MAAM,EAAE;gBAClB,KAAK,MAAMC,UAAUL,QAAS;oBAC5BV,YAAYH,IAAI,CAAC,GAAGkB,OAAO,CAAC,EAAEb,GAAG;gBACnC;YACF,OAAO;gBACLF,YAAYH,IAAI,CAACK;YACnB;QACF,GAAG,EAAE;QAELnB,aAAakB,OAAO,CAAC,CAAC,EAAEe,IAAI,EAAEC,WAAW,EAAE;YACzC,IAAI,CAACpC,kBAAkB;gBAAC;YAAM;YAE9B,IAAI,CAACoC,eAAeA,YAAYC,QAAQ,CAACrC,mBAAmB;gBAC1DmB,YAAYH,IAAI,CAACmB;YACnB;QACF;QAEA,OAAOhB;IACT,GAAG;QAACb;QAAeN;QAAkBC;QAAcC;KAAa;IAEhE,OAAO;QACL,GAAGJ,OAAO;QACV,GAAIG,YAAY,CAACG,WAAW,IAAI,CAAC,CAAC;QAClCa;IACF;AACF,EAAC"}
1
+ {"version":3,"sources":["../../../src/providers/InstructionsProvider/useInstructions.ts"],"sourcesContent":["import { InstructionsContext } from '@ai-stack/payloadcms/client'\nimport { useDocumentInfo } from '@payloadcms/ui'\nimport { useContext, useEffect, useMemo, useState } from 'react'\n\nimport { PLUGIN_INSTRUCTIONS_TABLE } from '../../defaults.js'\nimport { handlebarsHelpers, handlebarsHelpersMap } from '../../libraries/handlebars/helpersMap.js'\n\n\nconst warnedOnceOnNoInstructionId = new Set<string>()\nconst warnOnceOnMissingInstructions = (path: string) => {\n if (!warnedOnceOnNoInstructionId.has(path)) {\n warnedOnceOnNoInstructionId.add(path)\n // eslint-disable-next-line no-console\n console.info(`[AI Plugin] There are no AI instructions for this field: ${path}. Enable \"generatePromptOnInit\" option to enable them.`)\n }\n}\n\nexport const useInstructions = (\n update: {\n schemaPath?: unknown\n } = {},\n) => {\n const context = useContext(InstructionsContext)\n const { collectionSlug } = useDocumentInfo()\n const { activeCollection, hasInstructions, instructions, promptFields, setActiveCollection, debugging } = context\n\n const [schemaPath, setSchemaPath] = useState(update.schemaPath as string)\n\n useEffect(() => {\n if (update.schemaPath !== schemaPath) {\n setSchemaPath((update.schemaPath as string) ?? '')\n }\n }, [update.schemaPath])\n\n useEffect(() => {\n if (\n activeCollection !== collectionSlug &&\n collectionSlug !== PLUGIN_INSTRUCTIONS_TABLE &&\n typeof setActiveCollection === 'function'\n ) {\n setActiveCollection(collectionSlug ?? '')\n }\n }, [activeCollection, collectionSlug, setActiveCollection])\n\n const groupedFields = useMemo(() => {\n const result: Record<string, string[]> = {}\n\n for (const fullKey of Object.keys(instructions || {})) {\n const [collection, ...pathParts] = fullKey.split('.')\n const path = pathParts.join('.')\n if (!result[collection]) {\n result[collection] = []\n }\n result[collection].push(path)\n }\n\n return result\n }, [instructions])\n\n // Suggestions for prompt editor\n const promptEditorSuggestions = useMemo(() => {\n const activeFields = groupedFields[activeCollection as string] || []\n\n const suggestions: string[] = []\n\n activeFields.forEach((f) => {\n const fieldKey = Object.keys(instructions).find((k) => k.endsWith(f))\n const fieldInfo = fieldKey ? instructions[fieldKey] : undefined\n\n if (!fieldInfo) {return}\n\n if (fieldInfo.fieldType === 'upload') {\n suggestions.push(`${f}.url`)\n return\n }\n\n const helpers = handlebarsHelpers.filter(\n (h) => (handlebarsHelpersMap as Record<string, any>)[h]?.field === fieldInfo.fieldType,\n )\n\n if (helpers.length) {\n for (const helper of helpers) {\n suggestions.push(`${helper} ${f}`)\n }\n } else {\n suggestions.push(f)\n }\n }, [])\n\n promptFields.forEach(({ name, collections }) => {\n if (!activeCollection) {return}\n\n if (!collections || collections.includes(activeCollection)) {\n suggestions.push(name)\n }\n })\n\n return suggestions\n }, [groupedFields, activeCollection, instructions, promptFields])\n\n const pathInstructions = instructions[schemaPath]\n\n if (debugging && !pathInstructions && schemaPath && hasInstructions) {\n warnOnceOnMissingInstructions(schemaPath)\n }\n \n return {\n ...context,\n ...(pathInstructions || {}),\n promptEditorSuggestions,\n }\n}\n"],"names":["InstructionsContext","useDocumentInfo","useContext","useEffect","useMemo","useState","PLUGIN_INSTRUCTIONS_TABLE","handlebarsHelpers","handlebarsHelpersMap","warnedOnceOnNoInstructionId","Set","warnOnceOnMissingInstructions","path","has","add","console","info","useInstructions","update","context","collectionSlug","activeCollection","hasInstructions","instructions","promptFields","setActiveCollection","debugging","schemaPath","setSchemaPath","groupedFields","result","fullKey","Object","keys","collection","pathParts","split","join","push","promptEditorSuggestions","activeFields","suggestions","forEach","f","fieldKey","find","k","endsWith","fieldInfo","undefined","fieldType","helpers","filter","h","field","length","helper","name","collections","includes","pathInstructions"],"mappings":"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"}
package/dist/types.d.ts CHANGED
@@ -1,7 +1,8 @@
1
1
  import type { JSONSchema } from 'openai/lib/jsonschema';
2
2
  import type { ImageGenerateParams } from 'openai/resources/images';
3
- import type { CollectionSlug, DataFromCollectionSlug, Endpoint, Field, File, GlobalConfig, GroupField, PayloadRequest } from 'payload';
3
+ import type { CollectionConfig, CollectionSlug, DataFromCollectionSlug, Endpoint, Field, File, GlobalConfig, GroupField, PayloadRequest, TypedCollection } from 'payload';
4
4
  import type { CSSProperties, MouseEventHandler } from 'react';
5
+ import type { PLUGIN_INSTRUCTIONS_TABLE } from "./defaults.js";
5
6
  export interface PluginConfigAccess {
6
7
  /**
7
8
  * Control access to AI generation features (generate text, images, audio)
@@ -57,6 +58,7 @@ export interface PluginConfig {
57
58
  interfaceName?: string;
58
59
  mediaUpload?: PluginConfigMediaUploadFunction;
59
60
  options?: PluginOptions;
61
+ overrideInstructions?: Partial<CollectionConfig>;
60
62
  promptFields?: PromptField[];
61
63
  /**
62
64
  * Custom action prompts for AI text generation
@@ -115,10 +117,15 @@ export type SeedPromptOptions = {
115
117
  fieldType: string;
116
118
  path: string;
117
119
  };
118
- export type SeedPromptFunction = (options: SeedPromptOptions) => {
120
+ export type SeedPromptData = Omit<TypedCollection[typeof PLUGIN_INSTRUCTIONS_TABLE], 'createdAt' | 'id' | 'updatedAt'>;
121
+ export type SeedPromptResult = {
122
+ data?: SeedPromptData;
119
123
  prompt: string;
120
124
  system: string;
121
- };
125
+ } | {
126
+ data?: SeedPromptData;
127
+ } | false | undefined | void;
128
+ export type SeedPromptFunction = (options: SeedPromptOptions) => Promise<SeedPromptResult> | SeedPromptResult;
122
129
  export type ActionMenuEvents = 'onCompose' | 'onExpand' | 'onProofread' | 'onRephrase' | 'onSettings' | 'onSimplify' | 'onSummarize' | 'onTone' | 'onTranslate';
123
130
  export type UseMenuEvents = {
124
131
  [key in ActionMenuEvents]?: (data?: unknown) => void;
package/dist/types.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/types.ts"],"sourcesContent":["import type { JSONSchema } from 'openai/lib/jsonschema'\nimport type { ImageGenerateParams } from 'openai/resources/images'\nimport type {\n CollectionSlug,\n DataFromCollectionSlug,\n Endpoint,\n Field,\n File,\n GlobalConfig,\n GroupField,\n PayloadRequest,\n} from 'payload'\nimport type { CSSProperties, MouseEventHandler } from 'react'\n\nexport interface PluginConfigAccess {\n /**\n * Control access to AI generation features (generate text, images, audio)\n * @default () => !!req.user (requires authentication)\n */\n generate?: ({ req }: { req: PayloadRequest }) => Promise<boolean> | boolean\n /**\n * Control access to AI settings/configuration\n * @default () => !!req.user (requires authentication)\n */\n settings?: ({ req }: { req: PayloadRequest }) => Promise<boolean> | boolean\n}\n\nexport interface PluginOptions {\n /**\n * Provide local tags to filter language options from the Translate Menu\n * Check for the available local tags,\n * visit: https://www.npmjs.com/package/locale-codes\n * Example: [\"en-US\", \"zh-SG\", \"zh-CN\", \"en\"]\n */\n enabledLanguages?: string[]\n}\n\nexport type PluginConfigMediaUploadFunction = (\n result: { data: Record<any, any>; file: File },\n {\n collection,\n request,\n }: {\n collection: CollectionSlug\n request: PayloadRequest\n },\n) => Promise<DataFromCollectionSlug<CollectionSlug>>\n\nexport interface PluginConfig {\n /**\n * Access control configuration for AI features\n * By default, all AI features require authentication\n */\n access?: PluginConfigAccess\n collections: {\n [key: CollectionSlug]: boolean\n }\n debugging?: boolean\n disableSponsorMessage?: boolean\n editorConfig?: { nodes: JSONSchema[] }\n fields?: Field[]\n generatePromptOnInit?: boolean\n generationModels?: ((defaultModels: GenerationModel[]) => GenerationModel[]) | GenerationModel[]\n globals?: {\n [key: GlobalConfig['slug']]: boolean\n }\n interfaceName?: string\n mediaUpload?: PluginConfigMediaUploadFunction\n options?: PluginOptions\n promptFields?: PromptField[]\n /**\n * Custom action prompts for AI text generation\n * If not provided, uses default prompts\n * You can access default prompts by importing { defaultPrompts } from '@ai-stack/payloadcms'\n */\n prompts?: ActionPrompt[]\n /**\n * Custom seed prompt function for generating field-specific prompts\n * If not provided, uses default seed prompt function\n * You can access default seed prompts by importing { defaultSeedPrompts } from '@ai-stack/payloadcms'\n */\n seedPrompts?: SeedPromptFunction\n uploadCollectionSlug?: CollectionSlug\n}\n\nexport interface GenerationModel {\n fields: string[]\n generateText?: (prompt: string, system: string) => Promise<string>\n handler?: (prompt: string, options: any) => Promise<any> | Response\n id: string\n name: string\n output: 'audio' | 'file' | 'image' | 'json' | 'text' | 'video'\n settings?: GroupField\n supportsPromptOptimization?: boolean\n}\n\nexport interface GenerationConfig {\n models: GenerationModel[]\n provider: string\n}\n\nexport type GenerateTextarea<T = any> = (args: {\n collectionSlug: CollectionSlug\n doc: T\n documentId?: number | string\n locale?: string\n options?: any\n}) => Promise<string> | string\n\nexport interface Endpoints {\n textarea: Omit<Endpoint, 'root'>\n upload: Omit<Endpoint, 'root'>\n}\n\nexport type ActionMenuItems =\n | 'Compose'\n | 'Expand'\n | 'Proofread'\n | 'Rephrase'\n | 'Settings'\n | 'Simplify'\n | 'Summarize'\n | 'Tone'\n | 'Translate'\n\nexport type ActionPromptOptions = {\n layout?: string\n locale?: string\n prompt?: string\n systemPrompt?: string\n}\n\nexport type ActionPrompt = {\n layout?: (options?: ActionPromptOptions) => string\n name: ActionMenuItems\n system: (options: ActionPromptOptions) => string\n}\n\nexport type SeedPromptOptions = {\n fieldLabel: string\n fieldSchemaPaths: Record<string, any>\n fieldType: string\n path: string\n}\n\nexport type SeedPromptFunction = (options: SeedPromptOptions) => {\n prompt: string\n system: string\n}\n\nexport type ActionMenuEvents =\n | 'onCompose'\n | 'onExpand'\n | 'onProofread'\n | 'onRephrase'\n | 'onSettings'\n | 'onSimplify'\n | 'onSummarize'\n | 'onTone'\n | 'onTranslate'\n\nexport type UseMenuEvents = {\n [key in ActionMenuEvents]?: (data?: unknown) => void\n}\n\nexport type UseMenuOptions = {\n isConfigAllowed: boolean\n}\n\nexport type BaseItemProps<T = any> = {\n children?: React.ReactNode\n disabled?: boolean\n hideIcon?: boolean\n isActive?: boolean\n isMenu?: boolean\n onClick: (data?: unknown) => void\n onMouseEnter?: MouseEventHandler<T> | undefined\n onMouseLeave?: MouseEventHandler<T> | undefined\n style?: CSSProperties | undefined\n title?: string\n}\n\nexport type ImageReference = {\n data: Blob\n name: string\n size: number\n type: string\n url: string\n}\n\nexport type GenerateImageParams = {\n images?: ImageReference[]\n size?: ImageGenerateParams['size']\n style?: ImageGenerateParams['style']\n version?: ImageGenerateParams['model']\n}\n\nexport type SerializedPromptField = {\n collections?: (CollectionSlug)[]\n name: string\n}\n\nexport type PromptFieldGetterContext = {\n collection: CollectionSlug\n type: string\n}\n\nexport type PromptField = {\n // If not provided, the value will be returned from the data object as-is\n getter?: (data: object, ctx: PromptFieldGetterContext) => Promise<string> | string\n} & SerializedPromptField\n"],"names":[],"mappings":"AA+MA,WAGyB"}
1
+ {"version":3,"sources":["../src/types.ts"],"sourcesContent":["import type { JSONSchema } from 'openai/lib/jsonschema'\nimport type { ImageGenerateParams } from 'openai/resources/images'\nimport type {\n CollectionConfig,\n CollectionSlug,\n DataFromCollectionSlug,\n Endpoint,\n Field,\n File,\n GlobalConfig,\n GroupField,\n PayloadRequest,\n TypedCollection,\n} from 'payload'\nimport type { CSSProperties, MouseEventHandler } from 'react'\n\nimport type {PLUGIN_INSTRUCTIONS_TABLE} from \"./defaults.js\";\n\nexport interface PluginConfigAccess {\n /**\n * Control access to AI generation features (generate text, images, audio)\n * @default () => !!req.user (requires authentication)\n */\n generate?: ({ req }: { req: PayloadRequest }) => Promise<boolean> | boolean\n /**\n * Control access to AI settings/configuration\n * @default () => !!req.user (requires authentication)\n */\n settings?: ({ req }: { req: PayloadRequest }) => Promise<boolean> | boolean\n}\n\nexport interface PluginOptions {\n /**\n * Provide local tags to filter language options from the Translate Menu\n * Check for the available local tags,\n * visit: https://www.npmjs.com/package/locale-codes\n * Example: [\"en-US\", \"zh-SG\", \"zh-CN\", \"en\"]\n */\n enabledLanguages?: string[]\n}\n\nexport type PluginConfigMediaUploadFunction = (\n result: { data: Record<any, any>; file: File },\n {\n collection,\n request,\n }: {\n collection: CollectionSlug\n request: PayloadRequest\n },\n) => Promise<DataFromCollectionSlug<CollectionSlug>>\n\nexport interface PluginConfig {\n /**\n * Access control configuration for AI features\n * By default, all AI features require authentication\n */\n access?: PluginConfigAccess\n collections: {\n [key: CollectionSlug]: boolean\n }\n debugging?: boolean\n disableSponsorMessage?: boolean\n editorConfig?: { nodes: JSONSchema[] }\n fields?: Field[]\n generatePromptOnInit?: boolean\n generationModels?: ((defaultModels: GenerationModel[]) => GenerationModel[]) | GenerationModel[]\n globals?: {\n [key: GlobalConfig['slug']]: boolean\n }\n interfaceName?: string\n mediaUpload?: PluginConfigMediaUploadFunction\n options?: PluginOptions\n // Override the instructions collection config\n overrideInstructions?: Partial<CollectionConfig>\n promptFields?: PromptField[]\n /**\n * Custom action prompts for AI text generation\n * If not provided, uses default prompts\n * You can access default prompts by importing { defaultPrompts } from '@ai-stack/payloadcms'\n */\n prompts?: ActionPrompt[]\n /**\n * Custom seed prompt function for generating field-specific prompts\n * If not provided, uses default seed prompt function\n * You can access default seed prompts by importing { defaultSeedPrompts } from '@ai-stack/payloadcms'\n */\n seedPrompts?: SeedPromptFunction\n uploadCollectionSlug?: CollectionSlug\n}\n\nexport interface GenerationModel {\n fields: string[]\n generateText?: (prompt: string, system: string) => Promise<string>\n handler?: (prompt: string, options: any) => Promise<any> | Response\n id: string\n name: string\n output: 'audio' | 'file' | 'image' | 'json' | 'text' | 'video'\n settings?: GroupField\n supportsPromptOptimization?: boolean\n}\n\nexport interface GenerationConfig {\n models: GenerationModel[]\n provider: string\n}\n\nexport type GenerateTextarea<T = any> = (args: {\n collectionSlug: CollectionSlug\n doc: T\n documentId?: number | string\n locale?: string\n options?: any\n}) => Promise<string> | string\n\nexport interface Endpoints {\n textarea: Omit<Endpoint, 'root'>\n upload: Omit<Endpoint, 'root'>\n}\n\nexport type ActionMenuItems =\n | 'Compose'\n | 'Expand'\n | 'Proofread'\n | 'Rephrase'\n | 'Settings'\n | 'Simplify'\n | 'Summarize'\n | 'Tone'\n | 'Translate'\n\nexport type ActionPromptOptions = {\n layout?: string\n locale?: string\n prompt?: string\n systemPrompt?: string\n}\n\nexport type ActionPrompt = {\n layout?: (options?: ActionPromptOptions) => string\n name: ActionMenuItems\n system: (options: ActionPromptOptions) => string\n}\n\nexport type SeedPromptOptions = {\n fieldLabel: string\n fieldSchemaPaths: Record<string, any>\n fieldType: string\n path: string\n}\n\nexport type SeedPromptData = Omit<TypedCollection[typeof PLUGIN_INSTRUCTIONS_TABLE], 'createdAt' | 'id' | 'updatedAt'>\n\nexport type SeedPromptResult = {\n data?: SeedPromptData\n prompt: string\n system: string\n} | {\n data?: SeedPromptData\n} | false | undefined | void\n\nexport type SeedPromptFunction = (options: SeedPromptOptions) => Promise<SeedPromptResult> | SeedPromptResult\n\nexport type ActionMenuEvents =\n | 'onCompose'\n | 'onExpand'\n | 'onProofread'\n | 'onRephrase'\n | 'onSettings'\n | 'onSimplify'\n | 'onSummarize'\n | 'onTone'\n | 'onTranslate'\n\nexport type UseMenuEvents = {\n [key in ActionMenuEvents]?: (data?: unknown) => void\n}\n\nexport type UseMenuOptions = {\n isConfigAllowed: boolean\n}\n\nexport type BaseItemProps<T = any> = {\n children?: React.ReactNode\n disabled?: boolean\n hideIcon?: boolean\n isActive?: boolean\n isMenu?: boolean\n onClick: (data?: unknown) => void\n onMouseEnter?: MouseEventHandler<T> | undefined\n onMouseLeave?: MouseEventHandler<T> | undefined\n style?: CSSProperties | undefined\n title?: string\n}\n\nexport type ImageReference = {\n data: Blob\n name: string\n size: number\n type: string\n url: string\n}\n\nexport type GenerateImageParams = {\n images?: ImageReference[]\n size?: ImageGenerateParams['size']\n style?: ImageGenerateParams['style']\n version?: ImageGenerateParams['model']\n}\n\nexport type SerializedPromptField = {\n collections?: (CollectionSlug)[]\n name: string\n}\n\nexport type PromptFieldGetterContext = {\n collection: CollectionSlug\n type: string\n}\n\nexport type PromptField = {\n // If not provided, the value will be returned from the data object as-is\n getter?: (data: object, ctx: PromptFieldGetterContext) => Promise<string> | string\n} & SerializedPromptField\n"],"names":[],"mappings":"AA4NA,WAGyB"}
@@ -1,7 +1,7 @@
1
1
  'use client';
2
2
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
3
  import { useEditorConfigContext } from '@payloadcms/richtext-lexical/client';
4
- import { FieldDescription, Popup, useDocumentDrawer, useField } from '@payloadcms/ui';
4
+ import { Popup, useDocumentDrawer, useField } from '@payloadcms/ui';
5
5
  import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react';
6
6
  import { PLUGIN_INSTRUCTIONS_TABLE } from '../../defaults.js';
7
7
  import { setSafeLexicalState } from '../../utilities/setSafeLexicalState.js';
@@ -201,37 +201,28 @@ export const Compose = ({ descriptionProps, instructionId, isConfigAllowed })=>{
201
201
  isProcessing,
202
202
  isLoading
203
203
  ]);
204
- return /*#__PURE__*/ _jsxs(React.Fragment, {
204
+ return /*#__PURE__*/ _jsxs("label", {
205
+ className: `payloadai-compose__actions ${styles.actions}`,
206
+ onClick: (e)=>e.preventDefault(),
207
+ ref: actionsRef,
208
+ role: "presentation",
205
209
  children: [
206
- /*#__PURE__*/ _jsxs("label", {
207
- className: `${styles.actions}`,
208
- onClick: (e)=>e.preventDefault(),
209
- ref: actionsRef,
210
- role: "presentation",
211
- children: [
212
- /*#__PURE__*/ _jsx(DocumentDrawer, {
213
- onSave: ()=>{
214
- closeDrawer();
215
- }
216
- }),
217
- memoizedPopup,
218
- /*#__PURE__*/ _jsx(ActiveComponent, {
219
- isLoading: isProcessing || isLoading,
220
- stop: stop
221
- }),
222
- /*#__PURE__*/ _jsx(UndoRedoActions, {
223
- onChange: (val)=>{
224
- setValue(val);
225
- setIfValueIsLexicalState(val);
226
- }
227
- })
228
- ]
210
+ /*#__PURE__*/ _jsx(DocumentDrawer, {
211
+ onSave: ()=>{
212
+ closeDrawer();
213
+ }
214
+ }),
215
+ memoizedPopup,
216
+ /*#__PURE__*/ _jsx(ActiveComponent, {
217
+ isLoading: isProcessing || isLoading,
218
+ stop: stop
229
219
  }),
230
- descriptionProps ? /*#__PURE__*/ _jsx("div", {
231
- children: /*#__PURE__*/ _jsx(FieldDescription, {
232
- ...descriptionProps
233
- })
234
- }) : null
220
+ /*#__PURE__*/ _jsx(UndoRedoActions, {
221
+ onChange: (val)=>{
222
+ setValue(val);
223
+ setIfValueIsLexicalState(val);
224
+ }
225
+ })
235
226
  ]
236
227
  });
237
228
  };