Feat: add Jira connector (#11285)

### What problem does this PR solve?

Add Jira connector.

<img width="978" height="925" alt="image"
src="https://github.com/user-attachments/assets/78bb5c77-2710-4569-a76e-9087ca23b227"
/>

---

<img width="1903" height="489" alt="image"
src="https://github.com/user-attachments/assets/193bc5c5-f751-4bd5-883a-2173282c2b96"
/>

---

<img width="1035" height="925" alt="image"
src="https://github.com/user-attachments/assets/1a0aec19-30eb-4ada-9283-61d1c915f59d"
/>

---

<img width="1905" height="601" alt="image"
src="https://github.com/user-attachments/assets/3dde1062-3f27-4717-8e09-fd5fd5e64171"
/>

### Type of change

- [x] New Feature (non-breaking change which adds functionality)
This commit is contained in:
Yongteng Lei
2025-11-17 09:38:04 +08:00
committed by GitHub
parent 61cf430dbb
commit 13e212c856
15 changed files with 1521 additions and 179 deletions

View File

@ -0,0 +1,16 @@
<svg xmlns="http://www.w3.org/2000/svg" width="128" height="128" viewBox="0 0 128 128">
<defs>
<linearGradient id="jira-a" x1="88.136" y1="39.092" x2="68.472" y2="59.368" gradientUnits="userSpaceOnUse">
<stop offset="0.176" stop-color="#0052cc"/>
<stop offset="1" stop-color="#2684ff"/>
</linearGradient>
<linearGradient id="jira-b" x1="66.564" y1="62.256" x2="43.828" y2="84.376" gradientUnits="userSpaceOnUse">
<stop offset="0.176" stop-color="#0052cc"/>
<stop offset="1" stop-color="#2684ff"/>
</linearGradient>
</defs>
<path d="M108.023 16H61.805c0 11.52 9.324 20.848 20.847 20.848h8.5v8.226c0 11.52 9.328 20.848 20.848 20.848V19.977A3.98 3.98 0 00108.023 16z" fill="#2684ff"/>
<path d="M85.121 39.04H38.902c0 11.519 9.325 20.847 20.844 20.847h8.504v8.226c0 11.52 9.328 20.848 20.848 20.848V43.016a3.983 3.983 0 00-3.977-3.977z" fill="url(#jira-a)"/>
<path d="M62.219 62.078H16c0 11.524 9.324 20.848 20.848 20.848h8.5v8.23c0 11.52 9.328 20.844 20.847 20.844V66.059a3.984 3.984 0 00-3.976-3.98z" fill="url(#jira-b)"/>
</svg>

After

Width:  |  Height:  |  Size: 1.1 KiB

View File

@ -732,6 +732,33 @@ Example: general/v2/`,
'Comma-separated emails whose “My Drive” contents should be indexed (include the primary admin).',
google_driveSharedFoldersTip:
'Comma-separated Google Drive folder links to crawl.',
jiraDescription:
'Connect your Jira workspace to sync issues, comments, and attachments.',
jiraBaseUrlTip:
'Base URL of your Jira site (e.g., https://your-domain.atlassian.net).',
jiraProjectKeyTip:
'Optional: limit syncing to a single project key (e.g., ENG).',
jiraJqlTip:
'Optional JQL filter. Leave blank to rely on project/time filters.',
jiraBatchSizeTip:
'Maximum number of issues requested from Jira per batch.',
jiraCommentsTip:
'Include Jira comments in the generated markdown document.',
jiraAttachmentsTip:
'Download attachments as separate documents during sync.',
jiraAttachmentSizeTip:
'Attachments larger than this number of bytes will be skipped.',
jiraLabelsTip:
'Labels that should be skipped while indexing (comma separated).',
jiraBlacklistTip:
'Comments whose author email matches these entries will be ignored.',
jiraScopedTokenTip:
'Enable this when using scoped Atlassian tokens (api.atlassian.com).',
jiraEmailTip: 'Email associated with the Jira account/API token.',
jiraTokenTip:
'API token generated from https://id.atlassian.com/manage-profile/security/api-tokens.',
jiraPasswordTip:
'Optional password for Jira Server/Data Center environments.',
availableSourcesDescription: 'Select a data source to add',
availableSources: 'Available sources',
datasourceDescription: 'Manage your data source and connections',

View File

@ -716,6 +716,23 @@ General实体和关系提取提示来自 GitHub - microsoft/graphrag基于
'需要索引其 “我的云端硬盘” 的邮箱,多个邮箱用逗号分隔(建议包含管理员)。',
google_driveSharedFoldersTip:
'需要同步的 Google Drive 文件夹链接,多个链接用逗号分隔。',
jiraDescription: '接入 Jira 工作区持续同步Issues、评论与附件。',
jiraBaseUrlTip:
'Jira 的 Base URL例如https://your-domain.atlassian.net。',
jiraProjectKeyTip: '可选:仅同步指定的项目(如 RAG。',
jiraJqlTip: '可选:自定义 JQL 过滤条件,留空则使用项目 / 时间范围。',
jiraBatchSizeTip: '每次向 Jira 请求的 Issue 数量上限。',
jiraCommentsTip: '同步评论。',
jiraAttachmentsTip: '开启后会将附件下载为独立文档。',
jiraAttachmentSizeTip: '超过该字节阈值的附件会被跳过。',
jiraLabelsTip: '需要跳过的标签(逗号分隔)。',
jiraBlacklistTip: '这些邮箱作者的评论会被忽略。',
jiraScopedTokenTip:
'仅当凭证为 Atlassian scoped tokenapi.atlassian.com时生效。',
jiraEmailTip: '与 API Token 对应的 Jira 账户邮箱。',
jiraTokenTip:
'在 https://id.atlassian.com/manage-profile/security/api-tokens 生成的 API Token。 (Clould only)',
jiraPasswordTip: '可选:仅 Jira Server/Data Center 环境需要的密码字段。',
availableSourcesDescription: '选择要添加的数据源',
availableSources: '可用数据源',
datasourceDescription: '管理您的数据源和连接',

View File

@ -9,8 +9,8 @@ export enum DataSourceKey {
NOTION = 'notion',
DISCORD = 'discord',
GOOGLE_DRIVE = 'google_drive',
// GMAIL = 'gmail',
// JIRA = 'jira',
// GMAIL = 'gmail',
JIRA = 'jira',
// SHAREPOINT = 'sharepoint',
// SLACK = 'slack',
// TEAMS = 'teams',
@ -42,6 +42,11 @@ export const DataSourceInfo = {
description: t(`setting.${DataSourceKey.GOOGLE_DRIVE}Description`),
icon: <SvgIcon name={'data-source/google-drive'} width={38} />,
},
[DataSourceKey.JIRA]: {
name: 'Jira',
description: t(`setting.${DataSourceKey.JIRA}Description`),
icon: <SvgIcon name={'data-source/jira'} width={38} />,
},
};
export const DataSourceFormBaseFields = [
@ -270,6 +275,106 @@ export const DataSourceFormFields = {
defaultValue: 'uploaded',
},
],
[DataSourceKey.JIRA]: [
{
label: 'Jira Base URL',
name: 'config.base_url',
type: FormFieldType.Text,
required: true,
placeholder: 'https://your-domain.atlassian.net',
tooltip: t('setting.jiraBaseUrlTip'),
},
{
label: 'Project Key',
name: 'config.project_key',
type: FormFieldType.Text,
required: false,
placeholder: 'RAGFlow',
tooltip: t('setting.jiraProjectKeyTip'),
},
{
label: 'Custom JQL',
name: 'config.jql_query',
type: FormFieldType.Textarea,
required: false,
placeholder: 'project = RAG AND updated >= -7d',
tooltip: t('setting.jiraJqlTip'),
},
{
label: 'Batch Size',
name: 'config.batch_size',
type: FormFieldType.Number,
required: false,
tooltip: t('setting.jiraBatchSizeTip'),
},
{
label: 'Include Comments',
name: 'config.include_comments',
type: FormFieldType.Checkbox,
required: false,
defaultValue: true,
tooltip: t('setting.jiraCommentsTip'),
},
{
label: 'Include Attachments',
name: 'config.include_attachments',
type: FormFieldType.Checkbox,
required: false,
defaultValue: false,
tooltip: t('setting.jiraAttachmentsTip'),
},
{
label: 'Attachment Size Limit (bytes)',
name: 'config.attachment_size_limit',
type: FormFieldType.Number,
required: false,
defaultValue: 10 * 1024 * 1024,
tooltip: t('setting.jiraAttachmentSizeTip'),
},
{
label: 'Labels to Skip',
name: 'config.labels_to_skip',
type: FormFieldType.Tag,
required: false,
tooltip: t('setting.jiraLabelsTip'),
},
{
label: 'Comment Email Blacklist',
name: 'config.comment_email_blacklist',
type: FormFieldType.Tag,
required: false,
tooltip: t('setting.jiraBlacklistTip'),
},
{
label: 'Use Scoped Token (Clould only)',
name: 'config.scoped_token',
type: FormFieldType.Checkbox,
required: false,
tooltip: t('setting.jiraScopedTokenTip'),
},
{
label: 'Jira User Email (Cloud) or User Name (Server)',
name: 'config.credentials.jira_user_email',
type: FormFieldType.Text,
required: true,
placeholder: 'you@example.com',
tooltip: t('setting.jiraEmailTip'),
},
{
label: 'Jira API Token (Cloud only)',
name: 'config.credentials.jira_api_token',
type: FormFieldType.Password,
required: false,
tooltip: t('setting.jiraTokenTip'),
},
{
label: 'Jira Password (Server only)',
name: 'config.credentials.jira_password',
type: FormFieldType.Password,
required: false,
tooltip: t('setting.jiraPasswordTip'),
},
],
// [DataSourceKey.GOOGLE_DRIVE]: [
// {
// label: 'Primary Admin Email',
@ -433,4 +538,25 @@ export const DataSourceFormDefaultValues = {
},
},
},
[DataSourceKey.JIRA]: {
name: '',
source: DataSourceKey.JIRA,
config: {
base_url: '',
project_key: '',
jql_query: '',
batch_size: 2,
include_comments: true,
include_attachments: false,
attachment_size_limit: 10 * 1024 * 1024,
labels_to_skip: [],
comment_email_blacklist: [],
scoped_token: false,
credentials: {
jira_user_email: '',
jira_api_token: '',
jira_password: '',
},
},
},
};

View File

@ -44,6 +44,12 @@ const dataSourceTemplates = [
description: DataSourceInfo[DataSourceKey.NOTION].description,
icon: DataSourceInfo[DataSourceKey.NOTION].icon,
},
{
id: DataSourceKey.JIRA,
name: DataSourceInfo[DataSourceKey.JIRA].name,
description: DataSourceInfo[DataSourceKey.JIRA].description,
icon: DataSourceInfo[DataSourceKey.JIRA].icon,
},
];
const DataSource = () => {
const { t } = useTranslation();