Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
D
dify
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
ai-tech
dify
Commits
c8a39db9
Commit
c8a39db9
authored
Jun 30, 2023
by
Joel
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
feat: run once to new struct
parent
f4702d60
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
224 additions
and
145 deletions
+224
-145
index.tsx
web/app/components/share/text-generation/index.tsx
+27
-122
content.tsx
web/app/components/share/text-generation/result/content.tsx
+34
-0
index.tsx
web/app/components/share/text-generation/result/index.tsx
+163
-23
No files found.
web/app/components/share/text-generation/index.tsx
View file @
c8a39db9
...
...
@@ -11,21 +11,19 @@ import s from './style.module.css'
import
RunBatch
from
'./run-batch'
import
useBreakpoints
,
{
MediaType
}
from
'@/hooks/use-breakpoints'
import
ConfigScence
from
'@/app/components/share/text-generation/config-scence'
import
NoData
from
'@/app/components/share/text-generation/no-data'
// import History from '@/app/components/share/text-generation/history'
import
{
fetchSavedMessage
as
doFetchSavedMessage
,
fetchAppInfo
,
fetchAppParams
,
removeMessage
,
saveMessage
,
sendCompletionMessage
,
updateFeedback
}
from
'@/service/share'
import
{
fetchSavedMessage
as
doFetchSavedMessage
,
fetchAppInfo
,
fetchAppParams
,
removeMessage
,
saveMessage
}
from
'@/service/share'
import
type
{
SiteInfo
}
from
'@/models/share'
import
type
{
MoreLikeThisConfig
,
PromptConfig
,
SavedMessage
}
from
'@/models/debug'
import
Toast
from
'@/app/components/base/toast'
import
AppIcon
from
'@/app/components/base/app-icon'
import
type
{
Feedbacktype
}
from
'@/app/components/app/chat'
import
{
changeLanguage
}
from
'@/i18n/i18next-config'
import
Loading
from
'@/app/components/base/loading'
import
{
userInputsFormToPromptVariables
}
from
'@/utils/model-config'
import
TextGenerationRes
from
'@/app/components/app/text-generate/item
'
import
Res
from
'@/app/components/share/text-generation/result
'
import
SavedItems
from
'@/app/components/app/text-generate/saved-items'
import
type
{
InstalledApp
}
from
'@/models/explore'
import
{
appDefaultIconBackground
}
from
'@/config'
import
Toast
from
'@/app/components/base/toast'
export
type
IMainProps
=
{
isInstalledApp
?:
boolean
...
...
@@ -36,34 +34,22 @@ const TextGeneration: FC<IMainProps> = ({
isInstalledApp
=
false
,
installedAppInfo
,
})
=>
{
const
{
notify
}
=
Toast
const
{
t
}
=
useTranslation
()
const
media
=
useBreakpoints
()
const
isPC
=
media
===
MediaType
.
pc
const
isTablet
=
media
===
MediaType
.
tablet
const
isMoble
=
media
===
MediaType
.
mobile
const
isMob
i
le
=
media
===
MediaType
.
mobile
const
[
currTab
,
setCurrTab
]
=
useState
<
string
>
(
'batch'
)
const
[
inputs
,
setInputs
]
=
useState
<
Record
<
string
,
any
>>
({})
const
[
query
,
setQuery
]
=
useState
(
''
)
// run once query content
const
[
appId
,
setAppId
]
=
useState
<
string
>
(
''
)
const
[
siteInfo
,
setSiteInfo
]
=
useState
<
SiteInfo
|
null
>
(
null
)
const
[
promptConfig
,
setPromptConfig
]
=
useState
<
PromptConfig
|
null
>
(
null
)
const
[
moreLikeThisConfig
,
setMoreLikeThisConfig
]
=
useState
<
MoreLikeThisConfig
|
null
>
(
null
)
const
[
isResponsing
,
{
setTrue
:
setResponsingTrue
,
setFalse
:
setResponsingFalse
}]
=
useBoolean
(
false
)
const
[
query
,
setQuery
]
=
useState
(
''
)
const
[
completionRes
,
setCompletionRes
]
=
useState
(
''
)
const
{
notify
}
=
Toast
const
isNoData
=
!
completionRes
const
[
messageId
,
setMessageId
]
=
useState
<
string
|
null
>
(
null
)
const
[
feedback
,
setFeedback
]
=
useState
<
Feedbacktype
>
({
rating
:
null
,
})
const
handleFeedback
=
async
(
feedback
:
Feedbacktype
)
=>
{
await
updateFeedback
({
url
:
`/messages/
${
messageId
}
/feedbacks`
,
body
:
{
rating
:
feedback
.
rating
}
},
isInstalledApp
,
installedAppInfo
?.
id
)
setFeedback
(
feedback
)
}
const
[
savedMessages
,
setSavedMessages
]
=
useState
<
SavedMessage
[]
>
([])
...
...
@@ -91,83 +77,15 @@ const TextGeneration: FC<IMainProps> = ({
const
logError
=
(
message
:
string
)
=>
{
notify
({
type
:
'error'
,
message
})
}
const
checkCanSend
=
()
=>
{
const
prompt_variables
=
promptConfig
?.
prompt_variables
if
(
!
prompt_variables
||
prompt_variables
?.
length
===
0
)
return
true
let
hasEmptyInput
=
false
const
requiredVars
=
prompt_variables
?.
filter
(({
key
,
name
,
required
})
=>
{
const
res
=
(
!
key
||
!
key
.
trim
())
||
(
!
name
||
!
name
.
trim
())
||
(
required
||
required
===
undefined
||
required
===
null
)
return
res
})
||
[]
// compatible with old version
requiredVars
.
forEach
(({
key
})
=>
{
if
(
hasEmptyInput
)
return
if
(
!
inputs
[
key
])
hasEmptyInput
=
true
})
if
(
hasEmptyInput
)
{
logError
(
t
(
'appDebug.errorMessage.valueOfVarRequired'
))
return
false
}
return
!
hasEmptyInput
const
[
controlSend
,
setControlSend
]
=
useState
(
0
)
const
handleSend
=
()
=>
{
setControlSend
(
Date
.
now
())
}
const
handleSend
=
async
()
=>
{
if
(
isResponsing
)
{
notify
({
type
:
'info'
,
message
:
t
(
'appDebug.errorMessage.waitForResponse'
)
})
return
false
}
if
(
!
checkCanSend
())
return
if
(
!
query
)
{
logError
(
t
(
'appDebug.errorMessage.queryRequired'
))
return
false
}
const
data
=
{
inputs
,
query
,
}
setMessageId
(
null
)
setFeedback
({
rating
:
null
,
})
setCompletionRes
(
''
)
const
res
:
string
[]
=
[]
let
tempMessageId
=
''
if
(
!
isPC
)
// eslint-disable-next-line @typescript-eslint/no-use-before-define
showResSidebar
()
setResponsingTrue
()
sendCompletionMessage
(
data
,
{
onData
:
(
data
:
string
,
_isFirstMessage
:
boolean
,
{
messageId
}:
any
)
=>
{
tempMessageId
=
messageId
res
.
push
(
data
)
setCompletionRes
(
res
.
join
(
''
))
},
onCompleted
:
()
=>
{
setResponsingFalse
()
setMessageId
(
tempMessageId
)
},
onError
()
{
setResponsingFalse
()
},
},
isInstalledApp
,
installedAppInfo
?.
id
)
const
handleRunBatch
=
()
=>
{
setControlSend
(
Date
.
now
())
}
const
handleRunBatch
=
()
=>
{
}
const
fetchInitData
=
()
=>
{
return
Promise
.
all
([
isInstalledApp
?
{
...
...
@@ -219,7 +137,7 @@ const TextGeneration: FC<IMainProps> = ({
cn
(
'flex flex-col h-full shrink-0'
,
isPC
?
'px-10 py-8'
:
'bg-gray-50'
,
isTablet
&&
'p-6'
,
isMoble
&&
'p-4'
)
isTablet
&&
'p-6'
,
isMob
i
le
&&
'p-4'
)
}
>
<>
...
...
@@ -239,33 +157,20 @@ const TextGeneration: FC<IMainProps> = ({
</
div
>
<
div
className=
'grow overflow-y-auto'
>
{
(
isResponsing
&&
!
completionRes
)
?
(
<
div
className=
'flex h-full w-full justify-center items-center'
>
<
Loading
type=
'area'
/>
</
div
>)
:
(
<>
{
isNoData
?
<
NoData
/>
:
(
<
TextGenerationRes
className=
'mt-3'
content=
{
completionRes
}
messageId=
{
messageId
}
isInWebApp
moreLikeThis=
{
moreLikeThisConfig
?.
enabled
}
onFeedback=
{
handleFeedback
}
feedback=
{
feedback
}
onSave=
{
handleSaveMessage
}
isMobile=
{
isMoble
}
isInstalledApp=
{
isInstalledApp
}
installedAppId=
{
installedAppInfo
?.
id
}
/>
)
}
</>
)
}
<
Res
isBatch=
{
currTab
===
'batch'
}
isPC=
{
isPC
}
isMobile=
{
isMobile
}
isInstalledApp=
{
!!
isInstalledApp
}
installedAppInfo=
{
installedAppInfo
}
promptConfig=
{
promptConfig
}
moreLikeThisEnabled=
{
!!
moreLikeThisConfig
?.
enabled
}
inputs=
{
inputs
}
query=
{
query
}
controlSend=
{
controlSend
}
onShowRes=
{
showResSidebar
}
handleSaveMessage=
{
handleSaveMessage
}
/>
</
div
>
</>
</
div
>
...
...
web/app/components/share/text-generation/result/content.tsx
0 → 100644
View file @
c8a39db9
import
type
{
FC
}
from
'react'
import
React
from
'react'
import
Header
from
'./header'
import
type
{
Feedbacktype
}
from
'@/app/components/app/chat'
import
{
format
}
from
'@/service/base'
export
type
IResultProps
=
{
content
:
string
showFeedback
:
boolean
feedback
:
Feedbacktype
onFeedback
:
(
feedback
:
Feedbacktype
)
=>
void
}
const
Result
:
FC
<
IResultProps
>
=
({
content
,
showFeedback
,
feedback
,
onFeedback
,
})
=>
{
return
(
<
div
className=
'basis-3/4 h-max'
>
<
Header
result=
{
content
}
showFeedback=
{
showFeedback
}
feedback=
{
feedback
}
onFeedback=
{
onFeedback
}
/>
<
div
className=
'mt-4 w-full flex text-sm leading-5 overflow-scroll font-normal text-gray-900'
style=
{
{
maxHeight
:
'70vh'
,
}
}
dangerouslySetInnerHTML=
{
{
__html
:
format
(
content
),
}
}
></
div
>
</
div
>
)
}
export
default
React
.
memo
(
Result
)
web/app/components/share/text-generation/result/index.tsx
View file @
c8a39db9
'use client'
import
type
{
FC
}
from
'react'
import
React
from
'react'
import
Header
from
'./header'
import
{
Feedbacktype
}
from
'@/app/components/app/chat'
import
{
format
}
from
'@/service/base'
import
React
,
{
useEffect
,
useState
}
from
'react'
import
{
useBoolean
}
from
'ahooks'
import
{
t
}
from
'i18next'
import
cn
from
'classnames'
import
TextGenerationRes
from
'@/app/components/app/text-generate/item'
import
NoData
from
'@/app/components/share/text-generation/no-data'
import
Toast
from
'@/app/components/base/toast'
import
{
sendCompletionMessage
,
updateFeedback
}
from
'@/service/share'
import
type
{
Feedbacktype
}
from
'@/app/components/app/chat'
import
Loading
from
'@/app/components/base/loading'
import
type
{
PromptConfig
}
from
'@/models/debug'
import
type
{
InstalledApp
}
from
'@/models/explore'
export
type
IResultProps
=
{
content
:
string
showFeedback
:
boolean
feedback
:
Feedbacktype
onFeedback
:
(
feedback
:
Feedbacktype
)
=>
void
isBatch
:
boolean
isPC
:
boolean
isMobile
:
boolean
isInstalledApp
:
boolean
installedAppInfo
?:
InstalledApp
promptConfig
:
PromptConfig
|
null
moreLikeThisEnabled
:
boolean
inputs
:
Record
<
string
,
any
>
query
:
string
controlSend
:
number
onShowRes
:
()
=>
void
handleSaveMessage
:
(
messageId
:
string
)
=>
void
}
const
Result
:
FC
<
IResultProps
>
=
({
content
,
showFeedback
,
feedback
,
onFeedback
isBatch
,
isPC
,
isMobile
,
isInstalledApp
,
installedAppInfo
,
promptConfig
,
moreLikeThisEnabled
,
inputs
,
query
,
controlSend
,
onShowRes
,
handleSaveMessage
,
})
=>
{
const
[
isResponsing
,
{
setTrue
:
setResponsingTrue
,
setFalse
:
setResponsingFalse
}]
=
useBoolean
(
false
)
const
[
completionRes
,
setCompletionRes
]
=
useState
(
''
)
const
{
notify
}
=
Toast
const
isNoData
=
!
completionRes
const
[
messageId
,
setMessageId
]
=
useState
<
string
|
null
>
(
null
)
const
[
feedback
,
setFeedback
]
=
useState
<
Feedbacktype
>
({
rating
:
null
,
})
const
handleFeedback
=
async
(
feedback
:
Feedbacktype
)
=>
{
await
updateFeedback
({
url
:
`/messages/
${
messageId
}
/feedbacks`
,
body
:
{
rating
:
feedback
.
rating
}
},
isInstalledApp
,
installedAppInfo
?.
id
)
setFeedback
(
feedback
)
}
const
logError
=
(
message
:
string
)
=>
{
notify
({
type
:
'error'
,
message
})
}
const
checkCanSend
=
()
=>
{
const
prompt_variables
=
promptConfig
?.
prompt_variables
if
(
!
prompt_variables
||
prompt_variables
?.
length
===
0
)
return
true
let
hasEmptyInput
=
false
const
requiredVars
=
prompt_variables
?.
filter
(({
key
,
name
,
required
})
=>
{
const
res
=
(
!
key
||
!
key
.
trim
())
||
(
!
name
||
!
name
.
trim
())
||
(
required
||
required
===
undefined
||
required
===
null
)
return
res
})
||
[]
// compatible with old version
requiredVars
.
forEach
(({
key
})
=>
{
if
(
hasEmptyInput
)
return
if
(
!
inputs
[
key
])
hasEmptyInput
=
true
})
if
(
hasEmptyInput
)
{
logError
(
t
(
'appDebug.errorMessage.valueOfVarRequired'
))
return
false
}
return
!
hasEmptyInput
}
const
handleSend
=
async
()
=>
{
if
(
isResponsing
)
{
notify
({
type
:
'info'
,
message
:
t
(
'appDebug.errorMessage.waitForResponse'
)
})
return
false
}
if
(
!
checkCanSend
())
return
if
(
!
query
)
{
logError
(
t
(
'appDebug.errorMessage.queryRequired'
))
return
false
}
const
data
=
{
inputs
,
query
,
}
setMessageId
(
null
)
setFeedback
({
rating
:
null
,
})
setCompletionRes
(
''
)
const
res
:
string
[]
=
[]
let
tempMessageId
=
''
if
(
!
isPC
)
onShowRes
()
setResponsingTrue
()
sendCompletionMessage
(
data
,
{
onData
:
(
data
:
string
,
_isFirstMessage
:
boolean
,
{
messageId
}:
any
)
=>
{
tempMessageId
=
messageId
res
.
push
(
data
)
setCompletionRes
(
res
.
join
(
''
))
},
onCompleted
:
()
=>
{
setResponsingFalse
()
setMessageId
(
tempMessageId
)
},
onError
()
{
setResponsingFalse
()
},
},
isInstalledApp
,
installedAppInfo
?.
id
)
}
useEffect
(()
=>
{
if
(
controlSend
)
handleSend
()
},
[
controlSend
])
return
(
<
div
className=
'basis-3/4 h-max'
>
<
Header
result=
{
content
}
showFeedback=
{
showFeedback
}
feedback=
{
feedback
}
onFeedback=
{
onFeedback
}
/>
<
div
className=
'mt-4 w-full flex text-sm leading-5 overflow-scroll font-normal text-gray-900'
style=
{
{
maxHeight
:
'70vh'
}
}
dangerouslySetInnerHTML=
{
{
__html
:
format
(
content
)
}
}
></
div
>
<
div
className=
{
cn
((
isBatch
&&
!
isNoData
)
?
'h-52'
:
'h-full'
)
}
>
{
(
isResponsing
&&
!
completionRes
)
?
(
<
div
className=
'flex h-full w-full justify-center items-center'
>
<
Loading
type=
'area'
/>
</
div
>)
:
(
<>
{
isNoData
?
<
NoData
/>
:
(
<
TextGenerationRes
className=
'mt-3'
content=
{
completionRes
}
messageId=
{
messageId
}
isInWebApp
moreLikeThis=
{
moreLikeThisEnabled
}
onFeedback=
{
handleFeedback
}
feedback=
{
feedback
}
onSave=
{
handleSaveMessage
}
isMobile=
{
isMobile
}
isInstalledApp=
{
isInstalledApp
}
installedAppId=
{
installedAppInfo
?.
id
}
/>
)
}
</>
)
}
</
div
>
)
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment