handleSelectVariable(['memory_block', variable.id])}
+ >
{variable.name}
diff --git a/web/app/components/base/prompt-editor/plugins/workflow-variable-block/component.tsx b/web/app/components/base/prompt-editor/plugins/workflow-variable-block/component.tsx
index 72eb990dd3..e977296bd6 100644
--- a/web/app/components/base/prompt-editor/plugins/workflow-variable-block/component.tsx
+++ b/web/app/components/base/prompt-editor/plugins/workflow-variable-block/component.tsx
@@ -18,7 +18,7 @@ import {
DELETE_WORKFLOW_VARIABLE_BLOCK_COMMAND,
UPDATE_WORKFLOW_NODES_MAP,
} from './index'
-import { isConversationVar, isENV, isRagVariableVar, isSystemVar } from '@/app/components/workflow/nodes/_base/components/variable/utils'
+import { isConversationVar as isConversationVariable, isENV, isMemoryVariable, isRagVariableVar, isSystemVar } from '@/app/components/workflow/nodes/_base/components/variable/utils'
import Tooltip from '@/app/components/base/tooltip'
import { isExceptionVariable } from '@/app/components/workflow/utils'
import VarFullPathPanel from '@/app/components/workflow/nodes/_base/components/variable/var-full-path-panel'
@@ -34,6 +34,7 @@ type WorkflowVariableBlockComponentProps = {
workflowNodesMap: WorkflowNodesMap
environmentVariables?: Var[]
conversationVariables?: Var[]
+ memoryVariables?: Var[]
ragVariables?: Var[]
getVarType?: (payload: {
nodeId: string,
@@ -48,6 +49,7 @@ const WorkflowVariableBlockComponent = ({
getVarType,
environmentVariables,
conversationVariables,
+ memoryVariables,
ragVariables,
}: WorkflowVariableBlockComponentProps) => {
const { t } = useTranslation()
@@ -66,18 +68,23 @@ const WorkflowVariableBlockComponent = ({
const [localWorkflowNodesMap, setLocalWorkflowNodesMap] = useState
(workflowNodesMap)
const node = localWorkflowNodesMap![variables[isRagVar ? 1 : 0]]
const isEnv = isENV(variables)
- // const isChatVar = isConversationVar(variables) && conversationVariables?.some(v => v.variable === `${variables?.[0] ?? ''}.${variables?.[1] ?? ''}` && v.type !== 'memory')
- const isMemoryVar = isConversationVar(variables) && conversationVariables?.some(v => v.variable === `${variables?.[0] ?? ''}.${variables?.[1] ?? ''}` && v.type === 'memory')
+ const isConversationVar = isConversationVariable(variables)
+ const isMemoryVar = isMemoryVariable(variables)
const isException = isExceptionVariable(varName, node?.type)
+
let variableValid = true
if (isEnv) {
if (environmentVariables)
variableValid = environmentVariables.some(v => v.variable === `${variables?.[0] ?? ''}.${variables?.[1] ?? ''}`)
}
- else if (isConversationVar(variables)) {
+ else if (isConversationVar) {
if (conversationVariables)
variableValid = conversationVariables.some(v => v.variable === `${variables?.[0] ?? ''}.${variables?.[1] ?? ''}`)
}
+ else if (isMemoryVar) {
+ if (memoryVariables)
+ variableValid = memoryVariables.some(v => v.variable === `${variables?.[0] ?? ''}.${variables?.[1] ?? ''}`)
+ }
else if (isRagVar) {
if (ragVariables)
variableValid = ragVariables.some(v => v.variable === `${variables?.[0] ?? ''}.${variables?.[1] ?? ''}.${variables?.[2] ?? ''}`)
@@ -136,7 +143,6 @@ const WorkflowVariableBlockComponent = ({
handleVariableJump()
}}
isExceptionVariable={isException}
- isMemoryVariable={isMemoryVar}
errorMsg={!variableValid ? t('workflow.errorMsg.invalidVariable') : undefined}
isSelected={isSelected}
ref={ref}
diff --git a/web/app/components/base/prompt-editor/plugins/workflow-variable-block/node.tsx b/web/app/components/base/prompt-editor/plugins/workflow-variable-block/node.tsx
index bdecb21034..afdf7844ba 100644
--- a/web/app/components/base/prompt-editor/plugins/workflow-variable-block/node.tsx
+++ b/web/app/components/base/prompt-editor/plugins/workflow-variable-block/node.tsx
@@ -22,6 +22,7 @@ export class WorkflowVariableBlockNode extends DecoratorNode
__getVarType?: GetVarType
__environmentVariables?: Var[]
__conversationVariables?: Var[]
+ __memoryVariables?: Var[]
__ragVariables?: Var[]
static getType(): string {
@@ -36,7 +37,16 @@ export class WorkflowVariableBlockNode extends DecoratorNode
return true
}
- constructor(variables: string[], workflowNodesMap: WorkflowNodesMap, getVarType: any, key?: NodeKey, environmentVariables?: Var[], conversationVariables?: Var[], ragVariables?: Var[]) {
+ constructor(
+ variables: string[],
+ workflowNodesMap: WorkflowNodesMap,
+ getVarType: any,
+ key?: NodeKey,
+ environmentVariables?: Var[],
+ conversationVariables?: Var[],
+ memoryVariables?: Var[],
+ ragVariables?: Var[],
+ ) {
super(key)
this.__variables = variables
@@ -44,6 +54,7 @@ export class WorkflowVariableBlockNode extends DecoratorNode
this.__getVarType = getVarType
this.__environmentVariables = environmentVariables
this.__conversationVariables = conversationVariables
+ this.__memoryVariables = memoryVariables
this.__ragVariables = ragVariables
}
@@ -66,6 +77,7 @@ export class WorkflowVariableBlockNode extends DecoratorNode
getVarType={this.__getVarType!}
environmentVariables={this.__environmentVariables}
conversationVariables={this.__conversationVariables}
+ memoryVariables={this.__memoryVariables}
ragVariables={this.__ragVariables}
/>
)
@@ -115,6 +127,11 @@ export class WorkflowVariableBlockNode extends DecoratorNode
return self.__conversationVariables
}
+ getMemoryVariables(): any {
+ const self = this.getLatest()
+ return self.__memoryVariables
+ }
+
getRagVariables(): any {
const self = this.getLatest()
return self.__ragVariables
@@ -124,8 +141,8 @@ export class WorkflowVariableBlockNode extends DecoratorNode
return `{{#${this.getVariables().join('.')}#}}`
}
}
-export function $createWorkflowVariableBlockNode(variables: string[], workflowNodesMap: WorkflowNodesMap, getVarType?: GetVarType, environmentVariables?: Var[], conversationVariables?: Var[], ragVariables?: Var[]): WorkflowVariableBlockNode {
- return new WorkflowVariableBlockNode(variables, workflowNodesMap, getVarType, undefined, environmentVariables, conversationVariables, ragVariables)
+export function $createWorkflowVariableBlockNode(variables: string[], workflowNodesMap: WorkflowNodesMap, getVarType?: GetVarType, environmentVariables?: Var[], conversationVariables?: Var[], memoryVariables?: Var[], ragVariables?: Var[]): WorkflowVariableBlockNode {
+ return new WorkflowVariableBlockNode(variables, workflowNodesMap, getVarType, undefined, environmentVariables, conversationVariables, memoryVariables, ragVariables)
}
export function $isWorkflowVariableBlockNode(
diff --git a/web/app/components/workflow-app/components/workflow-main.tsx b/web/app/components/workflow-app/components/workflow-main.tsx
index f639eda08d..2e953f12d8 100644
--- a/web/app/components/workflow-app/components/workflow-main.tsx
+++ b/web/app/components/workflow-app/components/workflow-main.tsx
@@ -53,7 +53,7 @@ const WorkflowMain = ({
}
if (memory_blocks) {
const { setMemoryVariables } = workflowStore.getState()
- setMemoryVariables(formatMemoryVariables(memory_blocks, nodes))
+ setMemoryVariables(formatMemoryVariables(memory_blocks))
}
}, [featuresStore, workflowStore, formatMemoryVariables])
diff --git a/web/app/components/workflow-app/hooks/use-nodes-sync-draft.ts b/web/app/components/workflow-app/hooks/use-nodes-sync-draft.ts
index 853dfb907c..174debb982 100644
--- a/web/app/components/workflow-app/hooks/use-nodes-sync-draft.ts
+++ b/web/app/components/workflow-app/hooks/use-nodes-sync-draft.ts
@@ -85,7 +85,7 @@ export const useNodesSyncDraft = () => {
},
environment_variables: environmentVariables,
conversation_variables: conversationVariables,
- memory_blocks: memoryVariables.map(({ node, value_type, more, model, ...rest }) => {
+ memory_blocks: memoryVariables.map(({ value_type, more, model, ...rest }) => {
return {
...rest,
model: model ? {
diff --git a/web/app/components/workflow-app/hooks/use-workflow-init.ts b/web/app/components/workflow-app/hooks/use-workflow-init.ts
index 70049a3380..6defb6e4f5 100644
--- a/web/app/components/workflow-app/hooks/use-workflow-init.ts
+++ b/web/app/components/workflow-app/hooks/use-workflow-init.ts
@@ -55,7 +55,7 @@ export const useWorkflowInit = () => {
}, {} as Record),
environmentVariables: res.environment_variables?.map(env => env.value_type === 'secret' ? { ...env, value: '[__HIDDEN__]' } : env) || [],
conversationVariables: res.conversation_variables || [],
- memoryVariables: formatMemoryVariables((res.memory_blocks || []), res.graph.nodes),
+ memoryVariables: formatMemoryVariables((res.memory_blocks || [])),
})
setSyncWorkflowDraftHash(res.hash)
setIsLoading(false)
diff --git a/web/app/components/workflow-app/hooks/use-workflow-refresh-draft.ts b/web/app/components/workflow-app/hooks/use-workflow-refresh-draft.ts
index 110f96fee9..b26ee0d45d 100644
--- a/web/app/components/workflow-app/hooks/use-workflow-refresh-draft.ts
+++ b/web/app/components/workflow-app/hooks/use-workflow-refresh-draft.ts
@@ -30,7 +30,7 @@ export const useWorkflowRefreshDraft = () => {
}, {} as Record))
setEnvironmentVariables(response.environment_variables?.map(env => env.value_type === 'secret' ? { ...env, value: '[__HIDDEN__]' } : env) || [])
setConversationVariables(response.conversation_variables || [])
- setMemoryVariables(formatMemoryVariables((response.memory_blocks || []), response.graph.nodes))
+ setMemoryVariables(formatMemoryVariables((response.memory_blocks || [])))
}).finally(() => setIsSyncingWorkflowDraft(false))
}, [handleUpdateWorkflowCanvas, workflowStore, formatMemoryVariables])
diff --git a/web/app/components/workflow/hooks/use-memory-variable.ts b/web/app/components/workflow/hooks/use-memory-variable.ts
index 5b4b4d523f..edd913dda3 100644
--- a/web/app/components/workflow/hooks/use-memory-variable.ts
+++ b/web/app/components/workflow/hooks/use-memory-variable.ts
@@ -1,82 +1,29 @@
import { useCallback } from 'react'
-import { useStoreApi } from 'reactflow'
-import produce from 'immer'
import {
useStore,
useWorkflowStore,
} from '@/app/components/workflow/store'
-import { BlockEnum } from '@/app/components/workflow/types'
import { ChatVarType } from '@/app/components/workflow/panel/chat-variable-panel/type'
-import type { MemoryVariable, Node } from '@/app/components/workflow/types'
-import type { LLMNodeType } from '@/app/components/workflow/nodes/llm/types'
+import type { MemoryVariable } from '@/app/components/workflow/types'
export const useMemoryVariable = () => {
const workflowStore = useWorkflowStore()
const setMemoryVariables = useStore(s => s.setMemoryVariables)
- const store = useStoreApi()
-
- const handleAddMemoryVariableToNode = useCallback((nodeId: string, memoryVariableId: string) => {
- const { getNodes, setNodes } = store.getState()
- const nodes = getNodes()
- const newNodes = produce(nodes, (draft) => {
- const currentNode = draft.find(n => n.id === nodeId)
- if (currentNode) {
- currentNode.data.memory = {
- ...(currentNode.data.memory || {}),
- block_id: [...(currentNode.data.memory?.block_id || []), memoryVariableId],
- }
- }
- })
- setNodes(newNodes)
- }, [store])
-
- const handleDeleteMemoryVariableFromNode = useCallback((nodeId: string, memoryVariableId: string) => {
- const { getNodes, setNodes } = store.getState()
- const nodes = getNodes()
- const newNodes = produce(nodes, (draft) => {
- const currentNode = draft.find(n => n.id === nodeId)
- if (currentNode) {
- currentNode.data.memory = {
- ...(currentNode.data.memory || {}),
- block_id: currentNode.data.memory?.block_id?.filter((id: string) => id !== memoryVariableId) || [],
- }
- }
- })
- setNodes(newNodes)
- }, [store])
const handleAddMemoryVariable = useCallback((memoryVariable: MemoryVariable) => {
const { memoryVariables } = workflowStore.getState()
setMemoryVariables([memoryVariable, ...memoryVariables])
-
- if (memoryVariable.node)
- handleAddMemoryVariableToNode(memoryVariable.node, memoryVariable.id)
- }, [setMemoryVariables, workflowStore, handleAddMemoryVariableToNode])
+ }, [setMemoryVariables, workflowStore])
const handleUpdateMemoryVariable = useCallback((memoryVariable: MemoryVariable) => {
const { memoryVariables } = workflowStore.getState()
- const oldMemoryVariable = memoryVariables.find(v => v.id === memoryVariable.id)
setMemoryVariables(memoryVariables.map(v => v.id === memoryVariable.id ? memoryVariable : v))
-
- if (oldMemoryVariable && !oldMemoryVariable?.node && memoryVariable.node) {
- handleAddMemoryVariableToNode(memoryVariable.node, memoryVariable.id)
- }
- else if (oldMemoryVariable && oldMemoryVariable.node && !memoryVariable.node) {
- handleDeleteMemoryVariableFromNode(oldMemoryVariable.node, memoryVariable.id)
- }
- else if (oldMemoryVariable && oldMemoryVariable.node && memoryVariable.node && memoryVariable.node !== oldMemoryVariable.node) {
- handleDeleteMemoryVariableFromNode(oldMemoryVariable.node, memoryVariable.id)
- handleAddMemoryVariableToNode(memoryVariable.node, memoryVariable.id)
- }
- }, [setMemoryVariables, workflowStore, handleAddMemoryVariableToNode, handleDeleteMemoryVariableFromNode])
+ }, [setMemoryVariables, workflowStore])
const handleDeleteMemoryVariable = useCallback((memoryVariable: MemoryVariable) => {
const { memoryVariables } = workflowStore.getState()
setMemoryVariables(memoryVariables.filter(v => v.id !== memoryVariable.id))
-
- if (memoryVariable.node)
- handleDeleteMemoryVariableFromNode(memoryVariable.node, memoryVariable.id)
- }, [setMemoryVariables, workflowStore, handleDeleteMemoryVariableFromNode])
+ }, [setMemoryVariables, workflowStore])
return {
handleAddMemoryVariable,
@@ -86,32 +33,8 @@ export const useMemoryVariable = () => {
}
export const useFormatMemoryVariables = () => {
- const formatMemoryVariables = useCallback((memoryVariables: MemoryVariable[], nodes: Node[]) => {
- let clonedMemoryVariables = [...memoryVariables]
- const nodeScopeMemoryVariablesIds = clonedMemoryVariables.filter(v => v.scope === 'node').map(v => v.id)
- const nodeScopeMemoryVariablesMap = nodeScopeMemoryVariablesIds.reduce((acc, id) => {
- acc[id] = id
- return acc
- }, {} as Record)
-
- if (!!nodeScopeMemoryVariablesIds.length) {
- const llmNodes = nodes.filter(n => n.data.type === BlockEnum.LLM)
-
- clonedMemoryVariables = clonedMemoryVariables.map((v) => {
- if (nodeScopeMemoryVariablesMap[v.id]) {
- const node = llmNodes.find(n => ((n.data as LLMNodeType).memory?.block_id || []).includes(v.id))
-
- return {
- ...v,
- node: node?.id,
- }
- }
-
- return v
- })
- }
-
- return clonedMemoryVariables.map((v) => {
+ const formatMemoryVariables = useCallback((memoryVariables: MemoryVariable[]) => {
+ return memoryVariables.map((v) => {
return {
...v,
value_type: ChatVarType.Memory,
diff --git a/web/app/components/workflow/nodes/_base/components/variable/utils.ts b/web/app/components/workflow/nodes/_base/components/variable/utils.ts
index 29195377af..ddffcff4e7 100644
--- a/web/app/components/workflow/nodes/_base/components/variable/utils.ts
+++ b/web/app/components/workflow/nodes/_base/components/variable/utils.ts
@@ -72,6 +72,10 @@ export const isConversationVar = (valueSelector: ValueSelector) => {
return valueSelector[0] === 'conversation'
}
+export const isMemoryVariable = (valueSelector: ValueSelector) => {
+ return valueSelector[0] === 'memory_block'
+}
+
export const isRagVariableVar = (valueSelector: ValueSelector) => {
if (!valueSelector) return false
return valueSelector[0] === 'rag'
diff --git a/web/app/components/workflow/nodes/_base/components/variable/variable-label/base/variable-icon.tsx b/web/app/components/workflow/nodes/_base/components/variable/variable-label/base/variable-icon.tsx
index aa78eae341..93f47f794a 100644
--- a/web/app/components/workflow/nodes/_base/components/variable/variable-label/base/variable-icon.tsx
+++ b/web/app/components/workflow/nodes/_base/components/variable/variable-label/base/variable-icon.tsx
@@ -7,15 +7,13 @@ export type VariableIconProps = {
className?: string
variables?: string[]
variableCategory?: VarInInspectType | string
- isMemoryVariable?: boolean
}
const VariableIcon = ({
className,
variables = [],
variableCategory,
- isMemoryVariable,
}: VariableIconProps) => {
- const VarIcon = useVarIcon(variables, variableCategory, isMemoryVariable)
+ const VarIcon = useVarIcon(variables, variableCategory)
return VarIcon && (
{
+export const useVarIcon = (variables: string[], variableCategory?: VarInInspectType | string) => {
if (variableCategory === 'loop')
return Loop
@@ -21,7 +22,7 @@ export const useVarIcon = (variables: string[], variableCategory?: VarInInspectT
if (isENV(variables) || variableCategory === VarInInspectType.environment || variableCategory === 'environment')
return Env
- if (isMemoryVariable)
+ if (isMemoryVariable(variables) || variableCategory === VarInInspectType.memory || variableCategory === 'memory_block')
return Memory
if (isConversationVar(variables) || variableCategory === VarInInspectType.conversation || variableCategory === 'conversation')
@@ -44,6 +45,9 @@ export const useVarColor = (variables: string[], isExceptionVariable?: boolean,
if (isConversationVar(variables) || variableCategory === VarInInspectType.conversation || variableCategory === 'conversation')
return 'text-util-colors-teal-teal-700'
+ if (isMemoryVariable(variables) || variableCategory === VarInInspectType.memory || variableCategory === 'memory_block')
+ return 'text-util-colors-teal-teal-700'
+
return 'text-text-accent'
}, [variables, isExceptionVariable, variableCategory])
}
@@ -92,6 +96,15 @@ export const useVarBgColorInEditor = (variables: string[], hasError?: boolean) =
}
}
+ if (isMemoryVariable(variables)) {
+ return {
+ hoverBorderColor: 'hover:border-util-colors-teal-teal-100',
+ hoverBgColor: 'hover:bg-util-colors-teal-teal-50',
+ selectedBorderColor: 'border-util-colors-teal-teal-600',
+ selectedBgColor: 'bg-util-colors-teal-teal-50',
+ }
+ }
+
return {
hoverBorderColor: 'hover:border-state-accent-alt',
hoverBgColor: 'hover:bg-state-accent-hover',
diff --git a/web/app/components/workflow/nodes/llm/components/memory-system/block-memory.tsx b/web/app/components/workflow/nodes/llm/components/memory-system/block-memory.tsx
index 8f50a683ce..f05855e3ef 100644
--- a/web/app/components/workflow/nodes/llm/components/memory-system/block-memory.tsx
+++ b/web/app/components/workflow/nodes/llm/components/memory-system/block-memory.tsx
@@ -15,12 +15,12 @@ import Confirm from '@/app/components/base/confirm'
import { Memory as MemoryIcon } from '@/app/components/base/icons/src/vender/line/others'
type BlockMemoryProps = {
+ id: string
payload: Memory
}
-const BlockMemory = ({ payload }: BlockMemoryProps) => {
+const BlockMemory = ({ id }: BlockMemoryProps) => {
const { t } = useTranslation()
- const { block_id } = payload
- const { memoryVariablesInUsed } = useMemoryVariables(block_id || [])
+ const { memoryVariablesInUsed } = useMemoryVariables(id)
const [showConfirm, setShowConfirm] = useState<{
title: string
desc: string
diff --git a/web/app/components/workflow/nodes/llm/components/memory-system/hooks/use-memory-variables.ts b/web/app/components/workflow/nodes/llm/components/memory-system/hooks/use-memory-variables.ts
index df416ae640..4b303aeda4 100644
--- a/web/app/components/workflow/nodes/llm/components/memory-system/hooks/use-memory-variables.ts
+++ b/web/app/components/workflow/nodes/llm/components/memory-system/hooks/use-memory-variables.ts
@@ -1,12 +1,12 @@
import { useMemo } from 'react'
import { useStore } from '@/app/components/workflow/store'
-export const useMemoryVariables = (blockIds: string[]) => {
+export const useMemoryVariables = (nodeId: string) => {
const memoryVariables = useStore(s => s.memoryVariables)
const memoryVariablesInUsed = useMemo(() => {
- return memoryVariables.filter(variable => blockIds.includes(variable.id))
- }, [memoryVariables, blockIds])
+ return memoryVariables.filter(variable => variable.node_id === nodeId)
+ }, [memoryVariables, nodeId])
const handleDelete = (blockId: string) => {
console.log('delete', blockId)
diff --git a/web/app/components/workflow/nodes/llm/components/memory-system/index.tsx b/web/app/components/workflow/nodes/llm/components/memory-system/index.tsx
index 4eb11e3785..d4c8f5506f 100644
--- a/web/app/components/workflow/nodes/llm/components/memory-system/index.tsx
+++ b/web/app/components/workflow/nodes/llm/components/memory-system/index.tsx
@@ -92,7 +92,7 @@ const MemorySystem = ({
}
{
memoryType === MemoryMode.block && !collapsed && (
-
+
)
}
>
diff --git a/web/app/components/workflow/panel/chat-variable-panel/hooks/use-form/use-memory-schema.ts b/web/app/components/workflow/panel/chat-variable-panel/hooks/use-form/use-memory-schema.ts
index 8bf1fe73d2..5763ebb72c 100644
--- a/web/app/components/workflow/panel/chat-variable-panel/hooks/use-form/use-memory-schema.ts
+++ b/web/app/components/workflow/panel/chat-variable-panel/hooks/use-form/use-memory-schema.ts
@@ -118,7 +118,7 @@ export const useMemorySchema = () => {
},
},
{
- name: 'node',
+ name: 'node_id',
label: 'Node',
type: FormTypeEnum.nodeSelector,
fieldClassName: 'flex justify-between',
diff --git a/web/app/components/workflow/types.ts b/web/app/components/workflow/types.ts
index 357fb1511e..a39426df57 100644
--- a/web/app/components/workflow/types.ts
+++ b/web/app/components/workflow/types.ts
@@ -176,10 +176,10 @@ export type MemoryVariable = {
strategy?: string
update_turns?: number
scope?: string
+ node_id?: string
term?: string
end_user_editable?: boolean
value_type: ChatVarType
- node?: string
more?: boolean
}
diff --git a/web/app/components/workflow/update-dsl-modal.tsx b/web/app/components/workflow/update-dsl-modal.tsx
index d63cc4d8f5..29e53fa065 100644
--- a/web/app/components/workflow/update-dsl-modal.tsx
+++ b/web/app/components/workflow/update-dsl-modal.tsx
@@ -130,7 +130,7 @@ const UpdateDSLModal = ({
hash,
conversation_variables: conversation_variables || [],
environment_variables: environment_variables || [],
- memory_blocks: formatMemoryVariables(memory_blocks || [], formattedNodes),
+ memory_blocks: formatMemoryVariables(memory_blocks || []),
},
} as any)
}, [eventEmitter, formatMemoryVariables])
diff --git a/web/types/workflow.ts b/web/types/workflow.ts
index a32b6015bb..12f7763d5f 100644
--- a/web/types/workflow.ts
+++ b/web/types/workflow.ts
@@ -395,6 +395,7 @@ export enum VarInInspectType {
environment = 'env',
node = 'node',
system = 'sys',
+ memory = 'memory_block',
}
export type FullContent = {