Integrate CMS with Marketing Solutions page
Links the marketing solutions frontend page to the Payload CMS Pages collection via the new API library. Removes legacy static portfolio routes and components to consolidate marketing content. Enhances the Header and Footer Astro components with improved responsive styling.
This commit is contained in:
@@ -16,25 +16,9 @@ import { generateMeta } from '@/utilities/generateMeta'
|
||||
import PageClient from './page.client'
|
||||
import { LivePreviewListener } from '@/components/LivePreviewListener'
|
||||
|
||||
export async function generateStaticParams() {
|
||||
const payload = await getPayload({ config: configPromise })
|
||||
const posts = await payload.find({
|
||||
collection: 'posts',
|
||||
draft: false,
|
||||
limit: 1000,
|
||||
overrideAccess: false,
|
||||
pagination: false,
|
||||
select: {
|
||||
slug: true,
|
||||
},
|
||||
})
|
||||
|
||||
const params = posts.docs.map(({ slug }) => {
|
||||
return { slug }
|
||||
})
|
||||
|
||||
return params
|
||||
}
|
||||
// Use dynamic rendering instead of static generation
|
||||
// This avoids the need for database connection during build time
|
||||
export const dynamic = 'force-dynamic'
|
||||
|
||||
type Args = {
|
||||
params: Promise<{
|
||||
|
||||
@@ -8,7 +8,8 @@ import { getPayload } from 'payload'
|
||||
import React from 'react'
|
||||
import PageClient from './page.client'
|
||||
|
||||
export const dynamic = 'force-static'
|
||||
// Use dynamic rendering to avoid database connection during build
|
||||
export const dynamic = 'force-dynamic'
|
||||
export const revalidate = 600
|
||||
|
||||
export default async function Page() {
|
||||
|
||||
@@ -9,6 +9,8 @@ import React from 'react'
|
||||
import PageClient from './page.client'
|
||||
import { notFound } from 'next/navigation'
|
||||
|
||||
// Use dynamic rendering to avoid database connection during build
|
||||
export const dynamic = 'force-dynamic'
|
||||
export const revalidate = 600
|
||||
|
||||
type Args = {
|
||||
|
||||
86
apps/backend/src/blocks/ServicesList/config.ts
Normal file
86
apps/backend/src/blocks/ServicesList/config.ts
Normal file
@@ -0,0 +1,86 @@
|
||||
import type { Block } from 'payload'
|
||||
|
||||
export const ServicesList: Block = {
|
||||
slug: 'servicesList',
|
||||
interfaceName: 'ServicesListBlock',
|
||||
fields: [
|
||||
{
|
||||
name: 'services',
|
||||
type: 'array',
|
||||
required: true,
|
||||
admin: {
|
||||
initCollapsed: true,
|
||||
},
|
||||
fields: [
|
||||
{
|
||||
name: 'title',
|
||||
type: 'text',
|
||||
required: true,
|
||||
},
|
||||
{
|
||||
name: 'description',
|
||||
type: 'textarea',
|
||||
required: true,
|
||||
},
|
||||
{
|
||||
name: 'category',
|
||||
type: 'text',
|
||||
required: true,
|
||||
},
|
||||
{
|
||||
name: 'iconType',
|
||||
type: 'select',
|
||||
defaultValue: 'preset',
|
||||
options: [
|
||||
{ label: 'Preset Icon', value: 'preset' },
|
||||
{ label: 'Custom SVG', value: 'svg' },
|
||||
{ label: 'Upload Image', value: 'upload' },
|
||||
],
|
||||
},
|
||||
{
|
||||
name: 'icon',
|
||||
type: 'text',
|
||||
admin: {
|
||||
description: 'Preset icon name: facebook, google, ads, news, youtube, forum, web, video',
|
||||
condition: (_, siblingData) => siblingData?.iconType === 'preset',
|
||||
},
|
||||
},
|
||||
{
|
||||
name: 'iconSvg',
|
||||
type: 'textarea',
|
||||
admin: {
|
||||
description: 'Paste SVG code directly (e.g., <svg>...</svg>)',
|
||||
condition: (_, siblingData) => siblingData?.iconType === 'svg',
|
||||
},
|
||||
},
|
||||
{
|
||||
name: 'iconImage',
|
||||
type: 'upload',
|
||||
relationTo: 'media',
|
||||
admin: {
|
||||
description: 'Upload an icon image (SVG, PNG)',
|
||||
condition: (_, siblingData) => siblingData?.iconType === 'upload',
|
||||
},
|
||||
},
|
||||
{
|
||||
name: 'isHot',
|
||||
type: 'checkbox',
|
||||
defaultValue: false,
|
||||
},
|
||||
{
|
||||
name: 'image',
|
||||
type: 'upload',
|
||||
relationTo: 'media',
|
||||
},
|
||||
{
|
||||
name: 'link',
|
||||
type: 'text',
|
||||
},
|
||||
],
|
||||
},
|
||||
],
|
||||
labels: {
|
||||
singular: 'Services List',
|
||||
plural: 'Services Lists',
|
||||
},
|
||||
}
|
||||
@@ -8,6 +8,7 @@ import { Archive } from '../../blocks/ArchiveBlock/config'
|
||||
import { CallToAction } from '../../blocks/CallToAction/config'
|
||||
import { Content } from '../../blocks/Content/config'
|
||||
import { MediaBlock } from '../../blocks/MediaBlock/config'
|
||||
import { ServicesList } from '../../blocks/ServicesList/config'
|
||||
import { hero } from '@/heros/config'
|
||||
import { slugField } from '@/fields/slug'
|
||||
import { populatePublishedAt } from '../../hooks/populatePublishedAt'
|
||||
@@ -76,7 +77,7 @@ export const Pages: CollectionConfig<'pages'> = {
|
||||
{
|
||||
name: 'layout',
|
||||
type: 'blocks',
|
||||
blocks: [CallToAction, Content, MediaBlock, Archive],
|
||||
blocks: [CallToAction, Content, MediaBlock, Archive, ServicesList],
|
||||
required: true,
|
||||
admin: {
|
||||
initCollapsed: true,
|
||||
|
||||
@@ -194,7 +194,7 @@ export interface Page {
|
||||
| null;
|
||||
media?: (string | null) | Media;
|
||||
};
|
||||
layout: (CallToActionBlock | ContentBlock | MediaBlock | ArchiveBlock)[];
|
||||
layout: (CallToActionBlock | ContentBlock | MediaBlock | ArchiveBlock | ServicesListBlock)[];
|
||||
meta?: {
|
||||
title?: string | null;
|
||||
/**
|
||||
@@ -564,6 +564,37 @@ export interface ArchiveBlock {
|
||||
blockName?: string | null;
|
||||
blockType: 'archive';
|
||||
}
|
||||
/**
|
||||
* This interface was referenced by `Config`'s JSON-Schema
|
||||
* via the `definition` "ServicesListBlock".
|
||||
*/
|
||||
export interface ServicesListBlock {
|
||||
services: {
|
||||
title: string;
|
||||
description: string;
|
||||
category: string;
|
||||
iconType?: ('preset' | 'svg' | 'upload') | null;
|
||||
/**
|
||||
* Preset icon name: facebook, google, ads, news, youtube, forum, web, video
|
||||
*/
|
||||
icon?: string | null;
|
||||
/**
|
||||
* Paste SVG code directly (e.g., <svg>...</svg>)
|
||||
*/
|
||||
iconSvg?: string | null;
|
||||
/**
|
||||
* Upload an icon image (SVG, PNG)
|
||||
*/
|
||||
iconImage?: (string | null) | Media;
|
||||
isHot?: boolean | null;
|
||||
image?: (string | null) | Media;
|
||||
link?: string | null;
|
||||
id?: string | null;
|
||||
}[];
|
||||
id?: string | null;
|
||||
blockName?: string | null;
|
||||
blockType: 'servicesList';
|
||||
}
|
||||
/**
|
||||
* This interface was referenced by `Config`'s JSON-Schema
|
||||
* via the `definition` "portfolio".
|
||||
@@ -923,6 +954,7 @@ export interface PagesSelect<T extends boolean = true> {
|
||||
content?: T | ContentBlockSelect<T>;
|
||||
mediaBlock?: T | MediaBlockSelect<T>;
|
||||
archive?: T | ArchiveBlockSelect<T>;
|
||||
servicesList?: T | ServicesListBlockSelect<T>;
|
||||
};
|
||||
meta?:
|
||||
| T
|
||||
@@ -1011,6 +1043,29 @@ export interface ArchiveBlockSelect<T extends boolean = true> {
|
||||
id?: T;
|
||||
blockName?: T;
|
||||
}
|
||||
/**
|
||||
* This interface was referenced by `Config`'s JSON-Schema
|
||||
* via the `definition` "ServicesListBlock_select".
|
||||
*/
|
||||
export interface ServicesListBlockSelect<T extends boolean = true> {
|
||||
services?:
|
||||
| T
|
||||
| {
|
||||
title?: T;
|
||||
description?: T;
|
||||
category?: T;
|
||||
iconType?: T;
|
||||
icon?: T;
|
||||
iconSvg?: T;
|
||||
iconImage?: T;
|
||||
isHot?: T;
|
||||
image?: T;
|
||||
link?: T;
|
||||
id?: T;
|
||||
};
|
||||
id?: T;
|
||||
blockName?: T;
|
||||
}
|
||||
/**
|
||||
* This interface was referenced by `Config`'s JSON-Schema
|
||||
* via the `definition` "posts_select".
|
||||
|
||||
Reference in New Issue
Block a user