mirror of
https://github.com/farcasclaudiu/Flowise.git
synced 2026-06-28 15:00:57 +03:00
Add more nodes for agents, loaders
This commit is contained in:
@@ -8,7 +8,6 @@ export const SET_LAYOUT = '@customization/SET_LAYOUT '
|
||||
export const SET_DARKMODE = '@customization/SET_DARKMODE'
|
||||
|
||||
// action - canvas reducer
|
||||
export const REMOVE_EDGE = '@canvas/REMOVE_EDGE'
|
||||
export const SET_DIRTY = '@canvas/SET_DIRTY'
|
||||
export const REMOVE_DIRTY = '@canvas/REMOVE_DIRTY'
|
||||
export const SET_CHATFLOW = '@canvas/SET_CHATFLOW'
|
||||
|
||||
@@ -4,7 +4,8 @@ import PropTypes from 'prop-types'
|
||||
const initialValue = {
|
||||
reactFlowInstance: null,
|
||||
setReactFlowInstance: () => {},
|
||||
deleteNode: () => {}
|
||||
deleteNode: () => {},
|
||||
deleteEdge: () => {}
|
||||
}
|
||||
|
||||
export const flowContext = createContext(initialValue)
|
||||
@@ -17,12 +18,17 @@ export const ReactFlowContext = ({ children }) => {
|
||||
reactFlowInstance.setEdges(reactFlowInstance.getEdges().filter((ns) => ns.source !== id && ns.target !== id))
|
||||
}
|
||||
|
||||
const deleteEdge = (id) => {
|
||||
reactFlowInstance.setEdges(reactFlowInstance.getEdges().filter((edge) => edge.id !== id))
|
||||
}
|
||||
|
||||
return (
|
||||
<flowContext.Provider
|
||||
value={{
|
||||
reactFlowInstance,
|
||||
setReactFlowInstance,
|
||||
deleteNode
|
||||
deleteNode,
|
||||
deleteEdge
|
||||
}}
|
||||
>
|
||||
{children}
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
import * as actionTypes from '../actions'
|
||||
|
||||
export const initialState = {
|
||||
removeEdgeId: '',
|
||||
isDirty: false,
|
||||
chatflow: null
|
||||
}
|
||||
@@ -11,11 +10,6 @@ export const initialState = {
|
||||
|
||||
const canvasReducer = (state = initialState, action) => {
|
||||
switch (action.type) {
|
||||
case actionTypes.REMOVE_EDGE:
|
||||
return {
|
||||
...state,
|
||||
removeEdgeId: action.edgeId
|
||||
}
|
||||
case actionTypes.SET_DIRTY:
|
||||
return {
|
||||
...state,
|
||||
|
||||
@@ -0,0 +1,57 @@
|
||||
import { useState } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import { useTheme } from '@mui/material/styles'
|
||||
import { FormControl, Button } from '@mui/material'
|
||||
import { IconUpload } from '@tabler/icons'
|
||||
import { getFileName } from 'utils/genericHelper'
|
||||
|
||||
export const File = ({ value, fileType, onChange }) => {
|
||||
const theme = useTheme()
|
||||
|
||||
const [myValue, setMyValue] = useState(value ?? '')
|
||||
|
||||
const handleFileUpload = (e) => {
|
||||
if (!e.target.files) return
|
||||
|
||||
const file = e.target.files[0]
|
||||
const { name } = file
|
||||
|
||||
const reader = new FileReader()
|
||||
reader.onload = (evt) => {
|
||||
if (!evt?.target?.result) {
|
||||
return
|
||||
}
|
||||
const { result } = evt.target
|
||||
|
||||
const value = result + `,filename:${name}`
|
||||
|
||||
setMyValue(value)
|
||||
onChange(value)
|
||||
}
|
||||
reader.readAsDataURL(file)
|
||||
}
|
||||
|
||||
return (
|
||||
<FormControl sx={{ mt: 1, width: '100%' }} size='small'>
|
||||
<span
|
||||
style={{
|
||||
fontStyle: 'italic',
|
||||
color: theme.palette.grey['800'],
|
||||
marginBottom: '1rem'
|
||||
}}
|
||||
>
|
||||
{myValue ? getFileName(myValue) : 'Choose a file to upload'}
|
||||
</span>
|
||||
<Button variant='outlined' component='label' fullWidth startIcon={<IconUpload />} sx={{ marginRight: '1rem' }}>
|
||||
{'Upload File'}
|
||||
<input type='file' accept={fileType} hidden onChange={(e) => handleFileUpload(e)} />
|
||||
</Button>
|
||||
</FormControl>
|
||||
)
|
||||
}
|
||||
|
||||
File.propTypes = {
|
||||
value: PropTypes.string,
|
||||
fileType: PropTypes.string,
|
||||
onChange: PropTypes.func
|
||||
}
|
||||
@@ -1,7 +1,9 @@
|
||||
import { getBezierPath, EdgeText } from 'reactflow'
|
||||
import PropTypes from 'prop-types'
|
||||
import { useDispatch } from 'react-redux'
|
||||
import { REMOVE_EDGE } from 'store/actions'
|
||||
import { useContext } from 'react'
|
||||
import { SET_DIRTY } from 'store/actions'
|
||||
import { flowContext } from 'store/context/ReactFlowContext'
|
||||
|
||||
import './index.css'
|
||||
|
||||
@@ -17,11 +19,14 @@ const ButtonEdge = ({ id, sourceX, sourceY, targetX, targetY, sourcePosition, ta
|
||||
targetPosition
|
||||
})
|
||||
|
||||
const { deleteEdge } = useContext(flowContext)
|
||||
|
||||
const dispatch = useDispatch()
|
||||
|
||||
const onEdgeClick = (evt, id) => {
|
||||
evt.stopPropagation()
|
||||
dispatch({ type: REMOVE_EDGE, edgeId: `${id}:${Date.now()}` })
|
||||
deleteEdge(id)
|
||||
dispatch({ type: SET_DIRTY })
|
||||
}
|
||||
|
||||
return (
|
||||
|
||||
@@ -47,7 +47,7 @@ const CanvasNode = ({ data }) => {
|
||||
>
|
||||
<Box>
|
||||
<div style={{ display: 'flex', flexDirection: 'row', alignItems: 'center' }}>
|
||||
<Box item style={{ width: 50, marginRight: 10, padding: 5 }}>
|
||||
<Box style={{ width: 50, marginRight: 10, padding: 5 }}>
|
||||
<div
|
||||
style={{
|
||||
...theme.typography.commonAvatar,
|
||||
|
||||
@@ -8,6 +8,7 @@ import { Box, Typography, Tooltip } from '@mui/material'
|
||||
|
||||
import { Dropdown } from 'ui-component/dropdown/Dropdown'
|
||||
import { Input } from 'ui-component/input/Input'
|
||||
import { File } from 'ui-component/file/File'
|
||||
import { flowContext } from 'store/context/ReactFlowContext'
|
||||
import { isValidConnection } from 'utils/genericHelper'
|
||||
|
||||
@@ -73,6 +74,13 @@ const NodeInputHandler = ({ inputAnchor, inputParam, data }) => {
|
||||
{inputParam.label}
|
||||
{!inputParam.optional && <span style={{ color: 'red' }}> *</span>}
|
||||
</Typography>
|
||||
{inputParam.type === 'file' && (
|
||||
<File
|
||||
fileType={inputParam.fileType || '*'}
|
||||
onChange={(newValue) => (data.inputs[inputParam.name] = newValue)}
|
||||
value={data.inputs[inputParam.name] ?? inputParam.default ?? 'Choose a file to upload'}
|
||||
/>
|
||||
)}
|
||||
{(inputParam.type === 'string' || inputParam.type === 'password' || inputParam.type === 'number') && (
|
||||
<Input
|
||||
inputParam={inputParam}
|
||||
|
||||
@@ -124,7 +124,6 @@ const Canvas = () => {
|
||||
)
|
||||
|
||||
setEdges((eds) => addEdge(newEdge, eds))
|
||||
setDirty()
|
||||
}
|
||||
|
||||
const handleLoadFlow = (file) => {
|
||||
@@ -389,18 +388,6 @@ const Canvas = () => {
|
||||
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||
}, [testChatflowApi.error])
|
||||
|
||||
// Listen to edge button click remove redux event
|
||||
useEffect(() => {
|
||||
if (reactFlowInstance) {
|
||||
const edges = reactFlowInstance.getEdges()
|
||||
const toRemoveEdgeId = canvasDataStore.removeEdgeId.split(':')[0]
|
||||
setEdges(edges.filter((edge) => edge.id !== toRemoveEdgeId))
|
||||
setDirty()
|
||||
}
|
||||
|
||||
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||
}, [canvasDataStore.removeEdgeId])
|
||||
|
||||
useEffect(() => setChatflow(canvasDataStore.chatflow), [canvasDataStore.chatflow])
|
||||
|
||||
// Initialization
|
||||
|
||||
@@ -46,7 +46,6 @@ export const ChatMessage = ({ chatflowid }) => {
|
||||
|
||||
const [open, setOpen] = useState(false)
|
||||
const [userInput, setUserInput] = useState('')
|
||||
const [history, setHistory] = useState([])
|
||||
const [loading, setLoading] = useState(false)
|
||||
const [messages, setMessages] = useState([
|
||||
{
|
||||
@@ -157,7 +156,10 @@ export const ChatMessage = ({ chatflowid }) => {
|
||||
|
||||
// Send user question and history to API
|
||||
try {
|
||||
const response = await predictionApi.sendMessageAndGetPrediction(chatflowid, { question: userInput, history: history })
|
||||
const response = await predictionApi.sendMessageAndGetPrediction(chatflowid, {
|
||||
question: userInput,
|
||||
history: messages.filter((msg) => msg.message !== 'Hi there! How can I help?')
|
||||
})
|
||||
if (response.data) {
|
||||
const data = response.data
|
||||
setMessages((prevMessages) => [...prevMessages, { message: data, type: 'apiMessage' }])
|
||||
@@ -203,13 +205,6 @@ export const ChatMessage = ({ chatflowid }) => {
|
||||
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||
}, [getChatmessageApi.data])
|
||||
|
||||
// Keep history in sync with messages
|
||||
useEffect(() => {
|
||||
if (messages.length >= 3) {
|
||||
setHistory([[messages[messages.length - 2].message, messages[messages.length - 1].message]])
|
||||
}
|
||||
}, [messages])
|
||||
|
||||
// Auto scroll chat to bottom
|
||||
useEffect(() => {
|
||||
scrollToBottom()
|
||||
@@ -229,7 +224,6 @@ export const ChatMessage = ({ chatflowid }) => {
|
||||
|
||||
return () => {
|
||||
setUserInput('')
|
||||
setHistory([])
|
||||
setLoading(false)
|
||||
setMessages([
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user