Merge branch 'main' into feat/rag-pipeline

This commit is contained in:
twwu 2025-06-16 14:25:58 +08:00
commit 9ab0d5fe60
17 changed files with 82 additions and 58 deletions

28
.github/workflows/deploy-rag-dev.yml vendored Normal file
View File

@ -0,0 +1,28 @@
name: Deploy RAG Dev
permissions:
contents: read
on:
workflow_run:
workflows: ["Build and Push API & Web"]
branches:
- "deploy/rag-dev"
types:
- completed
jobs:
deploy:
runs-on: ubuntu-latest
if: |
github.event.workflow_run.conclusion == 'success' &&
github.event.workflow_run.head_branch == 'deploy/rag-dev'
steps:
- name: Deploy to server
uses: appleboy/ssh-action@v0.1.8
with:
host: ${{ secrets.RAG_SSH_HOST }}
username: ${{ secrets.SSH_USER }}
key: ${{ secrets.SSH_PRIVATE_KEY }}
script: |
${{ vars.SSH_SCRIPT || secrets.SSH_SCRIPT }}

View File

@ -6,7 +6,6 @@ from pydantic import BaseModel, Field
from core.model_runtime.entities.llm_entities import LLMUsage
from core.rag.entities.citation_metadata import RetrievalSourceMetadata
from core.workflow.entities.node_entities import NodeRunResult
from core.workflow.entities.workflow_node_execution import WorkflowNodeExecutionStatus
class RunCompletedEvent(BaseModel):
@ -39,11 +38,3 @@ class RunRetryEvent(BaseModel):
error: str = Field(..., description="error")
retry_index: int = Field(..., description="Retry attempt number")
start_at: datetime = Field(..., description="Retry start time")
class SingleStepRetryEvent(NodeRunResult):
"""Single step retry event"""
status: WorkflowNodeExecutionStatus = WorkflowNodeExecutionStatus.RETRY
elapsed_time: float = Field(..., description="elapsed time")

View File

