Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Binary file added public/image/logos/plivo.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
54 changes: 54 additions & 0 deletions src/pages/notificationChannels/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -649,6 +649,60 @@ export const getNotificationChannelTypes = () => {
},
},
},
'plivo-voice': {
logo: '/image/logos/plivo.png',
type: 'plivo',
default_values: {
param_config: {
user_info: {
contact_key: 'phone',
},
custom: {
params: null,
},
},
request_type: 'plivo',
request_config: {
plivo_request_config: {
auth_id: '',
auth_token: '',
src_number: '',
answer_url: '',
answer_method: 'POST',
proxy: '',
timeout: 10000,
retry_times: 3,
retry_sleep: 0,
},
},
},
},
'plivo-sms': {
logo: '/image/logos/plivo.png',
type: 'plivo',
default_values: {
param_config: {
user_info: {
contact_key: 'phone',
},
custom: {
params: null,
},
},
request_type: 'plivo',
request_config: {
plivo_request_config: {
auth_id: '',
auth_token: '',
src_number: '',
proxy: '',
timeout: 10000,
retry_times: 3,
retry_sleep: 0,
},
},
},
},
// slackbot: {
// logo: '/image/logos/slack.png',
// type: 'http',
Expand Down
18 changes: 18 additions & 0 deletions src/pages/notificationChannels/locale/en_US.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ const en_US = {
script: 'Script configuration',
flashduty: 'FlashDuty configuration',
pagerduty: 'PagerDuty configuration',
plivo: 'Plivo configuration',
dingtalkapp: 'DingTalk App configuration',
wecomapp: 'WeCom App configuration',
feishuapp: 'Feishu App configuration',
Expand Down Expand Up @@ -118,6 +119,21 @@ const en_US = {
timeout: 'Timeout (unit: ms)',
retry_times: 'Retry Times',
},
plivo_request_config: {
title: 'Plivo',
auth_id: 'Auth ID',
auth_token: 'Auth Token',
src_number: 'Source Number',
src_number_tip: 'The Plivo phone number used as the SMS sender or the caller ID for voice calls. May be entered with or without a leading +.',
answer_url: 'Answer URL',
answer_url_tip: 'For voice calls, the URL that returns Plivo XML instructing what to do when the call is answered.',
answer_method: 'Answer Method',
answer_method_tip: 'HTTP method Plivo uses to fetch the Answer URL. Defaults to POST; use GET only if your Answer URL is served over GET.',
proxy: 'Proxy',
proxy_tip: 'HTTP PROXY address, used in scenarios that require a proxy',
timeout: 'Timeout (unit: ms)',
retry_times: 'Retry Times',
},
dingtalkapp_request_config: {
app_key: 'App Key',
app_secret: 'App Secret',
Expand Down Expand Up @@ -162,6 +178,8 @@ const en_US = {
'ali-sms': 'Aliyun SMS',
'tx-voice': 'Tencent Cloud Voice',
'tx-sms': 'Tencent Cloud SMS',
'plivo-voice': 'Plivo Voice',
'plivo-sms': 'Plivo SMS',
slackbot: 'Slack Bot',
slackwebhook: 'Slack Webhook',
mattermostbot: 'Mattermost Bot',
Expand Down
18 changes: 18 additions & 0 deletions src/pages/notificationChannels/locale/ja_JP.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ const ja_JP = {
script: 'Script 設定',
flashduty: 'FlashDuty 設定',
pagerduty: 'PagerDuty 設定',
plivo: 'Plivo 設定',
dingtalkapp: 'DingTalk アプリ設定',
wecomapp: '企業微信アプリ設定',
feishuapp: 'Feishu アプリ設定',
Expand Down Expand Up @@ -117,6 +118,21 @@ const ja_JP = {
timeout: 'タイムアウト (単位: ミリ秒)',
retry_times: 'リトライ回数',
},
plivo_request_config: {
title: 'Plivo',
auth_id: 'Auth ID',
auth_token: 'Auth Token',
src_number: '送信元番号',
src_number_tip: 'SMS の送信元または音声通話の発信者番号として使用する Plivo の電話番号。先頭の + は付けても付けなくても構いません。',
answer_url: 'Answer URL',
answer_url_tip: '音声通話で使用します。通話に応答したときに Plivo XML を返す URL です。',
answer_method: 'Answer Method',
answer_method_tip: 'Plivo が Answer URL を取得する際の HTTP メソッド。デフォルトは POST で、Answer URL が GET で提供される場合のみ GET を選択します。',
proxy: 'プロキシ',
proxy_tip: 'プロキシが必要な場合は、ここに HTTP PROXY アドレスを入力してください',
timeout: 'タイムアウト (単位: ミリ秒)',
retry_times: 'リトライ回数',
},
dingtalkapp_request_config: {
app_key: 'アプリキー',
app_secret: 'アプリシークレット',
Expand Down Expand Up @@ -159,6 +175,8 @@ const ja_JP = {
telegram: 'Telegram',
'ali-voice': 'Alibaba Cloud音声',
'ali-sms': 'Alibaba Cloud SMS',
'plivo-voice': 'Plivo 音声',
'plivo-sms': 'Plivo SMS',
'tx-voice': 'Tencent Cloud音声',
'tx-sms': 'Tencent Cloud SMS',
slackbot: 'Slack Bot',
Expand Down
18 changes: 18 additions & 0 deletions src/pages/notificationChannels/locale/ru_RU.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ const ru_RU = {
script: 'Настройка Script',
flashduty: 'Настройка FlashDuty',
pagerduty: 'Настройка PagerDuty',
plivo: 'Настройка Plivo',
dingtalkapp: 'Настройка DingTalk App',
wecomapp: 'Настройка WeCom App',
feishuapp: 'Настройка Feishu App',
Expand Down Expand Up @@ -119,6 +120,21 @@ const ru_RU = {
timeout: 'Тайм-аут (мс)',
retry_times: 'Количество повторных попыток',
},
plivo_request_config: {
title: 'Plivo',
auth_id: 'Auth ID',
auth_token: 'Auth Token',
src_number: 'Номер отправителя',
src_number_tip: 'Номер Plivo, используемый как отправитель SMS или идентификатор вызывающего абонента для голосовых вызовов. Можно вводить с ведущим + или без него.',
answer_url: 'Answer URL',
answer_url_tip: 'Для голосовых вызовов — URL, возвращающий Plivo XML с инструкциями при ответе на вызов.',
answer_method: 'Answer Method',
answer_method_tip: 'HTTP-метод, которым Plivo запрашивает Answer URL. По умолчанию POST; выберите GET, только если ваш Answer URL обслуживается через GET.',
proxy: 'Прокси',
proxy_tip: 'Адрес HTTP-прокси для сценариев, требующих прокси',
timeout: 'Тайм-аут (мс)',
retry_times: 'Количество повторных попыток',
},
dingtalkapp_request_config: {
app_key: 'Ключ приложения',
app_secret: 'Секрет приложения',
Expand Down Expand Up @@ -161,6 +177,8 @@ const ru_RU = {
telegram: 'Telegram',
'ali-voice': 'Голосовой Alibaba Cloud',
'ali-sms': 'SMS Alibaba Cloud',
'plivo-voice': 'Plivo Голос',
'plivo-sms': 'Plivo SMS',
'tx-voice': 'Голосовой Tencent Cloud',
'tx-sms': 'SMS Tencent Cloud',
slackbot: 'Slack Bot',
Expand Down
18 changes: 18 additions & 0 deletions src/pages/notificationChannels/locale/zh_CN.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ const zh_CN = {
script: 'Script 配置',
flashduty: 'FlashDuty 配置',
pagerduty: 'PagerDuty 配置',
plivo: 'Plivo 配置',
dingtalkapp: '钉钉应用配置',
wecomapp: '企业微信应用配置',
feishuapp: '飞书应用配置',
Expand Down Expand Up @@ -114,6 +115,21 @@ const zh_CN = {
timeout: '超时时间 (单位: 毫秒)',
retry_times: '重试次数',
},
plivo_request_config: {
title: 'Plivo',
auth_id: 'Auth ID',
auth_token: 'Auth Token',
src_number: '发送号码',
src_number_tip: '作为短信发送方或语音主叫的 Plivo 号码,填写时可带或不带前导 +。',
answer_url: 'Answer URL',
answer_url_tip: '语音通道使用,呼叫接通后返回 Plivo XML 指令的 URL。',
answer_method: 'Answer Method',
answer_method_tip: 'Plivo 拉取 Answer URL 所用的 HTTP 方法,默认 POST;仅当 Answer URL 以 GET 提供时才选 GET。',
proxy: '代理',
proxy_tip: 'HTTP PROXY 地址,用于需要代理的场景',
timeout: '超时时间 (单位: 毫秒)',
retry_times: '重试次数',
},
dingtalkapp_request_config: {
app_key: '应用唯一标识',
app_secret: '应用密钥',
Expand Down Expand Up @@ -157,6 +173,8 @@ const zh_CN = {
telegram: 'Telegram',
'ali-voice': '阿里云语音',
'ali-sms': '阿里云短信',
'plivo-voice': 'Plivo 语音',
'plivo-sms': 'Plivo 短信',
'tx-voice': '腾讯云语音',
'tx-sms': '腾讯云短信',
slackbot: 'Slack Bot',
Expand Down
18 changes: 18 additions & 0 deletions src/pages/notificationChannels/locale/zh_HK.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ const zh_HK = {
script: 'Script 配置',
flashduty: 'FlashDuty 配置',
pagerduty: 'PagerDuty 配置',
plivo: 'Plivo 配置',
dingtalkapp: '釘釘應用配置',
wecomapp: '企業微信應用配置',
feishuapp: '飛書應用配置',
Expand Down Expand Up @@ -114,6 +115,21 @@ const zh_HK = {
timeout: '超時時間 (單位: 毫秒)',
retry_times: '重試次數',
},
plivo_request_config: {
title: 'Plivo',
auth_id: 'Auth ID',
auth_token: 'Auth Token',
src_number: '發送號碼',
src_number_tip: '作為短信發送方或語音主叫的 Plivo 號碼,填寫時可帶或不帶前導 +。',
answer_url: 'Answer URL',
answer_url_tip: '語音通道使用,呼叫接通後返回 Plivo XML 指令的 URL。',
answer_method: 'Answer Method',
answer_method_tip: 'Plivo 拉取 Answer URL 所用的 HTTP 方法,預設 POST;僅當 Answer URL 以 GET 提供時才選 GET。',
proxy: '代理',
proxy_tip: 'HTTP PROXY 地址,用於需要代理的場景',
timeout: '超時時間 (單位: 毫秒)',
retry_times: '重試次數',
},
dingtalkapp_request_config: {
app_key: '應用唯一標識',
app_secret: '應用密鑰',
Expand Down Expand Up @@ -156,6 +172,8 @@ const zh_HK = {
telegram: 'Telegram',
'ali-voice': '阿里雲語音',
'ali-sms': '阿里雲短信',
'plivo-voice': 'Plivo 語音',
'plivo-sms': 'Plivo 短信',
'tx-voice': '騰訊雲語音',
'tx-sms': '騰訊雲短信',
slackbot: 'Slack Bot',
Expand Down
88 changes: 88 additions & 0 deletions src/pages/notificationChannels/pages/Form/Plivo.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
import { useTranslation } from 'react-i18next';
import { NS } from '../../constants';
import { Form, Input, InputNumber, Select, Space, Tooltip } from 'antd';
import React from 'react';
import { QuestionCircleOutlined } from '@ant-design/icons';

export default function Plivo() {
const { t } = useTranslation(NS);
const names = ['request_config', 'plivo_request_config'];
const request_type = Form.useWatch('request_type');
const ident = Form.useWatch('ident');
const isPlivo = request_type === 'plivo';
const isVoice = ident === 'plivo-voice';

return (
<div
style={{
display: isPlivo ? 'block' : 'none',
}}
>
<Form.Item label={t('plivo_request_config.auth_id')} name={[...names, 'auth_id']} rules={[{ required: isPlivo }]}>
<Input />
</Form.Item>
<Form.Item label={t('plivo_request_config.auth_token')} name={[...names, 'auth_token']} rules={[{ required: isPlivo }]}>
<Input.Password />
</Form.Item>
<Form.Item
label={
<Space size={4}>
{t('plivo_request_config.src_number')}
<Tooltip className='n9e-ant-from-item-tooltip' overlayClassName='ant-tooltip-max-width-600' title={t('plivo_request_config.src_number_tip')}>
<QuestionCircleOutlined />
</Tooltip>
</Space>
}
name={[...names, 'src_number']}
rules={[{ required: isPlivo }]}
>
<Input />
</Form.Item>
{isVoice && (
<Form.Item
label={
<Space size={4}>
{t('plivo_request_config.answer_url')}
<Tooltip className='n9e-ant-from-item-tooltip' overlayClassName='ant-tooltip-max-width-600' title={t('plivo_request_config.answer_url_tip')}>
<QuestionCircleOutlined />
</Tooltip>
</Space>
}
name={[...names, 'answer_url']}
rules={[{ required: isVoice }]}
>
<Input />
</Form.Item>
)}
{isVoice && (
<Form.Item
label={
<Space size={4}>
{t('plivo_request_config.answer_method')}
<Tooltip className='n9e-ant-from-item-tooltip' overlayClassName='ant-tooltip-max-width-600' title={t('plivo_request_config.answer_method_tip')}>
<QuestionCircleOutlined />
</Tooltip>
</Space>
}
name={[...names, 'answer_method']}
>
<Select
options={[
{ label: 'POST', value: 'POST' },
{ label: 'GET', value: 'GET' },
]}
/>
</Form.Item>
)}
<Form.Item label={t('plivo_request_config.proxy')} tooltip={t('plivo_request_config.proxy_tip')} name={[...names, 'proxy']}>
<Input />
</Form.Item>
<Form.Item label={t('plivo_request_config.timeout')} name={[...names, 'timeout']}>
<InputNumber min={0} className='w-full' />
</Form.Item>
<Form.Item label={t('plivo_request_config.retry_times')} name={[...names, 'retry_times']}>
<InputNumber min={1} className='w-full' />
</Form.Item>
</div>
);
}
2 changes: 2 additions & 0 deletions src/pages/notificationChannels/pages/Form/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import Pagerduty from './Pagerduty';
import DingtalkApp from './DingtalkApp';
import WecomApp from './WecomApp';
import FeishuApp from './FeishuApp';
import Plivo from './Plivo';

interface Props {
initialValues?: ChannelItem;
Expand Down Expand Up @@ -155,6 +156,7 @@ export default function FormCpt(props: Props) {
<DingtalkApp />
<WecomApp />
<FeishuApp />
<Plivo />
</div>
</div>
<div className='border-t border-fc-200 px-4 py-3'>
Expand Down
15 changes: 14 additions & 1 deletion src/pages/notificationChannels/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,18 @@ interface PagerdutyRequestConfig {
integration_keys: string[];
}

interface PlivoRequestConfig {
auth_id: string;
auth_token: string;
src_number: string;
answer_url: string;
answer_method: string;
proxy: string;
timeout: number;
retry_times: number;
retry_sleep: number;
}
Comment on lines +64 to +74

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick win

Make voice-only fields optional.

plivo-sms defaults omit answer_url and answer_method, but this interface requires both. A valid SMS configuration therefore cannot satisfy ChannelItem. Make them optional; constrain answer_method to 'GET' | 'POST'.

Proposed fix
-  answer_url: string;
-  answer_method: string;
+  answer_url?: string;
+  answer_method?: 'GET' | 'POST';
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
interface PlivoRequestConfig {
auth_id: string;
auth_token: string;
src_number: string;
answer_url: string;
answer_method: string;
proxy: string;
timeout: number;
retry_times: number;
retry_sleep: number;
}
interface PlivoRequestConfig {
auth_id: string;
auth_token: string;
src_number: string;
answer_url?: string;
answer_method?: 'GET' | 'POST';
proxy: string;
timeout: number;
retry_times: number;
retry_sleep: number;
}
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/pages/notificationChannels/types.ts` around lines 64 - 74, Update the
PlivoRequestConfig interface so answer_url and answer_method are optional,
allowing valid plivo-sms defaults without those voice-only fields. Restrict
answer_method to the literal union 'GET' | 'POST' while preserving the existing
required fields and types.


interface DingtalkAppRequestConfig {
app_key: string;
app_secret: string;
Expand Down Expand Up @@ -97,13 +109,14 @@ export interface ChannelItem {
description: string;
enable: boolean;
param_config: ParamConfig;
request_type: 'http' | 'smtp' | 'script' | 'flashduty' | 'pagerduty' | 'feishuapp' | 'dingtalkapp' | 'wecomapp' | 'feishu' | 'feishucard' | 'lark' | 'larkcard' | 'dingtalk';
request_type: 'http' | 'smtp' | 'script' | 'flashduty' | 'pagerduty' | 'plivo' | 'feishuapp' | 'dingtalkapp' | 'wecomapp' | 'feishu' | 'feishucard' | 'lark' | 'larkcard' | 'dingtalk';
request_config: {
http_request_config: HttpRequestConfig;
smtp_request_config: SmtpRequestConfig;
script_request_config: ScriptRequestConfig;
flashduty_request_config: FlashdutyRequestConfig;
pagerduty_request_config: PagerdutyRequestConfig;
plivo_request_config: PlivoRequestConfig;
dingtalkapp_request_config: DingtalkAppRequestConfig;
wecomapp_request_config: WecomAppRequestConfig;
feishuapp_request_config: FeishuAppRequestConfig;
Expand Down