Add generate_page_content functionality for structured page content generation
- Introduced a new AI function `generate_page_content` to create structured content for website pages using JSON blocks. - Updated `AIEngine` to handle the new function and return appropriate messages for content generation. - Enhanced `PageGenerationService` to utilize the new AI function for generating page content based on blueprints. - Modified `prompts.py` to include detailed content generation requirements for the new function. - Updated site rendering logic to accommodate structured content blocks in various layouts.
This commit is contained in:
@@ -7,6 +7,7 @@
|
||||
import React from 'react';
|
||||
import type { SiteDefinition } from '../types';
|
||||
import { renderTemplate } from './templateEngine';
|
||||
import { renderPageByType } from './pageTypeRenderer';
|
||||
import {
|
||||
DefaultLayout,
|
||||
MinimalLayout,
|
||||
@@ -65,28 +66,20 @@ function renderDefaultLayout(siteDefinition: SiteDefinition): React.ReactElement
|
||||
const showHero = isHomePage || (homePage && siteDefinition.pages.length > 1);
|
||||
const hero: React.ReactNode = (showHero && heroBlock) ? (renderTemplate(heroBlock) as React.ReactNode) : undefined;
|
||||
|
||||
// Render all pages as sections (excluding hero from home page if it exists)
|
||||
// Render all pages using page-type-specific templates
|
||||
const sections = siteDefinition.pages
|
||||
.filter((page) => page.status !== 'draft' && page.status !== 'generating')
|
||||
.sort((a, b) => (a.order || 0) - (b.order || 0))
|
||||
.map((page) => {
|
||||
// Filter out hero block if it's the home page (already rendered as hero)
|
||||
// Use page-type-specific renderer if available
|
||||
const blocksToRender = page.slug === 'home' && heroBlock && showHero
|
||||
? page.blocks?.filter(b => b.type !== 'hero') || []
|
||||
: page.blocks || [];
|
||||
|
||||
// Render using page-type template
|
||||
return (
|
||||
<div key={page.id} className="page" data-page-slug={page.slug} style={{ textAlign: 'center' }}>
|
||||
{page.slug !== 'home' && <h2 style={{ textAlign: 'center', marginBottom: '1.5rem' }}>{page.title}</h2>}
|
||||
{blocksToRender.length > 0 ? (
|
||||
blocksToRender.map((block, index) => (
|
||||
<div key={index} className="block" data-block-type={block.type} style={{ textAlign: 'center' }}>
|
||||
{renderTemplate(block)}
|
||||
</div>
|
||||
))
|
||||
) : page.slug !== 'home' ? (
|
||||
<p>No content available for this page.</p>
|
||||
) : null}
|
||||
<div key={page.id} className="page-wrapper" data-page-slug={page.slug}>
|
||||
{renderPageByType(page, blocksToRender)}
|
||||
</div>
|
||||
);
|
||||
});
|
||||
@@ -107,17 +100,11 @@ function renderMinimalLayout(siteDefinition: SiteDefinition): React.ReactElement
|
||||
const mainContent = (
|
||||
<>
|
||||
{siteDefinition.pages
|
||||
.filter((page) => page.status !== 'draft')
|
||||
.filter((page) => page.status !== 'draft' && page.status !== 'generating')
|
||||
.sort((a, b) => (a.order || 0) - (b.order || 0))
|
||||
.map((page) => (
|
||||
<div key={page.id} className="page" data-page-slug={page.slug}>
|
||||
<h2>{page.title}</h2>
|
||||
{page.blocks && page.blocks.length > 0 ? (
|
||||
page.blocks.map((block, index) => (
|
||||
<div key={index} className="block" data-block-type={block.type}>
|
||||
{renderTemplate(block)}
|
||||
</div>
|
||||
))
|
||||
) : null}
|
||||
<div key={page.id} className="page-wrapper" data-page-slug={page.slug}>
|
||||
{renderPageByType(page, page.blocks || [])}
|
||||
</div>
|
||||
))}
|
||||
</>
|
||||
@@ -138,16 +125,11 @@ function renderMagazineLayout(siteDefinition: SiteDefinition): React.ReactElemen
|
||||
const mainContent = (
|
||||
<>
|
||||
{siteDefinition.pages
|
||||
.filter((page) => page.status !== 'draft')
|
||||
.filter((page) => page.status !== 'draft' && page.status !== 'generating')
|
||||
.sort((a, b) => (a.order || 0) - (b.order || 0))
|
||||
.map((page) => (
|
||||
<div key={page.id} className="page" data-page-slug={page.slug}>
|
||||
{page.blocks && page.blocks.length > 0 ? (
|
||||
page.blocks.map((block, index) => (
|
||||
<div key={index} className="block" data-block-type={block.type}>
|
||||
{renderTemplate(block)}
|
||||
</div>
|
||||
))
|
||||
) : null}
|
||||
<div key={page.id} className="page-wrapper" data-page-slug={page.slug}>
|
||||
{renderPageByType(page, page.blocks || [])}
|
||||
</div>
|
||||
))}
|
||||
</>
|
||||
@@ -168,16 +150,11 @@ function renderEcommerceLayout(siteDefinition: SiteDefinition): React.ReactEleme
|
||||
const mainContent = (
|
||||
<>
|
||||
{siteDefinition.pages
|
||||
.filter((page) => page.status !== 'draft')
|
||||
.filter((page) => page.status !== 'draft' && page.status !== 'generating')
|
||||
.sort((a, b) => (a.order || 0) - (b.order || 0))
|
||||
.map((page) => (
|
||||
<div key={page.id} className="page" data-page-slug={page.slug}>
|
||||
{page.blocks && page.blocks.length > 0 ? (
|
||||
page.blocks.map((block, index) => (
|
||||
<div key={index} className="block" data-block-type={block.type}>
|
||||
{renderTemplate(block)}
|
||||
</div>
|
||||
))
|
||||
) : null}
|
||||
<div key={page.id} className="page-wrapper" data-page-slug={page.slug}>
|
||||
{renderPageByType(page, page.blocks || [])}
|
||||
</div>
|
||||
))}
|
||||
</>
|
||||
@@ -198,16 +175,11 @@ function renderPortfolioLayout(siteDefinition: SiteDefinition): React.ReactEleme
|
||||
const mainContent = (
|
||||
<>
|
||||
{siteDefinition.pages
|
||||
.filter((page) => page.status !== 'draft')
|
||||
.filter((page) => page.status !== 'draft' && page.status !== 'generating')
|
||||
.sort((a, b) => (a.order || 0) - (b.order || 0))
|
||||
.map((page) => (
|
||||
<div key={page.id} className="page" data-page-slug={page.slug}>
|
||||
{page.blocks && page.blocks.length > 0 ? (
|
||||
page.blocks.map((block, index) => (
|
||||
<div key={index} className="block" data-block-type={block.type}>
|
||||
{renderTemplate(block)}
|
||||
</div>
|
||||
))
|
||||
) : null}
|
||||
<div key={page.id} className="page-wrapper" data-page-slug={page.slug}>
|
||||
{renderPageByType(page, page.blocks || [])}
|
||||
</div>
|
||||
))}
|
||||
</>
|
||||
@@ -228,16 +200,11 @@ function renderBlogLayout(siteDefinition: SiteDefinition): React.ReactElement {
|
||||
const mainContent = (
|
||||
<>
|
||||
{siteDefinition.pages
|
||||
.filter((page) => page.status !== 'draft')
|
||||
.filter((page) => page.status !== 'draft' && page.status !== 'generating')
|
||||
.sort((a, b) => (a.order || 0) - (b.order || 0))
|
||||
.map((page) => (
|
||||
<div key={page.id} className="page" data-page-slug={page.slug}>
|
||||
{page.blocks && page.blocks.length > 0 ? (
|
||||
page.blocks.map((block, index) => (
|
||||
<div key={index} className="block" data-block-type={block.type}>
|
||||
{renderTemplate(block)}
|
||||
</div>
|
||||
))
|
||||
) : null}
|
||||
<div key={page.id} className="page-wrapper" data-page-slug={page.slug}>
|
||||
{renderPageByType(page, page.blocks || [])}
|
||||
</div>
|
||||
))}
|
||||
</>
|
||||
@@ -258,16 +225,11 @@ function renderCorporateLayout(siteDefinition: SiteDefinition): React.ReactEleme
|
||||
const mainContent = (
|
||||
<>
|
||||
{siteDefinition.pages
|
||||
.filter((page) => page.status !== 'draft')
|
||||
.filter((page) => page.status !== 'draft' && page.status !== 'generating')
|
||||
.sort((a, b) => (a.order || 0) - (b.order || 0))
|
||||
.map((page) => (
|
||||
<div key={page.id} className="page" data-page-slug={page.slug}>
|
||||
{page.blocks && page.blocks.length > 0 ? (
|
||||
page.blocks.map((block, index) => (
|
||||
<div key={index} className="block" data-block-type={block.type}>
|
||||
{renderTemplate(block)}
|
||||
</div>
|
||||
))
|
||||
) : null}
|
||||
<div key={page.id} className="page-wrapper" data-page-slug={page.slug}>
|
||||
{renderPageByType(page, page.blocks || [])}
|
||||
</div>
|
||||
))}
|
||||
</>
|
||||
|
||||
Reference in New Issue
Block a user