@ -39,10 +39,6 @@ from core.variables.variables import (
from core.workflow.constants import CONVERSATION_VARIABLE_NODE_ID, ENVIRONMENT_VARIABLE_NODE_ID
class InvalidSelectorError(ValueError):
pass
class UnsupportedSegmentTypeError(Exception):
pass

View File

@ -4,7 +4,6 @@ from . import (
app_model_config,
audio,
base,
completion,
conversation,
dataset,
document,
@ -19,7 +18,6 @@ __all__ = [
"app_model_config",
"audio",
"base",
"completion",
"conversation",
"dataset",
"document",

View File

@ -55,7 +55,3 @@ class MemberNotInTenantError(BaseServiceError):
class RoleAlreadyAssignedError(BaseServiceError):
pass
class RateLimitExceededError(BaseServiceError):
pass

View File

@ -1,5 +0,0 @@
from services.errors.base import BaseServiceError
class CompletionStoppedError(BaseServiceError):
pass

View File

@ -314,7 +314,10 @@ function AppPreview({ mode }: { mode: AppMode }) {
'advanced-chat': {
title: t('app.types.advanced'),
description: t('app.newApp.advancedUserDescription'),
link: docLink('/guides/workflow/readme'),
link: docLink('/guides/workflow/README', {
'zh-Hans': '/guides/workflow/readme',
'ja-JP': '/guides/workflow/concepts',
}),
},
'agent-chat': {
title: t('app.types.agent'),
@ -324,13 +327,18 @@ function AppPreview({ mode }: { mode: AppMode }) {
'completion': {
title: t('app.newApp.completeApp'),
description: t('app.newApp.completionUserDescription'),
link: docLink('/guides/application-orchestrate/text-generator',
{ 'zh-Hans': '/guides/application-orchestrate/readme' }),
link: docLink('/guides/application-orchestrate/text-generator', {
'zh-Hans': '/guides/application-orchestrate/readme',
'ja-JP': '/guides/application-orchestrate/README',
}),
},
'workflow': {
title: t('app.types.workflow'),
description: t('app.newApp.workflowUserDescription'),
link: docLink('/guides/workflow/readme'),
link: docLink('/guides/workflow/README', {
'zh-Hans': '/guides/workflow/readme',
'ja-JP': '/guides/workflow/concepts',
}),
},
}
const previewInfo = modeToPreviewInfoMap[mode]

View File

@ -237,7 +237,9 @@ const SettingsModal: FC<ISettingsModalProps> = ({
</div>
<div className='system-xs-regular mt-0.5 text-text-tertiary'>
<span>{t(`${prefixSettings}.modalTip`)}</span>
<Link href={docLink('/guides/application-publishing/launch-your-webapp-quickly/README')}
<Link href={docLink('/guides/application-publishing/launch-your-webapp-quickly/README', {
'zh-Hans': '/guides/application-publishing/launch-your-webapp-quickly/readme',
})}
target='_blank' rel='noopener noreferrer' className='text-text-accent'>{t('common.operation.learnMore')}</Link>
</div>
</div>

View File

@ -59,7 +59,7 @@ const Form: FC<FormProps> = React.memo(({
</label>
{variable === 'endpoint' && (
<a
href={docLink('/guides/knowledge-base/external-knowledge-api-documentation') || '/'}
href={docLink('/guides/knowledge-base/connect-external-knowledge-base') || '/'}
target='_blank'
rel='noopener noreferrer'
className='body-xs-regular flex items-center text-text-accent'

View File

@ -53,7 +53,7 @@ const ExternalAPIPanel: React.FC<ExternalAPIPanelProps> = ({ onClose }) => {
<div className='system-xl-semibold self-stretch text-text-primary'>{t('dataset.externalAPIPanelTitle')}</div>
<div className='body-xs-regular self-stretch text-text-tertiary'>{t('dataset.externalAPIPanelDescription')}</div>
<a className='flex cursor-pointer items-center justify-center gap-1 self-stretch'
href={docLink('/guides/knowledge-base/external-knowledge-api-documentation')} target='_blank'>
href={docLink('/guides/knowledge-base/connect-external-knowledge-base')} target='_blank'>
<RiBookOpenLine className='h-3 w-3 text-text-accent' />
<div className='body-xs-regular grow text-text-accent'>{t('dataset.externalAPIPanelDocumentation')}</div>
</a>

View File

@ -74,7 +74,10 @@ const ModifyRetrievalModal: FC<Props> = ({
<a
target='_blank'
rel='noopener noreferrer'
href={docLink('/guides/knowledge-base/create-knowledge-and-upload-documents#id-4-retrieval-settings')}
href={docLink('/guides/knowledge-base/retrieval-test-and-citation#modify-text-retrieval-setting', {
'zh-Hans': '/guides/knowledge-base/retrieval-test-and-citation#修改文本检索方式',
'ja-JP': '/guides/knowledge-base/retrieval-test-and-citation',
})}
className='text-text-accent'
>
{t('datasetSettings.form.retrievalSetting.learnMore')}

View File

@ -37,7 +37,7 @@ import Divider from '@/app/components/base/divider'
import ChunkStructure from '../chunk-structure'
import Toast from '@/app/components/base/toast'
import { RiAlertFill } from '@remixicon/react'
import { useGetDocLanguage } from '@/context/i18n'
import { useDocLink } from '@/context/i18n'
const rowClass = 'flex gap-x-1'
const labelClass = 'flex items-center shrink-0 w-[180px] h-7 pt-1'
@ -57,6 +57,7 @@ const DEFAULT_APP_ICON: IconInfo = {
const Form = () => {
const { t } = useTranslation()
const docLink = useDocLink()
const { mutate } = useSWRConfig()
const isCurrentWorkspaceDatasetOperator = useAppContextWithSelector(state => state.isCurrentWorkspaceDatasetOperator)
const currentDataset = useDatasetDetailContextWithSelector(state => state.dataset)
@ -91,7 +92,6 @@ const Form = () => {
} = useModelListAndDefaultModelAndCurrentProviderAndModel(ModelTypeEnum.rerank)
const { data: embeddingModelList } = useModelList(ModelTypeEnum.textEmbedding)
const previousAppIcon = useRef(DEFAULT_APP_ICON)
const docLanguage = useGetDocLanguage()
const getMembers = async () => {
const { accounts } = await fetchMembers({ url: '/workspaces/current/members', params: {} })
@ -283,7 +283,7 @@ const Form = () => {
<a
target='_blank'
rel='noopener noreferrer'
href={`https://docs.dify.ai/${docLanguage}/guides/knowledge-base/create-knowledge-and-upload-documents/chunking-and-cleaning-text`}
href={docLink('/guides/knowledge-base/create-knowledge-and-upload-documents/chunking-and-cleaning-text')}
className='text-text-accent'
>
{t('datasetSettings.form.chunkStructure.learnMore')}
@ -423,7 +423,10 @@ const Form = () => {
<a
target='_blank'
rel='noopener noreferrer'
href={`https://docs.dify.ai/${docLanguage}/guides/knowledge-base/create-knowledge-and-upload-documents/setting-indexing-methods`}
href={docLink('/guides/knowledge-base/create-knowledge-and-upload-documents/setting-indexing-methods#setting-the-retrieval-setting', {
'zh-Hans': '/guides/knowledge-base/create-knowledge-and-upload-documents/setting-indexing-methods#指定检索方式',
'ja-JP': '/guides/knowledge-base/create-knowledge-and-upload-documents/setting-indexing-methods#検索方法の指定',
})}
className='text-text-accent'
>
{t('datasetSettings.form.retrievalSetting.learnMore')}

View File

@ -222,7 +222,8 @@ export const AgentStrategy = memo((props: AgentStrategyProps) => {
description={<div className='text-xs text-text-tertiary'>
{t('workflow.nodes.agent.strategy.configureTipDesc')} <br />
<Link href={docLink('/guides/workflow/node/agent#select-an-agent-strategy', {
'zh-Hans': '/guides/workflow/node/agent#xuan-ze-agent-ce-le',
'zh-Hans': '/guides/workflow/node/agent#选择-agent-策略',
'ja-JP': '/guides/workflow/node/agent#エージェント戦略の選択',
})}
className='text-text-accent-secondary' target='_blank'>
{t('workflow.nodes.agent.learnMore')}

View File

@ -36,7 +36,9 @@ const DefaultValue = ({
{t('workflow.nodes.common.errorHandle.defaultValue.desc')}
&nbsp;
<a
href={docLink('/guides/workflow/error-handling/README')}
href={docLink('/guides/workflow/error-handling/README', {
'zh-Hans': '/guides/workflow/error-handling/readme',
})}
target='_blank'
className='text-text-accent'
>

View File

@ -48,8 +48,11 @@ const VarReferencePopup: FC<Props> = ({
description={<div className='system-xs-regular text-text-tertiary'>
{t('workflow.variableReference.assignedVarsDescription')}
<a target='_blank' rel='noopener noreferrer'
className='text-text-accent-secondary'
href={docLink('/guides/workflow/variables#conversation-variables', { 'zh-Hans': '/guides/workflow/variables#hui-hua-bian-liang' })}>
className='text-text-accent-secondary'
href={docLink('/guides/workflow/variables#conversation-variables', {
'zh-Hans': '/guides/workflow/variables#会话变量',
'ja-JP': '/guides/workflow/variables#会話変数',
})}>
{t('workflow.variableReference.conversationVars')}
</a>
</div>}

View File

@ -138,10 +138,13 @@ const ChatVariablePanel = () => {
<div className='system-sm-regular mb-4 mt-1 text-text-secondary'>
{t('workflow.chatVariable.panelDescription')}
<a target='_blank' rel='noopener noreferrer' className='text-text-accent'
href={docLink('/guides/workflow/variables#conversation-variables', { 'zh-Hans': '/guides/workflow/variables#hui-hua-bian-liang' })}>
href={docLink('/guides/workflow/variables#conversation-variables', {
'zh-Hans': '/guides/workflow/variables#会话变量',
'ja-JP': '/guides/workflow/variables#会話変数',
})}>
{t('workflow.chatVariable.docLink')}
</a>
</div>
</div>
<div className='flex items-center gap-2'>
<div className='radius-lg flex flex-col border border-workflow-block-border bg-workflow-block-bg p-3 pb-4 shadow-md'>
<BubbleX className='mb-1 h-4 w-4 shrink-0 text-util-colors-teal-teal-700' />
@ -167,7 +170,7 @@ const ChatVariablePanel = () => {
</div>
</div>
</div>
<div className='absolute right-[38px] top-[-4px] z-10 h-3 w-3 rotate-45 bg-background-section-burn'/>
<div className='absolute right-[38px] top-[-4px] z-10 h-3 w-3 rotate-45 bg-background-section-burn' />
</div>
</div>
)}

View File

@ -24,11 +24,6 @@ export const useGetLanguage = () => {
return getLanguage(locale)
}
export const useGetDocLanguage = () => {
const { locale } = useI18N()
return getDocLanguage(locale)
}
export const useGetPricingPageLanguage = () => {
const { locale } = useI18N()
@ -37,15 +32,15 @@ export const useGetPricingPageLanguage = () => {
const defaultDocBaseUrl = 'https://docs.dify.ai'
export const useDocLink = (baseUrl?: string): ((path?: string, pathMap?: { [index: string]: string }) => string) => {
let baseDocUrl = baseUrl || defaultDocBaseUrl
baseDocUrl = (baseDocUrl.endsWith('/')) ? baseDocUrl.slice(0, -1) : baseDocUrl
const { locale } = useI18N()
const docLanguage = getDocLanguage(locale)
return (path?: string, pathMap?: { [index: string]: string }): string => {
const pathUrl = path || ''
let targetPath = (pathMap) ? pathMap[locale] || pathUrl : pathUrl
targetPath = (targetPath.startsWith('/')) ? targetPath.slice(0, -1) : targetPath
return `${baseDocUrl}/${docLanguage}/${targetPath}`
}
let baseDocUrl = baseUrl || defaultDocBaseUrl
baseDocUrl = (baseDocUrl.endsWith('/')) ? baseDocUrl.slice(0, -1) : baseDocUrl
const { locale } = useI18N()
const docLanguage = getDocLanguage(locale)
return (path?: string, pathMap?: { [index: string]: string }): string => {
const pathUrl = path || ''
let targetPath = (pathMap) ? pathMap[locale] || pathUrl : pathUrl
targetPath = (targetPath.startsWith('/')) ? targetPath.slice(1) : targetPath
return `${baseDocUrl}/${docLanguage}/${targetPath}`
}
}
export default I18NContext