@payloadcms/plugin-seo 3.0.0-canary.a192632 → 3.0.0-canary.a6e7305
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/fields/MetaDescription/MetaDescriptionComponent.d.ts +3 -3
- package/dist/fields/MetaDescription/MetaDescriptionComponent.d.ts.map +1 -1
- package/dist/fields/MetaDescription/MetaDescriptionComponent.js +37 -12
- package/dist/fields/MetaDescription/MetaDescriptionComponent.js.map +1 -1
- package/dist/fields/MetaImage/MetaImageComponent.d.ts +3 -3
- package/dist/fields/MetaImage/MetaImageComponent.d.ts.map +1 -1
- package/dist/fields/MetaImage/MetaImageComponent.js +40 -16
- package/dist/fields/MetaImage/MetaImageComponent.js.map +1 -1
- package/dist/fields/MetaTitle/MetaTitleComponent.d.ts +3 -3
- package/dist/fields/MetaTitle/MetaTitleComponent.d.ts.map +1 -1
- package/dist/fields/MetaTitle/MetaTitleComponent.js +37 -12
- package/dist/fields/MetaTitle/MetaTitleComponent.js.map +1 -1
- package/dist/fields/Overview/OverviewComponent.d.ts +8 -0
- package/dist/fields/Overview/OverviewComponent.d.ts.map +1 -1
- package/dist/fields/Overview/OverviewComponent.js +13 -7
- package/dist/fields/Overview/OverviewComponent.js.map +1 -1
- package/dist/fields/Overview/index.d.ts +8 -0
- package/dist/fields/Overview/index.d.ts.map +1 -1
- package/dist/fields/Overview/index.js +3 -1
- package/dist/fields/Overview/index.js.map +1 -1
- package/dist/fields/Preview/PreviewComponent.d.ts +3 -3
- package/dist/fields/Preview/PreviewComponent.d.ts.map +1 -1
- package/dist/fields/Preview/PreviewComponent.js +23 -9
- package/dist/fields/Preview/PreviewComponent.js.map +1 -1
- package/dist/fields/index.scss +5 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +61 -30
- package/dist/index.js.map +1 -1
- package/dist/translations/cs.d.ts +3 -0
- package/dist/translations/cs.d.ts.map +1 -0
- package/dist/translations/cs.js +25 -0
- package/dist/translations/cs.js.map +1 -0
- package/dist/translations/de.d.ts +3 -0
- package/dist/translations/de.d.ts.map +1 -0
- package/dist/translations/de.js +25 -0
- package/dist/translations/de.js.map +1 -0
- package/dist/translations/en.d.ts +3 -0
- package/dist/translations/en.d.ts.map +1 -0
- package/dist/translations/en.js +25 -0
- package/dist/translations/en.js.map +1 -0
- package/dist/translations/es.d.ts +3 -0
- package/dist/translations/es.d.ts.map +1 -0
- package/dist/translations/es.js +25 -0
- package/dist/translations/es.js.map +1 -0
- package/dist/translations/fa.d.ts +3 -0
- package/dist/translations/fa.d.ts.map +1 -0
- package/dist/translations/fa.js +25 -0
- package/dist/translations/fa.js.map +1 -0
- package/dist/translations/fr.d.ts +3 -0
- package/dist/translations/fr.d.ts.map +1 -0
- package/dist/translations/fr.js +25 -0
- package/dist/translations/fr.js.map +1 -0
- package/dist/translations/index.d.ts +15 -178
- package/dist/translations/index.d.ts.map +1 -1
- package/dist/translations/index.js +26 -176
- package/dist/translations/index.js.map +1 -1
- package/dist/translations/it.d.ts +3 -0
- package/dist/translations/it.d.ts.map +1 -0
- package/dist/translations/it.js +25 -0
- package/dist/translations/it.js.map +1 -0
- package/dist/translations/nb.d.ts +3 -0
- package/dist/translations/nb.d.ts.map +1 -0
- package/dist/translations/nb.js +25 -0
- package/dist/translations/nb.js.map +1 -0
- package/dist/translations/pl.d.ts +3 -0
- package/dist/translations/pl.d.ts.map +1 -0
- package/dist/translations/pl.js +25 -0
- package/dist/translations/pl.js.map +1 -0
- package/dist/translations/ru.d.ts +3 -0
- package/dist/translations/ru.d.ts.map +1 -0
- package/dist/translations/ru.js +25 -0
- package/dist/translations/ru.js.map +1 -0
- package/dist/translations/sv.d.ts +3 -0
- package/dist/translations/sv.d.ts.map +1 -0
- package/dist/translations/sv.js +25 -0
- package/dist/translations/sv.js.map +1 -0
- package/dist/translations/tr.d.ts +3 -0
- package/dist/translations/tr.d.ts.map +1 -0
- package/dist/translations/tr.js +25 -0
- package/dist/translations/tr.js.map +1 -0
- package/dist/translations/translation-schema.json +5 -1
- package/dist/translations/uk.d.ts +3 -0
- package/dist/translations/uk.d.ts.map +1 -0
- package/dist/translations/uk.js +25 -0
- package/dist/translations/uk.js.map +1 -0
- package/dist/translations/vi.d.ts +3 -0
- package/dist/translations/vi.d.ts.map +1 -0
- package/dist/translations/vi.js +25 -0
- package/dist/translations/vi.js.map +1 -0
- package/dist/types.d.ts +44 -11
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js.map +1 -1
- package/dist/ui/LengthIndicator.js +1 -1
- package/dist/ui/LengthIndicator.js.map +1 -1
- package/package.json +17 -17
- package/dist/translations/en.json +0 -22
- package/dist/translations/es.json +0 -22
- package/dist/translations/fa.json +0 -22
- package/dist/translations/fr.json +0 -22
- package/dist/translations/pl.json +0 -22
- package/dist/translations/ru.json +0 -22
- package/dist/translations/uk.json +0 -22
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { TextareaFieldClientProps } from 'payload';
|
|
2
2
|
import React from 'react';
|
|
3
3
|
type MetaDescriptionProps = {
|
|
4
|
-
hasGenerateDescriptionFn: boolean;
|
|
5
|
-
} &
|
|
4
|
+
readonly hasGenerateDescriptionFn: boolean;
|
|
5
|
+
} & TextareaFieldClientProps;
|
|
6
6
|
export declare const MetaDescriptionComponent: React.FC<MetaDescriptionProps>;
|
|
7
7
|
export {};
|
|
8
8
|
//# sourceMappingURL=MetaDescriptionComponent.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MetaDescriptionComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/MetaDescription/MetaDescriptionComponent.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,
|
|
1
|
+
{"version":3,"file":"MetaDescriptionComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/MetaDescription/MetaDescriptionComponent.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,SAAS,CAAA;AAavD,OAAO,KAAsB,MAAM,OAAO,CAAA;AAU1C,KAAK,oBAAoB,GAAG;IAC1B,QAAQ,CAAC,wBAAwB,EAAE,OAAO,CAAA;CAC3C,GAAG,wBAAwB,CAAA;AAE5B,eAAO,MAAM,wBAAwB,EAAE,KAAK,CAAC,EAAE,CAAC,oBAAoB,CAwLnE,CAAA"}
|
|
@@ -1,30 +1,42 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
-
import { FieldLabel, TextareaInput, useDocumentInfo, useField, useFieldProps, useForm, useLocale, useTranslation } from '@payloadcms/ui';
|
|
3
|
+
import { FieldLabel, TextareaInput, useConfig, useDocumentInfo, useField, useFieldProps, useForm, useLocale, useTranslation } from '@payloadcms/ui';
|
|
4
4
|
import React, { useCallback } from 'react';
|
|
5
5
|
import { defaults } from '../../defaults.js';
|
|
6
6
|
import { LengthIndicator } from '../../ui/LengthIndicator.js';
|
|
7
|
-
const { maxLength, minLength } = defaults.description;
|
|
7
|
+
const { maxLength: maxLengthDefault, minLength: minLengthDefault } = defaults.description;
|
|
8
8
|
export const MetaDescriptionComponent = (props)=>{
|
|
9
|
-
const { field: { admin: { components: { Label } }, label, required }, hasGenerateDescriptionFn, labelProps } = props;
|
|
9
|
+
const { field: { admin: { components: { afterInput, beforeInput, Label } }, label, maxLength: maxLengthFromProps, minLength: minLengthFromProps, required }, field: fieldFromProps, hasGenerateDescriptionFn, labelProps } = props;
|
|
10
10
|
const { path: pathFromContext } = useFieldProps();
|
|
11
|
+
const { config: { routes: { api }, serverURL } } = useConfig();
|
|
11
12
|
const { t } = useTranslation();
|
|
12
13
|
const locale = useLocale();
|
|
13
14
|
const { getData } = useForm();
|
|
14
15
|
const docInfo = useDocumentInfo();
|
|
16
|
+
const maxLength = maxLengthFromProps || maxLengthDefault;
|
|
17
|
+
const minLength = minLengthFromProps || minLengthDefault;
|
|
15
18
|
const field = useField({
|
|
16
19
|
path: pathFromContext
|
|
17
20
|
});
|
|
18
21
|
const { errorMessage, setValue, showError, value } = field;
|
|
19
22
|
const regenerateDescription = useCallback(async ()=>{
|
|
20
|
-
if (!hasGenerateDescriptionFn)
|
|
21
|
-
|
|
23
|
+
if (!hasGenerateDescriptionFn) {
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
const endpoint = `${serverURL}${api}/plugin-seo/generate-description`;
|
|
27
|
+
const genDescriptionResponse = await fetch(endpoint, {
|
|
22
28
|
body: JSON.stringify({
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
29
|
+
id: docInfo.id,
|
|
30
|
+
collectionSlug: docInfo.collectionSlug,
|
|
31
|
+
doc: getData(),
|
|
32
|
+
docPermissions: docInfo.docPermissions,
|
|
33
|
+
globalSlug: docInfo.globalSlug,
|
|
34
|
+
hasPublishPermission: docInfo.hasPublishPermission,
|
|
35
|
+
hasSavePermission: docInfo.hasSavePermission,
|
|
36
|
+
initialData: docInfo.initialData,
|
|
37
|
+
initialState: docInfo.initialState,
|
|
38
|
+
locale: typeof locale === 'object' ? locale?.code : locale,
|
|
39
|
+
title: docInfo.title
|
|
28
40
|
}),
|
|
29
41
|
credentials: 'include',
|
|
30
42
|
headers: {
|
|
@@ -36,7 +48,17 @@ export const MetaDescriptionComponent = (props)=>{
|
|
|
36
48
|
setValue(generatedDescription || '');
|
|
37
49
|
}, [
|
|
38
50
|
hasGenerateDescriptionFn,
|
|
39
|
-
|
|
51
|
+
serverURL,
|
|
52
|
+
api,
|
|
53
|
+
docInfo.id,
|
|
54
|
+
docInfo.collectionSlug,
|
|
55
|
+
docInfo.docPermissions,
|
|
56
|
+
docInfo.globalSlug,
|
|
57
|
+
docInfo.hasPublishPermission,
|
|
58
|
+
docInfo.hasSavePermission,
|
|
59
|
+
docInfo.initialData,
|
|
60
|
+
docInfo.initialState,
|
|
61
|
+
docInfo.title,
|
|
40
62
|
getData,
|
|
41
63
|
locale,
|
|
42
64
|
setValue
|
|
@@ -56,8 +78,10 @@ export const MetaDescriptionComponent = (props)=>{
|
|
|
56
78
|
className: "plugin-seo__field",
|
|
57
79
|
children: [
|
|
58
80
|
/*#__PURE__*/ _jsx(FieldLabel, {
|
|
81
|
+
field: fieldFromProps,
|
|
59
82
|
Label: Label,
|
|
60
83
|
label: label,
|
|
84
|
+
required: required,
|
|
61
85
|
...labelProps || {}
|
|
62
86
|
}),
|
|
63
87
|
hasGenerateDescriptionFn && /*#__PURE__*/ _jsxs(React.Fragment, {
|
|
@@ -108,12 +132,13 @@ export const MetaDescriptionComponent = (props)=>{
|
|
|
108
132
|
position: 'relative'
|
|
109
133
|
},
|
|
110
134
|
children: /*#__PURE__*/ _jsx(TextareaInput, {
|
|
135
|
+
afterInput: afterInput,
|
|
136
|
+
beforeInput: beforeInput,
|
|
111
137
|
Error: {
|
|
112
138
|
type: 'client',
|
|
113
139
|
Component: null,
|
|
114
140
|
RenderedComponent: errorMessage
|
|
115
141
|
},
|
|
116
|
-
label: label,
|
|
117
142
|
onChange: setValue,
|
|
118
143
|
path: pathFromContext,
|
|
119
144
|
required: required,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../src/fields/MetaDescription/MetaDescriptionComponent.tsx"],"sourcesContent":["'use client'\n\nimport type { FieldType, Options } from '@payloadcms/ui'\nimport type { TextareaFieldProps } from 'payload'\n\nimport {\n FieldLabel,\n TextareaInput,\n useDocumentInfo,\n useField,\n useFieldProps,\n useForm,\n useLocale,\n useTranslation,\n} from '@payloadcms/ui'\nimport React, { useCallback } from 'react'\n\nimport type { PluginSEOTranslationKeys, PluginSEOTranslations } from '../../translations/index.js'\nimport type { GenerateDescription } from '../../types.js'\n\nimport { defaults } from '../../defaults.js'\nimport { LengthIndicator } from '../../ui/LengthIndicator.js'\n\nconst { maxLength, minLength } = defaults.description\n\ntype MetaDescriptionProps = {\n hasGenerateDescriptionFn: boolean\n} & TextareaFieldProps\n\nexport const MetaDescriptionComponent: React.FC<MetaDescriptionProps> = (props) => {\n const {\n field: {\n admin: {\n components: { Label },\n },\n label,\n required,\n },\n hasGenerateDescriptionFn,\n labelProps,\n } = props\n const { path: pathFromContext } = useFieldProps()\n\n const { t } = useTranslation<PluginSEOTranslations, PluginSEOTranslationKeys>()\n\n const locale = useLocale()\n const { getData } = useForm()\n const docInfo = useDocumentInfo()\n\n const field: FieldType<string> = useField({\n path: pathFromContext,\n } as Options)\n\n const { errorMessage, setValue, showError, value } = field\n\n const regenerateDescription = useCallback(async () => {\n if (!hasGenerateDescriptionFn) return\n\n const genDescriptionResponse = await fetch('/api/plugin-seo/generate-description', {\n body: JSON.stringify({\n ...docInfo,\n doc: { ...getData() },\n locale: typeof locale === 'object' ? locale?.code : locale,\n } satisfies Parameters<GenerateDescription>[0]),\n credentials: 'include',\n headers: {\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n })\n\n const { result: generatedDescription } = await genDescriptionResponse.json()\n\n setValue(generatedDescription || '')\n }, [hasGenerateDescriptionFn, docInfo, getData, locale, setValue])\n\n return (\n <div\n style={{\n marginBottom: '20px',\n }}\n >\n <div\n style={{\n marginBottom: '5px',\n position: 'relative',\n }}\n >\n <div className=\"plugin-seo__field\">\n <FieldLabel Label={Label} label={label} {...(labelProps || {})} />\n {hasGenerateDescriptionFn && (\n <React.Fragment>\n — \n <button\n onClick={() => {\n void regenerateDescription()\n }}\n style={{\n background: 'none',\n backgroundColor: 'transparent',\n border: 'none',\n color: 'currentcolor',\n cursor: 'pointer',\n padding: 0,\n textDecoration: 'underline',\n }}\n type=\"button\"\n >\n {t('plugin-seo:autoGenerate')}\n </button>\n </React.Fragment>\n )}\n </div>\n <div\n style={{\n color: '#9A9A9A',\n }}\n >\n {t('plugin-seo:lengthTipDescription', { maxLength, minLength })}\n <a\n href=\"https://developers.google.com/search/docs/advanced/appearance/snippet#meta-descriptions\"\n rel=\"noopener noreferrer\"\n target=\"_blank\"\n >\n {t('plugin-seo:bestPractices')}\n </a>\n </div>\n </div>\n <div\n style={{\n marginBottom: '10px',\n position: 'relative',\n }}\n >\n <TextareaInput\n Error={{\n type: 'client',\n Component: null,\n RenderedComponent: errorMessage,\n }}\n label={label}\n onChange={setValue}\n path={pathFromContext}\n required={required}\n showError={showError}\n style={{\n marginBottom: 0,\n }}\n value={value}\n />\n </div>\n <div\n style={{\n alignItems: 'center',\n display: 'flex',\n width: '100%',\n }}\n >\n <LengthIndicator maxLength={maxLength} minLength={minLength} text={value} />\n </div>\n </div>\n )\n}\n"],"names":["FieldLabel","TextareaInput","useDocumentInfo","useField","useFieldProps","useForm","useLocale","useTranslation","React","useCallback","defaults","LengthIndicator","maxLength","minLength","description","MetaDescriptionComponent","props","field","admin","components","Label","label","required","hasGenerateDescriptionFn","labelProps","path","pathFromContext","t","locale","getData","docInfo","errorMessage","setValue","showError","value","regenerateDescription","genDescriptionResponse","fetch","body","JSON","stringify","doc","code","credentials","headers","method","result","generatedDescription","json","div","style","marginBottom","position","className","Fragment","button","onClick","background","backgroundColor","border","color","cursor","padding","textDecoration","type","a","href","rel","target","Error","Component","RenderedComponent","onChange","alignItems","display","width","text"],"mappings":"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"}
|
|
1
|
+
{"version":3,"sources":["../../../src/fields/MetaDescription/MetaDescriptionComponent.tsx"],"sourcesContent":["'use client'\n\nimport type { FieldType, Options } from '@payloadcms/ui'\nimport type { TextareaFieldClientProps } from 'payload'\n\nimport {\n FieldLabel,\n TextareaInput,\n useConfig,\n useDocumentInfo,\n useField,\n useFieldProps,\n useForm,\n useLocale,\n useTranslation,\n} from '@payloadcms/ui'\nimport React, { useCallback } from 'react'\n\nimport type { PluginSEOTranslationKeys, PluginSEOTranslations } from '../../translations/index.js'\nimport type { GenerateDescription } from '../../types.js'\n\nimport { defaults } from '../../defaults.js'\nimport { LengthIndicator } from '../../ui/LengthIndicator.js'\n\nconst { maxLength: maxLengthDefault, minLength: minLengthDefault } = defaults.description\n\ntype MetaDescriptionProps = {\n readonly hasGenerateDescriptionFn: boolean\n} & TextareaFieldClientProps\n\nexport const MetaDescriptionComponent: React.FC<MetaDescriptionProps> = (props) => {\n const {\n field: {\n admin: {\n components: { afterInput, beforeInput, Label },\n },\n label,\n maxLength: maxLengthFromProps,\n minLength: minLengthFromProps,\n required,\n },\n field: fieldFromProps,\n hasGenerateDescriptionFn,\n labelProps,\n } = props\n const { path: pathFromContext } = useFieldProps()\n\n const {\n config: {\n routes: { api },\n serverURL,\n },\n } = useConfig()\n\n const { t } = useTranslation<PluginSEOTranslations, PluginSEOTranslationKeys>()\n\n const locale = useLocale()\n const { getData } = useForm()\n const docInfo = useDocumentInfo()\n\n const maxLength = maxLengthFromProps || maxLengthDefault\n const minLength = minLengthFromProps || minLengthDefault\n\n const field: FieldType<string> = useField({\n path: pathFromContext,\n } as Options)\n\n const { errorMessage, setValue, showError, value } = field\n\n const regenerateDescription = useCallback(async () => {\n if (!hasGenerateDescriptionFn) {\n return\n }\n\n const endpoint = `${serverURL}${api}/plugin-seo/generate-description`\n\n const genDescriptionResponse = await fetch(endpoint, {\n body: JSON.stringify({\n id: docInfo.id,\n collectionSlug: docInfo.collectionSlug,\n doc: getData(),\n docPermissions: docInfo.docPermissions,\n globalSlug: docInfo.globalSlug,\n hasPublishPermission: docInfo.hasPublishPermission,\n hasSavePermission: docInfo.hasSavePermission,\n initialData: docInfo.initialData,\n initialState: docInfo.initialState,\n locale: typeof locale === 'object' ? locale?.code : locale,\n title: docInfo.title,\n } satisfies Omit<\n Parameters<GenerateDescription>[0],\n 'collectionConfig' | 'globalConfig' | 'req'\n >),\n credentials: 'include',\n headers: {\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n })\n\n const { result: generatedDescription } = await genDescriptionResponse.json()\n\n setValue(generatedDescription || '')\n }, [\n hasGenerateDescriptionFn,\n serverURL,\n api,\n docInfo.id,\n docInfo.collectionSlug,\n docInfo.docPermissions,\n docInfo.globalSlug,\n docInfo.hasPublishPermission,\n docInfo.hasSavePermission,\n docInfo.initialData,\n docInfo.initialState,\n docInfo.title,\n getData,\n locale,\n setValue,\n ])\n\n return (\n <div\n style={{\n marginBottom: '20px',\n }}\n >\n <div\n style={{\n marginBottom: '5px',\n position: 'relative',\n }}\n >\n <div className=\"plugin-seo__field\">\n <FieldLabel\n field={fieldFromProps}\n Label={Label}\n label={label}\n required={required}\n {...(labelProps || {})}\n />\n {hasGenerateDescriptionFn && (\n <React.Fragment>\n — \n <button\n onClick={() => {\n void regenerateDescription()\n }}\n style={{\n background: 'none',\n backgroundColor: 'transparent',\n border: 'none',\n color: 'currentcolor',\n cursor: 'pointer',\n padding: 0,\n textDecoration: 'underline',\n }}\n type=\"button\"\n >\n {t('plugin-seo:autoGenerate')}\n </button>\n </React.Fragment>\n )}\n </div>\n <div\n style={{\n color: '#9A9A9A',\n }}\n >\n {t('plugin-seo:lengthTipDescription', { maxLength, minLength })}\n <a\n href=\"https://developers.google.com/search/docs/advanced/appearance/snippet#meta-descriptions\"\n rel=\"noopener noreferrer\"\n target=\"_blank\"\n >\n {t('plugin-seo:bestPractices')}\n </a>\n </div>\n </div>\n <div\n style={{\n marginBottom: '10px',\n position: 'relative',\n }}\n >\n <TextareaInput\n afterInput={afterInput}\n beforeInput={beforeInput}\n Error={{\n type: 'client',\n Component: null,\n RenderedComponent: errorMessage,\n }}\n onChange={setValue}\n path={pathFromContext}\n required={required}\n showError={showError}\n style={{\n marginBottom: 0,\n }}\n value={value}\n />\n </div>\n <div\n style={{\n alignItems: 'center',\n display: 'flex',\n width: '100%',\n }}\n >\n <LengthIndicator maxLength={maxLength} minLength={minLength} text={value} />\n </div>\n </div>\n )\n}\n"],"names":["FieldLabel","TextareaInput","useConfig","useDocumentInfo","useField","useFieldProps","useForm","useLocale","useTranslation","React","useCallback","defaults","LengthIndicator","maxLength","maxLengthDefault","minLength","minLengthDefault","description","MetaDescriptionComponent","props","field","admin","components","afterInput","beforeInput","Label","label","maxLengthFromProps","minLengthFromProps","required","fieldFromProps","hasGenerateDescriptionFn","labelProps","path","pathFromContext","config","routes","api","serverURL","t","locale","getData","docInfo","errorMessage","setValue","showError","value","regenerateDescription","endpoint","genDescriptionResponse","fetch","body","JSON","stringify","id","collectionSlug","doc","docPermissions","globalSlug","hasPublishPermission","hasSavePermission","initialData","initialState","code","title","credentials","headers","method","result","generatedDescription","json","div","style","marginBottom","position","className","Fragment","button","onClick","background","backgroundColor","border","color","cursor","padding","textDecoration","type","a","href","rel","target","Error","Component","RenderedComponent","onChange","alignItems","display","width","text"],"mappings":"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"}
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { UploadFieldClientProps } from 'payload';
|
|
2
2
|
import React from 'react';
|
|
3
3
|
type MetaImageProps = {
|
|
4
|
-
hasGenerateImageFn: boolean;
|
|
5
|
-
} &
|
|
4
|
+
readonly hasGenerateImageFn: boolean;
|
|
5
|
+
} & UploadFieldClientProps;
|
|
6
6
|
export declare const MetaImageComponent: React.FC<MetaImageProps>;
|
|
7
7
|
export {};
|
|
8
8
|
//# sourceMappingURL=MetaImageComponent.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MetaImageComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/MetaImage/MetaImageComponent.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"MetaImageComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/MetaImage/MetaImageComponent.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,SAAS,CAAA;AAarD,OAAO,KAAsB,MAAM,OAAO,CAAA;AAO1C,KAAK,cAAc,GAAG;IACpB,QAAQ,CAAC,kBAAkB,EAAE,OAAO,CAAA;CACrC,GAAG,sBAAsB,CAAA;AAE1B,eAAO,MAAM,kBAAkB,EAAE,KAAK,CAAC,EAAE,CAAC,cAAc,CAiMvD,CAAA"}
|
|
@@ -4,8 +4,9 @@ import { FieldLabel, UploadInput, useConfig, useDocumentInfo, useField, useField
|
|
|
4
4
|
import React, { useCallback } from 'react';
|
|
5
5
|
import { Pill } from '../../ui/Pill.js';
|
|
6
6
|
export const MetaImageComponent = (props)=>{
|
|
7
|
-
const { field: { admin: { components: { Label } }, label, relationTo, required }, hasGenerateImageFn, labelProps } = props || {};
|
|
7
|
+
const { field: { admin: { components: { Label } }, label, relationTo, required }, field: fieldFromProps, hasGenerateImageFn, labelProps } = props || {};
|
|
8
8
|
const { path: pathFromContext } = useFieldProps();
|
|
9
|
+
const { config: { collections, routes: { api }, serverURL } } = useConfig();
|
|
9
10
|
const field = useField({
|
|
10
11
|
...props,
|
|
11
12
|
path: pathFromContext
|
|
@@ -16,14 +17,23 @@ export const MetaImageComponent = (props)=>{
|
|
|
16
17
|
const docInfo = useDocumentInfo();
|
|
17
18
|
const { errorMessage, setValue, showError, value } = field;
|
|
18
19
|
const regenerateImage = useCallback(async ()=>{
|
|
19
|
-
if (!hasGenerateImageFn)
|
|
20
|
-
|
|
20
|
+
if (!hasGenerateImageFn) {
|
|
21
|
+
return;
|
|
22
|
+
}
|
|
23
|
+
const endpoint = `${serverURL}${api}/plugin-seo/generate-image`;
|
|
24
|
+
const genImageResponse = await fetch(endpoint, {
|
|
21
25
|
body: JSON.stringify({
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
26
|
+
id: docInfo.id,
|
|
27
|
+
collectionSlug: docInfo.collectionSlug,
|
|
28
|
+
doc: getData(),
|
|
29
|
+
docPermissions: docInfo.docPermissions,
|
|
30
|
+
globalSlug: docInfo.globalSlug,
|
|
31
|
+
hasPublishPermission: docInfo.hasPublishPermission,
|
|
32
|
+
hasSavePermission: docInfo.hasSavePermission,
|
|
33
|
+
initialData: docInfo.initialData,
|
|
34
|
+
initialState: docInfo.initialState,
|
|
35
|
+
locale: typeof locale === 'object' ? locale?.code : locale,
|
|
36
|
+
title: docInfo.title
|
|
27
37
|
}),
|
|
28
38
|
credentials: 'include',
|
|
29
39
|
headers: {
|
|
@@ -35,14 +45,22 @@ export const MetaImageComponent = (props)=>{
|
|
|
35
45
|
setValue(generatedImage || '');
|
|
36
46
|
}, [
|
|
37
47
|
hasGenerateImageFn,
|
|
38
|
-
|
|
48
|
+
serverURL,
|
|
49
|
+
api,
|
|
50
|
+
docInfo.id,
|
|
51
|
+
docInfo.collectionSlug,
|
|
52
|
+
docInfo.docPermissions,
|
|
53
|
+
docInfo.globalSlug,
|
|
54
|
+
docInfo.hasPublishPermission,
|
|
55
|
+
docInfo.hasSavePermission,
|
|
56
|
+
docInfo.initialData,
|
|
57
|
+
docInfo.initialState,
|
|
58
|
+
docInfo.title,
|
|
39
59
|
getData,
|
|
40
60
|
locale,
|
|
41
61
|
setValue
|
|
42
62
|
]);
|
|
43
63
|
const hasImage = Boolean(value);
|
|
44
|
-
const { config } = useConfig();
|
|
45
|
-
const { collections, routes: { api } = {}, serverURL } = config;
|
|
46
64
|
const collection = collections?.find((coll)=>coll.slug === relationTo) || undefined;
|
|
47
65
|
return /*#__PURE__*/ _jsxs("div", {
|
|
48
66
|
style: {
|
|
@@ -59,8 +77,10 @@ export const MetaImageComponent = (props)=>{
|
|
|
59
77
|
className: "plugin-seo__field",
|
|
60
78
|
children: [
|
|
61
79
|
/*#__PURE__*/ _jsx(FieldLabel, {
|
|
80
|
+
field: fieldFromProps,
|
|
62
81
|
Label: Label,
|
|
63
82
|
label: label,
|
|
83
|
+
required: required,
|
|
64
84
|
...labelProps || {}
|
|
65
85
|
}),
|
|
66
86
|
hasGenerateImageFn && /*#__PURE__*/ _jsxs(React.Fragment, {
|
|
@@ -100,23 +120,27 @@ export const MetaImageComponent = (props)=>{
|
|
|
100
120
|
position: 'relative'
|
|
101
121
|
},
|
|
102
122
|
children: /*#__PURE__*/ _jsx(UploadInput, {
|
|
123
|
+
api: api,
|
|
124
|
+
collection: collection,
|
|
103
125
|
Error: {
|
|
104
126
|
type: 'client',
|
|
105
127
|
Component: null,
|
|
106
128
|
RenderedComponent: errorMessage
|
|
107
129
|
},
|
|
108
|
-
api: api,
|
|
109
|
-
collection: collection,
|
|
110
130
|
filterOptions: field.filterOptions,
|
|
111
|
-
label: undefined,
|
|
112
131
|
onChange: (incomingImage)=>{
|
|
113
132
|
if (incomingImage !== null) {
|
|
114
|
-
|
|
115
|
-
|
|
133
|
+
if (typeof incomingImage === 'object') {
|
|
134
|
+
const { id: incomingID } = incomingImage;
|
|
135
|
+
setValue(incomingID);
|
|
136
|
+
} else {
|
|
137
|
+
setValue(incomingImage);
|
|
138
|
+
}
|
|
116
139
|
} else {
|
|
117
140
|
setValue(null);
|
|
118
141
|
}
|
|
119
142
|
},
|
|
143
|
+
path: field.path,
|
|
120
144
|
relationTo: relationTo,
|
|
121
145
|
required: required,
|
|
122
146
|
serverURL: serverURL,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../src/fields/MetaImage/MetaImageComponent.tsx"],"sourcesContent":["'use client'\n\nimport type { FieldType, Options
|
|
1
|
+
{"version":3,"sources":["../../../src/fields/MetaImage/MetaImageComponent.tsx"],"sourcesContent":["'use client'\n\nimport type { FieldType, Options } from '@payloadcms/ui'\nimport type { UploadFieldClientProps } from 'payload'\n\nimport {\n FieldLabel,\n UploadInput,\n useConfig,\n useDocumentInfo,\n useField,\n useFieldProps,\n useForm,\n useLocale,\n useTranslation,\n} from '@payloadcms/ui'\nimport React, { useCallback } from 'react'\n\nimport type { PluginSEOTranslationKeys, PluginSEOTranslations } from '../../translations/index.js'\nimport type { GenerateImage } from '../../types.js'\n\nimport { Pill } from '../../ui/Pill.js'\n\ntype MetaImageProps = {\n readonly hasGenerateImageFn: boolean\n} & UploadFieldClientProps\n\nexport const MetaImageComponent: React.FC<MetaImageProps> = (props) => {\n const {\n field: {\n admin: {\n components: { Label },\n },\n label,\n relationTo,\n required,\n },\n field: fieldFromProps,\n hasGenerateImageFn,\n labelProps,\n } = props || {}\n const { path: pathFromContext } = useFieldProps()\n\n const {\n config: {\n collections,\n routes: { api },\n serverURL,\n },\n } = useConfig()\n\n const field: FieldType<string> = useField({ ...props, path: pathFromContext } as Options)\n\n const { t } = useTranslation<PluginSEOTranslations, PluginSEOTranslationKeys>()\n\n const locale = useLocale()\n const { getData } = useForm()\n const docInfo = useDocumentInfo()\n\n const { errorMessage, setValue, showError, value } = field\n\n const regenerateImage = useCallback(async () => {\n if (!hasGenerateImageFn) {\n return\n }\n\n const endpoint = `${serverURL}${api}/plugin-seo/generate-image`\n\n const genImageResponse = await fetch(endpoint, {\n body: JSON.stringify({\n id: docInfo.id,\n collectionSlug: docInfo.collectionSlug,\n doc: getData(),\n docPermissions: docInfo.docPermissions,\n globalSlug: docInfo.globalSlug,\n hasPublishPermission: docInfo.hasPublishPermission,\n hasSavePermission: docInfo.hasSavePermission,\n initialData: docInfo.initialData,\n initialState: docInfo.initialState,\n locale: typeof locale === 'object' ? locale?.code : locale,\n title: docInfo.title,\n } satisfies Omit<Parameters<GenerateImage>[0], 'collectionConfig' | 'globalConfig' | 'req'>),\n credentials: 'include',\n headers: {\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n })\n\n const generatedImage = await genImageResponse.text()\n\n setValue(generatedImage || '')\n }, [\n hasGenerateImageFn,\n serverURL,\n api,\n docInfo.id,\n docInfo.collectionSlug,\n docInfo.docPermissions,\n docInfo.globalSlug,\n docInfo.hasPublishPermission,\n docInfo.hasSavePermission,\n docInfo.initialData,\n docInfo.initialState,\n docInfo.title,\n getData,\n locale,\n setValue,\n ])\n\n const hasImage = Boolean(value)\n\n const collection = collections?.find((coll) => coll.slug === relationTo) || undefined\n\n return (\n <div\n style={{\n marginBottom: '20px',\n }}\n >\n <div\n style={{\n marginBottom: '5px',\n position: 'relative',\n }}\n >\n <div className=\"plugin-seo__field\">\n <FieldLabel\n field={fieldFromProps}\n Label={Label}\n label={label}\n required={required}\n {...(labelProps || {})}\n />\n {hasGenerateImageFn && (\n <React.Fragment>\n — \n <button\n onClick={() => {\n void regenerateImage()\n }}\n style={{\n background: 'none',\n backgroundColor: 'transparent',\n border: 'none',\n color: 'currentcolor',\n cursor: 'pointer',\n padding: 0,\n textDecoration: 'underline',\n }}\n type=\"button\"\n >\n {t('plugin-seo:autoGenerate')}\n </button>\n </React.Fragment>\n )}\n </div>\n {hasGenerateImageFn && (\n <div\n style={{\n color: '#9A9A9A',\n }}\n >\n {t('plugin-seo:imageAutoGenerationTip')}\n </div>\n )}\n </div>\n <div\n style={{\n marginBottom: '10px',\n position: 'relative',\n }}\n >\n <UploadInput\n api={api}\n collection={collection}\n Error={{\n type: 'client',\n Component: null,\n RenderedComponent: errorMessage,\n }}\n filterOptions={field.filterOptions}\n onChange={(incomingImage) => {\n if (incomingImage !== null) {\n if (typeof incomingImage === 'object') {\n const { id: incomingID } = incomingImage\n setValue(incomingID)\n } else {\n setValue(incomingImage)\n }\n } else {\n setValue(null)\n }\n }}\n path={field.path}\n relationTo={relationTo}\n required={required}\n serverURL={serverURL}\n showError={showError}\n style={{\n marginBottom: 0,\n }}\n value={value}\n />\n </div>\n <div\n style={{\n alignItems: 'center',\n display: 'flex',\n width: '100%',\n }}\n >\n <Pill\n backgroundColor={hasImage ? 'green' : 'red'}\n color=\"white\"\n label={hasImage ? t('plugin-seo:good') : t('plugin-seo:noImage')}\n />\n </div>\n </div>\n )\n}\n"],"names":["FieldLabel","UploadInput","useConfig","useDocumentInfo","useField","useFieldProps","useForm","useLocale","useTranslation","React","useCallback","Pill","MetaImageComponent","props","field","admin","components","Label","label","relationTo","required","fieldFromProps","hasGenerateImageFn","labelProps","path","pathFromContext","config","collections","routes","api","serverURL","t","locale","getData","docInfo","errorMessage","setValue","showError","value","regenerateImage","endpoint","genImageResponse","fetch","body","JSON","stringify","id","collectionSlug","doc","docPermissions","globalSlug","hasPublishPermission","hasSavePermission","initialData","initialState","code","title","credentials","headers","method","generatedImage","text","hasImage","Boolean","collection","find","coll","slug","undefined","div","style","marginBottom","position","className","Fragment","button","onClick","background","backgroundColor","border","color","cursor","padding","textDecoration","type","Error","Component","RenderedComponent","filterOptions","onChange","incomingImage","incomingID","alignItems","display","width"],"mappings":"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"}
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { TextFieldClientProps } from 'payload';
|
|
2
2
|
import React from 'react';
|
|
3
3
|
import '../index.scss';
|
|
4
4
|
type MetaTitleProps = {
|
|
5
|
-
hasGenerateTitleFn: boolean;
|
|
6
|
-
} &
|
|
5
|
+
readonly hasGenerateTitleFn: boolean;
|
|
6
|
+
} & TextFieldClientProps;
|
|
7
7
|
export declare const MetaTitleComponent: React.FC<MetaTitleProps>;
|
|
8
8
|
export {};
|
|
9
9
|
//# sourceMappingURL=MetaTitleComponent.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MetaTitleComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/MetaTitle/MetaTitleComponent.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,
|
|
1
|
+
{"version":3,"file":"MetaTitleComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/MetaTitle/MetaTitleComponent.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,SAAS,CAAA;AAanD,OAAO,KAAsB,MAAM,OAAO,CAAA;AAO1C,OAAO,eAAe,CAAA;AAItB,KAAK,cAAc,GAAG;IACpB,QAAQ,CAAC,kBAAkB,EAAE,OAAO,CAAA;CACrC,GAAG,oBAAoB,CAAA;AAExB,eAAO,MAAM,kBAAkB,EAAE,KAAK,CAAC,EAAE,CAAC,cAAc,CAqLvD,CAAA"}
|
|
@@ -1,31 +1,43 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
-
import { FieldLabel, TextInput, useDocumentInfo, useField, useFieldProps, useForm, useLocale, useTranslation } from '@payloadcms/ui';
|
|
3
|
+
import { FieldLabel, TextInput, useConfig, useDocumentInfo, useField, useFieldProps, useForm, useLocale, useTranslation } from '@payloadcms/ui';
|
|
4
4
|
import React, { useCallback } from 'react';
|
|
5
5
|
import { defaults } from '../../defaults.js';
|
|
6
6
|
import { LengthIndicator } from '../../ui/LengthIndicator.js';
|
|
7
7
|
import '../index.scss';
|
|
8
|
-
const { maxLength, minLength } = defaults.title;
|
|
8
|
+
const { maxLength: maxLengthDefault, minLength: minLengthDefault } = defaults.title;
|
|
9
9
|
export const MetaTitleComponent = (props)=>{
|
|
10
|
-
const { field: { admin: { components: { Label } }, label, required }, hasGenerateTitleFn, labelProps } = props || {};
|
|
10
|
+
const { field: { admin: { components: { afterInput, beforeInput, Label } }, label, maxLength: maxLengthFromProps, minLength: minLengthFromProps, required }, field: fieldFromProps, hasGenerateTitleFn, labelProps } = props || {};
|
|
11
11
|
const { path: pathFromContext } = useFieldProps();
|
|
12
12
|
const { t } = useTranslation();
|
|
13
|
+
const { config: { routes: { api }, serverURL } } = useConfig();
|
|
13
14
|
const field = useField({
|
|
14
15
|
path: pathFromContext
|
|
15
16
|
});
|
|
16
17
|
const locale = useLocale();
|
|
17
18
|
const { getData } = useForm();
|
|
18
19
|
const docInfo = useDocumentInfo();
|
|
20
|
+
const minLength = minLengthFromProps || minLengthDefault;
|
|
21
|
+
const maxLength = maxLengthFromProps || maxLengthDefault;
|
|
19
22
|
const { errorMessage, setValue, showError, value } = field;
|
|
20
23
|
const regenerateTitle = useCallback(async ()=>{
|
|
21
|
-
if (!hasGenerateTitleFn)
|
|
22
|
-
|
|
24
|
+
if (!hasGenerateTitleFn) {
|
|
25
|
+
return;
|
|
26
|
+
}
|
|
27
|
+
const endpoint = `${serverURL}${api}/plugin-seo/generate-title`;
|
|
28
|
+
const genTitleResponse = await fetch(endpoint, {
|
|
23
29
|
body: JSON.stringify({
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
30
|
+
id: docInfo.id,
|
|
31
|
+
collectionSlug: docInfo.collectionSlug,
|
|
32
|
+
doc: getData(),
|
|
33
|
+
docPermissions: docInfo.docPermissions,
|
|
34
|
+
globalSlug: docInfo.globalSlug,
|
|
35
|
+
hasPublishPermission: docInfo.hasPublishPermission,
|
|
36
|
+
hasSavePermission: docInfo.hasSavePermission,
|
|
37
|
+
initialData: docInfo.initialData,
|
|
38
|
+
initialState: docInfo.initialState,
|
|
39
|
+
locale: typeof locale === 'object' ? locale?.code : locale,
|
|
40
|
+
title: docInfo.title
|
|
29
41
|
}),
|
|
30
42
|
credentials: 'include',
|
|
31
43
|
headers: {
|
|
@@ -37,7 +49,17 @@ export const MetaTitleComponent = (props)=>{
|
|
|
37
49
|
setValue(generatedTitle || '');
|
|
38
50
|
}, [
|
|
39
51
|
hasGenerateTitleFn,
|
|
40
|
-
|
|
52
|
+
serverURL,
|
|
53
|
+
api,
|
|
54
|
+
docInfo.id,
|
|
55
|
+
docInfo.collectionSlug,
|
|
56
|
+
docInfo.docPermissions,
|
|
57
|
+
docInfo.globalSlug,
|
|
58
|
+
docInfo.hasPublishPermission,
|
|
59
|
+
docInfo.hasSavePermission,
|
|
60
|
+
docInfo.initialData,
|
|
61
|
+
docInfo.initialState,
|
|
62
|
+
docInfo.title,
|
|
41
63
|
getData,
|
|
42
64
|
locale,
|
|
43
65
|
setValue
|
|
@@ -57,8 +79,10 @@ export const MetaTitleComponent = (props)=>{
|
|
|
57
79
|
className: "plugin-seo__field",
|
|
58
80
|
children: [
|
|
59
81
|
/*#__PURE__*/ _jsx(FieldLabel, {
|
|
82
|
+
field: fieldFromProps,
|
|
60
83
|
Label: Label,
|
|
61
84
|
label: label,
|
|
85
|
+
required: required,
|
|
62
86
|
...labelProps || {}
|
|
63
87
|
}),
|
|
64
88
|
hasGenerateTitleFn && /*#__PURE__*/ _jsxs(React.Fragment, {
|
|
@@ -110,12 +134,13 @@ export const MetaTitleComponent = (props)=>{
|
|
|
110
134
|
position: 'relative'
|
|
111
135
|
},
|
|
112
136
|
children: /*#__PURE__*/ _jsx(TextInput, {
|
|
137
|
+
afterInput: afterInput,
|
|
138
|
+
beforeInput: beforeInput,
|
|
113
139
|
Error: {
|
|
114
140
|
type: 'client',
|
|
115
141
|
Component: null,
|
|
116
142
|
RenderedComponent: errorMessage
|
|
117
143
|
},
|
|
118
|
-
label: label,
|
|
119
144
|
onChange: setValue,
|
|
120
145
|
path: pathFromContext,
|
|
121
146
|
required: required,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../src/fields/MetaTitle/MetaTitleComponent.tsx"],"sourcesContent":["'use client'\n\nimport type { FieldType, Options } from '@payloadcms/ui'\nimport type {
|
|
1
|
+
{"version":3,"sources":["../../../src/fields/MetaTitle/MetaTitleComponent.tsx"],"sourcesContent":["'use client'\n\nimport type { FieldType, Options } from '@payloadcms/ui'\nimport type { TextFieldClientProps } from 'payload'\n\nimport {\n FieldLabel,\n TextInput,\n useConfig,\n useDocumentInfo,\n useField,\n useFieldProps,\n useForm,\n useLocale,\n useTranslation,\n} from '@payloadcms/ui'\nimport React, { useCallback } from 'react'\n\nimport type { PluginSEOTranslationKeys, PluginSEOTranslations } from '../../translations/index.js'\nimport type { GenerateTitle } from '../../types.js'\n\nimport { defaults } from '../../defaults.js'\nimport { LengthIndicator } from '../../ui/LengthIndicator.js'\nimport '../index.scss'\n\nconst { maxLength: maxLengthDefault, minLength: minLengthDefault } = defaults.title\n\ntype MetaTitleProps = {\n readonly hasGenerateTitleFn: boolean\n} & TextFieldClientProps\n\nexport const MetaTitleComponent: React.FC<MetaTitleProps> = (props) => {\n const {\n field: {\n admin: {\n components: { afterInput, beforeInput, Label },\n },\n label,\n maxLength: maxLengthFromProps,\n minLength: minLengthFromProps,\n required,\n },\n field: fieldFromProps,\n hasGenerateTitleFn,\n labelProps,\n } = props || {}\n const { path: pathFromContext } = useFieldProps()\n const { t } = useTranslation<PluginSEOTranslations, PluginSEOTranslationKeys>()\n\n const {\n config: {\n routes: { api },\n serverURL,\n },\n } = useConfig()\n\n const field: FieldType<string> = useField({\n path: pathFromContext,\n } as Options)\n\n const locale = useLocale()\n const { getData } = useForm()\n const docInfo = useDocumentInfo()\n\n const minLength = minLengthFromProps || minLengthDefault\n const maxLength = maxLengthFromProps || maxLengthDefault\n\n const { errorMessage, setValue, showError, value } = field\n\n const regenerateTitle = useCallback(async () => {\n if (!hasGenerateTitleFn) {\n return\n }\n\n const endpoint = `${serverURL}${api}/plugin-seo/generate-title`\n\n const genTitleResponse = await fetch(endpoint, {\n body: JSON.stringify({\n id: docInfo.id,\n collectionSlug: docInfo.collectionSlug,\n doc: getData(),\n docPermissions: docInfo.docPermissions,\n globalSlug: docInfo.globalSlug,\n hasPublishPermission: docInfo.hasPublishPermission,\n hasSavePermission: docInfo.hasSavePermission,\n initialData: docInfo.initialData,\n initialState: docInfo.initialState,\n locale: typeof locale === 'object' ? locale?.code : locale,\n title: docInfo.title,\n } satisfies Omit<Parameters<GenerateTitle>[0], 'collectionConfig' | 'globalConfig' | 'req'>),\n credentials: 'include',\n headers: {\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n })\n\n const { result: generatedTitle } = await genTitleResponse.json()\n\n setValue(generatedTitle || '')\n }, [\n hasGenerateTitleFn,\n serverURL,\n api,\n docInfo.id,\n docInfo.collectionSlug,\n docInfo.docPermissions,\n docInfo.globalSlug,\n docInfo.hasPublishPermission,\n docInfo.hasSavePermission,\n docInfo.initialData,\n docInfo.initialState,\n docInfo.title,\n getData,\n locale,\n setValue,\n ])\n\n return (\n <div\n style={{\n marginBottom: '20px',\n }}\n >\n <div\n style={{\n marginBottom: '5px',\n position: 'relative',\n }}\n >\n <div className=\"plugin-seo__field\">\n <FieldLabel\n field={fieldFromProps}\n Label={Label}\n label={label}\n required={required}\n {...(labelProps || {})}\n />\n {hasGenerateTitleFn && (\n <React.Fragment>\n — \n <button\n onClick={() => {\n void regenerateTitle()\n }}\n style={{\n background: 'none',\n backgroundColor: 'transparent',\n border: 'none',\n color: 'currentcolor',\n cursor: 'pointer',\n padding: 0,\n textDecoration: 'underline',\n }}\n type=\"button\"\n >\n {t('plugin-seo:autoGenerate')}\n </button>\n </React.Fragment>\n )}\n </div>\n <div\n style={{\n color: '#9A9A9A',\n }}\n >\n {t('plugin-seo:lengthTipTitle', { maxLength, minLength })}\n <a\n href=\"https://developers.google.com/search/docs/advanced/appearance/title-link#page-titles\"\n rel=\"noopener noreferrer\"\n target=\"_blank\"\n >\n {t('plugin-seo:bestPractices')}\n </a>\n .\n </div>\n </div>\n <div\n style={{\n marginBottom: '10px',\n position: 'relative',\n }}\n >\n <TextInput\n afterInput={afterInput}\n beforeInput={beforeInput}\n Error={{\n type: 'client',\n Component: null,\n RenderedComponent: errorMessage,\n }}\n onChange={setValue}\n path={pathFromContext}\n required={required}\n showError={showError}\n style={{\n marginBottom: 0,\n }}\n value={value}\n />\n </div>\n <div\n style={{\n alignItems: 'center',\n display: 'flex',\n width: '100%',\n }}\n >\n <LengthIndicator maxLength={maxLength} minLength={minLength} text={value} />\n </div>\n </div>\n )\n}\n"],"names":["FieldLabel","TextInput","useConfig","useDocumentInfo","useField","useFieldProps","useForm","useLocale","useTranslation","React","useCallback","defaults","LengthIndicator","maxLength","maxLengthDefault","minLength","minLengthDefault","title","MetaTitleComponent","props","field","admin","components","afterInput","beforeInput","Label","label","maxLengthFromProps","minLengthFromProps","required","fieldFromProps","hasGenerateTitleFn","labelProps","path","pathFromContext","t","config","routes","api","serverURL","locale","getData","docInfo","errorMessage","setValue","showError","value","regenerateTitle","endpoint","genTitleResponse","fetch","body","JSON","stringify","id","collectionSlug","doc","docPermissions","globalSlug","hasPublishPermission","hasSavePermission","initialData","initialState","code","credentials","headers","method","result","generatedTitle","json","div","style","marginBottom","position","className","Fragment","button","onClick","background","backgroundColor","border","color","cursor","padding","textDecoration","type","a","href","rel","target","Error","Component","RenderedComponent","onChange","alignItems","display","width","text"],"mappings":"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"}
|
|
@@ -1,8 +1,16 @@
|
|
|
1
1
|
import type { UIField } from 'payload';
|
|
2
2
|
import React from 'react';
|
|
3
3
|
type OverviewProps = {
|
|
4
|
+
descriptionOverrides?: {
|
|
5
|
+
maxLength?: number;
|
|
6
|
+
minLength?: number;
|
|
7
|
+
};
|
|
4
8
|
descriptionPath?: string;
|
|
5
9
|
imagePath?: string;
|
|
10
|
+
titleOverrides?: {
|
|
11
|
+
maxLength?: number;
|
|
12
|
+
minLength?: number;
|
|
13
|
+
};
|
|
6
14
|
titlePath?: string;
|
|
7
15
|
} & UIField;
|
|
8
16
|
export declare const OverviewComponent: React.FC<OverviewProps>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"OverviewComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/Overview/OverviewComponent.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAa,OAAO,EAAE,MAAM,SAAS,CAAA;AAGjD,OAAO,KAA2C,MAAM,OAAO,CAAA;AAW/D,KAAK,aAAa,GAAG;IACnB,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB,GAAG,OAAO,CAAA;AAEX,eAAO,MAAM,iBAAiB,EAAE,KAAK,CAAC,EAAE,CAAC,aAAa,
|
|
1
|
+
{"version":3,"file":"OverviewComponent.d.ts","sourceRoot":"","sources":["../../../src/fields/Overview/OverviewComponent.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAa,OAAO,EAAE,MAAM,SAAS,CAAA;AAGjD,OAAO,KAA2C,MAAM,OAAO,CAAA;AAW/D,KAAK,aAAa,GAAG;IACnB,oBAAoB,CAAC,EAAE;QACrB,SAAS,CAAC,EAAE,MAAM,CAAA;QAClB,SAAS,CAAC,EAAE,MAAM,CAAA;KACnB,CAAA;IACD,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,cAAc,CAAC,EAAE;QACf,SAAS,CAAC,EAAE,MAAM,CAAA;QAClB,SAAS,CAAC,EAAE,MAAM,CAAA;KACnB,CAAA;IACD,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB,GAAG,OAAO,CAAA;AAEX,eAAO,MAAM,iBAAiB,EAAE,KAAK,CAAC,EAAE,CAAC,aAAa,CAiErD,CAAA"}
|
|
@@ -3,10 +3,9 @@ import { jsx as _jsx } from "react/jsx-runtime";
|
|
|
3
3
|
import { useAllFormFields, useForm, useTranslation } from '@payloadcms/ui';
|
|
4
4
|
import React, { useCallback, useEffect, useState } from 'react';
|
|
5
5
|
import { defaults } from '../../defaults.js';
|
|
6
|
-
const { description: { maxLength:
|
|
7
|
-
export const OverviewComponent = ({ descriptionPath: descriptionPathFromContext, imagePath: imagePathFromContext, titlePath: titlePathFromContext })=>{
|
|
8
|
-
const {
|
|
9
|
-
getFields } = useForm();
|
|
6
|
+
const { description: { maxLength: maxDescDefault, minLength: minDescDefault }, title: { maxLength: maxTitleDefault, minLength: minTitleDefault } } = defaults;
|
|
7
|
+
export const OverviewComponent = ({ descriptionOverrides, descriptionPath: descriptionPathFromContext, imagePath: imagePathFromContext, titleOverrides, titlePath: titlePathFromContext })=>{
|
|
8
|
+
const { getFields } = useForm();
|
|
10
9
|
const descriptionPath = descriptionPathFromContext || 'meta.description';
|
|
11
10
|
const titlePath = titlePathFromContext || 'meta.title';
|
|
12
11
|
const imagePath = imagePathFromContext || 'meta.image';
|
|
@@ -15,7 +14,10 @@ export const OverviewComponent = ({ descriptionPath: descriptionPathFromContext,
|
|
|
15
14
|
const [titleIsValid, setTitleIsValid] = useState();
|
|
16
15
|
const [descIsValid, setDescIsValid] = useState();
|
|
17
16
|
const [imageIsValid, setImageIsValid] = useState();
|
|
18
|
-
|
|
17
|
+
const minDesc = descriptionOverrides?.minLength || minDescDefault;
|
|
18
|
+
const maxDesc = descriptionOverrides?.maxLength || maxDescDefault;
|
|
19
|
+
const minTitle = titleOverrides?.minLength || minTitleDefault;
|
|
20
|
+
const maxTitle = titleOverrides?.maxLength || maxTitleDefault;
|
|
19
21
|
const resetAll = useCallback(()=>{
|
|
20
22
|
const fields = getFields();
|
|
21
23
|
const fieldsWithoutMeta = fields;
|
|
@@ -27,8 +29,12 @@ export const OverviewComponent = ({ descriptionPath: descriptionPathFromContext,
|
|
|
27
29
|
getFields
|
|
28
30
|
]);
|
|
29
31
|
useEffect(()=>{
|
|
30
|
-
if (typeof metaTitle === 'string')
|
|
31
|
-
|
|
32
|
+
if (typeof metaTitle === 'string') {
|
|
33
|
+
setTitleIsValid(metaTitle.length >= minTitle && metaTitle.length <= maxTitle);
|
|
34
|
+
}
|
|
35
|
+
if (typeof metaDesc === 'string') {
|
|
36
|
+
setDescIsValid(metaDesc.length >= minDesc && metaDesc.length <= maxDesc);
|
|
37
|
+
}
|
|
32
38
|
setImageIsValid(Boolean(metaImage));
|
|
33
39
|
}, [
|
|
34
40
|
metaTitle,
|