fix(xray): test UDP outbounds via xray probe (#4657) + Vision testseed & Flow form fixes

Outbound connection tester (#4657): UDP-based outbounds (wireguard,
hysteria, kcp/quic transports) were probed with a raw UDP dial that
treated the inevitable read timeout as success, so every one reported a
fake ~5s 'alive'. Route them through the authoritative xray
burstObservatory probe and drop the broken raw-UDP path. Test All now
runs a parallel TCP lane and a serial HTTP lane so xray-probe outbounds
don't collide on the test semaphore.

Vision testseed: the [900, 500, 900, 256] default repeats 900, and a
tags Select keys each tag by value -> 'two children with the same key,
900'. Render it as four InputNumbers (inbound + outbound forms); the
field is a fixed 4-tuple where repeats are valid.

Inbound form: drop the null-valued 'Local Panel' Select option (AntD
rejects null option values; placeholder + allowClear already cover it).

Outbound form: add an explicit 'None' option to the Flow selector.
This commit is contained in:
MHSanaei
2026-05-29 21:07:01 +02:00
parent 8c30ddbfd9
commit cb7af04cd3
5 changed files with 88 additions and 133 deletions
@@ -931,14 +931,11 @@ export default function InboundFormModal({
disabled={mode === 'edit'}
placeholder={t('pages.inbounds.localPanel')}
allowClear
options={[
{ value: null, label: t('pages.inbounds.localPanel') },
...selectableNodes.map((n) => ({
value: n.id,
label: `${n.name}${n.status === 'offline' ? ' (offline)' : ''}`,
disabled: n.status === 'offline',
})),
]}
options={selectableNodes.map((n) => ({
value: n.id,
label: `${n.name}${n.status === 'offline' ? ' (offline)' : ''}`,
disabled: n.status === 'offline',
}))}
/>
</Form.Item>
)}
@@ -1498,16 +1495,15 @@ export default function InboundFormModal({
{network === 'tcp' && (security === 'tls' || security === 'reality') && (
<Form.Item
label={t('pages.inbounds.form.visionTestseed')}
name={['settings', 'testseed']}
initialValue={[900, 500, 900, 256]}
normalize={(v: unknown) =>
Array.isArray(v)
? v.map((x) => Number(x)).filter((n) => Number.isInteger(n) && n > 0)
: []
}
extra="Applies only to clients using the xtls-rprx-vision flow; ignored otherwise."
>
<Select mode="tags" tokenSeparators={[',', ' ']} placeholder="four positive integers" />
<Space.Compact block>
{[900, 500, 900, 256].map((def, i) => (
<Form.Item key={i} name={['settings', 'testseed', i]} noStyle initialValue={def}>
<InputNumber min={1} style={{ width: '25%' }} />
</Form.Item>
))}
</Space.Compact>
</Form.Item>
)}
</>