Skip to content

Shadowsocks — sing-box

sing-box implements the full Shadowsocks family: classic AEAD, Shadowsocks-2022 with EIH multi-user, plugin protocols for v2ray-plugin and obfs, and the server-side relay form unique to SS-2022.

Inbound

type: "shadowsocks" inbound:

FieldTypeDefaultAllowed valuesDescription
networkNetworkList(tcp+udp)tcp | udp | Restrict to TCP-only or UDP-only. Empty enables both.
methodstring(required)none | aes-128-gcm | aes-256-gcm | chacha20-ietf-poly1305 | xchacha20-ietf-poly1305 | 2022-blake3-aes-128-gcm | 2022-blake3-aes-256-gcm | 2022-blake3-chacha20-poly1305Cipher used by the inbound. SS-2022 ciphers enable `users[]` and `destinations[]`.
passwordstring(required for single-user)<string> | <base64 key>Single-user password or the SS-2022 server EIH key.
users[]ShadowsocksUser[][ShadowsocksUser]Per-user list — SS-2022 only. Each user has their own EIH key.
destinations[]ShadowsocksDestination[][ShadowsocksDestination]Server-side relay targets. SS-2022 servers can use this to fan a single inbound out to multiple upstream addresses, picked by EIH.
multiplex*InboundMultiplexOptions(disabled)InboundMultiplexOptionsServer-side multiplex.
managedboolfalsetrue | falseEnable the managed-mode protocol that lets ssmgmt-compatible clients reconfigure users at runtime.

Source: option/shadowsocks.go:3-12 · pinned at v1.13.11 (553cfa1)

The struct embeds ListenOptions (listen address, port, sniff, …).

users[]

FieldTypeDefaultAllowed valuesDescription
namestring(unset)<string>Display name used in stats and logs.
passwordstring(required)<base64 key>User EIH key. Length must match the cipher (16 or 32 bytes).

Source: option/shadowsocks.go:14-17 · pinned at v1.13.11 (553cfa1)

destinations[]

Each destination embeds ServerOptions (server, server_port) plus its own name/password.

FieldTypeDefaultAllowed valuesDescription
namestring(unset)<string>Display name for this destination.
passwordstring(required)<base64 key>Destination EIH key.

Source: option/shadowsocks.go:19-23 · pinned at v1.13.11 (553cfa1)

Outbound

type: "shadowsocks" outbound:

FieldTypeDefaultAllowed valuesDescription
methodstring(required)<cipher>Server cipher.
passwordstring(required)<string> | <base64 key>Server password / SS-2022 key.
pluginstring(unset)obfs-local | v2ray-plugin | shadow-tls | kcptunExternal Shadowsocks plugin to wrap the stream. Compiled into sing-box for `obfs-local` and `v2ray-plugin`; others require an external binary on PATH.
plugin_optsstring(unset)<plugin-specific string>Semicolon-separated options forwarded to the plugin (`mode=tls;host=example.com;...`).
networkNetworkList(tcp+udp)tcp | udp | Restrict to TCP-only or UDP-only.
udp_over_tcp*UDPOverTCPOptions(disabled)UDPOverTCPOptionsWrap UDP packets inside the TCP stream. Object form: `{enabled, version}`.
multiplex*OutboundMultiplexOptions(disabled)OutboundMultiplexOptionsClient-side multiplex (must match the server).

Source: option/shadowsocks.go:25-35 · pinned at v1.13.11 (553cfa1)

Embeds DialerOptions and ServerOptions.

Examples

Classic AEAD inbound:

json
{
  "inbounds": [
    {
      "type": "shadowsocks",
      "tag": "ss-in",
      "listen": "::",
      "listen_port": 8388,
      "method": "aes-256-gcm",
      "password": "<password>"
    }
  ]
}

SS-2022 inbound with two users:

json
{
  "inbounds": [
    {
      "type": "shadowsocks",
      "tag": "ss22-in",
      "listen": "::",
      "listen_port": 8388,
      "method": "2022-blake3-aes-128-gcm",
      "password": "<base64 16-byte server key>",
      "users": [
        { "name": "alice", "password": "<base64 16-byte alice key>" },
        { "name": "bob",   "password": "<base64 16-byte bob key>" }
      ]
    }
  ]
}

Outbound with v2ray-plugin:

json
{
  "outbounds": [
    {
      "type": "shadowsocks",
      "tag": "ss-out",
      "server": "example.com",
      "server_port": 8388,
      "method": "chacha20-ietf-poly1305",
      "password": "<password>",
      "plugin": "v2ray-plugin",
      "plugin_opts": "mode=websocket;tls;host=example.com;path=/ss"
    }
  ]
}

Outbound with UDP-over-TCP v2:

json
{
  "outbounds": [
    {
      "type": "shadowsocks",
      "server": "example.com",
      "server_port": 8388,
      "method": "2022-blake3-aes-256-gcm",
      "password": "<base64 32-byte key>",
      "udp_over_tcp": { "enabled": true, "version": 2 }
    }
  ]
}

Notes

  • sing-box accepts both the IETF cipher names (chacha20-ietf-poly1305) and the non-IETF historical names — but it tightens to a single spelling per cipher inside the protocol layer.
  • destinations[] is sing-box specific. An SS-2022 server with destinations acts as an EIH-discriminated relay: each destination carries its own EIH key, and an inbound connection that authenticates against one of them is forwarded to that destination's server / server_port rather than handled locally.
  • plugin: "v2ray-plugin" and plugin: "obfs-local" are compiled into sing-box (no external binary needed). Other plugin names invoke an external executable of the same name; the plugin protocol matches the shadowsocks-libev plugin spec.
  • udp_over_tcp is an object ({enabled, version}) where Xray uses two fields (uot, uotVersion) and mihomo uses two fields under different names again.

Cross-core notes

  • Xray uses clients[] (not users[]) and exposes UoT as two separate fields (uot, uotVersion) on the outbound. It has no destinations[] relay shape. See Shadowsocks — Xray-core.
  • mihomo uses cipher (not method) and accepts plugin-opts as a typed YAML map keyed by plugin name. See Shadowsocks — mihomo.

Source: option/shadowsocks.go:3-35 · v1.13.11 (553cfa1)

Core Tutorial by Argsment