mirror of
https://github.com/MHSanaei/3x-ui.git
synced 2026-06-05 20:54:14 +00:00
refactor(frontend): split inbound-only protocol forms (tun, tunnel) into per-file
Extract the tun and tunnel protocol blocks from InboundFormModal into inbounds/form/protocols/{tun,tunnel}.tsx (presentational, declarative). First inbound-side per-protocol split. Verbatim relocation; inbound snapshots unchanged -> no behavior change. typecheck/lint/build green.
This commit is contained in:
parent
d40f6b9831
commit
afd44ed687
4 changed files with 135 additions and 115 deletions
|
|
@ -84,6 +84,7 @@ import { InputAddon } from '@/components/ui';
|
||||||
import './InboundFormModal.css';
|
import './InboundFormModal.css';
|
||||||
|
|
||||||
import { AdvancedAllEditor, AdvancedSliceEditor } from './advanced-editors';
|
import { AdvancedAllEditor, AdvancedSliceEditor } from './advanced-editors';
|
||||||
|
import { TunFields, TunnelFields } from './protocols';
|
||||||
|
|
||||||
const { TextArea } = Input;
|
const { TextArea } = Input;
|
||||||
import { coerceInboundJsonField, type DBInbound } from '@/models/dbinbound';
|
import { coerceInboundJsonField, type DBInbound } from '@/models/dbinbound';
|
||||||
|
|
@ -1053,122 +1054,9 @@ export default function InboundFormModal({
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{protocol === Protocols.TUN && (
|
{protocol === Protocols.TUN && <TunFields />}
|
||||||
<>
|
|
||||||
<Form.Item name={['settings', 'name']} label={t('pages.inbounds.info.interfaceName')}>
|
|
||||||
<Input placeholder="xray0" />
|
|
||||||
</Form.Item>
|
|
||||||
<Form.Item name={['settings', 'mtu']} label="MTU">
|
|
||||||
<InputNumber min={0} />
|
|
||||||
</Form.Item>
|
|
||||||
<Form.List name={['settings', 'gateway']}>
|
|
||||||
{(fields, { add, remove }) => (
|
|
||||||
<Form.Item label={t('pages.inbounds.info.gateway')}>
|
|
||||||
<Button size="small" onClick={() => add('')}>
|
|
||||||
<PlusOutlined />
|
|
||||||
</Button>
|
|
||||||
{fields.map((field, j) => (
|
|
||||||
<Space.Compact key={field.key} block className="mt-4">
|
|
||||||
<Form.Item name={field.name} noStyle>
|
|
||||||
<Input placeholder={j === 0 ? '10.0.0.1/16' : 'fc00::1/64'} />
|
|
||||||
</Form.Item>
|
|
||||||
<Button size="small" onClick={() => remove(field.name)}>
|
|
||||||
<MinusOutlined />
|
|
||||||
</Button>
|
|
||||||
</Space.Compact>
|
|
||||||
))}
|
|
||||||
</Form.Item>
|
|
||||||
)}
|
|
||||||
</Form.List>
|
|
||||||
<Form.List name={['settings', 'dns']}>
|
|
||||||
{(fields, { add, remove }) => (
|
|
||||||
<Form.Item label="DNS">
|
|
||||||
<Button size="small" onClick={() => add('')}>
|
|
||||||
<PlusOutlined />
|
|
||||||
</Button>
|
|
||||||
{fields.map((field, j) => (
|
|
||||||
<Space.Compact key={field.key} block className="mt-4">
|
|
||||||
<Form.Item name={field.name} noStyle>
|
|
||||||
<Input placeholder={j === 0 ? '1.1.1.1' : '8.8.8.8'} />
|
|
||||||
</Form.Item>
|
|
||||||
<Button size="small" onClick={() => remove(field.name)}>
|
|
||||||
<MinusOutlined />
|
|
||||||
</Button>
|
|
||||||
</Space.Compact>
|
|
||||||
))}
|
|
||||||
</Form.Item>
|
|
||||||
)}
|
|
||||||
</Form.List>
|
|
||||||
<Form.Item name={['settings', 'userLevel']} label={t('pages.xray.tun.userLevel')}>
|
|
||||||
<InputNumber min={0} />
|
|
||||||
</Form.Item>
|
|
||||||
<Form.List name={['settings', 'autoSystemRoutingTable']}>
|
|
||||||
{(fields, { add, remove }) => (
|
|
||||||
<Form.Item
|
|
||||||
label={
|
|
||||||
<Tooltip title={t('pages.inbounds.form.autoSystemRoutesTooltip')}>
|
|
||||||
{t('pages.inbounds.info.autoSystemRoutes')}
|
|
||||||
</Tooltip>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<Button size="small" onClick={() => add('')}>
|
|
||||||
<PlusOutlined />
|
|
||||||
</Button>
|
|
||||||
{fields.map((field, j) => (
|
|
||||||
<Space.Compact key={field.key} block className="mt-4">
|
|
||||||
<Form.Item name={field.name} noStyle>
|
|
||||||
<Input placeholder={j === 0 ? '0.0.0.0/0' : '::/0'} />
|
|
||||||
</Form.Item>
|
|
||||||
<Button size="small" onClick={() => remove(field.name)}>
|
|
||||||
<MinusOutlined />
|
|
||||||
</Button>
|
|
||||||
</Space.Compact>
|
|
||||||
))}
|
|
||||||
</Form.Item>
|
|
||||||
)}
|
|
||||||
</Form.List>
|
|
||||||
<Form.Item
|
|
||||||
name={['settings', 'autoOutboundsInterface']}
|
|
||||||
label={
|
|
||||||
<Tooltip title={t('pages.inbounds.form.autoOutboundsInterfaceTooltip')}>
|
|
||||||
{t('pages.inbounds.form.autoOutboundsInterface')}
|
|
||||||
</Tooltip>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<Input placeholder="auto" />
|
|
||||||
</Form.Item>
|
|
||||||
</>
|
|
||||||
)}
|
|
||||||
|
|
||||||
{protocol === Protocols.TUNNEL && (
|
{protocol === Protocols.TUNNEL && <TunnelFields />}
|
||||||
<>
|
|
||||||
<Form.Item name={['settings', 'rewriteAddress']} label={t('pages.inbounds.form.rewriteAddress')}>
|
|
||||||
<Input />
|
|
||||||
</Form.Item>
|
|
||||||
<Form.Item name={['settings', 'rewritePort']} label={t('pages.inbounds.form.rewritePort')}>
|
|
||||||
<InputNumber min={0} max={65535} />
|
|
||||||
</Form.Item>
|
|
||||||
<Form.Item name={['settings', 'allowedNetwork']} label={t('pages.inbounds.form.allowedNetwork')}>
|
|
||||||
<Select
|
|
||||||
options={[
|
|
||||||
{ value: 'tcp,udp', label: 'TCP, UDP' },
|
|
||||||
{ value: 'tcp', label: 'TCP' },
|
|
||||||
{ value: 'udp', label: 'UDP' },
|
|
||||||
]}
|
|
||||||
/>
|
|
||||||
</Form.Item>
|
|
||||||
<Form.Item label={t('pages.inbounds.portMap')} name={['settings', 'portMap']}>
|
|
||||||
<HeaderMapEditor mode="v1" />
|
|
||||||
</Form.Item>
|
|
||||||
<Form.Item
|
|
||||||
name={['settings', 'followRedirect']}
|
|
||||||
label={t('pages.inbounds.form.followRedirect')}
|
|
||||||
valuePropName="checked"
|
|
||||||
>
|
|
||||||
<Switch />
|
|
||||||
</Form.Item>
|
|
||||||
</>
|
|
||||||
)}
|
|
||||||
|
|
||||||
{(protocol === Protocols.HTTP || protocol === Protocols.MIXED) && (
|
{(protocol === Protocols.HTTP || protocol === Protocols.MIXED) && (
|
||||||
<>
|
<>
|
||||||
|
|
|
||||||
2
frontend/src/pages/inbounds/form/protocols/index.ts
Normal file
2
frontend/src/pages/inbounds/form/protocols/index.ts
Normal file
|
|
@ -0,0 +1,2 @@
|
||||||
|
export { default as TunFields } from './tun';
|
||||||
|
export { default as TunnelFields } from './tunnel';
|
||||||
93
frontend/src/pages/inbounds/form/protocols/tun.tsx
Normal file
93
frontend/src/pages/inbounds/form/protocols/tun.tsx
Normal file
|
|
@ -0,0 +1,93 @@
|
||||||
|
import { useTranslation } from 'react-i18next';
|
||||||
|
import { Button, Form, Input, InputNumber, Space, Tooltip } from 'antd';
|
||||||
|
import { MinusOutlined, PlusOutlined } from '@ant-design/icons';
|
||||||
|
|
||||||
|
export default function TunFields() {
|
||||||
|
const { t } = useTranslation();
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Form.Item name={['settings', 'name']} label={t('pages.inbounds.info.interfaceName')}>
|
||||||
|
<Input placeholder="xray0" />
|
||||||
|
</Form.Item>
|
||||||
|
<Form.Item name={['settings', 'mtu']} label="MTU">
|
||||||
|
<InputNumber min={0} />
|
||||||
|
</Form.Item>
|
||||||
|
<Form.List name={['settings', 'gateway']}>
|
||||||
|
{(fields, { add, remove }) => (
|
||||||
|
<Form.Item label={t('pages.inbounds.info.gateway')}>
|
||||||
|
<Button size="small" onClick={() => add('')}>
|
||||||
|
<PlusOutlined />
|
||||||
|
</Button>
|
||||||
|
{fields.map((field, j) => (
|
||||||
|
<Space.Compact key={field.key} block className="mt-4">
|
||||||
|
<Form.Item name={field.name} noStyle>
|
||||||
|
<Input placeholder={j === 0 ? '10.0.0.1/16' : 'fc00::1/64'} />
|
||||||
|
</Form.Item>
|
||||||
|
<Button size="small" onClick={() => remove(field.name)}>
|
||||||
|
<MinusOutlined />
|
||||||
|
</Button>
|
||||||
|
</Space.Compact>
|
||||||
|
))}
|
||||||
|
</Form.Item>
|
||||||
|
)}
|
||||||
|
</Form.List>
|
||||||
|
<Form.List name={['settings', 'dns']}>
|
||||||
|
{(fields, { add, remove }) => (
|
||||||
|
<Form.Item label="DNS">
|
||||||
|
<Button size="small" onClick={() => add('')}>
|
||||||
|
<PlusOutlined />
|
||||||
|
</Button>
|
||||||
|
{fields.map((field, j) => (
|
||||||
|
<Space.Compact key={field.key} block className="mt-4">
|
||||||
|
<Form.Item name={field.name} noStyle>
|
||||||
|
<Input placeholder={j === 0 ? '1.1.1.1' : '8.8.8.8'} />
|
||||||
|
</Form.Item>
|
||||||
|
<Button size="small" onClick={() => remove(field.name)}>
|
||||||
|
<MinusOutlined />
|
||||||
|
</Button>
|
||||||
|
</Space.Compact>
|
||||||
|
))}
|
||||||
|
</Form.Item>
|
||||||
|
)}
|
||||||
|
</Form.List>
|
||||||
|
<Form.Item name={['settings', 'userLevel']} label={t('pages.xray.tun.userLevel')}>
|
||||||
|
<InputNumber min={0} />
|
||||||
|
</Form.Item>
|
||||||
|
<Form.List name={['settings', 'autoSystemRoutingTable']}>
|
||||||
|
{(fields, { add, remove }) => (
|
||||||
|
<Form.Item
|
||||||
|
label={
|
||||||
|
<Tooltip title={t('pages.inbounds.form.autoSystemRoutesTooltip')}>
|
||||||
|
{t('pages.inbounds.info.autoSystemRoutes')}
|
||||||
|
</Tooltip>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Button size="small" onClick={() => add('')}>
|
||||||
|
<PlusOutlined />
|
||||||
|
</Button>
|
||||||
|
{fields.map((field, j) => (
|
||||||
|
<Space.Compact key={field.key} block className="mt-4">
|
||||||
|
<Form.Item name={field.name} noStyle>
|
||||||
|
<Input placeholder={j === 0 ? '0.0.0.0/0' : '::/0'} />
|
||||||
|
</Form.Item>
|
||||||
|
<Button size="small" onClick={() => remove(field.name)}>
|
||||||
|
<MinusOutlined />
|
||||||
|
</Button>
|
||||||
|
</Space.Compact>
|
||||||
|
))}
|
||||||
|
</Form.Item>
|
||||||
|
)}
|
||||||
|
</Form.List>
|
||||||
|
<Form.Item
|
||||||
|
name={['settings', 'autoOutboundsInterface']}
|
||||||
|
label={
|
||||||
|
<Tooltip title={t('pages.inbounds.form.autoOutboundsInterfaceTooltip')}>
|
||||||
|
{t('pages.inbounds.form.autoOutboundsInterface')}
|
||||||
|
</Tooltip>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Input placeholder="auto" />
|
||||||
|
</Form.Item>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
37
frontend/src/pages/inbounds/form/protocols/tunnel.tsx
Normal file
37
frontend/src/pages/inbounds/form/protocols/tunnel.tsx
Normal file
|
|
@ -0,0 +1,37 @@
|
||||||
|
import { useTranslation } from 'react-i18next';
|
||||||
|
import { Form, Input, InputNumber, Select, Switch } from 'antd';
|
||||||
|
|
||||||
|
import { HeaderMapEditor } from '@/components/form';
|
||||||
|
|
||||||
|
export default function TunnelFields() {
|
||||||
|
const { t } = useTranslation();
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Form.Item name={['settings', 'rewriteAddress']} label={t('pages.inbounds.form.rewriteAddress')}>
|
||||||
|
<Input />
|
||||||
|
</Form.Item>
|
||||||
|
<Form.Item name={['settings', 'rewritePort']} label={t('pages.inbounds.form.rewritePort')}>
|
||||||
|
<InputNumber min={0} max={65535} />
|
||||||
|
</Form.Item>
|
||||||
|
<Form.Item name={['settings', 'allowedNetwork']} label={t('pages.inbounds.form.allowedNetwork')}>
|
||||||
|
<Select
|
||||||
|
options={[
|
||||||
|
{ value: 'tcp,udp', label: 'TCP, UDP' },
|
||||||
|
{ value: 'tcp', label: 'TCP' },
|
||||||
|
{ value: 'udp', label: 'UDP' },
|
||||||
|
]}
|
||||||
|
/>
|
||||||
|
</Form.Item>
|
||||||
|
<Form.Item label={t('pages.inbounds.portMap')} name={['settings', 'portMap']}>
|
||||||
|
<HeaderMapEditor mode="v1" />
|
||||||
|
</Form.Item>
|
||||||
|
<Form.Item
|
||||||
|
name={['settings', 'followRedirect']}
|
||||||
|
label={t('pages.inbounds.form.followRedirect')}
|
||||||
|
valuePropName="checked"
|
||||||
|
>
|
||||||
|
<Switch />
|
||||||
|
</Form.Item>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
Loading…
Reference in a new issue