'use client' import type { FC } from 'react' import { useEffect } from 'react' import type { EditorState, } from 'lexical' import { $getRoot, TextNode, } from 'lexical' import { LexicalComposer } from '@lexical/react/LexicalComposer' import { RichTextPlugin } from '@lexical/react/LexicalRichTextPlugin' import { ContentEditable } from '@lexical/react/LexicalContentEditable' import LexicalErrorBoundary from '@lexical/react/LexicalErrorBoundary' import { OnChangePlugin } from '@lexical/react/LexicalOnChangePlugin' // import TreeView from './plugins/tree-view' import Placeholder from './plugins/placeholder' import ComponentPicker from './plugins/component-picker' import VariablePicker from './plugins/variable-picker' import ContextBlock from './plugins/context-block' import { ContextBlockNode } from './plugins/context-block/node' import ContextBlockReplacementBlock from './plugins/context-block-replacement-block' import HistoryBlock from './plugins/history-block' import { HistoryBlockNode } from './plugins/history-block/node' import HistoryBlockReplacementBlock from './plugins/history-block-replacement-block' import QueryBlock from './plugins/query-block' import { QueryBlockNode } from './plugins/query-block/node' import QueryBlockReplacementBlock from './plugins/query-block-replacement-block' import VariableBlock from './plugins/variable-block' import VariableValueBlock from './plugins/variable-value-block' import { VariableValueBlockNode } from './plugins/variable-value-block/node' import { CustomTextNode } from './plugins/custom-text/node' import OnBlurBlock from './plugins/on-blur-block' import { textToEditorState } from './utils' import type { Dataset } from './plugins/context-block' import type { RoleName } from './plugins/history-block' import type { ExternalToolOption, Option } from './plugins/variable-picker' import { UPDATE_DATASETS_EVENT_EMITTER, UPDATE_HISTORY_EVENT_EMITTER, } from './constants' import { useEventEmitterContextContext } from '@/context/event-emitter' export type PromptEditorProps = { className?: string value?: string editable?: boolean onChange?: (text: string) => void onBlur?: () => void contextBlock?: { show?: boolean selectable?: boolean datasets: Dataset[] onInsert?: () => void onDelete?: () => void onAddContext: () => void } variableBlock?: { selectable?: boolean variables: Option[] externalTools?: ExternalToolOption[] onAddExternalTool?: () => void } historyBlock?: { show?: boolean selectable?: boolean history: RoleName onInsert?: () => void onDelete?: () => void onEditRole: () => void } queryBlock?: { show?: boolean selectable?: boolean onInsert?: () => void onDelete?: () => void } } const PromptEditor: FC = ({ className, value, editable = true, onChange, onBlur, contextBlock = { show: true, selectable: true, datasets: [], onAddContext: () => {}, onInsert: () => {}, onDelete: () => {}, }, historyBlock = { show: true, selectable: true, history: { user: '', assistant: '', }, onEditRole: () => {}, onInsert: () => {}, onDelete: () => {}, }, variableBlock = { variables: [], }, queryBlock = { show: true, selectable: true, onInsert: () => {}, onDelete: () => {}, }, }) => { const { eventEmitter } = useEventEmitterContextContext() const initialConfig = { namespace: 'prompt-editor', nodes: [ CustomTextNode, { replace: TextNode, with: (node: TextNode) => new CustomTextNode(node.__text), }, ContextBlockNode, HistoryBlockNode, QueryBlockNode, VariableValueBlockNode, ], editorState: value ? textToEditorState(value as string) : null, onError: (error: Error) => { throw error }, } const handleEditorChange = (editorState: EditorState) => { const text = editorState.read(() => $getRoot().getTextContent()) if (onChange) onChange(text.replaceAll('\n\n', '\n')) } useEffect(() => { eventEmitter?.emit({ type: UPDATE_DATASETS_EVENT_EMITTER, payload: contextBlock.datasets, } as any) }, [eventEmitter, contextBlock.datasets]) useEffect(() => { eventEmitter?.emit({ type: UPDATE_HISTORY_EVENT_EMITTER, payload: historyBlock.history, } as any) }, [eventEmitter, historyBlock.history]) return (
} placeholder={} ErrorBoundary={LexicalErrorBoundary} /> { contextBlock.show && ( <> ) } { historyBlock.show && ( <> ) } { queryBlock.show && ( <> ) } {/* */}
) } export default PromptEditor