mirror of
https://github.com/MHSanaei/3x-ui.git
synced 2026-08-26 21:17:14 +00:00
da01b7637d
* feat(sub): add SubBalancer model and migration Client-side JSON-subscription balancer row: remark, strategy, member inbound ids, sort order, enabled. Registered in allModels and migrationModels so AutoMigrate and SQLite->Postgres copy pick it up. * feat(sub): add SubBalancer service List/Get/Create/Update/Delete over the sub_balancers table with remark trim, strategy allowlist (leastLoad/leastPing/random) and sort-order floor. Rows are read per request by the subscription builder, so mutations need no xray restart. * feat(sub): add SubBalancer API controller and routes GET/POST /panel/api/sub-balancers, POST /:id (update), DELETE /:id and POST /:id/del alias. inboundIds bind from repeated form keys. Mounted under the /panel/api group so the existing API token + CSRF middleware cover it. * feat(sub): emit client-side balancers in JSON subscription For each enabled balancer, append one config document whose outbounds are the selected inbounds' proxy outbounds retagged under a per-balancer prefix, with routing.balancers + burstObservatory selecting it. Balancer entries interleave with inbound entries by sort order; on equal numbers the balancer follows the inbound. Skipped when disabled or no member outbound is present. * test(sub): cover SubBalancer service and JSON output Service: validation gates (remark/strategy/inbound ids/sort order) and CRUD round-trip. JSON: balancer document shape, sort interleaving with inbounds, disabled/empty skip, and member tag dedup. * feat(sub): add sub-balancers i18n keys pages.settings.subBalancers.* block (menu, title, add, desc, field labels, strategy names, sort-order help, validation messages) added to all 13 locales. * feat(sub): add SubBalancer schema and API queries Zod schema (entity + form, strategy enum, validation messages wired to i18n keys), react-query hooks for list/create/update/delete, and the sub-balancers query key. * feat(sub): add subscription balancers settings tab SubscriptionBalancersTab lists balancers (sort order, remark, strategy, inbound count, enabled toggle, edit/delete) with a form modal (remark, strategy, sort order, multi-select inbounds filtered to multi-client protocols, enabled). Wired into SettingsPage under #subscription-balancers, and the sidebar shows the entry only when JSON subscription is enabled. * test(sub): add SubBalancer form modal test Covers add-mode (no validation errors, confirm with parsed values) and edit-mode (seeds from the balancer, preserves strategy/sort order/enabled). * feat(sub): register sub-balancers in API docs and OpenAPI Adds the sub-balancers endpoint group to endpoints.ts (list/create/update/delete + POST del alias) and regenerates frontend/public/openapi.json from it. * docs: sync openapi.json with frontend docs/public/openapi.json had fallen behind frontend/public/openapi.json (fewer paths/schemas). Copy the current frontend spec so the docs site renders the full API. * docs: add subscription balancers API reference Registers the sub-balancers page (generated MDX) and adds the sub-balancers paths to docs/public/openapi.json so the page renders the list/create/update/delete operations. * feat(sub): accept roundRobin balancer strategy Add roundRobin to the model oneof tag and the service strategy allowlist, alongside leastLoad/leastPing/random. Covered by a service-level create test that fails on the old allowlist. * feat(sub): add roundRobin strategy label pages.settings.subBalancers.strategyRoundRobin added to all 13 locales. * feat(sub): expose roundRobin in balancer form Zod strategy enum, form modal label key, and table strategy colour for roundRobin. * docs(sub): list roundRobin in strategy description The create/update strategy param description now mentions roundRobin alongside the other three. * feat(sub): add subJsonObservatory setting Panel-wide JSON string carrying the burstObservatory ping config (destination, connectivity, interval, sampling, timeout, httpMethod) emitted into client-side balancer docs. Stored like subJsonMux/Rules/FinalMask. * feat(sub): wire observatory config through sub controller WithSUBJsonObservatory option; the controller calls SubJsonService.SetObservatoryConfig after construction. * feat(sub): emit observatory conditionally with configurable probes burstObservatory is emitted only for leastPing/leastLoad; random/roundRobin get none (no fallback, so an observatory would only probe for nothing). Probe params come from the subJsonObservatory setting, falling back to the built-in defaults when empty or partial. Test covers the conditional emit and the override. * feat(sub): add subJsonObservatory to AllSetting model Frontend AllSetting model and Zod schema carry the new panel-wide observatory config string. * feat(sub): add balancer observatory config card New Sub Formats tab editing destination/connectivity/interval/sampling/timeout/httpMethod, stored as JSON in subJsonObservatory. Toggle off clears the setting; the backend then falls back to defaults. * fix(sub): hide save/restart header on sub-balancers tab Sub-balancer mutations are incremental (own CRUD API, no Save, no restart), so the page-wide 'every change needs to be saved / restart the panel' banner is misleading there. The in-tab alert already explains it correctly. * feat(sub): add observatory config i18n keys pages.settings.subBalancers.observatory.* (title, desc, probe field labels and help texts) added to all 13 locales. * feat(sub): regenerate openapi for subJsonObservatory openapigen picks up the new AllSetting field; openapi.json synced into docs. * feat(sub): add observatory tab to sub-balancers Mirrors the Xray Balancers page: two tabs (Balancers + Observatory). Wires allSetting/updateSetting into the tab and adds tabBalancers / tabObservatory labels to all locales. The page Save header is shown again on this tab so the observatory config can be saved. * refactor(sub): drop observatory tab from sub-formats Now that the observatory config lives under sub-balancers, remove the duplicate tab plus its state and defaults from sub-formats. * fix(sub): add missing inboundsCount i18n key The sub-balancers table rendered the raw key path in the Inbounds column because pages.settings.subBalancers.inboundsCount was not defined. Added it to all 13 locales. * test(sub): pin disabled-inbound exclusion from balancer The balancer builds its members from the subscriber's already-filtered entry set, so an inbound disabled for that user can never surface as a member. Adds tests for both shapes (one of several disabled, and the only selected one disabled). * fix(sub): make observatory toggle honest, default connectivity off, add balancer fallback Three coupled defects on the balancer observatory surface, flagged in PR review: - The Observatory Switch wrote '' which the Go side treats as "use built-in defaults", so leastPing/leastLoad still shipped a burstObservatory the admin could no longer see or edit. The observatory is mandatory for these strategies (Xray refuses to start leastPing/leastLoad without one — verified against Xray 26.7), so the switch is relabelled to "customise probe parameters vs built-in defaults" rather than on/off: '' keeps the defaults, a stored JSON overrides them. An info Alert explains this. - Connectivity defaulted to http://www.google.com/generate_204 and an explicit {"connectivity":""} restored it, so the UI's "Leave empty to skip" was unreachable and the direct pre-check was dead on arrival on censored client networks. Default to "" and honour an explicit empty value. - routing.balancers had no fallbackTag, so a leastPing/leastLoad balancer whose probes all fail selects nothing and dispatch fails. Emit fallbackTag pointing at the first member so a probe outage degrades instead of breaking. Also skip balancer entries (kind!=0) in the member scan so a balancer can never match another balancer's row id. Tests cover each fix and fail without it. * fix(sub-balancer): localize controller toasts and reject malformed ids Route the new controller's user-facing messages through I18nWeb so non-English admins get localized toasts like every other controller, and switch parseID to strconv.Atoi rejecting ids < 1 so "12abc" and negative ids no longer coerce to a silent no-op delete that reports success. * fix(sub-balancer): enforce remark length cap server-side The model's validate:"max=256" tag was never enforced (parseSubBalancerForm binds an ad-hoc struct without validate.Struct), so a scripted API client could store an unbounded remark that is emitted verbatim as the remarks field of every affected subscriber's config. Reject len > 256 in validate() to match the frontend Zod cap. * fix(sub-balancer): exclude mtproto from balancer member picker SubJsonService.getConfig has no mtproto case, so an mtproto inbound's first outbound is "direct" and the buildBalancerConfig "tag != proxy" guard drops it — an admin could select it, save without error, and get a balancer that silently omits it (or no document at all). Drop it from the picker and fix the comment. * docs(sub-balancers): add nav entry, fix tab pointer, note mirror scope - Add "subscription-balancers" to the en reference/api meta.json pages array so the new MDX page is reachable from the sidebar (fa/ru/zh have no MDX — gen-openapi.ts emits into en only). - Fix the endpoints.ts section description from "Settings -> Subscription" to "Settings -> Sub Balancers" (the feature's own tab) and regenerate the OpenAPI spec + MDX. - Note in docs/lib/xray/subscription.ts that balancer documents are intentionally out of scope for that mirror. * style(model): trim SubBalancer comment to 2-line cap CLAUDE.md caps committed Go comment blocks at 2 lines; this one was 3. * fix(sub-balancer): parse enabled explicitly and preserve it on partial update parseSubBalancerForm treated any non-"false" value as true (so "bogus" silently enabled) and always overwrote Enabled on update, so a PATCH that omitted the toggle reset a disabled balancer back to enabled. Parse the field with strconv.ParseBool and return *bool: absent means "no change" on update and "true" on create; a malformed value is rejected as 400. Update keeps the stored Enabled when the pointer is nil. * fix(sub-balancer): clear deleted inbound from sub_balancers.InboundIds DelInbound cascaded hosts but left the deleted inbound id in every sub_balancers.InboundIds, so the balancer kept emitting a member no subscriber could resolve — a dangling outbound tag with no proxy behind it. Strip the id inside the existing delete transaction (same shape as the hosts cascade, #5648); with the last member gone the balancer stops emitting. * fix(sub-balancer): return not-found when deleting a missing balancer Delete returned the gorm result error only, which is nil when no row matched, so the controller reported success:true for an id that never existed — a stale UI row looked like a clean delete. Check RowsAffected and return a not-found error on 0 so the toast reflects reality. * style(sub): shorten leastPing/leastLoad observatory comments The observatory-emission guard comment and its test comment ran a few lines long; trim them to a couple of lines each without dropping the invariant that leastPing/leastLoad require a burst observatory. * fix(sub): validate observatory setting instead of silently dropping it SetObservatoryConfig applied whatever survived json.Unmarshal with no checks, so a bad probe URL ("not-a-url"), non-duration interval/timeout, or even unparseable JSON was either silently applied or silently ignored. Validate each field: parse durations with time.ParseDuration, require http(s) URLs for destination/connectivity, and log a warning naming the field and the bad value on every fallback — including the unmarshal error, which was a quiet return. Bad values now keep the built-in defaults instead of leaking into the emitted burstObservatory. * fix(sub): deduplicate burst-observatory defaults across Go and frontend The burst-observatory ping defaults lived in three places that had drifted: Go defaultSubBalancerObservatoryConfig (http probe, sampling 3), the Zod PingConfigSchema, and DEFAULT_BURST_OBSERVATORY (both with a connectivity pre-check URL). Align them to one set: https probe destination, sampling 2, and empty connectivity (skip the direct pre-check). The settings tab now parses the stored JSON through PingConfigSchema and seeds its default from DEFAULT_BURST_OBSERVATORY instead of carrying its own literal. * refactor(sub): extract proxy outbounds once before the balancer loop buildBalancerConfig unmarshalled every inbound document and re-extracted its first outbound on each balancer, so with B balancers and N inbound docs the same document was parsed B*N times. Pull each doc's proxy outbound in a single pre-pass over the entries and cache it per entry; buildBalancerConfig now clones the cached map before retagging, so one parse serves every balancer. Output is byte-for-byte unchanged. * fix(sub): form balancer member tags from the inbound protocol, not tcp→vless balancerTransport derived the bal-N tag suffix from the outbound's transport network and hard-coded tcp→vless, so a vmess/tcp or trojan/tcp member was mislabelled "vless" in every client config — the tag lied about the proxy type. Use the outbound's real protocol as the suffix (bal-1-vmess, bal-1-vless, bal-1-trojan, …) so the tag names the actual proxy; the selector prefix and dedup suffix are unchanged. Update the existing tag assertions and add a vmess case that fails under the old mapping. * fix(sub-balancer): default strategy to random in the create form The create-balancer form seeded strategy to 'leastLoad', but the service validate() defaults an empty strategy to 'random' and the API docs say the default is 'random' — so a freshly opened form showed leastLoad while saving without touching the field silently stored random. Align the form default to 'random' so what the admin sees is what gets persisted. * feat(api-docs): document the SubBalancer response schema The five sub-balancer endpoints carried no responseSchema, so the API docs page rendered them without a typed example. Add example: tags to every SubBalancer field, allow the struct through openapigen, and point the list (responseSchemaArray) and single-row endpoints at 'SubBalancer'. Regenerate the Zod/JSON schemas and OpenAPI doc and mirror openapi.json into docs/. * style(sub-balancer): drop whitespace-only separator lines, add final newline subBalancer.ts and SubBalancerFormModal.tsx used single-space blank lines as separators between statements and had no trailing newline. Replace them with clean empty blank lines and end each file with a newline. * fix(i18n): translate sub-balancer toasts and observatory note The sub-balancer toast messages (list/create/update/delete/invalidId) and the observatory note were left in English across 11 non-English locales (ar, es, fa, id, ja, pt-BR, tr, uk, vi, zh-CN, zh-TW) while every other key in the subBalancers block was already translated. Translate them to match the meaning and terminology of the surrounding keys in each file; the JSON structure and keys are unchanged. * fix(sub-balancer): hide disabled inbounds from the member picker The picker offered every protocol-eligible inbound regardless of its enable flag, but getInboundsBySubId filters `AND inbounds.enable = true`. A disabled member is therefore dropped from every subscriber's entries, and when it was the balancer's only member the balancer document silently stops being emitted — with nothing in the UI explaining why. TestSubJson_BalancerSkippedWhenAll MembersDisabled already documents that backend behavior. Filter the way the sibling client picker has since #5645: hide disabled inbounds, but keep one that is already selected so editing an existing balancer cannot silently drop a member. Drop the `?? []` on the useWatch result so the new useMemo dependency stays referentially stable. * style(sub): trim the balancerMemberSuffix comment to the 2-line cap Comment blocks in committed Go are capped at 2 lines; the name already carries what the function picks, so keep only the why. --------- Co-authored-by: Sanaei <ho3ein.sanaei@gmail.com> Co-authored-by: claude[bot] <41898282+claude[bot]@users.noreply.github.com>
207 lines
18 KiB
Plaintext
207 lines
18 KiB
Plaintext
---
|
||
title: Inbounds
|
||
description: Manage inbound configurations and their clients. All endpoints live
|
||
under /panel/api/inbounds and require a logged-in session or Bearer token.
|
||
Link-generating endpoints honour forwarded headers only when the request comes
|
||
from a configured trusted proxy.
|
||
full: true
|
||
_openapi:
|
||
preload:
|
||
- ./public/openapi.json
|
||
toc:
|
||
- depth: 2
|
||
title: List every inbound owned by the authenticated user, including each
|
||
inbound’s clientStats traffic counters. settings, streamSettings, and
|
||
sniffing are returned as nested JSON objects (no escaped strings);
|
||
legacy callers that send them back as JSON-encoded strings are still
|
||
accepted on write.
|
||
url: '#list-every-inbound-owned-by-the-authenticated-user-including-each-inbounds-clientstats-traffic-counters-settings-streamsettings-and-sniffing-are-returned-as-nested-json-objects-no-escaped-strings-legacy-callers-that-send-them-back-as-json-encoded-strings-are-still-accepted-on-write'
|
||
- depth: 2
|
||
title: Same shape as /list but with settings.clients[] stripped down to {email,
|
||
enable, comment} and ClientStats not enriched with UUID/SubId. Use this
|
||
for list pages; fetch /get/:id when you need the full per-client payload
|
||
(uuid, password, flow, ...).
|
||
url: '#same-shape-as-list-but-with-settingsclients-stripped-down-to-email-enable-comment-and-clientstats-not-enriched-with-uuidsubid-use-this-for-list-pages-fetch-getid-when-you-need-the-full-per-client-payload-uuid-password-flow-'
|
||
- depth: 2
|
||
title: Lightweight picker projection of the authenticated user’s inbounds.
|
||
Returns id, remark, tag, protocol, port, a server-computed
|
||
tlsFlowCapable flag (true for VLESS on TCP with tls or reality, or on
|
||
XHTTP with VLESS encryption / vlessenc enabled), and ssMethod (the
|
||
Shadowsocks cipher, empty for non-Shadowsocks inbounds — used by the
|
||
client UI to generate a valid Shadowsocks 2022 PSK). Use this for
|
||
dropdowns and attach pickers — it skips settings, streamSettings, and
|
||
clientStats so the payload stays small even on panels with thousands of
|
||
clients.
|
||
url: '#lightweight-picker-projection-of-the-authenticated-users-inbounds-returns-id-remark-tag-protocol-port-a-server-computed-tlsflowcapable-flag-true-for-vless-on-tcp-with-tls-or-reality-or-on-xhttp-with-vless-encryption--vlessenc-enabled-and-ssmethod-the-shadowsocks-cipher-empty-for-non-shadowsocks-inbounds--used-by-the-client-ui-to-generate-a-valid-shadowsocks-2022-psk-use-this-for-dropdowns-and-attach-pickers--it-skips-settings-streamsettings-and-clientstats-so-the-payload-stays-small-even-on-panels-with-thousands-of-clients'
|
||
- depth: 2
|
||
title: Return every protocol URL (vless://, vmess://, trojan://, ss://,
|
||
hysteria://, mtproto) across all inbounds and all of their clients.
|
||
Links are rendered through the subscription engine, so the configured
|
||
remark template (name-only display part) is applied per client — the
|
||
same output the client info/QR pages use. Protocols without a URL form
|
||
(socks, http, mixed, wireguard, dokodemo, tunnel) contribute nothing.
|
||
Used by the panel’s "Export all inbound links" action.
|
||
url: '#return-every-protocol-url-vless-vmess-trojan-ss-hysteria-mtproto-across-all-inbounds-and-all-of-their-clients-links-are-rendered-through-the-subscription-engine-so-the-configured-remark-template-name-only-display-part-is-applied-per-client--the-same-output-the-client-infoqr-pages-use-protocols-without-a-url-form-socks-http-mixed-wireguard-dokodemo-tunnel-contribute-nothing-used-by-the-panels-export-all-inbound-links-action'
|
||
- depth: 2
|
||
title: Fetch a single inbound by numeric ID.
|
||
url: '#fetch-a-single-inbound-by-numeric-id'
|
||
- depth: 2
|
||
title: Create a new inbound. Send the full inbound payload (protocol, port,
|
||
settings, streamSettings, sniffing, remark, expiryTime, total, enable).
|
||
settings, streamSettings, and sniffing may be sent as nested JSON
|
||
objects (preferred) or as JSON-encoded strings (legacy).
|
||
url: '#create-a-new-inbound-send-the-full-inbound-payload-protocol-port-settings-streamsettings-sniffing-remark-expirytime-total-enable-settings-streamsettings-and-sniffing-may-be-sent-as-nested-json-objects-preferred-or-as-json-encoded-strings-legacy'
|
||
- depth: 2
|
||
title: Delete an inbound by ID. Also removes its associated client stats rows.
|
||
url: '#delete-an-inbound-by-id-also-removes-its-associated-client-stats-rows'
|
||
- depth: 2
|
||
title: Delete many inbounds in one call. Processes the list sequentially;
|
||
failures are reported per id and the rest still proceed. Restarts xray
|
||
at most once.
|
||
url: '#delete-many-inbounds-in-one-call-processes-the-list-sequentially-failures-are-reported-per-id-and-the-rest-still-proceed-restarts-xray-at-most-once'
|
||
- depth: 2
|
||
title: Replace an inbound’s configuration. Body shape mirrors /add. Heavy on
|
||
inbounds with thousands of clients — prefer /setEnable for enable-only
|
||
flips.
|
||
url: '#replace-an-inbounds-configuration-body-shape-mirrors-add-heavy-on-inbounds-with-thousands-of-clients--prefer-setenable-for-enable-only-flips'
|
||
- depth: 2
|
||
title: Toggle only the enable flag without serialising the whole settings JSON.
|
||
Recommended for UI switches on large inbounds.
|
||
url: '#toggle-only-the-enable-flag-without-serialising-the-whole-settings-json-recommended-for-ui-switches-on-large-inbounds'
|
||
- depth: 2
|
||
title: Set only the subscription sort order. Reads the stored inbound, so a
|
||
reorder cannot carry a stale client list over a concurrent edit.
|
||
url: '#set-only-the-subscription-sort-order-reads-the-stored-inbound-so-a-reorder-cannot-carry-a-stale-client-list-over-a-concurrent-edit'
|
||
- depth: 2
|
||
title: Zero out upload + download counters for a single inbound. Does not touch
|
||
per-client counters.
|
||
url: '#zero-out-upload--download-counters-for-a-single-inbound-does-not-touch-per-client-counters'
|
||
- depth: 2
|
||
title: Remove every client attached to a single inbound while keeping the
|
||
inbound itself. Collects emails from settings.clients[] and feeds them
|
||
into the optimized bulk-delete path (runtime user removal + traffic-row
|
||
cleanup + SyncInbound). Destructive and cannot be undone.
|
||
url: '#remove-every-client-attached-to-a-single-inbound-while-keeping-the-inbound-itself-collects-emails-from-settingsclients-and-feeds-them-into-the-optimized-bulk-delete-path-runtime-user-removal--traffic-row-cleanup--syncinbound-destructive-and-cannot-be-undone'
|
||
- depth: 2
|
||
title: Reset upload + download counters on every inbound. Destructive —
|
||
accounting history is lost.
|
||
url: '#reset-upload--download-counters-on-every-inbound-destructive--accounting-history-is-lost'
|
||
- depth: 2
|
||
title: Bulk-import an inbound from a JSON blob (e.g. one exported via the UI).
|
||
The body uses form encoding with a single "data" field.
|
||
url: '#bulk-import-an-inbound-from-a-json-blob-eg-one-exported-via-the-ui-the-body-uses-form-encoding-with-a-single-data-field'
|
||
- depth: 2
|
||
title: Receive a master panel's aggregated per-client usage, keyed by the
|
||
master's GUID. Stored in a side table used only for the UI display
|
||
overlay and local quota enforcement — never folded into the local
|
||
counters that masters poll, so delta accounting stays intact. Called
|
||
panel-to-panel by the node traffic sync job.
|
||
url: '#receive-a-master-panels-aggregated-per-client-usage-keyed-by-the-masters-guid-stored-in-a-side-table-used-only-for-the-ui-display-overlay-and-local-quota-enforcement--never-folded-into-the-local-counters-that-masters-poll-so-delta-accounting-stays-intact-called-panel-to-panel-by-the-node-traffic-sync-job'
|
||
- depth: 2
|
||
title: List the fallback rules attached to a master VLESS/Trojan TCP-TLS
|
||
inbound. Each rule links one child inbound (the dest) to optional
|
||
SNI/ALPN/path/dest/xver match criteria. When dest is empty the child
|
||
inbound's listen+port is used.
|
||
url: '#list-the-fallback-rules-attached-to-a-master-vlesstrojan-tcp-tls-inbound-each-rule-links-one-child-inbound-the-dest-to-optional-snialpnpathdestxver-match-criteria-when-dest-is-empty-the-child-inbounds-listenport-is-used'
|
||
- depth: 2
|
||
title: Replace the entire fallback list for a master inbound. Body is JSON.
|
||
Triggers an Xray restart.
|
||
url: '#replace-the-entire-fallback-list-for-a-master-inbound-body-is-json-triggers-an-xray-restart'
|
||
structuredData:
|
||
headings:
|
||
- content: List every inbound owned by the authenticated user, including each
|
||
inbound’s clientStats traffic counters. settings, streamSettings, and
|
||
sniffing are returned as nested JSON objects (no escaped strings);
|
||
legacy callers that send them back as JSON-encoded strings are still
|
||
accepted on write.
|
||
id: list-every-inbound-owned-by-the-authenticated-user-including-each-inbounds-clientstats-traffic-counters-settings-streamsettings-and-sniffing-are-returned-as-nested-json-objects-no-escaped-strings-legacy-callers-that-send-them-back-as-json-encoded-strings-are-still-accepted-on-write
|
||
- content: Same shape as /list but with settings.clients[] stripped down to
|
||
{email, enable, comment} and ClientStats not enriched with UUID/SubId.
|
||
Use this for list pages; fetch /get/:id when you need the full
|
||
per-client payload (uuid, password, flow, ...).
|
||
id: same-shape-as-list-but-with-settingsclients-stripped-down-to-email-enable-comment-and-clientstats-not-enriched-with-uuidsubid-use-this-for-list-pages-fetch-getid-when-you-need-the-full-per-client-payload-uuid-password-flow-
|
||
- content: Lightweight picker projection of the authenticated user’s inbounds.
|
||
Returns id, remark, tag, protocol, port, a server-computed
|
||
tlsFlowCapable flag (true for VLESS on TCP with tls or reality, or on
|
||
XHTTP with VLESS encryption / vlessenc enabled), and ssMethod (the
|
||
Shadowsocks cipher, empty for non-Shadowsocks inbounds — used by the
|
||
client UI to generate a valid Shadowsocks 2022 PSK). Use this for
|
||
dropdowns and attach pickers — it skips settings, streamSettings, and
|
||
clientStats so the payload stays small even on panels with thousands
|
||
of clients.
|
||
id: lightweight-picker-projection-of-the-authenticated-users-inbounds-returns-id-remark-tag-protocol-port-a-server-computed-tlsflowcapable-flag-true-for-vless-on-tcp-with-tls-or-reality-or-on-xhttp-with-vless-encryption--vlessenc-enabled-and-ssmethod-the-shadowsocks-cipher-empty-for-non-shadowsocks-inbounds--used-by-the-client-ui-to-generate-a-valid-shadowsocks-2022-psk-use-this-for-dropdowns-and-attach-pickers--it-skips-settings-streamsettings-and-clientstats-so-the-payload-stays-small-even-on-panels-with-thousands-of-clients
|
||
- content: Return every protocol URL (vless://, vmess://, trojan://, ss://,
|
||
hysteria://, mtproto) across all inbounds and all of their clients.
|
||
Links are rendered through the subscription engine, so the configured
|
||
remark template (name-only display part) is applied per client — the
|
||
same output the client info/QR pages use. Protocols without a URL form
|
||
(socks, http, mixed, wireguard, dokodemo, tunnel) contribute nothing.
|
||
Used by the panel’s "Export all inbound links" action.
|
||
id: return-every-protocol-url-vless-vmess-trojan-ss-hysteria-mtproto-across-all-inbounds-and-all-of-their-clients-links-are-rendered-through-the-subscription-engine-so-the-configured-remark-template-name-only-display-part-is-applied-per-client--the-same-output-the-client-infoqr-pages-use-protocols-without-a-url-form-socks-http-mixed-wireguard-dokodemo-tunnel-contribute-nothing-used-by-the-panels-export-all-inbound-links-action
|
||
- content: Fetch a single inbound by numeric ID.
|
||
id: fetch-a-single-inbound-by-numeric-id
|
||
- content: Create a new inbound. Send the full inbound payload (protocol, port,
|
||
settings, streamSettings, sniffing, remark, expiryTime, total,
|
||
enable). settings, streamSettings, and sniffing may be sent as nested
|
||
JSON objects (preferred) or as JSON-encoded strings (legacy).
|
||
id: create-a-new-inbound-send-the-full-inbound-payload-protocol-port-settings-streamsettings-sniffing-remark-expirytime-total-enable-settings-streamsettings-and-sniffing-may-be-sent-as-nested-json-objects-preferred-or-as-json-encoded-strings-legacy
|
||
- content: Delete an inbound by ID. Also removes its associated client stats rows.
|
||
id: delete-an-inbound-by-id-also-removes-its-associated-client-stats-rows
|
||
- content: Delete many inbounds in one call. Processes the list sequentially;
|
||
failures are reported per id and the rest still proceed. Restarts xray
|
||
at most once.
|
||
id: delete-many-inbounds-in-one-call-processes-the-list-sequentially-failures-are-reported-per-id-and-the-rest-still-proceed-restarts-xray-at-most-once
|
||
- content: Replace an inbound’s configuration. Body shape mirrors /add. Heavy on
|
||
inbounds with thousands of clients — prefer /setEnable for enable-only
|
||
flips.
|
||
id: replace-an-inbounds-configuration-body-shape-mirrors-add-heavy-on-inbounds-with-thousands-of-clients--prefer-setenable-for-enable-only-flips
|
||
- content: Toggle only the enable flag without serialising the whole settings
|
||
JSON. Recommended for UI switches on large inbounds.
|
||
id: toggle-only-the-enable-flag-without-serialising-the-whole-settings-json-recommended-for-ui-switches-on-large-inbounds
|
||
- content: Set only the subscription sort order. Reads the stored inbound, so a
|
||
reorder cannot carry a stale client list over a concurrent edit.
|
||
id: set-only-the-subscription-sort-order-reads-the-stored-inbound-so-a-reorder-cannot-carry-a-stale-client-list-over-a-concurrent-edit
|
||
- content: Zero out upload + download counters for a single inbound. Does not
|
||
touch per-client counters.
|
||
id: zero-out-upload--download-counters-for-a-single-inbound-does-not-touch-per-client-counters
|
||
- content: Remove every client attached to a single inbound while keeping the
|
||
inbound itself. Collects emails from settings.clients[] and feeds them
|
||
into the optimized bulk-delete path (runtime user removal +
|
||
traffic-row cleanup + SyncInbound). Destructive and cannot be undone.
|
||
id: remove-every-client-attached-to-a-single-inbound-while-keeping-the-inbound-itself-collects-emails-from-settingsclients-and-feeds-them-into-the-optimized-bulk-delete-path-runtime-user-removal--traffic-row-cleanup--syncinbound-destructive-and-cannot-be-undone
|
||
- content: Reset upload + download counters on every inbound. Destructive —
|
||
accounting history is lost.
|
||
id: reset-upload--download-counters-on-every-inbound-destructive--accounting-history-is-lost
|
||
- content: Bulk-import an inbound from a JSON blob (e.g. one exported via the UI).
|
||
The body uses form encoding with a single "data" field.
|
||
id: bulk-import-an-inbound-from-a-json-blob-eg-one-exported-via-the-ui-the-body-uses-form-encoding-with-a-single-data-field
|
||
- content: Receive a master panel's aggregated per-client usage, keyed by the
|
||
master's GUID. Stored in a side table used only for the UI display
|
||
overlay and local quota enforcement — never folded into the local
|
||
counters that masters poll, so delta accounting stays intact. Called
|
||
panel-to-panel by the node traffic sync job.
|
||
id: receive-a-master-panels-aggregated-per-client-usage-keyed-by-the-masters-guid-stored-in-a-side-table-used-only-for-the-ui-display-overlay-and-local-quota-enforcement--never-folded-into-the-local-counters-that-masters-poll-so-delta-accounting-stays-intact-called-panel-to-panel-by-the-node-traffic-sync-job
|
||
- content: List the fallback rules attached to a master VLESS/Trojan TCP-TLS
|
||
inbound. Each rule links one child inbound (the dest) to optional
|
||
SNI/ALPN/path/dest/xver match criteria. When dest is empty the child
|
||
inbound's listen+port is used.
|
||
id: list-the-fallback-rules-attached-to-a-master-vlesstrojan-tcp-tls-inbound-each-rule-links-one-child-inbound-the-dest-to-optional-snialpnpathdestxver-match-criteria-when-dest-is-empty-the-child-inbounds-listenport-is-used
|
||
- content: Replace the entire fallback list for a master inbound. Body is JSON.
|
||
Triggers an Xray restart.
|
||
id: replace-the-entire-fallback-list-for-a-master-inbound-body-is-json-triggers-an-xray-restart
|
||
contents: []
|
||
---
|
||
|
||
{/* This file was generated by Fumadocs. Do not edit this file directly. Any changes should be made by running the generation command again. */}
|
||
|
||
export default function Layout(props) {
|
||
const { APIPage, OpenAPIPage } = props.components ?? {};
|
||
// "APIPage" is the old name from v10, this allows both for backward compatibility
|
||
const Comp = OpenAPIPage ?? APIPage;
|
||
return (
|
||
<>
|
||
{props.children}
|
||
<Comp document="./public/openapi.json" webhooks={[]} operations={[{"path":"/panel/api/inbounds/list","method":"get"},{"path":"/panel/api/inbounds/list/slim","method":"get"},{"path":"/panel/api/inbounds/options","method":"get"},{"path":"/panel/api/inbounds/allLinks","method":"get"},{"path":"/panel/api/inbounds/get/{id}","method":"get"},{"path":"/panel/api/inbounds/add","method":"post"},{"path":"/panel/api/inbounds/del/{id}","method":"post"},{"path":"/panel/api/inbounds/bulkDel","method":"post"},{"path":"/panel/api/inbounds/update/{id}","method":"post"},{"path":"/panel/api/inbounds/setEnable/{id}","method":"post"},{"path":"/panel/api/inbounds/{id}/subSortIndex","method":"post"},{"path":"/panel/api/inbounds/{id}/resetTraffic","method":"post"},{"path":"/panel/api/inbounds/{id}/delAllClients","method":"post"},{"path":"/panel/api/inbounds/resetAllTraffics","method":"post"},{"path":"/panel/api/inbounds/import","method":"post"},{"path":"/panel/api/inbounds/pushClientTraffics","method":"post"},{"path":"/panel/api/inbounds/{id}/fallbacks","method":"get"},{"path":"/panel/api/inbounds/{id}/fallbacks","method":"post"}]} showTitle />
|
||
</>
|
||
);
|
||
} |