Skip to content

Instantly share code, notes, and snippets.

@zhongwencool
Last active May 26, 2022 08:33
Show Gist options
  • Save zhongwencool/7d5e7abddaa47e85f1ff7ce796a12c14 to your computer and use it in GitHub Desktop.
Save zhongwencool/7d5e7abddaa47e85f1ff7ce796a12c14 to your computer and use it in GitHub Desktop.
## Title
## Body
listeners {
## @doc
## TCP listeners
##
## @path listeners.tcp
## @type map()
## tcp:
## $default {
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.tcp.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path listeners.tcp.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path listeners.tcp.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path listeners.tcp.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path listeners.tcp.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path listeners.tcp.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path listeners.tcp.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path listeners.tcp.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path listeners.tcp.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path listeners.tcp.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc
## IP address and port for the listening socket.
##
## @path listeners.tcp.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc
## The size of the listener's receiving pool.
##
## @path listeners.tcp.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## The maximum number of concurrent connections allowed by the listener.
##
## @path listeners.tcp.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message
## is delivered to the subscriber. The mountpoint is a way that users can use
## to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint`
## set to `some_tenant`, then the client actually subscribes to the topic
## `some_tenant/t`. Similarly, if another client B (connected to the same listener
## as the client A) sends a message to topic `t`, the message is routed
## to all the clients subscribed `some_tenant/t`, so client A will receive the
## message, with topic name `t`.</br>
## Set to `""` to disable the feature.</br>
##
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.tcp.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## The configuration zone to which the listener belongs.
##
## @path listeners.tcp.$default.zone
## @type atom()
## zone: default
## @doc
## Type of the rate limit.
##
## @path listeners.tcp.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.tcp.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc
## The access control rules for this listener.</br>See: https://github.com/emqtt/esockd#allowdeny
##
## @path listeners.tcp.$default
## @type array
## access_rules: ["allow all"]
## @doc
## Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.</br>
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.tcp.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## Timeout for proxy protocol. EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
##
## @path listeners.tcp.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## Per-listener authentication override.
## Authentication can be one single authenticator instance or a chain of authenticators as an array.
## When authenticating a login (username, client ID, etc.) the authenticators are checked in the configured order.</br>
##
##
## @path listeners.tcp.$default
## @type array
## authentication: []
## @path listeners.tcp.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc
## SSL listeners
##
## @path listeners.ssl
## @type map()
## ssl:
## $default {
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.ssl.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path listeners.ssl.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path listeners.ssl.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path listeners.ssl.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path listeners.ssl.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path listeners.ssl.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path listeners.ssl.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path listeners.ssl.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path listeners.ssl.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path listeners.ssl.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path listeners.ssl.$default.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path listeners.ssl.$default.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path listeners.ssl.$default.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path listeners.ssl.$default.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path listeners.ssl.$default.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path listeners.ssl.$default.ssl.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path listeners.ssl.$default.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path listeners.ssl.$default.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path listeners.ssl.$default.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path listeners.ssl.$default.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path listeners.ssl.$default.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path listeners.ssl.$default.ssl.dhfile
## @type string()
## dhfile:
## @doc
## Used together with {verify, verify_peer} by an TLS/DTLS server.
## If set to true, the server fails if the client does not have a
## certificate to send, that is, sends an empty certificate.
## If set to false, it fails only if the client sends an invalid
## certificate (an empty certificate is considered valid).
##
## @path listeners.ssl.$default.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path listeners.ssl.$default.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path listeners.ssl.$default.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## @doc
## IP address and port for the listening socket.
##
## @path listeners.ssl.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc
## The size of the listener's receiving pool.
##
## @path listeners.ssl.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## The maximum number of concurrent connections allowed by the listener.
##
## @path listeners.ssl.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message
## is delivered to the subscriber. The mountpoint is a way that users can use
## to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint`
## set to `some_tenant`, then the client actually subscribes to the topic
## `some_tenant/t`. Similarly, if another client B (connected to the same listener
## as the client A) sends a message to topic `t`, the message is routed
## to all the clients subscribed `some_tenant/t`, so client A will receive the
## message, with topic name `t`.</br>
## Set to `""` to disable the feature.</br>
##
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.ssl.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## The configuration zone to which the listener belongs.
##
## @path listeners.ssl.$default.zone
## @type atom()
## zone: default
## @doc
## Type of the rate limit.
##
## @path listeners.ssl.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.ssl.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc
## The access control rules for this listener.</br>See: https://github.com/emqtt/esockd#allowdeny
##
## @path listeners.ssl.$default
## @type array
## access_rules: ["allow all"]
## @doc
## Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.</br>
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.ssl.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## Timeout for proxy protocol. EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
##
## @path listeners.ssl.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## Per-listener authentication override.
## Authentication can be one single authenticator instance or a chain of authenticators as an array.
## When authenticating a login (username, client ID, etc.) the authenticators are checked in the configured order.</br>
##
##
## @path listeners.ssl.$default
## @type array
## authentication: []
## @path listeners.ssl.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc
## HTTP websocket listeners
##
## @path listeners.ws
## @type map()
## ws:
## $default {
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.ws.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path listeners.ws.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path listeners.ws.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path listeners.ws.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path listeners.ws.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path listeners.ws.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path listeners.ws.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path listeners.ws.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path listeners.ws.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path listeners.ws.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## websocket {
## @doc
## WebSocket's MQTT protocol path. So the address of EMQX Broker's WebSocket is:
## <code>ws://{ip}:{port}/mqtt</code>
##
## @path listeners.ws.$default.websocket.mqtt_path
## @type string()
## mqtt_path: "/mqtt"
## @doc
## Whether a WebSocket message is allowed to contain multiple MQTT packets.
##
## @path listeners.ws.$default.websocket.mqtt_piggyback
## @type enum: single | multiple
## mqtt_piggyback: multiple
## @doc
## If <code>true</code>, compress WebSocket messages using <code>zlib</code>.</br>
## The configuration items under <code>deflate_opts</code> belong to the compression-related parameter configuration.
##
## @path listeners.ws.$default.websocket.compress
## @type boolean()
## compress: false
## @doc
## Close transport-layer connections from the clients that have not sent MQTT CONNECT
## message within this interval.
##
## @path listeners.ws.$default.websocket.idle_timeout
## @type emqx_schema:duration()
## idle_timeout: "15s"
## @doc
## The maximum length of a single MQTT packet.
##
## @path listeners.ws.$default.websocket.max_frame_size
## @type union: infinity | integer()
## max_frame_size: infinity
## @doc
## If <code>true</code>, the server will return an error when
## the client does not carry the <code>Sec-WebSocket-Protocol</code> field.
## </br>Note: WeChat applet needs to disable this verification.
##
## @path listeners.ws.$default.websocket.fail_if_no_subprotocol
## @type boolean()
## fail_if_no_subprotocol: true
## @doc
## Comma-separated list of supported subprotocols.
##
## @path listeners.ws.$default.websocket.supported_subprotocols
## @type emqx_schema:comma_separated_list()
## supported_subprotocols: "mqtt, mqtt-v3, mqtt-v3.1.1, mqtt-v5"
## @doc
## If <code>true</code>, <code>origin</code> HTTP header will be
## validated against the list of allowed origins configured in <code>check_origins</code>
## parameter.
##
## @path listeners.ws.$default.websocket.check_origin_enable
## @type boolean()
## check_origin_enable: false
## @doc
## If <code>false</code> and <code>check_origin_enable</code> is
## <code>true</code>, the server will reject requests that don't have <code>origin</code>
## HTTP header.
##
## @path listeners.ws.$default.websocket.allow_origin_absence
## @type boolean()
## allow_origin_absence: true
## @doc
## List of allowed origins.</br>See <code>check_origin_enable</code>.
##
## @path listeners.ws.$default.websocket
## @type array
## check_origins: []
## @doc
## HTTP header used to pass information about the client IP address.
## Relevant when the EMQX cluster is deployed behind a load-balancer.
##
## @path listeners.ws.$default.websocket.proxy_address_header
## @type string()
## proxy_address_header: "x-forwarded-for"
## @doc
## HTTP header used to pass information about the client port.
## Relevant when the EMQX cluster is deployed behind a load-balancer.
##
## @path listeners.ws.$default.websocket.proxy_port_header
## @type string()
## proxy_port_header: "x-forwarded-port"
## deflate_opts {
## @doc
## Compression level.
##
## @path listeners.ws.$default.websocket.deflate_opts.level
## @type enum: none | default | best_compression | best_speed
## level: none
## @doc
## Specifies the size of the compression state.</br>
## Lower values decrease memory usage per connection.
##
## @path listeners.ws.$default.websocket.deflate_opts.mem_level
## @type 1..9
## mem_level: 8
## @doc
## Specifies the compression strategy.
##
## @path listeners.ws.$default.websocket.deflate_opts.strategy
## @type enum: default | filtered | huffman_only | rle
## strategy: default
## @doc
## Takeover means the compression state is retained between server messages.
##
## @path listeners.ws.$default.websocket.deflate_opts.server_context_takeover
## @type enum: takeover | no_takeover
## server_context_takeover: takeover
## @doc
## Takeover means the compression state is retained between client messages.
##
## @path listeners.ws.$default.websocket.deflate_opts.client_context_takeover
## @type enum: takeover | no_takeover
## client_context_takeover: takeover
## @doc
## Specifies the size of the compression context for the server.
##
## @path listeners.ws.$default.websocket.deflate_opts.server_max_window_bits
## @type 8..15
## server_max_window_bits: 15
## @doc
## Specifies the size of the compression context for the client.
##
## @path listeners.ws.$default.websocket.deflate_opts.client_max_window_bits
## @type 8..15
## client_max_window_bits: 15
## }
## }
## @doc
## IP address and port for the listening socket.
##
## @path listeners.ws.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc
## The size of the listener's receiving pool.
##
## @path listeners.ws.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## The maximum number of concurrent connections allowed by the listener.
##
## @path listeners.ws.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message
## is delivered to the subscriber. The mountpoint is a way that users can use
## to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint`
## set to `some_tenant`, then the client actually subscribes to the topic
## `some_tenant/t`. Similarly, if another client B (connected to the same listener
## as the client A) sends a message to topic `t`, the message is routed
## to all the clients subscribed `some_tenant/t`, so client A will receive the
## message, with topic name `t`.</br>
## Set to `""` to disable the feature.</br>
##
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.ws.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## The configuration zone to which the listener belongs.
##
## @path listeners.ws.$default.zone
## @type atom()
## zone: default
## @doc
## Type of the rate limit.
##
## @path listeners.ws.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.ws.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc
## The access control rules for this listener.</br>See: https://github.com/emqtt/esockd#allowdeny
##
## @path listeners.ws.$default
## @type array
## access_rules: ["allow all"]
## @doc
## Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.</br>
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.ws.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## Timeout for proxy protocol. EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
##
## @path listeners.ws.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## Per-listener authentication override.
## Authentication can be one single authenticator instance or a chain of authenticators as an array.
## When authenticating a login (username, client ID, etc.) the authenticators are checked in the configured order.</br>
##
##
## @path listeners.ws.$default
## @type array
## authentication: []
## @path listeners.ws.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc
## HTTPS websocket listeners
##
## @path listeners.wss
## @type map()
## wss:
## $default {
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.wss.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path listeners.wss.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path listeners.wss.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path listeners.wss.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path listeners.wss.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path listeners.wss.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path listeners.wss.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path listeners.wss.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path listeners.wss.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path listeners.wss.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path listeners.wss.$default.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path listeners.wss.$default.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path listeners.wss.$default.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path listeners.wss.$default.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path listeners.wss.$default.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path listeners.wss.$default.ssl.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path listeners.wss.$default.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path listeners.wss.$default.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path listeners.wss.$default.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path listeners.wss.$default.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path listeners.wss.$default.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path listeners.wss.$default.ssl.dhfile
## @type string()
## dhfile:
## @doc
## Used together with {verify, verify_peer} by an TLS/DTLS server.
## If set to true, the server fails if the client does not have a
## certificate to send, that is, sends an empty certificate.
## If set to false, it fails only if the client sends an invalid
## certificate (an empty certificate is considered valid).
##
## @path listeners.wss.$default.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path listeners.wss.$default.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path listeners.wss.$default.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## @doc
## Maximum time duration allowed for the handshake to complete
##
## @path listeners.wss.$default.ssl.handshake_timeout
## @type emqx_schema:duration()
## handshake_timeout: "15s"
## }
## websocket {
## @doc
## WebSocket's MQTT protocol path. So the address of EMQX Broker's WebSocket is:
## <code>ws://{ip}:{port}/mqtt</code>
##
## @path listeners.wss.$default.websocket.mqtt_path
## @type string()
## mqtt_path: "/mqtt"
## @doc
## Whether a WebSocket message is allowed to contain multiple MQTT packets.
##
## @path listeners.wss.$default.websocket.mqtt_piggyback
## @type enum: single | multiple
## mqtt_piggyback: multiple
## @doc
## If <code>true</code>, compress WebSocket messages using <code>zlib</code>.</br>
## The configuration items under <code>deflate_opts</code> belong to the compression-related parameter configuration.
##
## @path listeners.wss.$default.websocket.compress
## @type boolean()
## compress: false
## @doc
## Close transport-layer connections from the clients that have not sent MQTT CONNECT
## message within this interval.
##
## @path listeners.wss.$default.websocket.idle_timeout
## @type emqx_schema:duration()
## idle_timeout: "15s"
## @doc
## The maximum length of a single MQTT packet.
##
## @path listeners.wss.$default.websocket.max_frame_size
## @type union: infinity | integer()
## max_frame_size: infinity
## @doc
## If <code>true</code>, the server will return an error when
## the client does not carry the <code>Sec-WebSocket-Protocol</code> field.
## </br>Note: WeChat applet needs to disable this verification.
##
## @path listeners.wss.$default.websocket.fail_if_no_subprotocol
## @type boolean()
## fail_if_no_subprotocol: true
## @doc
## Comma-separated list of supported subprotocols.
##
## @path listeners.wss.$default.websocket.supported_subprotocols
## @type emqx_schema:comma_separated_list()
## supported_subprotocols: "mqtt, mqtt-v3, mqtt-v3.1.1, mqtt-v5"
## @doc
## If <code>true</code>, <code>origin</code> HTTP header will be
## validated against the list of allowed origins configured in <code>check_origins</code>
## parameter.
##
## @path listeners.wss.$default.websocket.check_origin_enable
## @type boolean()
## check_origin_enable: false
## @doc
## If <code>false</code> and <code>check_origin_enable</code> is
## <code>true</code>, the server will reject requests that don't have <code>origin</code>
## HTTP header.
##
## @path listeners.wss.$default.websocket.allow_origin_absence
## @type boolean()
## allow_origin_absence: true
## @doc
## List of allowed origins.</br>See <code>check_origin_enable</code>.
##
## @path listeners.wss.$default.websocket
## @type array
## check_origins: []
## @doc
## HTTP header used to pass information about the client IP address.
## Relevant when the EMQX cluster is deployed behind a load-balancer.
##
## @path listeners.wss.$default.websocket.proxy_address_header
## @type string()
## proxy_address_header: "x-forwarded-for"
## @doc
## HTTP header used to pass information about the client port.
## Relevant when the EMQX cluster is deployed behind a load-balancer.
##
## @path listeners.wss.$default.websocket.proxy_port_header
## @type string()
## proxy_port_header: "x-forwarded-port"
## deflate_opts {
## @doc
## Compression level.
##
## @path listeners.wss.$default.websocket.deflate_opts.level
## @type enum: none | default | best_compression | best_speed
## level: none
## @doc
## Specifies the size of the compression state.</br>
## Lower values decrease memory usage per connection.
##
## @path listeners.wss.$default.websocket.deflate_opts.mem_level
## @type 1..9
## mem_level: 8
## @doc
## Specifies the compression strategy.
##
## @path listeners.wss.$default.websocket.deflate_opts.strategy
## @type enum: default | filtered | huffman_only | rle
## strategy: default
## @doc
## Takeover means the compression state is retained between server messages.
##
## @path listeners.wss.$default.websocket.deflate_opts.server_context_takeover
## @type enum: takeover | no_takeover
## server_context_takeover: takeover
## @doc
## Takeover means the compression state is retained between client messages.
##
## @path listeners.wss.$default.websocket.deflate_opts.client_context_takeover
## @type enum: takeover | no_takeover
## client_context_takeover: takeover
## @doc
## Specifies the size of the compression context for the server.
##
## @path listeners.wss.$default.websocket.deflate_opts.server_max_window_bits
## @type 8..15
## server_max_window_bits: 15
## @doc
## Specifies the size of the compression context for the client.
##
## @path listeners.wss.$default.websocket.deflate_opts.client_max_window_bits
## @type 8..15
## client_max_window_bits: 15
## }
## }
## @doc
## IP address and port for the listening socket.
##
## @path listeners.wss.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc
## The size of the listener's receiving pool.
##
## @path listeners.wss.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## The maximum number of concurrent connections allowed by the listener.
##
## @path listeners.wss.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message
## is delivered to the subscriber. The mountpoint is a way that users can use
## to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint`
## set to `some_tenant`, then the client actually subscribes to the topic
## `some_tenant/t`. Similarly, if another client B (connected to the same listener
## as the client A) sends a message to topic `t`, the message is routed
## to all the clients subscribed `some_tenant/t`, so client A will receive the
## message, with topic name `t`.</br>
## Set to `""` to disable the feature.</br>
##
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.wss.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## The configuration zone to which the listener belongs.
##
## @path listeners.wss.$default.zone
## @type atom()
## zone: default
## @doc
## Type of the rate limit.
##
## @path listeners.wss.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.wss.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc
## The access control rules for this listener.</br>See: https://github.com/emqtt/esockd#allowdeny
##
## @path listeners.wss.$default
## @type array
## access_rules: ["allow all"]
## @doc
## Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.</br>
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.wss.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## Timeout for proxy protocol. EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
##
## @path listeners.wss.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## Per-listener authentication override.
## Authentication can be one single authenticator instance or a chain of authenticators as an array.
## When authenticating a login (username, client ID, etc.) the authenticators are checked in the configured order.</br>
##
##
## @path listeners.wss.$default
## @type array
## authentication: []
## @path listeners.wss.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc
## QUIC listeners
##
## @path listeners.quic
## @type map()
## quic:
## $default {
## @doc
## Enable QUIC listener.
##
## @path listeners.quic.$default.enabled
## @type boolean()
## enabled: true
## @doc
## Path to the certificate file.
##
## @path listeners.quic.$default.certfile
## @type string()
## certfile:
## @doc
## Path to the secret key file.
##
## @path listeners.quic.$default.keyfile
## @type string()
## keyfile:
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## NOTE: QUIC listener supports only 'tlsv1.3' ciphers</br>
##
## @path listeners.quic.$default
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256"]
## @doc
## Close transport-layer connections from the clients that have not sent MQTT CONNECT
## message within this interval.
##
## @path listeners.quic.$default.idle_timeout
## @type emqx_schema:duration()
## idle_timeout: "15s"
## @doc
## IP address and port for the listening socket.
##
## @path listeners.quic.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc
## The size of the listener's receiving pool.
##
## @path listeners.quic.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## The maximum number of concurrent connections allowed by the listener.
##
## @path listeners.quic.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message
## is delivered to the subscriber. The mountpoint is a way that users can use
## to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint`
## set to `some_tenant`, then the client actually subscribes to the topic
## `some_tenant/t`. Similarly, if another client B (connected to the same listener
## as the client A) sends a message to topic `t`, the message is routed
## to all the clients subscribed `some_tenant/t`, so client A will receive the
## message, with topic name `t`.</br>
## Set to `""` to disable the feature.</br>
##
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.quic.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## The configuration zone to which the listener belongs.
##
## @path listeners.quic.$default.zone
## @type atom()
## zone: default
## @doc
## Type of the rate limit.
##
## @path listeners.quic.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.quic.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## }
}
## @doc A zone is a set of configs grouped by the zone <code>name</code>.
## For flexible configuration mapping, the <code>name</code> can be set to a listener's <code>zone</code> config.
## NOTE: A built-in zone named <code>default</code> is auto created and can not be deleted.
##
## @doc A zone is a set of configs grouped by the zone <code>name</code>.
## For flexible configuration mapping, the <code>name</code> can be set to a listener's <code>zone</code> config.
## NOTE: A built-in zone named <code>default</code> is auto created and can not be deleted.
##
## @path zones
## @type map()
## zones:
## $my_zone_name {
## mqtt {
## @doc After the TCP connection is established, if the MQTT CONNECT packet from the client is not received within the time specified by <code>idle_timeout</code>, the connection will be disconnected.
## @path zones.$my_zone_name.mqtt.idle_timeout
## @type union: infinity | emqx_schema:duration()
## idle_timeout:
## @doc Maximum MQTT packet size allowed.
## @path zones.$my_zone_name.mqtt.max_packet_size
## @type emqx_schema:bytesize()
## max_packet_size:
## @doc Maximum allowed length of MQTT Client ID.
## @path zones.$my_zone_name.mqtt.max_clientid_len
## @type 23..65535
## max_clientid_len:
## @doc Maximum topic levels allowed.
## @path zones.$my_zone_name.mqtt.max_topic_levels
## @type 1..65535
## max_topic_levels:
## @doc Maximum QoS allowed.
## @path zones.$my_zone_name.mqtt.max_qos_allowed
## @type qos()
## max_qos_allowed:
## @doc Maximum topic alias, 0 means no topic alias supported.
## @path zones.$my_zone_name.mqtt.max_topic_alias
## @type 0..65535
## max_topic_alias:
## @doc Whether to enable support for MQTT retained message.
## @path zones.$my_zone_name.mqtt.retain_available
## @type boolean()
## retain_available:
## @doc Whether to enable support for MQTT wildcard subscription.
## @path zones.$my_zone_name.mqtt.wildcard_subscription
## @type boolean()
## wildcard_subscription:
## @doc Whether to enable support for MQTT shared subscription.
## @path zones.$my_zone_name.mqtt.shared_subscription
## @type boolean()
## shared_subscription:
## @doc Ignore loop delivery of messages for MQTT v3.1.1/v3.1.0, similar to <code>No Local</code> subscription option in MQTT 5.0
## @path zones.$my_zone_name.mqtt.ignore_loop_deliver
## @type boolean()
## ignore_loop_deliver:
## @doc Parse MQTT messages in strict mode.
## When set to true, invalid utf8 strings in for example client ID, topic name, etc. will cause the client to be disconnected
## @path zones.$my_zone_name.mqtt.strict_mode
## @type boolean()
## strict_mode:
## @doc Specify the response information returned to the client. This feature is disabled if is set to "". Applies only to clients using MQTT 5.0.
## @path zones.$my_zone_name.mqtt.response_information
## @type string()
## response_information:
## @doc The keep alive that EMQX requires the client to use. If configured as <code>disabled</code>, it means that the keep alive specified by the client will be used. Requires <code>Server Keep Alive</code> in MQTT 5.0, so it is only applicable to clients using MQTT 5.0 protocol.
## @path zones.$my_zone_name.mqtt.server_keepalive
## @type union: integer() | disabled
## server_keepalive:
## @doc The backoff multiplier used by the broker to determine the client keep alive timeout. If EMQX doesn't receive any packet in <code>Keep Alive * Backoff * 2</code> seconds, EMQX will close the current connection.
## @path zones.$my_zone_name.mqtt.keepalive_backoff
## @type float()
## keepalive_backoff:
## @doc Maximum number of subscriptions allowed per client.
## @path zones.$my_zone_name.mqtt.max_subscriptions
## @type union: 1..inf | infinity
## max_subscriptions:
## @doc Force upgrade of QoS level according to subscription.
## @path zones.$my_zone_name.mqtt.upgrade_qos
## @type boolean()
## upgrade_qos:
## @doc Maximum number of QoS 1 and QoS 2 messages that are allowed to be delivered simultaneously before completing the acknowledgment.
## @path zones.$my_zone_name.mqtt.max_inflight
## @type 1..65535
## max_inflight:
## @doc Retry interval for QoS 1/2 message delivering.
## @path zones.$my_zone_name.mqtt.retry_interval
## @type emqx_schema:duration()
## retry_interval:
## @doc Maximum QoS 2 packets (Client -> Broker) awaiting PUBREL.
## @path zones.$my_zone_name.mqtt.max_awaiting_rel
## @type union: integer() | infinity
## max_awaiting_rel:
## @doc The QoS 2 messages (Client -> Broker) will be dropped if awaiting PUBREL timeout.
## @path zones.$my_zone_name.mqtt.await_rel_timeout
## @type emqx_schema:duration()
## await_rel_timeout:
## @doc Specifies how long the session will expire after the connection is disconnected, only for non-MQTT 5.0 connections.
## @path zones.$my_zone_name.mqtt.session_expiry_interval
## @type emqx_schema:duration()
## session_expiry_interval:
## @doc Maximum queue length. Enqueued messages when persistent client disconnected, or inflight window is full.
## @path zones.$my_zone_name.mqtt.max_mqueue_len
## @type union: non_neg_integer() | infinity
## max_mqueue_len:
## @doc Topic priorities. Priority number [1-255]
## There's no priority table by default, hence all messages are treated equal.
##
## **NOTE**: Comma and equal signs are not allowed for priority topic names.
## **NOTE**: Messages for topics not in the priority table are treated as either highest or lowest priority depending on the configured value for <code>mqtt.mqueue_default_priority</code>.
##
## **Examples**:
## To configure <code>"topic/1" > "topic/2"</code>:
## <code>mqueue_priorities: {"topic/1": 10, "topic/2": 8}</code>
##
## @path zones.$my_zone_name.mqtt.mqueue_priorities
## @type union: map() | disabled
## mqueue_priorities:
## @doc Default topic priority, which will be used by topics not in <code>Topic Priorities</code> (<code>mqueue_priorities</code>).
## @path zones.$my_zone_name.mqtt.mqueue_default_priority
## @type enum: highest | lowest
## mqueue_default_priority: highest
## @doc Specifies whether to store QoS 0 messages in the message queue while the connection is down but the session remains.
## @path zones.$my_zone_name.mqtt.mqueue_store_qos0
## @type boolean()
## mqueue_store_qos0:
## @doc Whether to user Client ID as Username.
## This setting takes effect later than <code>Use Peer Certificate as Username</code> (<code>peer_cert_as_username</code>) and <code>Use peer certificate as Client ID</code> (<code>peer_cert_as_clientid</code>).
##
## @path zones.$my_zone_name.mqtt.use_username_as_clientid
## @type boolean()
## use_username_as_clientid:
## @doc Use the CN, DN field in the peer certificate or the entire certificate content as Username. Only works for the TLS connection.
## Supported configurations are the following:
## - <code>cn</code>: Take the CN field of the certificate as Username
## - <code>dn</code>: Take the DN field of the certificate as Username
## - <code>crt</code>: Take the content of the <code>DER</code> or <code>PEM</code> certificate as Username
## - <code>pem</code>: Convert <code>DER</code> certificate content to <code>PEM</code> format as Username
## - <code>md5</code>: Take the MD5 value of the content of the <code>DER</code> or <code>PEM</code> certificate as Username
##
## @path zones.$my_zone_name.mqtt.peer_cert_as_username
## @type enum: disabled | cn | dn | crt | pem | md5
## peer_cert_as_username: disabled
## @doc Use the CN, DN field in the peer certificate or the entire certificate content as Client ID. Only works for the TLS connection.
## Supported configurations are the following:
## - <code>cn</code>: Take the CN field of the certificate as Client ID
## - <code>dn</code>: Take the DN field of the certificate as Client ID
## - <code>crt</code>: Take the content of the <code>DER</code> or <code>PEM</code> certificate as Client ID
## - <code>pem</code>: Convert <code>DER</code> certificate content to <code>PEM</code> format as Client ID
## - <code>md5</code>: Take the MD5 value of the content of the <code>DER</code> or <code>PEM</code> certificate as Client ID
##
## @path zones.$my_zone_name.mqtt.peer_cert_as_clientid
## @type enum: disabled | cn | dn | crt | pem | md5
## peer_cert_as_clientid: disabled
## }
## stats {
## @doc Enable/disable statistic data collection.
## @path zones.$my_zone_name.stats.enable
## @type boolean()
## enable:
## }
## flapping_detect {
## @doc Enable flapping connection detection feature.
## @path zones.$my_zone_name.flapping_detect.enable
## @type boolean()
## enable:
## @doc The maximum number of disconnects allowed for a MQTT Client in `window_time`
## @path zones.$my_zone_name.flapping_detect.max_count
## @type integer()
## max_count:
## @doc The time window for flapping detection.
## @path zones.$my_zone_name.flapping_detect.window_time
## @type emqx_schema:duration()
## window_time:
## @doc How long the flapping clientid will be banned.
## @path zones.$my_zone_name.flapping_detect.ban_time
## @type emqx_schema:duration()
## ban_time:
## }
## force_shutdown {
## @doc Enable `force_shutdown` feature.
## @path zones.$my_zone_name.force_shutdown.enable
## @type boolean()
## enable:
## @doc Maximum message queue length.
## @path zones.$my_zone_name.force_shutdown.max_message_queue_len
## @type 0..inf
## max_message_queue_len:
## @doc Total heap size
## @path zones.$my_zone_name.force_shutdown.max_heap_size
## @type emqx_schema:wordsize()
## max_heap_size:
## }
## conn_congestion {
## @doc Enable or disable connection congestion alarm.
## @path zones.$my_zone_name.conn_congestion.enable_alarm
## @type boolean()
## enable_alarm:
## @doc Minimal time before clearing the alarm.
##
## The alarm is cleared only when there's no pending data in
## the queue, and at least `min_alarm_sustain_duration`
## milliseconds passed since the last time we considered the connection "congested".
##
## This is to avoid clearing and raising the alarm again too often.
## @path zones.$my_zone_name.conn_congestion.min_alarm_sustain_duration
## @type emqx_schema:duration()
## min_alarm_sustain_duration:
## }
## force_gc {
## @doc Enable forced garbage collection.
## @path zones.$my_zone_name.force_gc.enable
## @type boolean()
## enable:
## @doc GC the process after this many received messages.
## @path zones.$my_zone_name.force_gc.count
## @type 0..inf
## count:
## @doc GC the process after specified number of bytes have passed through.
## @path zones.$my_zone_name.force_gc.bytes
## @type emqx_schema:bytesize()
## bytes:
## }
## overload_protection {
## @doc React on system overload or not
## @path zones.$my_zone_name.overload_protection.enable
## @type boolean()
## enable:
## @doc Some unimportant tasks could be delayed for execution, here set the delays in ms
## @path zones.$my_zone_name.overload_protection.backoff_delay
## @type 0..inf
## backoff_delay:
## @doc Skip forceful GC if necessary
## @path zones.$my_zone_name.overload_protection.backoff_gc
## @type boolean()
## backoff_gc:
## @doc Skip process hibernation if necessary
## @path zones.$my_zone_name.overload_protection.backoff_hibernation
## @type boolean()
## backoff_hibernation:
## @doc Close new incoming connections if necessary
## @path zones.$my_zone_name.overload_protection.backoff_new_conn
## @type boolean()
## backoff_new_conn:
## }
## }
## @doc Global MQTT configuration.
## The configs here work as default values which can be overridden in <code>zone</code> configs
##
mqtt {
## @doc After the TCP connection is established, if the MQTT CONNECT packet from the client is not received within the time specified by <code>idle_timeout</code>, the connection will be disconnected.
## @path mqtt.idle_timeout
## @type union: infinity | emqx_schema:duration()
idle_timeout: "15s"
## @doc Maximum MQTT packet size allowed.
## @path mqtt.max_packet_size
## @type emqx_schema:bytesize()
max_packet_size: "1MB"
## @doc Maximum allowed length of MQTT Client ID.
## @path mqtt.max_clientid_len
## @type 23..65535
max_clientid_len: 65535
## @doc Maximum topic levels allowed.
## @path mqtt.max_topic_levels
## @type 1..65535
max_topic_levels: 65535
## @doc Maximum QoS allowed.
## @path mqtt.max_qos_allowed
## @type qos()
max_qos_allowed: 2
## @doc Maximum topic alias, 0 means no topic alias supported.
## @path mqtt.max_topic_alias
## @type 0..65535
max_topic_alias: 65535
## @doc Whether to enable support for MQTT retained message.
## @path mqtt.retain_available
## @type boolean()
retain_available: true
## @doc Whether to enable support for MQTT wildcard subscription.
## @path mqtt.wildcard_subscription
## @type boolean()
wildcard_subscription: true
## @doc Whether to enable support for MQTT shared subscription.
## @path mqtt.shared_subscription
## @type boolean()
shared_subscription: true
## @doc Ignore loop delivery of messages for MQTT v3.1.1/v3.1.0, similar to <code>No Local</code> subscription option in MQTT 5.0
## @path mqtt.ignore_loop_deliver
## @type boolean()
ignore_loop_deliver: false
## @doc Parse MQTT messages in strict mode.
## When set to true, invalid utf8 strings in for example client ID, topic name, etc. will cause the client to be disconnected
## @path mqtt.strict_mode
## @type boolean()
strict_mode: false
## @doc Specify the response information returned to the client. This feature is disabled if is set to "". Applies only to clients using MQTT 5.0.
## @path mqtt.response_information
## @type string()
response_information: []
## @doc The keep alive that EMQX requires the client to use. If configured as <code>disabled</code>, it means that the keep alive specified by the client will be used. Requires <code>Server Keep Alive</code> in MQTT 5.0, so it is only applicable to clients using MQTT 5.0 protocol.
## @path mqtt.server_keepalive
## @type union: integer() | disabled
server_keepalive: disabled
## @doc The backoff multiplier used by the broker to determine the client keep alive timeout. If EMQX doesn't receive any packet in <code>Keep Alive * Backoff * 2</code> seconds, EMQX will close the current connection.
## @path mqtt.keepalive_backoff
## @type float()
keepalive_backoff: 0.75
## @doc Maximum number of subscriptions allowed per client.
## @path mqtt.max_subscriptions
## @type union: 1..inf | infinity
max_subscriptions: infinity
## @doc Force upgrade of QoS level according to subscription.
## @path mqtt.upgrade_qos
## @type boolean()
upgrade_qos: false
## @doc Maximum number of QoS 1 and QoS 2 messages that are allowed to be delivered simultaneously before completing the acknowledgment.
## @path mqtt.max_inflight
## @type 1..65535
max_inflight: 32
## @doc Retry interval for QoS 1/2 message delivering.
## @path mqtt.retry_interval
## @type emqx_schema:duration()
retry_interval: "30s"
## @doc Maximum QoS 2 packets (Client -> Broker) awaiting PUBREL.
## @path mqtt.max_awaiting_rel
## @type union: integer() | infinity
max_awaiting_rel: 100
## @doc The QoS 2 messages (Client -> Broker) will be dropped if awaiting PUBREL timeout.
## @path mqtt.await_rel_timeout
## @type emqx_schema:duration()
await_rel_timeout: "300s"
## @doc Specifies how long the session will expire after the connection is disconnected, only for non-MQTT 5.0 connections.
## @path mqtt.session_expiry_interval
## @type emqx_schema:duration()
session_expiry_interval: "2h"
## @doc Maximum queue length. Enqueued messages when persistent client disconnected, or inflight window is full.
## @path mqtt.max_mqueue_len
## @type union: non_neg_integer() | infinity
max_mqueue_len: 1000
## @doc Topic priorities. Priority number [1-255]
## There's no priority table by default, hence all messages are treated equal.
##
## **NOTE**: Comma and equal signs are not allowed for priority topic names.
## **NOTE**: Messages for topics not in the priority table are treated as either highest or lowest priority depending on the configured value for <code>mqtt.mqueue_default_priority</code>.
##
## **Examples**:
## To configure <code>"topic/1" > "topic/2"</code>:
## <code>mqueue_priorities: {"topic/1": 10, "topic/2": 8}</code>
##
## @path mqtt.mqueue_priorities
## @type union: map() | disabled
mqueue_priorities: disabled
## @doc Default topic priority, which will be used by topics not in <code>Topic Priorities</code> (<code>mqueue_priorities</code>).
## @path mqtt.mqueue_default_priority
## @type enum: highest | lowest
mqueue_default_priority: lowest
## @doc Specifies whether to store QoS 0 messages in the message queue while the connection is down but the session remains.
## @path mqtt.mqueue_store_qos0
## @type boolean()
mqueue_store_qos0: true
## @doc Whether to user Client ID as Username.
## This setting takes effect later than <code>Use Peer Certificate as Username</code> (<code>peer_cert_as_username</code>) and <code>Use peer certificate as Client ID</code> (<code>peer_cert_as_clientid</code>).
##
## @path mqtt.use_username_as_clientid
## @type boolean()
use_username_as_clientid: false
## @doc Use the CN, DN field in the peer certificate or the entire certificate content as Username. Only works for the TLS connection.
## Supported configurations are the following:
## - <code>cn</code>: Take the CN field of the certificate as Username
## - <code>dn</code>: Take the DN field of the certificate as Username
## - <code>crt</code>: Take the content of the <code>DER</code> or <code>PEM</code> certificate as Username
## - <code>pem</code>: Convert <code>DER</code> certificate content to <code>PEM</code> format as Username
## - <code>md5</code>: Take the MD5 value of the content of the <code>DER</code> or <code>PEM</code> certificate as Username
##
## @path mqtt.peer_cert_as_username
## @type enum: disabled | cn | dn | crt | pem | md5
peer_cert_as_username: disabled
## @doc Use the CN, DN field in the peer certificate or the entire certificate content as Client ID. Only works for the TLS connection.
## Supported configurations are the following:
## - <code>cn</code>: Take the CN field of the certificate as Client ID
## - <code>dn</code>: Take the DN field of the certificate as Client ID
## - <code>crt</code>: Take the content of the <code>DER</code> or <code>PEM</code> certificate as Client ID
## - <code>pem</code>: Convert <code>DER</code> certificate content to <code>PEM</code> format as Client ID
## - <code>md5</code>: Take the MD5 value of the content of the <code>DER</code> or <code>PEM</code> certificate as Client ID
##
## @path mqtt.peer_cert_as_clientid
## @type enum: disabled | cn | dn | crt | pem | md5
peer_cert_as_clientid: disabled
}
## @doc Default authentication configs for all MQTT listeners.
##
## For per-listener overrides see <code>authentication</code> in listener configs
##
## This option can be configured with:
## <ul>
## <li><code>[]</code>: The default value, it allows *ALL* logins</li>
## <li>one: For example <code>{enable:true,backend:"built_in_database",mechanism="password_based"}</code></li>
## <li>chain: An array of structs.</li>
## </ul>
##
## When a chain is configured, the login credentials are checked against the backends per the configured order, until an 'allow' or 'deny' decision can be made.
##
## If there is no decision after a full chain exhaustion, the login is rejected.
##
## @doc Default authentication configs for all MQTT listeners.
##
## For per-listener overrides see <code>authentication</code> in listener configs
##
## This option can be configured with:
## <ul>
## <li><code>[]</code>: The default value, it allows *ALL* logins</li>
## <li>one: For example <code>{enable:true,backend:"built_in_database",mechanism="password_based"}</code></li>
## <li>chain: An array of structs.</li>
## </ul>
##
## When a chain is configured, the login credentials are checked against the backends per the configured order, until an 'allow' or 'deny' decision can be made.
##
## If there is no decision after a full chain exhaustion, the login is rejected.
##
## @path
## @type array
authentication: []
## @path authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## @doc
## Authorization a.k.a. ACL.</br>
## In EMQX, MQTT client access control is extremely flexible.</br>
## An out-of-the-box set of authorization data sources are supported.
## For example,</br>
## 'file' source is to support concise and yet generic ACL rules in a file;</br>
## 'built_in_database' source can be used to store per-client customizable rule sets,
## natively in the EMQX node;</br>
## 'http' source to make EMQX call an external HTTP API to make the decision;</br>
## 'PostgreSQL' etc. to look up clients or rules from external databases;</br>
##
authorization {
## @doc
## Default access control action if the user or client matches no ACL rules,
## or if no such user or client is found by the configurable authorization
## sources such as built_in_database, an HTTP API, or a query against PostgreSQL.
## Find more details in 'authorization.sources' config.
##
## @path authorization.no_match
## @type enum: allow | deny
no_match: allow
## @doc
## The action when the authorization check rejects an operation.
##
## @path authorization.deny_action
## @type enum: ignore | disconnect
deny_action: ignore
cache {
## @doc
## Enable or disable the authorization cache.
##
## @path authorization.cache.enable
## @type boolean()
enable: true
## @doc
## Maximum number of cached items.
##
## @path authorization.cache.max_size
## @type 1..1048576
max_size: 32
## @doc
## Time to live for the cached data.
##
## @path authorization.cache.ttl
## @type emqx_schema:duration()
ttl: "1m"
}
## @doc
## Authorization data sources.</br>
## An array of authorization (ACL) data providers.
## It is designed as an array, not a hash-map, so the sources can be
## ordered to form a chain of access controls.</br>
##
## When authorizing a 'publish' or 'subscribe' action, the configured
## sources are checked in order. When checking an ACL source,
## in case the client (identified by username or client ID) is not found,
## it moves on to the next source. And it stops immediately
## once an 'allow' or 'deny' decision is returned.</br>
##
## If the client is not found in any of the sources,
## the default action configured in 'authorization.no_match' is applied.</br>
##
## NOTE:
## The source elements are identified by their 'type'.
## It is NOT allowed to configure two or more sources of the same type.
##
## @path authorization
## @type array
sources: []
## @path authorization.sources.$INDEX
## @type union: authz:file | authz:http_get | authz:http_post | authz:mnesia | authz:mongo_single | authz:mongo_rs | authz:mongo_sharded | authz:mysql | authz:postgresql | authz:redis_single | authz:redis_sentinel | authz:redis_cluster
## $INDEX:
}
node {
## @doc Unique name of the EMQX node. It must follow <code>%name%@FQDN</code> or
## <code>%name%@IPv4</code> format.
##
## @path node.name
## @type string()
name: "emqx@127.0.0.1"
## @doc Secret cookie is a random string that should be the same on all nodes in
## the given EMQX cluster, but unique per EMQX cluster. It is used to prevent EMQX nodes that
## belong to different clusters from accidentally connecting to each other.
## @path node.cookie
## @type string()
cookie: "emqxsecretcookie"
## @doc
## Path to the persistent data directory.</br>
## Possible auto-created subdirectories are:</br>
## - `mnesia/<node_name>`: EMQX's built-in database directory.</br>
## For example, `mnesia/emqx@127.0.0.1`.</br>
## There should be only one such subdirectory.</br>
## Meaning, in case the node is to be renamed (to e.g. `emqx@10.0.1.1`),</br>
## the old dir should be deleted first.</br>
## - `configs`: Generated configs at boot time, and cluster/local override configs.</br>
## - `patches`: Hot-patch beam files are to be placed here.</br>
## - `trace`: Trace log files.</br>
##
## **NOTE**: One data dir cannot be shared by two or more EMQX nodes.
##
## @path node.data_dir
## @type string()
## data_dir:
## @doc List of configuration files that are read during startup. The order is
## significant: later configuration files override the previous ones.
##
## @path node.config_files
## @type [string()]
## config_files:
## @doc Periodic garbage collection interval.
## @path node.global_gc_interval
## @type emqx_schema:duration()
global_gc_interval: "15m"
## @doc Location of the crash dump file.
## @path node.crash_dump_file
## @type emqx_conf_schema:file()
crash_dump_file: "log/erl_crash.dump"
## @doc The number of seconds that the broker is allowed to spend writing a crash dump.
## @path node.crash_dump_seconds
## @type emqx_schema:duration_s()
crash_dump_seconds: "30s"
## @doc The maximum size of a crash dump file in bytes.
## @path node.crash_dump_bytes
## @type emqx_schema:bytesize()
crash_dump_bytes: "100MB"
## @doc This is the approximate time an EMQX node may be unresponsive until it is considered down and thereby disconnected.
## @path node.dist_net_ticktime
## @type emqx_schema:duration_s()
dist_net_ticktime: "2m"
## @doc Maximum depth of the call stack printed in error messages and
## <code>process_info</code>.
##
## @path node.backtrace_depth
## @type integer()
backtrace_depth: 23
## @doc List of Erlang applications that shall be rebooted when the EMQX broker joins the cluster.
##
## @path node.applications
## @type emqx_schema:comma_separated_atoms()
applications: []
## @doc <code>etc</code> dir for the node
## @path node.etc_dir
## @type string()
## etc_dir:
cluster_call {
## @doc Time interval to retry after a failed call.
## @path node.cluster_call.retry_interval
## @type emqx_schema:duration()
retry_interval: "1s"
## @doc Retain the maximum number of completed transactions (for queries).
## @path node.cluster_call.max_history
## @type 1..500
max_history: 100
## @doc Time interval to clear completed but stale transactions.
## Ensure that the number of completed transactions is less than the <code>max_history</code>.
## @path node.cluster_call.cleanup_interval
## @type emqx_schema:duration()
cleanup_interval: "5m"
}
}
cluster {
## @doc Human-friendly name of the EMQX cluster.
## @path cluster.name
## @type atom()
name: emqxcl
## @doc Service discovery method for the cluster nodes.
## @path cluster.discovery_strategy
## @type enum: manual | static | mcast | dns | etcd | k8s
discovery_strategy: manual
## @doc Remove disconnected nodes from the cluster after this interval.
## @path cluster.autoclean
## @type emqx_schema:duration()
autoclean: "5m"
## @doc If <code>true</code>, the node will try to heal network partitions automatically.
## @path cluster.autoheal
## @type boolean()
autoheal: true
## @doc The Erlang distribution protocol for the cluster.
## @path cluster.proto_dist
## @type enum: inet_tcp | inet6_tcp | inet_tls
proto_dist: inet_tcp
static {
## @doc List EMQX node names in the static cluster. See <code>node.name</code>.
## @path cluster.static
## @type array
seeds: []
}
mcast {
## @doc Multicast IPv4 address.
## @path cluster.mcast.addr
## @type string()
addr: "239.192.0.1"
## @doc List of UDP ports used for service discovery.</br>
## Note: probe messages are broadcast to all the specified ports.
##
## @path cluster.mcast
## @type array
ports: [4369,4370]
## @doc Local IP address the node discovery service needs to bind to.
## @path cluster.mcast.iface
## @type string()
iface: "0.0.0.0"
## @doc Time-to-live (TTL) for the outgoing UDP datagrams.
## @path cluster.mcast.ttl
## @type 0..255
ttl: 255
## @doc If <code>true</code>, loop UDP datagrams back to the local socket.
## @path cluster.mcast.loop
## @type boolean()
loop: true
## @doc Size of the kernel-level buffer for outgoing datagrams.
## @path cluster.mcast.sndbuf
## @type emqx_schema:bytesize()
sndbuf: "16KB"
## @doc Size of the kernel-level buffer for incoming datagrams.
## @path cluster.mcast.recbuf
## @type emqx_schema:bytesize()
recbuf: "16KB"
## @doc Size of the user-level buffer.
## @path cluster.mcast.buffer
## @type emqx_schema:bytesize()
buffer: "32KB"
}
dns {
## @doc The domain name of the EMQX cluster.
## @path cluster.dns.name
## @type string()
name: "localhost"
## @doc The symbolic name of the EMQX service.
## @path cluster.dns.app
## @type string()
app: "emqx"
}
etcd {
## @doc List of endpoint URLs of the etcd cluster
## @path cluster.etcd.server
## @type emqx_schema:comma_separated_list()
## server:
## @doc Key prefix used for EMQX service discovery.
## @path cluster.etcd.prefix
## @type string()
prefix: "emqxcl"
## @doc Expiration time of the etcd key associated with the node.
## It is refreshed automatically, as long as the node is alive.
##
## @path cluster.etcd.node_ttl
## @type emqx_schema:duration()
node_ttl: "1m"
ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path cluster.etcd.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path cluster.etcd.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path cluster.etcd.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path cluster.etcd.ssl.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path cluster.etcd.ssl.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path cluster.etcd.ssl.depth
## @type integer()
depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path cluster.etcd.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path cluster.etcd.ssl
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path cluster.etcd.ssl
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path cluster.etcd.ssl.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path cluster.etcd.ssl.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc
## Enable TLS.
##
## @path cluster.etcd.ssl.enable
## @type boolean()
enable: false
## @doc
## Specify the host name to be used in TLS Server Name Indication extension.</br>
## For instance, when connecting to "server.example.net", the genuine server
## which accepts the connection and performs TLS handshake may differ from the
## host the TLS client initially connects to, e.g. when connecting to an IP address
## or when the host has multiple resolvable DNS records </br>
## If not specified, it will default to the host name string which is used
## to establish the connection, unless it is IP addressed used.</br>
## The host name is then also used in the host name verification of the peer
## certificate.</br> The special value 'disable' prevents the Server Name
## Indication extension from being sent and disables the hostname
## verification check.
##
## @path cluster.etcd.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
}
}
k8s {
## @doc Kubernetes API endpoint URL.
## @path cluster.k8s.apiserver
## @type string()
## apiserver:
## @doc EMQX broker service name.
## @path cluster.k8s.service_name
## @type string()
service_name: "emqx"
## @doc Address type used for connecting to the discovered nodes.
## @path cluster.k8s.address_type
## @type enum: ip | dns | hostname
address_type: ip
## @doc This parameter should be set to the part of the <code>node.name</code>
## before the '@'.</br>
## For example, if the <code>node.name</code> is <code>emqx@127.0.0.1</code>, then this parameter
## should be set to <code>emqx</code>.
## @path cluster.k8s.app_name
## @type string()
app_name: "emqx"
## @doc Kubernetes namespace.
## @path cluster.k8s.namespace
## @type string()
namespace: "default"
## @doc Node name suffix.</br>
## Note: this parameter is only relevant when <code>address_type</code> is <code>dns</code>
## or <code>hostname</code>.
## @path cluster.k8s.suffix
## @type string()
suffix: "pod.local"
}
}
log {
console_handler {
## @doc Enable this log handler.
## @path log.console_handler.enable
## @type boolean()
enable: false
## @doc Global log level. This includes the primary log level and all log handlers.
## @path log.console_handler.level
## @type emqx_conf_schema:log_level()
level: warning
## @doc The time offset to be used when formatting the timestamp.
## @path log.console_handler.time_offset
## @type string()
time_offset: "system"
## @doc Set the maximum length of a single log message. If this length is exceeded, the log message will be truncated.
## @path log.console_handler.chars_limit
## @type union: unlimited | 100..inf
chars_limit: unlimited
## @doc Choose log format. <code>text</code> for free text, and <code>json</code> for structured logging.
## @path log.console_handler.formatter
## @type enum: text | json
formatter: text
## @doc Print logs in a single line if set to true. Otherwise, log messages may span multiple lines.
## @path log.console_handler.single_line
## @type boolean()
single_line: true
## @doc As long as the number of buffered log events is lower than this value,
## all log events are handled asynchronously. This means that the client process sending the log event,
## by calling a log function in the Logger API, does not wait for a response from the handler
## but continues executing immediately after the event is sent.
## It is not affected by the time it takes the handler to print the event to the log device.
## If the message queue grows larger than this value,
## the handler starts handling log events synchronously instead,
## meaning that the client process sending the event must wait for a response.
## When the handler reduces the message queue to a level below the sync_mode_qlen threshold,
## asynchronous operation is resumed.
##
## @path log.console_handler.sync_mode_qlen
## @type non_neg_integer()
sync_mode_qlen: 100
## @doc When the number of buffered log events is larger than this value, the new log events are dropped.
## When drop mode is activated or deactivated, a message is printed in the logs.
## @path log.console_handler.drop_mode_qlen
## @type pos_integer()
drop_mode_qlen: 3000
## @doc If the number of buffered log events grows larger than this threshold, a flush (delete) operation takes place. To flush events, the handler discards the buffered log messages without logging.
## @path log.console_handler.flush_qlen
## @type pos_integer()
flush_qlen: 8000
overload_kill {
## @doc Enable log handler overload kill feature.
## @path log.console_handler.overload_kill.enable
## @type boolean()
enable: true
## @doc Maximum memory size that the handler process is allowed to use.
## @path log.console_handler.overload_kill.mem_size
## @type emqx_schema:bytesize()
mem_size: "30MB"
## @doc Maximum allowed queue length.
## @path log.console_handler.overload_kill.qlen
## @type pos_integer()
qlen: 20000
## @doc If the handler is terminated, it restarts automatically after a delay specified in milliseconds. The value `infinity` prevents restarts.
## @path log.console_handler.overload_kill.restart_after
## @type union: emqx_schema:duration_ms() | infinity
restart_after: "5s"
}
burst_limit {
## @doc Enable log burst control feature.
## @path log.console_handler.burst_limit.enable
## @type boolean()
enable: true
## @doc Maximum number of log events to handle within a `window_time` interval. After the limit is reached, successive events are dropped until the end of the `window_time`.
## @path log.console_handler.burst_limit.max_count
## @type pos_integer()
max_count: 10000
## @doc See `max_count`.
## @path log.console_handler.burst_limit.window_time
## @type emqx_schema:duration()
window_time: "1s"
}
## @doc Type of supervisor reports that are logged.
## - `error`: only log errors in the Erlang processes.
## - `progress`: log process startup.
## @path log.console_handler.supervisor_reports
## @type enum: error | progress
supervisor_reports: error
## @doc Maximum depth for Erlang term log formatting and Erlang process message queue inspection.
## @path log.console_handler.max_depth
## @type union: unlimited | non_neg_integer()
max_depth: 100
}
## @doc Key-value list of file-based log handlers.
## @path log.file_handlers
## @type map()
## file_handlers:
## $name {
## @doc Name the log file.
## @path log.file_handlers.$name.file
## @type emqx_conf_schema:file()
## file:
## rotation {
## @doc Enable log rotation feature.
## @path log.file_handlers.$name.rotation.enable
## @type boolean()
## enable: true
## @doc Maximum number of log files.
## @path log.file_handlers.$name.rotation.count
## @type 1..2048
## count: 10
## }
## @doc This parameter controls log file rotation. The value `infinity` means the log file will grow indefinitely, otherwise the log file will be rotated once it reaches `max_size` in bytes.
## @path log.file_handlers.$name.max_size
## @type union: infinity | emqx_schema:bytesize()
## max_size: "50MB"
## @doc Enable this log handler.
## @path log.file_handlers.$name.enable
## @type boolean()
## enable: true
## @doc Global log level. This includes the primary log level and all log handlers.
## @path log.file_handlers.$name.level
## @type emqx_conf_schema:log_level()
## level: warning
## @doc The time offset to be used when formatting the timestamp.
## @path log.file_handlers.$name.time_offset
## @type string()
## time_offset: "system"
## @doc Set the maximum length of a single log message. If this length is exceeded, the log message will be truncated.
## @path log.file_handlers.$name.chars_limit
## @type union: unlimited | 100..inf
## chars_limit: unlimited
## @doc Choose log format. <code>text</code> for free text, and <code>json</code> for structured logging.
## @path log.file_handlers.$name.formatter
## @type enum: text | json
## formatter: text
## @doc Print logs in a single line if set to true. Otherwise, log messages may span multiple lines.
## @path log.file_handlers.$name.single_line
## @type boolean()
## single_line: true
## @doc As long as the number of buffered log events is lower than this value,
## all log events are handled asynchronously. This means that the client process sending the log event,
## by calling a log function in the Logger API, does not wait for a response from the handler
## but continues executing immediately after the event is sent.
## It is not affected by the time it takes the handler to print the event to the log device.
## If the message queue grows larger than this value,
## the handler starts handling log events synchronously instead,
## meaning that the client process sending the event must wait for a response.
## When the handler reduces the message queue to a level below the sync_mode_qlen threshold,
## asynchronous operation is resumed.
##
## @path log.file_handlers.$name.sync_mode_qlen
## @type non_neg_integer()
## sync_mode_qlen: 100
## @doc When the number of buffered log events is larger than this value, the new log events are dropped.
## When drop mode is activated or deactivated, a message is printed in the logs.
## @path log.file_handlers.$name.drop_mode_qlen
## @type pos_integer()
## drop_mode_qlen: 3000
## @doc If the number of buffered log events grows larger than this threshold, a flush (delete) operation takes place. To flush events, the handler discards the buffered log messages without logging.
## @path log.file_handlers.$name.flush_qlen
## @type pos_integer()
## flush_qlen: 8000
## overload_kill {
## @doc Enable log handler overload kill feature.
## @path log.file_handlers.$name.overload_kill.enable
## @type boolean()
## enable: true
## @doc Maximum memory size that the handler process is allowed to use.
## @path log.file_handlers.$name.overload_kill.mem_size
## @type emqx_schema:bytesize()
## mem_size: "30MB"
## @doc Maximum allowed queue length.
## @path log.file_handlers.$name.overload_kill.qlen
## @type pos_integer()
## qlen: 20000
## @doc If the handler is terminated, it restarts automatically after a delay specified in milliseconds. The value `infinity` prevents restarts.
## @path log.file_handlers.$name.overload_kill.restart_after
## @type union: emqx_schema:duration_ms() | infinity
## restart_after: "5s"
## }
## burst_limit {
## @doc Enable log burst control feature.
## @path log.file_handlers.$name.burst_limit.enable
## @type boolean()
## enable: true
## @doc Maximum number of log events to handle within a `window_time` interval. After the limit is reached, successive events are dropped until the end of the `window_time`.
## @path log.file_handlers.$name.burst_limit.max_count
## @type pos_integer()
## max_count: 10000
## @doc See `max_count`.
## @path log.file_handlers.$name.burst_limit.window_time
## @type emqx_schema:duration()
## window_time: "1s"
## }
## @doc Type of supervisor reports that are logged.
## - `error`: only log errors in the Erlang processes.
## - `progress`: log process startup.
## @path log.file_handlers.$name.supervisor_reports
## @type enum: error | progress
## supervisor_reports: error
## @doc Maximum depth for Erlang term log formatting and Erlang process message queue inspection.
## @path log.file_handlers.$name.max_depth
## @type union: unlimited | non_neg_integer()
## max_depth: 100
## }
## @doc Keep error_logger silent.
## @path log.error_logger
## @type atom()
error_logger: silent
}
rpc {
## @doc In <code>sync</code> mode the sending side waits for the ack from the receiving side.
## @path rpc.mode
## @type enum: sync | async
mode: async
## @doc Transport protocol used for inter-broker communication
## @path rpc.driver
## @type enum: tcp | ssl
driver: tcp
## @doc The maximum number of batch messages sent in asynchronous mode.
## Note that this configuration does not work in synchronous mode.
##
## @path rpc.async_batch_size
## @type integer()
async_batch_size: 256
## @doc <code>manual</code>: discover ports by <code>tcp_server_port</code>.</br>
## <code>stateless</code>: discover ports in a stateless manner, using the following algorithm.
## If node name is <code>emqxN@127.0.0.1</code>, where the N is an integer,
## then the listening port will be 5370 + N.
## @path rpc.port_discovery
## @type enum: manual | stateless
port_discovery: stateless
## @doc Listening port used by RPC local service.</br>
## Note that this config only takes effect when rpc.port_discovery is set to manual.
## @path rpc.tcp_server_port
## @type integer()
tcp_server_port: 5369
## @doc Listening port used by RPC local service.</br>
## Note that this config only takes effect when rpc.port_discovery is set to manual
## and <code>driver</code> is set to <code>ssl</code>.
## @path rpc.ssl_server_port
## @type integer()
ssl_server_port: 5369
## @doc Set the maximum number of RPC communication channels initiated by this node to each remote node.
## @path rpc.tcp_client_num
## @type 1..256
tcp_client_num: 10
## @doc Timeout for establishing an RPC connection.
## @path rpc.connect_timeout
## @type emqx_schema:duration()
connect_timeout: "5s"
## @doc Path to TLS certificate file used to validate identity of the cluster nodes.
## Note that this config only takes effect when <code>rpc.driver</code> is set to <code>ssl</code>.
##
## @path rpc.certfile
## @type emqx_conf_schema:file()
## certfile:
## @doc Path to the private key file for the <code>rpc.certfile</code>.</br>
## Note: contents of this file are secret, so it's necessary to set permissions to 600.
## @path rpc.keyfile
## @type emqx_conf_schema:file()
## keyfile:
## @doc Path to certification authority TLS certificate file used to validate <code>rpc.certfile</code>.</br>
## Note: certificates of all nodes in the cluster must be signed by the same CA.
## @path rpc.cacertfile
## @type emqx_conf_schema:file()
## cacertfile:
## @doc Timeout for sending the RPC request.
## @path rpc.send_timeout
## @type emqx_schema:duration()
send_timeout: "5s"
## @doc Timeout for the remote node authentication.
## @path rpc.authentication_timeout
## @type emqx_schema:duration()
authentication_timeout: "5s"
## @doc Timeout for the reply to a synchronous RPC.
## @path rpc.call_receive_timeout
## @type emqx_schema:duration()
call_receive_timeout: "15s"
## @doc How long the connections between the brokers should remain open after the last message is sent.
## @path rpc.socket_keepalive_idle
## @type emqx_schema:duration_s()
socket_keepalive_idle: "7200s"
## @doc The interval between keepalive messages.
## @path rpc.socket_keepalive_interval
## @type emqx_schema:duration_s()
socket_keepalive_interval: "75s"
## @doc How many times the keepalive probe message can fail to receive a reply
## until the RPC connection is considered lost.
## @path rpc.socket_keepalive_count
## @type integer()
socket_keepalive_count: 9
## @doc TCP tuning parameters. TCP sending buffer size.
## @path rpc.socket_sndbuf
## @type emqx_schema:bytesize()
socket_sndbuf: "1MB"
## @doc TCP tuning parameters. TCP receiving buffer size.
## @path rpc.socket_recbuf
## @type emqx_schema:bytesize()
socket_recbuf: "1MB"
## @doc TCP tuning parameters. Socket buffer size in user mode.
## @path rpc.socket_buffer
## @type emqx_schema:bytesize()
socket_buffer: "1MB"
}
db {
## @doc
## Select the backend for the embedded database.</br>
## <code>rlog</code> is the default backend,
## that is suitable for very large clusters.</br>
## <code>mnesia</code> is a backend that offers decent performance in small clusters.
##
## @path db.backend
## @type enum: mnesia | rlog
backend: rlog
## @doc
## Select a node role.</br>
## <code>core</code> nodes provide durability of the data, and take care of writes.
## It is recommended to place core nodes in different racks or different availability zones.</br>
## <code>replicant</code> nodes are ephemeral worker nodes. Removing them from the cluster
## doesn't affect database redundancy</br>
## It is recommended to have more replicant nodes than core nodes.</br>
## Note: this parameter only takes effect when the <code>backend</code> is set
## to <code>rlog</code>.
##
## @path db.role
## @type enum: core | replicant
role: core
## @doc
## List of core nodes that the replicant will connect to.</br>
## Note: this parameter only takes effect when the <code>backend</code> is set
## to <code>rlog</code> and the <code>role</code> is set to <code>replicant</code>.</br>
## This value needs to be defined for manual or static cluster discovery mechanisms.</br>
## If an automatic cluster discovery mechanism is being used (such as <code>etcd</code>),
## there is no need to set this value.
##
## @path db.core_nodes
## @type emqx_schema:comma_separated_atoms()
core_nodes: []
## @doc Protocol used for pushing transaction logs to the replicant nodes.
## @path db.rpc_module
## @type enum: gen_rpc | rpc
rpc_module: gen_rpc
## @doc
## In sync mode the core node waits for an ack from the replicant nodes before sending the next
## transaction log entry.
##
## @path db.tlog_push_mode
## @type enum: sync | async
tlog_push_mode: async
}
## @doc Message broker options.
broker {
## @doc Enable session registry
## @path broker.enable_session_registry
## @type boolean()
enable_session_registry: true
## @doc Session locking strategy in a cluster.
## - `local`: only lock the session on the current node
## - `one`: select only one remote node to lock the session
## - `quorum`: select some nodes to lock the session
## - `all`: lock the session on all the nodes in the cluster
##
## @path broker.session_locking_strategy
## @type enum: local | leader | quorum | all
session_locking_strategy: quorum
## @doc Dispatch strategy for shared subscription.
## - `random`: dispatch the message to a random selected subscriber
## - `round_robin`: select the subscribers in a round-robin manner
## - `sticky`: always use the last selected subscriber to dispatch, until the subscriber disconnects.
## - `hash`: select the subscribers by the hash of `clientIds`
##
## @path broker.shared_subscription_strategy
## @type enum: random | round_robin | sticky | local | hash_topic | hash_clientid
shared_subscription_strategy: round_robin
## @doc Enable/disable shared dispatch acknowledgement for QoS 1 and QoS 2 messages.
## This should allow messages to be dispatched to a different subscriber in the group in case the picked (based on `shared_subscription_strategy`) subscriber is offline.
##
## @path broker.shared_dispatch_ack_enabled
## @type boolean()
shared_dispatch_ack_enabled: false
## @doc Enable batch clean for deleted routes.
## @path broker.route_batch_clean
## @type boolean()
route_batch_clean: true
perf {
## @doc Performance tuning for subscribing/unsubscribing a wildcard topic.
## Change this parameter only when there are many wildcard topics.
##
## NOTE: when changing from/to `global` lock, it requires all nodes in the cluster to be stopped before the change.
## - `key`: mnesia transactional updates with per-key locks. Recommended for a single-node setup.
## - `tab`: mnesia transactional updates with table lock. Recommended for a cluster setup.
## - `global`: updates are protected with a global lock. Recommended for large clusters.
##
## @path broker.perf.route_lock_type
## @type enum: key | tab | global
route_lock_type: key
## @doc Enable trie path compaction.
## Enabling it significantly improves wildcard topic subscribe rate, if wildcard topics have unique prefixes like: 'sensor/{{id}}/+/', where ID is unique per subscriber.
## Topic match performance (when publishing) may degrade if messages are mostly published to topics with large number of levels.
##
## NOTE: This is a cluster-wide configuration. It requires all nodes to be stopped before changing it.
##
## @path broker.perf.trie_compaction
## @type boolean()
trie_compaction: true
}
## @doc Per group dispatch strategy for shared subscription.
## This config is a map from shared subscription group name to the strategy
## name. The group name should be of format `[A-Za-z0-9]`. i.e. no
## special characters are allowed.
##
## @path broker.shared_subscription_group
## @type map()
## shared_subscription_group:
## $name {
## @doc Dispatch strategy for shared subscription.
## - `random`: dispatch the message to a random selected subscriber
## - `round_robin`: select the subscribers in a round-robin manner
## - `sticky`: always use the last selected subscriber to dispatch,
## until the subscriber disconnects.
## - `hash`: select the subscribers by the hash of `clientIds`
## - `local`: send to a random local subscriber. If local
## subscriber was not found, send to a random subscriber cluster-wide
##
## @path broker.shared_subscription_group.$name.strategy
## @type enum: random | round_robin | sticky | local | hash_topic | hash_clientid
## strategy: random
## }
}
## @doc System topics configuration.
sys_topics {
## @doc Time interval of publishing `$SYS` messages.
## @path sys_topics.sys_msg_interval
## @type union: disabled | emqx_schema:duration()
sys_msg_interval: "1m"
## @doc Time interval for publishing following heartbeat messages:
## - `$SYS/brokers/<node>/uptime`
## - `$SYS/brokers/<node>/datetime`
##
## @path sys_topics.sys_heartbeat_interval
## @type union: disabled | emqx_schema:duration()
sys_heartbeat_interval: "30s"
sys_event_messages {
## @doc Enable to publish client connected event messages
## @path sys_topics.sys_event_messages.client_connected
## @type boolean()
client_connected: true
## @doc Enable to publish client disconnected event messages.
## @path sys_topics.sys_event_messages.client_disconnected
## @type boolean()
client_disconnected: true
## @doc Enable to publish event message that client subscribed a topic successfully.
## @path sys_topics.sys_event_messages.client_subscribed
## @type boolean()
client_subscribed: false
## @doc Enable to publish event message that client unsubscribed a topic successfully.
## @path sys_topics.sys_event_messages.client_unsubscribed
## @type boolean()
client_unsubscribed: false
}
}
force_shutdown {
## @doc Enable `force_shutdown` feature.
## @path force_shutdown.enable
## @type boolean()
enable: true
## @doc Maximum message queue length.
## @path force_shutdown.max_message_queue_len
## @type 0..inf
max_message_queue_len: 1000
## @doc Total heap size
## @path force_shutdown.max_heap_size
## @type emqx_schema:wordsize()
max_heap_size: "32MB"
}
overload_protection {
## @doc React on system overload or not
## @path overload_protection.enable
## @type boolean()
enable: false
## @doc Some unimportant tasks could be delayed for execution, here set the delays in ms
## @path overload_protection.backoff_delay
## @type 0..inf
backoff_delay: 1
## @doc Skip forceful GC if necessary
## @path overload_protection.backoff_gc
## @type boolean()
backoff_gc: false
## @doc Skip process hibernation if necessary
## @path overload_protection.backoff_hibernation
## @type boolean()
backoff_hibernation: true
## @doc Close new incoming connections if necessary
## @path overload_protection.backoff_new_conn
## @type boolean()
backoff_new_conn: true
}
force_gc {
## @doc Enable forced garbage collection.
## @path force_gc.enable
## @type boolean()
enable: true
## @doc GC the process after this many received messages.
## @path force_gc.count
## @type 0..inf
count: 16000
## @doc GC the process after specified number of bytes have passed through.
## @path force_gc.bytes
## @type emqx_schema:bytesize()
bytes: "16MB"
}
conn_congestion {
## @doc Enable or disable connection congestion alarm.
## @path conn_congestion.enable_alarm
## @type boolean()
enable_alarm: false
## @doc Minimal time before clearing the alarm.
##
## The alarm is cleared only when there's no pending data in
## the queue, and at least `min_alarm_sustain_duration`
## milliseconds passed since the last time we considered the connection "congested".
##
## This is to avoid clearing and raising the alarm again too often.
## @path conn_congestion.min_alarm_sustain_duration
## @type emqx_schema:duration()
min_alarm_sustain_duration: "1m"
}
stats {
## @doc Enable/disable statistic data collection.
## @path stats.enable
## @type boolean()
enable: true
}
sysmon {
vm {
## @doc The time interval for the periodic process limit check.
## @path sysmon.vm.process_check_interval
## @type emqx_schema:duration()
process_check_interval: "30s"
## @doc The threshold, as percentage of processes, for how many
## processes can simultaneously exist at the local node before the corresponding
## alarm is raised.
## @path sysmon.vm.process_high_watermark
## @type emqx_schema:percent()
process_high_watermark: "80%"
## @doc The threshold, as percentage of processes, for how many
## processes can simultaneously exist at the local node before the corresponding
## alarm is cleared.
## @path sysmon.vm.process_low_watermark
## @type emqx_schema:percent()
process_low_watermark: "60%"
## @doc Enable Long GC monitoring.
## @path sysmon.vm.long_gc
## @type union: disabled | emqx_schema:duration()
## long_gc:
## @doc Enable Long Schedule monitoring.
## @path sysmon.vm.long_schedule
## @type union: disabled | emqx_schema:duration()
long_schedule: "240ms"
## @doc Enable Large Heap monitoring.
## @path sysmon.vm.large_heap
## @type union: disabled | emqx_schema:bytesize()
large_heap: "32MB"
## @doc Enable Busy Distribution Port monitoring.
## @path sysmon.vm.busy_dist_port
## @type boolean()
busy_dist_port: true
## @doc Enable Busy Port monitoring.
## @path sysmon.vm.busy_port
## @type boolean()
busy_port: true
}
os {
## @doc The time interval for the periodic CPU check.
## @path sysmon.os.cpu_check_interval
## @type emqx_schema:duration()
cpu_check_interval: "60s"
## @doc The threshold, as percentage of system CPU load,
## for how much system cpu can be used before the corresponding alarm is raised.
## @path sysmon.os.cpu_high_watermark
## @type emqx_schema:percent()
cpu_high_watermark: "80%"
## @doc The threshold, as percentage of system CPU load,
## for how much system cpu can be used before the corresponding alarm is cleared.
## @path sysmon.os.cpu_low_watermark
## @type emqx_schema:percent()
cpu_low_watermark: "60%"
## @doc The time interval for the periodic memory check.
## @path sysmon.os.mem_check_interval
## @type union: disabled | emqx_schema:duration()
mem_check_interval: "60s"
## @doc The threshold, as percentage of system memory,
## for how much system memory can be allocated before the corresponding alarm is raised.
## @path sysmon.os.sysmem_high_watermark
## @type emqx_schema:percent()
sysmem_high_watermark: "70%"
## @doc The threshold, as percentage of system memory,
## for how much system memory can be allocated by one Erlang process before
## the corresponding alarm is raised.
## @path sysmon.os.procmem_high_watermark
## @type emqx_schema:percent()
procmem_high_watermark: "5%"
}
top {
## @doc The number of top processes per monitoring group
## @path sysmon.top.num_items
## @type non_neg_integer()
num_items: 10
## @doc Specifies how often process top should be collected
## @path sysmon.top.sample_interval
## @type emqx_schema:duration()
sample_interval: "2s"
## @doc Stop collecting data when the number of processes
## in the VM exceeds this value
## @path sysmon.top.max_procs
## @type non_neg_integer()
max_procs: 1000000
## @doc Hostname of the PostgreSQL database that collects the data points
## @path sysmon.top.db_hostname
## @type string()
db_hostname: []
## @doc Port of the PostgreSQL database that collects the data points
## @path sysmon.top.db_port
## @type integer()
db_port: 5432
## @doc Username of the PostgreSQL database
## @path sysmon.top.db_username
## @type string()
db_username: "system_monitor"
## @doc EMQX user password in the PostgreSQL database
## @path sysmon.top.db_password
## @type binary()
db_password: "system_monitor_password"
## @doc PostgreSQL database name
## @path sysmon.top.db_name
## @type string()
db_name: "postgres"
}
}
alarm {
## @doc The actions triggered when the alarm is activated.</br>
## Currently, the following actions are supported: <code>log</code> and <code>publish</code>.
## <code>log</code> is to write the alarm to log (console or file).
## <code>publish</code> is to publish the alarm as an MQTT message to the system topics:
## <code>$SYS/brokers/emqx@xx.xx.xx.x/alarms/activate</code> and
## <code>$SYS/brokers/emqx@xx.xx.xx.x/alarms/deactivate</code>
## @path alarm
## @type array
actions: [log, publish]
## @doc The maximum total number of deactivated alarms to keep as history.</br>
## When this limit is exceeded, the oldest deactivated alarms are deleted to cap the total number.
##
## @path alarm.size_limit
## @type 1..3000
size_limit: 1000
## @doc Retention time of deactivated alarms. Alarms are not deleted immediately
## when deactivated, but after the retention time.
##
## @path alarm.validity_period
## @type emqx_schema:duration()
validity_period: "24h"
}
flapping_detect {
## @doc Enable flapping connection detection feature.
## @path flapping_detect.enable
## @type boolean()
enable: false
## @doc The maximum number of disconnects allowed for a MQTT Client in `window_time`
## @path flapping_detect.max_count
## @type integer()
max_count: 15
## @doc The time window for flapping detection.
## @path flapping_detect.window_time
## @type emqx_schema:duration()
window_time: "1m"
## @doc How long the flapping clientid will be banned.
## @path flapping_detect.ban_time
## @type emqx_schema:duration()
ban_time: "5m"
}
persistent_session_store {
## @doc Use the database to store information about persistent sessions.
## This makes it possible to migrate a client connection to another
## cluster node if a node is stopped.
##
## @path persistent_session_store.enabled
## @type boolean()
enabled: false
## @doc Save information about the persistent sessions on disc.
## If this option is enabled, persistent sessions will survive full restart of the cluster.
## Otherwise, all the data will be stored in RAM, and it will be lost when all the nodes in the cluster are stopped.
## @path persistent_session_store.on_disc
## @type boolean()
on_disc: true
## @doc Maintain a copy of the data in RAM for faster access.
## @path persistent_session_store.ram_cache
## @type boolean()
ram_cache: false
## @doc Database management system used to store information about persistent sessions and messages.
## - `builtin`: Use the embedded database (mria)
## @path persistent_session_store.backend
## @type union: broker:persistent_session_builtin
backend:
{
messages {ram_cache = "false"}
session {ram_cache = "true"}
session_messages {ram_cache = "true"}
type = "builtin"
}
## @doc The time messages that was not delivered to a persistent session
## is stored before being garbage collected if the node the previous
## session was handled on restarts of is stopped.
##
## @path persistent_session_store.max_retain_undelivered
## @type emqx_schema:duration()
max_retain_undelivered: "1h"
## @doc The starting interval for garbage collection of undelivered messages to
## a persistent session. This affects how often the "max_retain_undelivered"
## is checked for removal.
##
## @path persistent_session_store.message_gc_interval
## @type emqx_schema:duration()
message_gc_interval: "1h"
## @doc The starting interval for garbage collection of transient data for
## persistent session messages. This does not affect the lifetime length
## of persistent session messages.
##
## @path persistent_session_store.session_message_gc_interval
## @type emqx_schema:duration()
session_message_gc_interval: "1m"
}
trace {
## @doc
## Determine the format of the payload format in the trace file.</br>
## `text`: Text-based protocol or plain text protocol.
## It is recommended when payload is JSON encoded.</br>
## `hex`: Binary hexadecimal encode. It is recommended when payload is a custom binary protocol.</br>
## `hidden`: payload is obfuscated as `******`
##
##
## @path trace.payload_encode
## @type enum: hex | text | hidden
payload_encode: text
}
bridges {
## @doc HTTP bridges to an HTTP server.
## @path bridges.http
## @type map()
## http:
## $name {
## @doc Enable or disable this bridge
## @path bridges.http.$name.enable
## @type boolean()
## enable: true
## @doc The direction of this bridge, MUST be 'egress'
## @path bridges.http.$name.direction
## @type singleton
## direction: egress
## @doc The timeout when connecting to the HTTP server.
## @path bridges.http.$name.connect_timeout
## @type emqx_schema:duration_ms()
## connect_timeout: "15s"
## @doc Max retry times if error on sending request.
## @path bridges.http.$name.max_retries
## @type non_neg_integer()
## max_retries: 5
## @doc Interval between retries.
## @path bridges.http.$name.retry_interval
## @type emqx_schema:duration()
## retry_interval: "1s"
## @doc The type of the pool. Can be one of `random`, `hash`.
## @path bridges.http.$name.pool_type
## @type emqx_connector_http:pool_type()
## pool_type: random
## @doc The pool size.
## @path bridges.http.$name.pool_size
## @type pos_integer()
## pool_size: 8
## @doc Enable the HTTP pipeline.
## @path bridges.http.$name.enable_pipelining
## @type boolean()
## enable_pipelining: true
## request {
## @doc HTTP method.
## @path bridges.http.$name.request.method
## @type enum: post | put | get | delete
## method: post
## @doc URL path.
## @path bridges.http.$name.request.path
## @type binary()
## path:
## @doc HTTP request body.
## @path bridges.http.$name.request.body
## @type binary()
## body:
## @doc List of HTTP headers.
## @path bridges.http.$name.request.headers
## @type map()
## headers:
## @doc HTTP request timeout.
## @path bridges.http.$name.request.request_timeout
## @type emqx_schema:duration_ms()
## request_timeout:
## }
## ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path bridges.http.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path bridges.http.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path bridges.http.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path bridges.http.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path bridges.http.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path bridges.http.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path bridges.http.$name.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path bridges.http.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path bridges.http.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path bridges.http.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path bridges.http.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Enable TLS.
##
## @path bridges.http.$name.ssl.enable
## @type boolean()
## enable: false
## @doc
## Specify the host name to be used in TLS Server Name Indication extension.</br>
## For instance, when connecting to "server.example.net", the genuine server
## which accepts the connection and performs TLS handshake may differ from the
## host the TLS client initially connects to, e.g. when connecting to an IP address
## or when the host has multiple resolvable DNS records </br>
## If not specified, it will default to the host name string which is used
## to establish the connection, unless it is IP addressed used.</br>
## The host name is then also used in the host name verification of the peer
## certificate.</br> The special value 'disable' prevents the Server Name
## Indication extension from being sent and disables the hostname
## verification check.
##
## @path bridges.http.$name.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
## }
## @doc
## The URL of the HTTP Bridge.</br>
## Template with variables is allowed in the path, but variables cannot be used in the scheme, host,
## or port part.</br>
## For example, <code> http://localhost:9901/${topic} </code> is allowed, but
## <code> http://${host}:9901/message </code> or <code> http://localhost:${port}/message </code>
## is not allowed.
##
## @path bridges.http.$name.url
## @type binary()
## url:
## @doc
## The MQTT topic filter to be forwarded to the HTTP server. All MQTT 'PUBLISH' messages with the topic
## matching the local_topic will be forwarded.</br>
## NOTE: if this bridge is used as the output of a rule (EMQX rule engine), and also local_topic is
## configured, then both the data got from the rule and the MQTT messages that match local_topic
## will be forwarded.
##
## @path bridges.http.$name.local_topic
## @type binary()
## local_topic:
## @doc
## The method of the HTTP request. All the available methods are: post, put, get, delete.</br>
## Template with variables is allowed.</br>
##
## @path bridges.http.$name.method
## @type enum: post | put | get | delete
## method: post
## @doc
## The headers of the HTTP request.</br>
## Template with variables is allowed.
##
## @path bridges.http.$name.headers
## @type map()
## headers:
## {
## accept = "application/json"
## "cache-control" = "no-cache"
## connection = "keep-alive"
## "content-type" = "application/json"
## "keep-alive" = "timeout=5"
## }
##
## @doc
## The body of the HTTP request.</br>
## Template with variables is allowed.
##
## @path bridges.http.$name.body
## @type binary()
## body: "${payload}"
## @doc HTTP request timeout.
## @path bridges.http.$name.request_timeout
## @type emqx_schema:duration_ms()
## request_timeout: "15s"
## }
## @doc MQTT bridges to/from another MQTT broker
## @path bridges.mqtt
## @type map()
## mqtt:
## @path bridges.mqtt.$name
## @type union: ingress | egress
## $name:
}
retainer {
## @doc Enable retainer feature
## @path retainer.enable
## @type boolean()
enable: true
## @doc Message retention time. 0 means message will never be expired.
## @path retainer.msg_expiry_interval
## @type emqx_schema:duration_ms()
msg_expiry_interval: "0s"
## @doc Periodic interval for cleaning up expired messages.
## Never clear if the value is 0.
##
## @path retainer.msg_clear_interval
## @type emqx_schema:duration_ms()
msg_clear_interval: "0s"
flow_control {
## @doc Size of the batch when reading messages from storage. 0 means no limit.
## @path retainer.flow_control.batch_read_number
## @type non_neg_integer()
batch_read_number: 0
## @doc The number of retained messages can be delivered per batch.
## @path retainer.flow_control.batch_deliver_number
## @type 0..1000
batch_deliver_number: 0
## @doc The rate limiter name for retained messages' delivery.
## Limiter helps to avoid delivering too many messages to the client at once, which may cause the client to block or crash, or drop messages due to exceeding the size of the message queue.
## The names of the available rate limiters are taken from the existing rate limiters under `limiter.batch`.
## If this field is empty, limiter is not used.
## @path retainer.flow_control.batch_deliver_limiter
## @type emqx_limiter_schema:bucket_name()
## batch_deliver_limiter:
}
## @doc Maximum retained message size.
## @path retainer.max_payload_size
## @type emqx_schema:bytesize()
max_payload_size: "1MB"
## @doc When the retained flag of the `PUBLISH` message is set and Payload is empty,
## whether to continue to publish the message.
## See:
## http://docs.oasis-open.org/mqtt/mqtt/v3.1.1/os/mqtt-v3.1.1-os.html#_Toc398718038
## @path retainer.stop_publish_clear_msg
## @type boolean()
stop_publish_clear_msg: false
backend {
## @doc Backend type.
## @path retainer.backend.type
## @type enum: built_in_database
type: built_in_database
## @doc Specifies whether the messages are stored in RAM or persisted on disc.
## @path retainer.backend.storage_type
## @type union: ram | disc
storage_type: ram
## @doc Maximum number of retained messages. 0 means no limit.
## @path retainer.backend.max_retained_messages
## @type non_neg_integer()
max_retained_messages: 0
## @doc Retainer index specifications: list of arrays of positive ascending integers. Each array specifies an index. Numbers in an index specification are 1-based word positions in topics. Words from specified positions will be used for indexing.</br>For example, it is good to have <code>[2, 4]</code> index to optimize <code>+/X/+/Y/...</code> topic wildcard subscriptions.
## @path retainer.backend.index_specs
## @type [[integer()]]
index_specs:
[
[1, 2, 3],
[1, 3],
[2, 3],
[3]
]
}
}
statsd {
## @doc Turn Statsd data pushing on or off
## @path statsd.enable
## @type boolean()
enable: false
## @doc URL of Statsd server
## @path statsd.server
## @type emqx_schema:ip_port()
server: "127.0.0.1:8125"
## @doc Data collection interval in second.
## @path statsd.sample_time_interval
## @type emqx_schema:duration_ms()
sample_time_interval: "10s"
## @doc Data reporting interval, in second.
## @path statsd.flush_time_interval
## @type emqx_schema:duration_ms()
flush_time_interval: "10s"
}
auto_subscribe {
## @doc After the device logs in successfully, the subscription is automatically completed for the device through the pre-defined subscription representation. Supports the use of placeholders.
## @path auto_subscribe
## @type array
topics: []
## $INDEX {
## @doc Topic name, placeholders are supported. For example: client/${clientid}/username/${username}/host/${host}/port/${port}
## Required field, and cannot be empty string
## @path auto_subscribe.topics.$INDEX.topic
## @type binary()
## topic:
## @doc Default value 0. Quality of service.
## At most once (0)
## At least once (1)
## Exactly once (2)
## @path auto_subscribe.topics.$INDEX.qos
## @type qos()
## qos: 0
## @doc Default value 0. This option is used to specify whether the server forwards the retained message to the client when establishing a subscription.
## Retain Handling is equal to 0, as long as the client successfully subscribes, the server will send the retained message.
## Retain Handling is equal to 1, if the client successfully subscribes and this subscription does not exist previously, the server sends the retained message. After all, sometimes the client re-initiate the subscription just to change the QoS, but it does not mean that it wants to receive the reserved messages again.
## Retain Handling is equal to 2, even if the client successfully subscribes, the server does not send the retained message.
## @path auto_subscribe.topics.$INDEX.rh
## @type 0..2
## rh: 0
## @doc Default value 0. This option is used to specify whether the server retains the RETAIN mark when forwarding messages to the client, and this option does not affect the RETAIN mark in the retained message. Therefore, when the option Retain As Publish is set to 0, the client will directly distinguish whether this is a normal forwarded message or a retained message according to the RETAIN mark in the message, instead of judging whether this message is the first received after subscribing(the forwarded message may be sent before the retained message, which depends on the specific implementation of different brokers).
## @path auto_subscribe.topics.$INDEX.rap
## @type 0..1
## rap: 0
## @doc Default value 0.
## MQTT v3.1.1: if you subscribe to the topic published by yourself, you will receive all messages that you published.
## MQTT v5: if you set this option as 1 when subscribing, the server will not forward the message you published to you.
## @path auto_subscribe.topics.$INDEX.nl
## @type 0..1
## nl: 0
## }
}
delayed {
## @doc Enable this feature
## @path delayed.enable
## @type boolean()
enable: true
## @doc Maximum number of delayed messages (0 is no limit).
## @path delayed.max_delayed_messages
## @type integer()
max_delayed_messages: 0
}
telemetry {
## @doc Enable telemetry.
## @path telemetry.enable
## @type boolean()
enable: true
}
## @doc List of topic rewrite rules.
## @doc List of topic rewrite rules.
## @path
## @type array
rewrite: []
## $INDEX {
## @doc Topic rewriting takes effect on the type of operation:
## - `subscribe`: Rewrite topic when client do subscribe.
## - `publish`: Rewrite topic when client do publish.
## - `all`: Both
## @path rewrite.$INDEX.action
## @type enum: subscribe | publish | all
## action: subscribe
## @doc Source topic, specified by the client.
## @path rewrite.$INDEX.source_topic
## @type binary()
## source_topic:
## @doc Destination topic.
## @path rewrite.$INDEX.dest_topic
## @type binary()
## dest_topic:
## @doc Regular expressions
## @path rewrite.$INDEX.re
## @type binary()
## re:
## }
## @doc List of topics whose metrics are reported.
## @doc List of topics whose metrics are reported.
## @path
## @type array
topic_metrics: []
## $INDEX {
## @doc Collect metrics for the topic.
## @path topic_metrics.$INDEX.topic
## @type binary()
## topic:
## }
plugins {
## @doc An array of plugins in the desired states.</br>
## The plugins are started in the defined order
## @path plugins
## @type array
states: []
## $INDEX {
## @doc The {name}-{version} of the plugin.</br>
## It should match the plugin application name-version as the for the plugin release package name</br>
## For example: my_plugin-0.1.0.
##
## @path plugins.states.$INDEX.name_vsn
## @type string()
## name_vsn:
## @doc Set to 'true' to enable this plugin
## @path plugins.states.$INDEX.enable
## @type boolean()
## enable:
## }
## @doc
## The installation directory for the external plugins.
## The plugin beam files and configuration files should reside in
## the subdirectory named as <code>emqx_foo_bar-0.1.0</code>.
## </br>
## NOTE: For security reasons, this directory should **NOT** be writable
## by anyone except <code>emqx</code> (or any user which runs EMQX).
##
## @path plugins.install_dir
## @type string()
install_dir: "plugins"
## @doc Check interval: check if the status of the plugins in the cluster is consistent, </br>
## if the results of 3 consecutive checks are not consistent, then alarm.
##
## @path plugins.check_interval
## @type emqx_schema:duration()
check_interval: "5s"
}
dashboard {
listeners {
http {
## @doc Ignore or enable this listener
## @path dashboard.listeners.http.enable
## @type boolean()
enable: true
## @doc Port without IP(18083) or port with specified IP(127.0.0.1:18083).
## @path dashboard.listeners.http.bind
## @type union: non_neg_integer() | emqx_schema:ip_port()
bind: 18803
## @doc Socket acceptor pool size for TCP protocols.
## @path dashboard.listeners.http.num_acceptors
## @type integer()
num_acceptors: 4
## @doc Maximum number of simultaneous connections.
## @path dashboard.listeners.http.max_connections
## @type integer()
max_connections: 512
## @doc Defines the maximum length that the queue of pending connections can grow to.
## @path dashboard.listeners.http.backlog
## @type integer()
backlog: 1024
## @doc Send timeout for the socket.
## @path dashboard.listeners.http.send_timeout
## @type emqx_schema:duration()
send_timeout: "5s"
## @doc Enable IPv6 support, default is false, which means IPv4 only.
## @path dashboard.listeners.http.inet6
## @type boolean()
inet6: false
## @doc Disable IPv4-to-IPv6 mapping for the listener.
## @path dashboard.listeners.http.ipv6_v6only
## @type boolean()
ipv6_v6only: false
}
https {
## @doc Ignore or enable this listener
## @path dashboard.listeners.https.enable
## @type boolean()
enable: false
## @doc Port without IP(18083) or port with specified IP(127.0.0.1:18083).
## @path dashboard.listeners.https.bind
## @type union: non_neg_integer() | emqx_schema:ip_port()
bind: 18804
## @doc Socket acceptor pool size for TCP protocols.
## @path dashboard.listeners.https.num_acceptors
## @type integer()
num_acceptors: 4
## @doc Maximum number of simultaneous connections.
## @path dashboard.listeners.https.max_connections
## @type integer()
max_connections: 512
## @doc Defines the maximum length that the queue of pending connections can grow to.
## @path dashboard.listeners.https.backlog
## @type integer()
backlog: 1024
## @doc Send timeout for the socket.
## @path dashboard.listeners.https.send_timeout
## @type emqx_schema:duration()
send_timeout: "5s"
## @doc Enable IPv6 support, default is false, which means IPv4 only.
## @path dashboard.listeners.https.inet6
## @type boolean()
inet6: false
## @doc Disable IPv4-to-IPv6 mapping for the listener.
## @path dashboard.listeners.https.ipv6_v6only
## @type boolean()
ipv6_v6only: false
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path dashboard.listeners.https.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path dashboard.listeners.https.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path dashboard.listeners.https.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path dashboard.listeners.https.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path dashboard.listeners.https.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path dashboard.listeners.https.depth
## @type integer()
depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path dashboard.listeners.https.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path dashboard.listeners.https
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path dashboard.listeners.https
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path dashboard.listeners.https.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path dashboard.listeners.https.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path dashboard.listeners.https.dhfile
## @type string()
## dhfile:
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path dashboard.listeners.https.honor_cipher_order
## @type boolean()
honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path dashboard.listeners.https.client_renegotiation
## @type boolean()
client_renegotiation: true
## @doc
## Maximum time duration allowed for the handshake to complete
##
## @path dashboard.listeners.https.handshake_timeout
## @type emqx_schema:duration()
handshake_timeout: "15s"
}
}
## @doc The default username of the automatically created dashboard user.
## @path dashboard.default_username
## @type binary()
default_username: "admin"
## @doc The initial default password for dashboard 'admin' user.
## For safety, it should be changed as soon as possible.
## @path dashboard.default_password
## @type binary()
default_password: "public"
## @doc How often to update metrics displayed in the dashboard.
## Note: `sample_interval` should be a divisor of 60.
## @path dashboard.sample_interval
## @type emqx_schema:duration_s()
sample_interval: "10s"
## @doc JWT token expiration time.
## @path dashboard.token_expired_time
## @type emqx_schema:duration()
token_expired_time: "60m"
## @doc Support Cross-Origin Resource Sharing (CORS).
## Allows a server to indicate any origins (domain, scheme, or port) other than
## its own from which a browser should permit loading resources.
## @path dashboard.cors
## @type boolean()
cors: false
## @doc Internationalization language support.
## @path dashboard.i18n_lang
## @type enum: en | zh
i18n_lang: en
}
gateway {
stomp {
frame {
## @doc The maximum number of Header
## @path gateway.stomp.frame.max_headers
## @type non_neg_integer()
max_headers: 10
## @doc The maximum string length of the Header Value
## @path gateway.stomp.frame.max_headers_length
## @type non_neg_integer()
max_headers_length: 1024
## @doc Maximum number of bytes of Body allowed per Stomp packet
## @path gateway.stomp.frame.max_body_length
## @type integer()
max_body_length: 65536
}
## @doc
## @path gateway.stomp.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.stomp.listeners.tcp
## @type map()
## tcp:
## $name {
## @doc Size of the acceptor pool.
## @path gateway.stomp.listeners.tcp.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.stomp.listeners.tcp.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path gateway.stomp.listeners.tcp.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.stomp.listeners.tcp.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc Timeout for proxy protocol.
## EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
## @path gateway.stomp.listeners.tcp.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc Enable the listener.
## @path gateway.stomp.listeners.tcp.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.stomp.listeners.tcp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.stomp.listeners.tcp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.stomp.listeners.tcp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.stomp.listeners.tcp.$name.authentication
## @link gateway.exproto.listeners.tcp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.stomp.listeners.tcp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.stomp.listeners.tcp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.stomp.listeners.ssl
## @type map()
## ssl:
## $name {
## @doc Size of the acceptor pool.
## @path gateway.stomp.listeners.ssl.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.stomp.listeners.ssl.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path gateway.stomp.listeners.ssl.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.stomp.listeners.ssl.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc Timeout for proxy protocol.
## EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
## @path gateway.stomp.listeners.ssl.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc Enable the listener.
## @path gateway.stomp.listeners.ssl.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.stomp.listeners.ssl.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.stomp.listeners.ssl.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.stomp.listeners.ssl.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.stomp.listeners.ssl.$name.authentication
## @link gateway.exproto.listeners.ssl.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.stomp.listeners.ssl.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.stomp.listeners.ssl.$name
## @type array
## access_rules: []
## ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path gateway.stomp.listeners.ssl.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.stomp.listeners.ssl.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.dhfile
## @type string()
## dhfile:
## @doc
## Used together with {verify, verify_peer} by an TLS/DTLS server.
## If set to true, the server fails if the client does not have a
## certificate to send, that is, sends an empty certificate.
## If set to false, it fails only if the client sends an invalid
## certificate (an empty certificate is considered valid).
##
## @path gateway.stomp.listeners.ssl.$name.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path gateway.stomp.listeners.ssl.$name.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
}
## @doc Whether to enable this gateway
## @path gateway.stomp.enable
## @type boolean()
enable: true
## @doc Whether to enable client process statistic
## @path gateway.stomp.enable_stats
## @type boolean()
enable_stats: true
## @doc The idle time of the client connection process. It has two purposes:
## 1. A newly created client process that does not receive any client requests after that time will be closed directly.
## 2. A running client process that does not receive any client requests after this time will go into hibernation to save resources.
## @path gateway.stomp.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc Template for overriding username.
## @path gateway.stomp.clientinfo_override.username
## @type binary()
## username:
## @doc Template for overriding password.
## @path gateway.stomp.clientinfo_override.password
## @type binary()
## password:
## @doc Template for overriding clientid.
## @path gateway.stomp.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.stomp.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
mqttsn {
## @doc MQTT-SN Gateway ID.
## When the <code>broadcast</code> option is enabled, the gateway will broadcast ADVERTISE message with this value
## @path gateway.mqttsn.gateway_id
## @type integer()
gateway_id: 1
## @doc Whether to periodically broadcast ADVERTISE messages
## @path gateway.mqttsn.broadcast
## @type boolean()
broadcast: false
## @doc Allows connectionless clients to publish messages with a Qos of -1.
## This feature is defined for very simple client implementations which do not support any other features except this one. There is no connection setup nor tear down, no registration nor subscription. The client just sends its 'PUBLISH' messages to a GW
## @path gateway.mqttsn.enable_qos3
## @type boolean()
enable_qos3: true
## @doc Whether to initiate all subscribed topic name registration messages to the client after the Session has been taken over by a new channel
## @path gateway.mqttsn.subs_resume
## @type boolean()
subs_resume: false
## @doc The pre-defined topic IDs and topic names.
## A 'pre-defined' topic ID is a topic ID whose mapping to a topic name is known in advance by both the client's application and the gateway
## @path gateway.mqttsn
## @type array
predefined: []
## $INDEX {
## @doc Topic ID. Range: 1-65535
## @path gateway.mqttsn.predefined.$INDEX.id
## @type integer()
## id:
## @doc Topic Name
## @path gateway.mqttsn.predefined.$INDEX.topic
## @type binary()
## topic:
## }
## @doc
## @path gateway.mqttsn.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.mqttsn.listeners.udp
## @link gateway.coap.listeners.udp
## @type map()
## @doc
## @path gateway.mqttsn.listeners.dtls
## @link gateway.coap.listeners.dtls
## @type map()
}
## @doc Whether to enable this gateway
## @path gateway.mqttsn.enable
## @type boolean()
enable: true
## @doc Whether to enable client process statistic
## @path gateway.mqttsn.enable_stats
## @type boolean()
enable_stats: true
## @doc The idle time of the client connection process. It has two purposes:
## 1. A newly created client process that does not receive any client requests after that time will be closed directly.
## 2. A running client process that does not receive any client requests after this time will go into hibernation to save resources.
## @path gateway.mqttsn.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc Template for overriding username.
## @path gateway.mqttsn.clientinfo_override.username
## @type binary()
## username:
## @doc Template for overriding password.
## @path gateway.mqttsn.clientinfo_override.password
## @type binary()
## password:
## @doc Template for overriding clientid.
## @path gateway.mqttsn.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.mqttsn.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
coap {
## @doc The gateway server required minimum heartbeat interval.
## When connection mode is enabled, this parameter is used to set the minimum heartbeat interval for the connection to be alive
## @path gateway.coap.heartbeat
## @type emqx_gateway_schema:duration()
heartbeat: "30s"
## @doc Enable or disable connection mode.
## Connection mode is a feature of non-standard protocols. When connection mode is enabled, it is necessary to maintain the creation, authentication and alive of connection resources
## @path gateway.coap.connection_required
## @type boolean()
connection_required: false
## @doc The Notification Message will be delivered to the CoAP client if a new message received on an observed topic.
## The type of delivered coap message can be set to:
## - non: Non-confirmable;
## - con: Confirmable;
## - qos: Mapping from QoS type of received message, QoS0 -> non, QoS1,2 -> con
##
## @path gateway.coap.notify_type
## @type union: non | con | qos
notify_type: qos
## @doc The Default QoS Level indicator for subscribe request.
## This option specifies the QoS level for the CoAP Client when establishing a subscription membership, if the subscribe request is not carried `qos` option. The indicator can be set to:
## - qos0, qos1, qos2: Fixed default QoS level
## - coap: Dynamic QoS level by the message type of subscribe request
## * qos0: If the subscribe request is non-confirmable
## * qos1: If the subscribe request is confirmable
##
## @path gateway.coap.subscribe_qos
## @type enum: qos0 | qos1 | qos2 | coap
subscribe_qos: coap
## @doc The Default QoS Level indicator for publish request.
## This option specifies the QoS level for the CoAP Client when publishing a message to EMQX PUB/SUB system, if the publish request is not carried `qos` option. The indicator can be set to:
## - qos0, qos1, qos2: Fixed default QoS level
## - coap: Dynamic QoS level by the message type of publish request
## * qos0: If the publish request is non-confirmable
## * qos1: If the publish request is confirmable
## @path gateway.coap.publish_qos
## @type enum: qos0 | qos1 | qos2 | coap
publish_qos: coap
## @doc
## @path gateway.coap.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.coap.listeners.udp
## @type map()
## udp:
## $name {
## udp {
## @doc Specify the {active, N} option for the socket.
## See: https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.coap.listeners.udp.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Size of the kernel-space receive buffer for the socket.
## @path gateway.coap.listeners.udp.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Size of the kernel-space send buffer for the socket.
## @path gateway.coap.listeners.udp.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Size of the user-space buffer for the socket.
## @path gateway.coap.listeners.udp.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc Allow local reuse of port numbers.
## @path gateway.coap.listeners.udp.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the listener.
## @path gateway.coap.listeners.udp.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.coap.listeners.udp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.coap.listeners.udp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.coap.listeners.udp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.coap.listeners.udp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.coap.listeners.udp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.coap.listeners.udp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.coap.listeners.dtls
## @type map()
## dtls:
## $name {
## @doc Size of the acceptor pool.
## @path gateway.coap.listeners.dtls.$name.acceptors
## @type integer()
## acceptors: 16
## udp {
## @doc Specify the {active, N} option for the socket.
## See: https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.coap.listeners.dtls.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Size of the kernel-space receive buffer for the socket.
## @path gateway.coap.listeners.dtls.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Size of the kernel-space send buffer for the socket.
## @path gateway.coap.listeners.dtls.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Size of the user-space buffer for the socket.
## @path gateway.coap.listeners.dtls.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc Allow local reuse of port numbers.
## @path gateway.coap.listeners.dtls.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the listener.
## @path gateway.coap.listeners.dtls.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.coap.listeners.dtls.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.coap.listeners.dtls.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.coap.listeners.dtls.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.coap.listeners.dtls.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.coap.listeners.dtls.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.coap.listeners.dtls.$name
## @type array
## access_rules: []
## dtls {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path gateway.coap.listeners.dtls.$name.dtls.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path gateway.coap.listeners.dtls.$name.dtls.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path gateway.coap.listeners.dtls.$name.dtls.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path gateway.coap.listeners.dtls.$name.dtls.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path gateway.coap.listeners.dtls.$name.dtls.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path gateway.coap.listeners.dtls.$name.dtls.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path gateway.coap.listeners.dtls.$name.dtls.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path gateway.coap.listeners.dtls.$name.dtls
## @type array
## versions: [dtlsv1.2, dtlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.coap.listeners.dtls.$name.dtls
## @type array
## ciphers: ["ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path gateway.coap.listeners.dtls.$name.dtls.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path gateway.coap.listeners.dtls.$name.dtls.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path gateway.coap.listeners.dtls.$name.dtls.dhfile
## @type string()
## dhfile:
## @doc
## Used together with {verify, verify_peer} by an TLS/DTLS server.
## If set to true, the server fails if the client does not have a
## certificate to send, that is, sends an empty certificate.
## If set to false, it fails only if the client sends an invalid
## certificate (an empty certificate is considered valid).
##
## @path gateway.coap.listeners.dtls.$name.dtls.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path gateway.coap.listeners.dtls.$name.dtls.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path gateway.coap.listeners.dtls.$name.dtls.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
}
## @doc Whether to enable this gateway
## @path gateway.coap.enable
## @type boolean()
enable: true
## @doc Whether to enable client process statistic
## @path gateway.coap.enable_stats
## @type boolean()
enable_stats: true
## @doc The idle time of the client connection process. It has two purposes:
## 1. A newly created client process that does not receive any client requests after that time will be closed directly.
## 2. A running client process that does not receive any client requests after this time will go into hibernation to save resources.
## @path gateway.coap.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc Template for overriding username.
## @path gateway.coap.clientinfo_override.username
## @type binary()
## username:
## @doc Template for overriding password.
## @path gateway.coap.clientinfo_override.password
## @type binary()
## password:
## @doc Template for overriding clientid.
## @path gateway.coap.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.coap.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
lwm2m {
## @doc The Directory for LwM2M Resource definition
## @path gateway.lwm2m.xml_dir
## @type binary()
xml_dir: "etc/lwm2m_xml"
## @doc Minimum value of lifetime allowed to be set by the LwM2M client
## @path gateway.lwm2m.lifetime_min
## @type emqx_gateway_schema:duration()
lifetime_min: "15s"
## @doc Maximum value of lifetime allowed to be set by the LwM2M client
## @path gateway.lwm2m.lifetime_max
## @type emqx_gateway_schema:duration()
lifetime_max: "86400s"
## @doc The value of the time window during which the network link is considered valid by the LwM2M Gateway in QMode mode.
## For example, after receiving an update message from a client, any messages within this time window are sent directly to the LwM2M client, and all messages beyond this time window are temporarily stored in memory.
## @path gateway.lwm2m.qmode_time_window
## @type emqx_gateway_schema:duration_s()
qmode_time_window: "22s"
## @doc Automatically observe the object list of REGISTER packet
## @path gateway.lwm2m.auto_observe
## @type boolean()
auto_observe: false
## @doc Policy for publishing UPDATE event message.
## - always: send update events as long as the UPDATE request is received.
## - contains_object_list: send update events only if the UPDATE request carries any Object List
##
## @path gateway.lwm2m.update_msg_publish_condition
## @type union: always | contains_object_list
update_msg_publish_condition: "contains_object_list"
translators {
command {
## @doc Topic Name
## @path gateway.lwm2m.translators.command.topic
## @type binary()
## topic:
## @doc QoS Level
## @path gateway.lwm2m.translators.command.qos
## @type qos()
qos: 0
}
response {
## @doc Topic Name
## @path gateway.lwm2m.translators.response.topic
## @type binary()
## topic:
## @doc QoS Level
## @path gateway.lwm2m.translators.response.qos
## @type qos()
qos: 0
}
notify {
## @doc Topic Name
## @path gateway.lwm2m.translators.notify.topic
## @type binary()
## topic:
## @doc QoS Level
## @path gateway.lwm2m.translators.notify.qos
## @type qos()
qos: 0
}
register {
## @doc Topic Name
## @path gateway.lwm2m.translators.register.topic
## @type binary()
## topic:
## @doc QoS Level
## @path gateway.lwm2m.translators.register.qos
## @type qos()
qos: 0
}
update {
## @doc Topic Name
## @path gateway.lwm2m.translators.update.topic
## @type binary()
## topic:
## @doc QoS Level
## @path gateway.lwm2m.translators.update.qos
## @type qos()
qos: 0
}
}
## @doc
## @path gateway.lwm2m.mountpoint
## @type binary()
mountpoint: "lwm2m/${endpoint_name}/"
listeners {
## @doc
## @path gateway.lwm2m.listeners.udp
## @link gateway.coap.listeners.udp
## @type map()
## @doc
## @path gateway.lwm2m.listeners.dtls
## @link gateway.coap.listeners.dtls
## @type map()
}
## @doc Whether to enable this gateway
## @path gateway.lwm2m.enable
## @type boolean()
enable: true
## @doc Whether to enable client process statistic
## @path gateway.lwm2m.enable_stats
## @type boolean()
enable_stats: true
## @doc The idle time of the client connection process. It has two purposes:
## 1. A newly created client process that does not receive any client requests after that time will be closed directly.
## 2. A running client process that does not receive any client requests after this time will go into hibernation to save resources.
## @path gateway.lwm2m.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc Template for overriding username.
## @path gateway.lwm2m.clientinfo_override.username
## @type binary()
## username:
## @doc Template for overriding password.
## @path gateway.lwm2m.clientinfo_override.password
## @type binary()
## password:
## @doc Template for overriding clientid.
## @path gateway.lwm2m.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.lwm2m.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
exproto {
server {
## @doc Listening address and port for the gRPC server.
## @path gateway.exproto.server.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path gateway.exproto.server.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path gateway.exproto.server.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path gateway.exproto.server.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path gateway.exproto.server.ssl.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path gateway.exproto.server.ssl.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path gateway.exproto.server.ssl.depth
## @type integer()
depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path gateway.exproto.server.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path gateway.exproto.server.ssl
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.server.ssl
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path gateway.exproto.server.ssl.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path gateway.exproto.server.ssl.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path gateway.exproto.server.ssl.dhfile
## @type string()
## dhfile:
## @doc
## Used together with {verify, verify_peer} by an TLS/DTLS server.
## If set to true, the server fails if the client does not have a
## certificate to send, that is, sends an empty certificate.
## If set to false, it fails only if the client sends an invalid
## certificate (an empty certificate is considered valid).
##
## @path gateway.exproto.server.ssl.fail_if_no_peer_cert
## @type boolean()
fail_if_no_peer_cert: false
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path gateway.exproto.server.ssl.honor_cipher_order
## @type boolean()
honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path gateway.exproto.server.ssl.client_renegotiation
## @type boolean()
client_renegotiation: true
## @doc
## Maximum time duration allowed for the handshake to complete
##
## @path gateway.exproto.server.ssl.handshake_timeout
## @type emqx_schema:duration()
handshake_timeout: "15s"
}
}
handler {
## @doc gRPC server address.
## @path gateway.exproto.handler.address
## @type binary()
## address:
ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path gateway.exproto.handler.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path gateway.exproto.handler.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path gateway.exproto.handler.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path gateway.exproto.handler.ssl.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path gateway.exproto.handler.ssl.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path gateway.exproto.handler.ssl.depth
## @type integer()
depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path gateway.exproto.handler.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path gateway.exproto.handler.ssl
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.handler.ssl
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path gateway.exproto.handler.ssl.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path gateway.exproto.handler.ssl.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc
## Enable TLS.
##
## @path gateway.exproto.handler.ssl.enable
## @type boolean()
enable: false
## @doc
## Specify the host name to be used in TLS Server Name Indication extension.</br>
## For instance, when connecting to "server.example.net", the genuine server
## which accepts the connection and performs TLS handshake may differ from the
## host the TLS client initially connects to, e.g. when connecting to an IP address
## or when the host has multiple resolvable DNS records </br>
## If not specified, it will default to the host name string which is used
## to establish the connection, unless it is IP addressed used.</br>
## The host name is then also used in the host name verification of the peer
## certificate.</br> The special value 'disable' prevents the Server Name
## Indication extension from being sent and disables the hostname
## verification check.
##
## @path gateway.exproto.handler.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
}
}
## @doc
## @path gateway.exproto.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.exproto.listeners.tcp
## @type map()
## tcp:
## $name {
## @doc Size of the acceptor pool.
## @path gateway.exproto.listeners.tcp.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.exproto.listeners.tcp.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path gateway.exproto.listeners.tcp.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.exproto.listeners.tcp.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc Timeout for proxy protocol.
## EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
## @path gateway.exproto.listeners.tcp.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc Enable the listener.
## @path gateway.exproto.listeners.tcp.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.exproto.listeners.tcp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.exproto.listeners.tcp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.exproto.listeners.tcp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.exproto.listeners.tcp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.exproto.listeners.tcp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.tcp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.exproto.listeners.ssl
## @type map()
## ssl:
## $name {
## @doc Size of the acceptor pool.
## @path gateway.exproto.listeners.ssl.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## Specify the {active, N} option for this Socket.</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.exproto.listeners.ssl.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog defines the maximum length that the queue of
## pending connections can grow to.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## The TCP send timeout for the connections.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## Close the connection if send timeout.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## The TCP receive buffer (OS kernel) for the connections.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## The TCP send buffer (OS kernel) for the connections.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## The size of the user-space buffer used by the driver.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## The socket is set to a busy state when the amount of data queued internally
## by the VM socket implementation reaches this limit.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## The TCP_NODELAY flag for the connections.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## The SO_REUSEADDR flag for the connections.
##
## @path gateway.exproto.listeners.ssl.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the Proxy Protocol V1/2 if the EMQX cluster is deployed behind HAProxy or Nginx.
## See: https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.exproto.listeners.ssl.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc Timeout for proxy protocol.
## EMQX will close the TCP connection if proxy protocol packet is not received within the timeout.
## @path gateway.exproto.listeners.ssl.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc Enable the listener.
## @path gateway.exproto.listeners.ssl.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.exproto.listeners.ssl.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.exproto.listeners.ssl.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.exproto.listeners.ssl.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.exproto.listeners.ssl.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.exproto.listeners.ssl.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.ssl.$name
## @type array
## access_rules: []
## ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path gateway.exproto.listeners.ssl.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.listeners.ssl.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.dhfile
## @type string()
## dhfile:
## @doc
## Used together with {verify, verify_peer} by an TLS/DTLS server.
## If set to true, the server fails if the client does not have a
## certificate to send, that is, sends an empty certificate.
## If set to false, it fails only if the client sends an invalid
## certificate (an empty certificate is considered valid).
##
## @path gateway.exproto.listeners.ssl.$name.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path gateway.exproto.listeners.ssl.$name.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
## @doc
## @path gateway.exproto.listeners.udp
## @type map()
## udp:
## $name {
## udp {
## @doc Specify the {active, N} option for the socket.
## See: https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.exproto.listeners.udp.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Size of the kernel-space receive buffer for the socket.
## @path gateway.exproto.listeners.udp.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Size of the kernel-space send buffer for the socket.
## @path gateway.exproto.listeners.udp.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Size of the user-space buffer for the socket.
## @path gateway.exproto.listeners.udp.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc Allow local reuse of port numbers.
## @path gateway.exproto.listeners.udp.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the listener.
## @path gateway.exproto.listeners.udp.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.exproto.listeners.udp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.exproto.listeners.udp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.exproto.listeners.udp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.exproto.listeners.udp.$name.authentication
## @link gateway.coap.listeners.udp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.exproto.listeners.udp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.udp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.exproto.listeners.dtls
## @type map()
## dtls:
## $name {
## @doc Size of the acceptor pool.
## @path gateway.exproto.listeners.dtls.$name.acceptors
## @type integer()
## acceptors: 16
## udp {
## @doc Specify the {active, N} option for the socket.
## See: https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.exproto.listeners.dtls.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Size of the kernel-space receive buffer for the socket.
## @path gateway.exproto.listeners.dtls.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Size of the kernel-space send buffer for the socket.
## @path gateway.exproto.listeners.dtls.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Size of the user-space buffer for the socket.
## @path gateway.exproto.listeners.dtls.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc Allow local reuse of port numbers.
## @path gateway.exproto.listeners.dtls.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc Enable the listener.
## @path gateway.exproto.listeners.dtls.$name.enable
## @type boolean()
## enable: true
## @doc The IP address and port that the listener will bind.
## @path gateway.exproto.listeners.dtls.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc Maximum number of concurrent connections.
## @path gateway.exproto.listeners.dtls.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc Maximum connections per second.
## @path gateway.exproto.listeners.dtls.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.exproto.listeners.dtls.$name.authentication
## @link gateway.coap.listeners.dtls.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc When publishing or subscribing, prefix all topics with a mountpoint string.
## The prefixed string will be removed from the topic name when the message is delivered to the subscriber. The mountpoint is a way that users can use to implement isolation of message routing between different listeners.
## For example if a client A subscribes to `t` with `listeners.tcp.<name>.mountpoint` set to `some_tenant`, then the client actually subscribes to the topic `some_tenant/t`. Similarly, if another client B (connected to the same listener as the client A) sends a message to topic `t`, the message is routed to all the clients subscribed `some_tenant/t`, so client A will receive the message, with topic name `t`. Set to `""` to disable the feature.
## Variables in mountpoint string:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path gateway.exproto.listeners.dtls.$name.mountpoint
## @type binary()
## mountpoint:
## @doc The access control rules for this listener.
## See: https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.dtls.$name
## @type array
## access_rules: []
## dtls {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path gateway.exproto.listeners.dtls.$name.dtls
## @type array
## versions: [dtlsv1.2, dtlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.listeners.dtls.$name.dtls
## @type array
## ciphers: ["ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Path to a file containing PEM-encoded Diffie-Hellman parameters
## to be used by the server if a cipher suite using Diffie-Hellman
## key exchange is negotiated. If not specified, default parameters
## are used.</br>
## NOTE: The <code>dhfile</code> option is not supported by TLS 1.3.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.dhfile
## @type string()
## dhfile:
## @doc
## Used together with {verify, verify_peer} by an TLS/DTLS server.
## If set to true, the server fails if the client does not have a
## certificate to send, that is, sends an empty certificate.
## If set to false, it fails only if the client sends an invalid
## certificate (an empty certificate is considered valid).
##
## @path gateway.exproto.listeners.dtls.$name.dtls.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## An important security setting, it forces the cipher to be set based
## on the server-specified order instead of the client-specified order,
## hence enforcing the (usually more properly configured) security
## ordering of the server administrator.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## In protocols that support client-initiated renegotiation,
## the cost of resources of such an operation is higher for the server than the client.
## This can act as a vector for denial of service attacks.
## The SSL application already takes measures to counter-act such attempts,
## but client-initiated renegotiation can be strictly disabled by setting this option to false.
## The default value is true. Note that disabling renegotiation can result in
## long-lived connections becoming unusable due to limits on
## the number of messages the underlying cipher suite can encipher.
##
## @path gateway.exproto.listeners.dtls.$name.dtls.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
}
## @doc Whether to enable this gateway
## @path gateway.exproto.enable
## @type boolean()
enable: true
## @doc Whether to enable client process statistic
## @path gateway.exproto.enable_stats
## @type boolean()
enable_stats: true
## @doc The idle time of the client connection process. It has two purposes:
## 1. A newly created client process that does not receive any client requests after that time will be closed directly.
## 2. A running client process that does not receive any client requests after this time will go into hibernation to save resources.
## @path gateway.exproto.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc Template for overriding username.
## @path gateway.exproto.clientinfo_override.username
## @type binary()
## username:
## @doc Template for overriding password.
## @path gateway.exproto.clientinfo_override.password
## @type binary()
## password:
## @doc Template for overriding clientid.
## @path gateway.exproto.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc Default authentication configs for all the gateway listeners. For per-listener overrides see <code>authentication</code>
## in listener configs
## @path gateway.exproto.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
}
prometheus {
## @doc URL of Prometheus server
## @path prometheus.push_gateway_server
## @type string()
push_gateway_server: "http://127.0.0.1:9091"
## @doc Data reporting interval, in milliseconds.
## @path prometheus.interval
## @type emqx_schema:duration_ms()
interval: "15s"
## @doc Turn Prometheus data pushing on or off
## @path prometheus.enable
## @type boolean()
enable: false
}
rule_engine {
## @doc When set to 'true' (default), rule-engine will ignore messages published to $SYS topics.
## @path rule_engine.ignore_sys_message
## @type boolean()
ignore_sys_message: true
## @doc The rules
## @path rule_engine.rules
## @type map()
rules: {}
## rules:
## $id {
## @doc The name of the rule
## @path rule_engine.rules.$id.name
## @type binary()
## name: ""
## @doc
## SQL query to transform the messages.
## Example: <code>SELECT * FROM "test/topic" WHERE payload.x = 1</code>
##
## @path rule_engine.rules.$id.sql
## @type binary()
## sql:
## @doc
## A list of outputs of the rule.
## An output can be a string that refers to the channel ID of an EMQX bridge, or an object
## that refers to a function.
## There a some built-in functions like "republish" and "console", and we also support user
## provided functions in the format: "{module}:{function}".
## The outputs in the list are executed sequentially.
## This means that if one of the output is executing slowly, all the following outputs will not
## be executed until it returns.
## If one of the output crashed, all other outputs come after it will still be executed, in the
## original order.
## If there's any error when running an output, there will be an error message, and the 'failure'
## counter of the function output or the bridge channel will increase.
##
## @path rule_engine.rules.$id
## @type array
## outputs: []
## @path rule_engine.rules.$id.outputs.$INDEX
## @type union: binary() | rule_engine:builtin_output_republish | rule_engine:builtin_output_console | rule_engine:user_provided_function
## $INDEX:
## @doc Enable or disable the rule
## @path rule_engine.rules.$id.enable
## @type boolean()
## enable: true
## @doc The description of the rule
## @path rule_engine.rules.$id.description
## @type binary()
## description: ""
## }
## @doc Default timeout for the `jq` rule engine function
## @path rule_engine.jq_function_default_timeout
## @type emqx_schema:duration_ms()
jq_function_default_timeout: "10s"
}
exhook {
## @doc List of exhook servers
## @path exhook
## @type array
servers: []
## $INDEX {
## @doc Name of the exhook server
## @path exhook.servers.$INDEX.name
## @type binary()
## name:
## @doc Enable this Exhook server
## @path exhook.servers.$INDEX.enable
## @type boolean()
## enable: true
## @doc URL of the gRPC server
## @path exhook.servers.$INDEX.url
## @type binary()
## url:
## @doc The timeout of request gRPC server
## @path exhook.servers.$INDEX.request_timeout
## @type emqx_exhook_schema:duration()
## request_timeout: "5s"
## @doc The value that is returned when the request to the gRPC server fails for any reason
## @path exhook.servers.$INDEX.failed_action
## @type enum: deny | ignore
## failed_action: deny
## ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path exhook.servers.$INDEX.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path exhook.servers.$INDEX.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path exhook.servers.$INDEX.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path exhook.servers.$INDEX.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path exhook.servers.$INDEX.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path exhook.servers.$INDEX.ssl.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path exhook.servers.$INDEX.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path exhook.servers.$INDEX.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path exhook.servers.$INDEX.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path exhook.servers.$INDEX.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Enable TLS.
##
## @path exhook.servers.$INDEX.ssl.enable
## @type boolean()
## enable: false
## @doc
## Specify the host name to be used in TLS Server Name Indication extension.</br>
## For instance, when connecting to "server.example.net", the genuine server
## which accepts the connection and performs TLS handshake may differ from the
## host the TLS client initially connects to, e.g. when connecting to an IP address
## or when the host has multiple resolvable DNS records </br>
## If not specified, it will default to the host name string which is used
## to establish the connection, unless it is IP addressed used.</br>
## The host name is then also used in the host name verification of the peer
## certificate.</br> The special value 'disable' prevents the Server Name
## Indication extension from being sent and disables the hostname
## verification check.
##
## @path exhook.servers.$INDEX.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
## }
## @doc Whether to automatically reconnect (initialize) the gRPC server.
## When gRPC is not available, Exhook tries to request the gRPC service at that interval and reinitialize the list of mounted hooks.
## @path exhook.servers.$INDEX.auto_reconnect
## @type union: false | emqx_exhook_schema:duration()
## auto_reconnect: "60s"
## @doc The process pool size for gRPC client
## @path exhook.servers.$INDEX.pool_size
## @type pos_integer()
## pool_size: 8
## }
}
psk_authentication {
## @doc Whether to enable TLS PSK support
## @path psk_authentication.enable
## @type boolean()
enable: false
## @doc If init_file is specified, EMQX will import PSKs from the file into the built-in database at startup for use by the runtime.
## The file has to be structured line-by-line, each line must be in the format of <code>PSKIdentity:SharedSecret</code>.
## For example: <code>mydevice1:c2VjcmV0</code>
## @path psk_authentication.init_file
## @type binary()
## init_file:
## @doc The separator between <code>PSKIdentity</code> and <code>SharedSecret</code> in the PSK file
## @path psk_authentication.separator
## @type binary()
separator: ":"
## @doc The size of each chunk used to import to the built-in database from PSK file
## @path psk_authentication.chunk_size
## @type integer()
chunk_size: 50
}
limiter {
bytes_in {
## @doc Enable
## @path limiter.bytes_in.enable
## @type boolean()
enable: true
## @doc Rate for this bucket.
## @path limiter.bytes_in.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc The burst, This value is based on rate.</br>
## This value + rate = the maximum limit that can be achieved when limiter burst.
## @path limiter.bytes_in.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc Bucket Configs
## @path limiter.bytes_in.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
message_in {
## @doc Enable
## @path limiter.message_in.enable
## @type boolean()
enable: true
## @doc Rate for this bucket.
## @path limiter.message_in.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc The burst, This value is based on rate.</br>
## This value + rate = the maximum limit that can be achieved when limiter burst.
## @path limiter.message_in.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc Bucket Configs
## @path limiter.message_in.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
connection {
## @doc Enable
## @path limiter.connection.enable
## @type boolean()
enable: true
## @doc Rate for this bucket.
## @path limiter.connection.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc The burst, This value is based on rate.</br>
## This value + rate = the maximum limit that can be achieved when limiter burst.
## @path limiter.connection.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc Bucket Configs
## @path limiter.connection.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
message_routing {
## @doc Enable
## @path limiter.message_routing.enable
## @type boolean()
enable: true
## @doc Rate for this bucket.
## @path limiter.message_routing.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc The burst, This value is based on rate.</br>
## This value + rate = the maximum limit that can be achieved when limiter burst.
## @path limiter.message_routing.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc Bucket Configs
## @path limiter.message_routing.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
batch {
## @doc Enable
## @path limiter.batch.enable
## @type boolean()
enable: true
## @doc Rate for this bucket.
## @path limiter.batch.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc The burst, This value is based on rate.</br>
## This value + rate = the maximum limit that can be achieved when limiter burst.
## @path limiter.batch.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc Bucket Configs
## @path limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
## bucket:
## $bucket_name {
## @doc Rate for this bucket.
## @path limiter.batch.bucket.$bucket_name.rate
## @type emqx_limiter_schema:rate()
## rate: "infinity"
## @doc The capacity of this token bucket.
## @path limiter.batch.bucket.$bucket_name.capacity
## @type emqx_limiter_schema:capacity()
## capacity: "infinity"
## @doc The initial number of tokens for this bucket.
## @path limiter.batch.bucket.$bucket_name.initial
## @type emqx_limiter_schema:initial()
## initial: "0"
## per_client {
## @doc Rate for this bucket.
## @path limiter.batch.bucket.$bucket_name.per_client.rate
## @type emqx_limiter_schema:rate()
## rate: "infinity"
## @doc The initial number of tokens for this bucket.
## @path limiter.batch.bucket.$bucket_name.per_client.initial
## @type emqx_limiter_schema:initial()
## initial: "0"
## @doc If the remaining tokens are lower than this value,
## the check/consume will succeed, but it will be forced to wait for a short period of time.
## @path limiter.batch.bucket.$bucket_name.per_client.low_watermark
## @type emqx_limiter_schema:initial()
## low_watermark: "0"
## @doc The capacity of per user.
## @path limiter.batch.bucket.$bucket_name.per_client.capacity
## @type emqx_limiter_schema:capacity()
## capacity: "infinity"
## @doc Is it possible to split the number of requested tokens?
## @path limiter.batch.bucket.$bucket_name.per_client.divisible
## @type boolean()
## divisible: false
## @doc The maximum retry time when acquire failed.
## @path limiter.batch.bucket.$bucket_name.per_client.max_retry_time
## @type emqx_schema:duration()
## max_retry_time: "10s"
## @doc The strategy when all the retries failed.
## @path limiter.batch.bucket.$bucket_name.per_client.failure_strategy
## @type emqx_limiter_schema:failure_strategy()
## failure_strategy: force
## }
## }
}
}
connectors {
## @doc MQTT bridges.
## @path connectors.mqtt
## @type map()
## mqtt:
## $name {
## @doc
## The mode of the MQTT Bridge. Can be one of 'cluster_singleton' or 'cluster_shareload'</br>
##
## - cluster_singleton: create a unique MQTT connection within the emqx cluster.</br>
## In 'cluster_singleton' node, all messages toward the remote broker go through the same
## MQTT connection.</br>
## - cluster_shareload: create an MQTT connection on each node in the emqx cluster.</br>
## In 'cluster_shareload' mode, the incoming load from the remote broker is shared by
## using shared subscription.</br>
## Note that the 'clientid' is suffixed by the node name, this is to avoid
## clientid conflicts between different nodes. And we can only use shared subscription
## topic filters for 'remote_topic' of ingress connections.
##
## @path connectors.mqtt.$name.mode
## @type enum: cluster_shareload
## mode: cluster_shareload
## @doc The host and port of the remote MQTT broker
## @path connectors.mqtt.$name.server
## @type emqx_schema:ip_port()
## server:
## @doc Reconnect interval. Delay for the MQTT bridge to retry establishing the connection in case of transportation failure. Time interval is a string that contains a number followed by time unit:</br>
## - `ms` for milliseconds,
## - `s` for seconds,
## - `m` for minutes,
## - `h` for hours;
## </br>or combination of whereof: `1h5m0s`
## @path connectors.mqtt.$name.reconnect_interval
## @type string()
## reconnect_interval: "15s"
## @doc The MQTT protocol version
## @path connectors.mqtt.$name.proto_ver
## @type enum: v3 | v4 | v5
## proto_ver: v4
## @doc
## If enable bridge mode.
## NOTE: This setting is only for MQTT protocol version older than 5.0, and the remote MQTT
## broker MUST support this feature.
##
## @path connectors.mqtt.$name.bridge_mode
## @type boolean()
## bridge_mode: false
## @doc The username of the MQTT protocol
## @path connectors.mqtt.$name.username
## @type binary()
## username: "emqx"
## @doc The password of the MQTT protocol
## @path connectors.mqtt.$name.password
## @type binary()
## password: "emqx"
## @doc The clean-start or the clean-session of the MQTT protocol
## @path connectors.mqtt.$name.clean_start
## @type boolean()
## clean_start: true
## @doc MQTT Keepalive. Time interval is a string that contains a number followed by time unit:</br>
## - `ms` for milliseconds,
## - `s` for seconds,
## - `m` for minutes,
## - `h` for hours;
## </br>or combination of whereof: `1h5m0s`
## @path connectors.mqtt.$name.keepalive
## @type string()
## keepalive: "300s"
## @doc Message retry interval. Delay for the MQTT bridge to retry sending the QoS1/QoS2 messages in case of ACK not received. Time interval is a string that contains a number followed by time unit:</br>
## - `ms` for milliseconds,
## - `s` for seconds,
## - `m` for minutes,
## - `h` for hours;
## </br>or combination of whereof: `1h5m0s`
## @path connectors.mqtt.$name.retry_interval
## @type string()
## retry_interval: "15s"
## @doc Max inflight (sent, but un-acked) messages of the MQTT protocol
## @path connectors.mqtt.$name.max_inflight
## @type non_neg_integer()
## max_inflight: 32
## replayq {
## @doc
## The dir where the replayq file saved.</br>
## Set to 'false' disables the replayq feature.
##
## @path connectors.mqtt.$name.replayq.dir
## @type union: boolean() | string()
## dir:
## @doc
## The size in bytes of a single segment.</br>
## A segment is mapping to a file in the replayq dir. If the current segment is full, a new segment
## (file) will be opened to write.
##
## @path connectors.mqtt.$name.replayq.seg_bytes
## @type emqx_schema:bytesize()
## seg_bytes: "100MB"
## @doc
## In offload mode, the disk queue is only used to offload queue tail segments.</br>
## The messages are cached in the memory first, then it writes to the replayq files after the size of
## the memory cache reaches 'seg_bytes'.
##
## @path connectors.mqtt.$name.replayq.offload
## @type boolean()
## offload: false
## }
## ssl {
## @doc
## Trusted PEM format CA certificates bundle file.</br>
## The certificates in this file are used to verify the TLS peer's certificates.
## Append new certificates to the file if new CAs are to be trusted.
## There is no need to restart EMQX to have the updated file loaded, because
## the system regularly checks if file has been updated (and reload).</br>
## NOTE: invalidating (deleting) a certificate from the file will not affect
## already established connections.
##
## @path connectors.mqtt.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM format certificates chain file.</br>
## The certificates in this file should be in reversed order of the certificate
## issue chain. That is, the host's certificate should be placed in the beginning
## of the file, followed by the immediate issuer certificate and so on.
## Although the root CA certificate is optional, it should be placed at the end of
## the file if it is to be added.
##
## @path connectors.mqtt.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM format private key file.
##
## @path connectors.mqtt.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## Enable or disable peer verification.
##
## @path connectors.mqtt.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## Enable TLS session reuse.
##
## @path connectors.mqtt.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## Maximum number of non-self-issued intermediate certificates that can follow the peer certificate in a valid certification path. So, if depth is 0 the PEER must be signed by the trusted ROOT-CA directly; if 1 the path can be PEER, CA, ROOT-CA; if 2 the path can be PEER, CA, CA, ROOT-CA, and so on. The default value is 10.
##
## @path connectors.mqtt.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## String containing the user's password.
## Only used if the private key file is password-protected.
##
## @path connectors.mqtt.$name.ssl.password
## @type string()
## password:
## @doc
## All TLS/DTLS versions to be supported.</br>
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config.</br>
## In case PSK cipher suites are intended, make sure to configured
## <code>['tlsv1.2', 'tlsv1.1']</code> here.
##
## @path connectors.mqtt.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## This config holds TLS cipher suite names separated by comma,
## or as an array of strings. e.g.
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code> or
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>.
## </br>
## Ciphers (and their ordering) define the way in which the
## client and server encrypts information over the network connection.
## Selecting a good cipher suite is critical for the
## application's data security, confidentiality and performance.
##
## The names should be in OpenSSL string format (not RFC format).
## All default values and examples provided by EMQX config
## documentation are all in OpenSSL format.</br>
##
## NOTE: Certain cipher suites are only compatible with
## specific TLS <code>versions</code> ('tlsv1.1', 'tlsv1.2' or 'tlsv1.3')
## incompatible cipher suites will be silently dropped.
## For instance, if only 'tlsv1.3' is given in the <code>versions</code>,
## configuring cipher suites for other versions will have no effect.
## </br>
##
## NOTE: PSK ciphers are suppressed by 'tlsv1.3' version config</br>
## If PSK cipher suites are intended, 'tlsv1.3' should be disabled from <code>versions</code>.</br>
## PSK cipher suites: <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path connectors.mqtt.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## EMQX-internal callback that is used to lookup pre-shared key (PSK) identity.
##
## @path connectors.mqtt.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL parameter renegotiation is a feature that allows a client and a server
## to renegotiate the parameters of the SSL connection on the fly.
## RFC 5746 defines a more secure way of doing this. By enabling secure renegotiation,
## you drop support for the insecure renegotiation, prone to MitM attacks.
##
## @path connectors.mqtt.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## Enable TLS.
##
## @path connectors.mqtt.$name.ssl.enable
## @type boolean()
## enable: false
## @doc
## Specify the host name to be used in TLS Server Name Indication extension.</br>
## For instance, when connecting to "server.example.net", the genuine server
## which accepts the connection and performs TLS handshake may differ from the
## host the TLS client initially connects to, e.g. when connecting to an IP address
## or when the host has multiple resolvable DNS records </br>
## If not specified, it will default to the host name string which is used
## to establish the connection, unless it is IP addressed used.</br>
## The host name is then also used in the host name verification of the peer
## certificate.</br> The special value 'disable' prevents the Server Name
## Indication extension from being sent and disables the hostname
## verification check.
##
## @path connectors.mqtt.$name.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
## }
## }
}
slow_subs {
## @doc Enable this feature
## @path slow_subs.enable
## @type boolean()
enable: false
## @doc The latency threshold for statistics
## @path slow_subs.threshold
## @type emqx_schema:duration_ms()
threshold: "500ms"
## @doc The eviction time of the record, which in the statistics record table
## @path slow_subs.expire_interval
## @type emqx_schema:duration_ms()
expire_interval: "300s"
## @doc The maximum number of records in the slow subscription statistics record table
## @path slow_subs.top_k_num
## @type pos_integer()
top_k_num: 10
## @doc The method to calculate the latency
## @path slow_subs.stats_type
## @type enum: whole | internal | response
stats_type: whole
}
## Title
## Body
listeners {
## @doc TCP 监听器
## @path listeners.tcp
## @type map()
## tcp:
## $default {
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.tcp.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path listeners.tcp.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path listeners.tcp.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path listeners.tcp.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path listeners.tcp.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path listeners.tcp.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path listeners.tcp.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path listeners.tcp.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path listeners.tcp.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path listeners.tcp.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc
## 监听套接字的 IP 地址和端口。
##
## @path listeners.tcp.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc 监听器接收池的大小。
## @path listeners.tcp.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## 监听器允许的最大并发连接数。
##
## @path listeners.tcp.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## 发布或订阅时,请在所有主题前面加上 mountpoint 字符串。
##
## 将消息传递给订阅者时,将从主题名称中删除带前缀的字符串。挂载点是一种用户可以用来实现不同侦听器之间消息路由隔离的方法。
##
## 例如,如果客户机 A 使用 <code>listeners.tcp.<name>.mountpoint</code> 设置为'some_tenant',那么客户端实际上订阅了主题'some_tenant/t'。</br>
## 类似地,如果另一个客户端B(与客户端A连接到同一个侦听器)向主题 't' 发送消息,该消息将路由到所有订阅了'some_租户/t'的客户端,因此客户端 A 将接收主题名为't'的消息</br>
##
## 设置为<code>""</code> 以禁用该功能</br>
##
## mountpoint 字符串中的变量:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.tcp.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## 监听器所属的配置组。
##
## @path listeners.tcp.$default.zone
## @type atom()
## zone: default
## @doc
## 速率限制类型
##
## @path listeners.tcp.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.tcp.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc 此监听器的访问控制规则。
## @path listeners.tcp.$default
## @type array
## access_rules: ["allow all"]
## @doc
## 如果EMQX集群部署在 HAProxy 或 Nginx 之后,请启用代理协议 V1/2 </br>
## 详情见: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.tcp.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## 代理协议超时。如果在超时时间内未收到代理协议数据包,EMQX将关闭TCP连接。
##
## @path listeners.tcp.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## 监听器认证重载。
##
## 认证配置可以是单个认证器实例,也可以是一个认证器数组组成的认证链。
## 执行登录验证时(用户名、客户端 ID 等),将按配置的顺序执行</br>
##
## @path listeners.tcp.$default
## @type array
## authentication: []
## @path listeners.tcp.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc SSL 监听器
## @path listeners.ssl
## @type map()
## ssl:
## $default {
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.ssl.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path listeners.ssl.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path listeners.ssl.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path listeners.ssl.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path listeners.ssl.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path listeners.ssl.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path listeners.ssl.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path listeners.ssl.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path listeners.ssl.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path listeners.ssl.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path listeners.ssl.$default.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path listeners.ssl.$default.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path listeners.ssl.$default.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path listeners.ssl.$default.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path listeners.ssl.$default.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path listeners.ssl.$default.ssl.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path listeners.ssl.$default.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path listeners.ssl.$default.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path listeners.ssl.$default.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path listeners.ssl.$default.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path listeners.ssl.$default.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path listeners.ssl.$default.ssl.dhfile
## @type string()
## dhfile:
## @doc
## TLS/DTLS 服务器与 {verify,verify_peer} 一起使用。
## 如果设置为true,则如果客户端没有要发送的证书,即发送空证书,服务器将失败。
## 如果设置为false,则仅当客户端发送无效证书(空证书被视为有效证书)时才会失败。
##
## @path listeners.ssl.$default.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path listeners.ssl.$default.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path listeners.ssl.$default.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## @doc
## 监听套接字的 IP 地址和端口。
##
## @path listeners.ssl.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc 监听器接收池的大小。
## @path listeners.ssl.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## 监听器允许的最大并发连接数。
##
## @path listeners.ssl.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## 发布或订阅时,请在所有主题前面加上 mountpoint 字符串。
##
## 将消息传递给订阅者时,将从主题名称中删除带前缀的字符串。挂载点是一种用户可以用来实现不同侦听器之间消息路由隔离的方法。
##
## 例如,如果客户机 A 使用 <code>listeners.tcp.<name>.mountpoint</code> 设置为'some_tenant',那么客户端实际上订阅了主题'some_tenant/t'。</br>
## 类似地,如果另一个客户端B(与客户端A连接到同一个侦听器)向主题 't' 发送消息,该消息将路由到所有订阅了'some_租户/t'的客户端,因此客户端 A 将接收主题名为't'的消息</br>
##
## 设置为<code>""</code> 以禁用该功能</br>
##
## mountpoint 字符串中的变量:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.ssl.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## 监听器所属的配置组。
##
## @path listeners.ssl.$default.zone
## @type atom()
## zone: default
## @doc
## 速率限制类型
##
## @path listeners.ssl.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.ssl.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc 此监听器的访问控制规则。
## @path listeners.ssl.$default
## @type array
## access_rules: ["allow all"]
## @doc
## 如果EMQX集群部署在 HAProxy 或 Nginx 之后,请启用代理协议 V1/2 </br>
## 详情见: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.ssl.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## 代理协议超时。如果在超时时间内未收到代理协议数据包,EMQX将关闭TCP连接。
##
## @path listeners.ssl.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## 监听器认证重载。
##
## 认证配置可以是单个认证器实例,也可以是一个认证器数组组成的认证链。
## 执行登录验证时(用户名、客户端 ID 等),将按配置的顺序执行</br>
##
## @path listeners.ssl.$default
## @type array
## authentication: []
## @path listeners.ssl.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc HTTP websocket 监听器
## @path listeners.ws
## @type map()
## ws:
## $default {
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.ws.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path listeners.ws.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path listeners.ws.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path listeners.ws.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path listeners.ws.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path listeners.ws.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path listeners.ws.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path listeners.ws.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path listeners.ws.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path listeners.ws.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## websocket {
## @doc
## WebSocket 的 MQTT 协议路径。因此,EMQX Broker的WebSocket地址为:
## <code>ws://{ip}:{port}/mqtt</code>
##
## @path listeners.ws.$default.websocket.mqtt_path
## @type string()
## mqtt_path: "/mqtt"
## @doc
## WebSocket消息是否允许包含多个 MQTT 数据包。
##
## @path listeners.ws.$default.websocket.mqtt_piggyback
## @type enum: single | multiple
## mqtt_piggyback: multiple
## @doc
## 如果 <code>true</code>,则使用<code>zlib</code> 压缩 WebSocket 消息</br>
## <code>deflate_opts</code> 下的配置项属于压缩相关参数配置。
##
## @path listeners.ws.$default.websocket.compress
## @type boolean()
## compress: false
## @doc
## 关闭在此间隔内未发送 MQTT CONNECT 消息的客户端的传输层连接。
##
## @path listeners.ws.$default.websocket.idle_timeout
## @type emqx_schema:duration()
## idle_timeout: "15s"
## @doc
## 单个 MQTT 数据包的最大长度。
##
## @path listeners.ws.$default.websocket.max_frame_size
## @type union: infinity | integer()
## max_frame_size: infinity
## @doc
## 如果<code>true</code>,当客户端未携带<code>Sec WebSocket Protocol</code>字段时,服务器将返回一个错误。
## </br>注意:微信小程序需要禁用此验证。
##
## @path listeners.ws.$default.websocket.fail_if_no_subprotocol
## @type boolean()
## fail_if_no_subprotocol: true
## @doc
## 逗号分隔的 subprotocols 支持列表。
##
## @path listeners.ws.$default.websocket.supported_subprotocols
## @type emqx_schema:comma_separated_list()
## supported_subprotocols: "mqtt, mqtt-v3, mqtt-v3.1.1, mqtt-v5"
## @doc
## 如果<code>true</code>,<code>origin</code>HTTP 头将根据<code>check_origins</code>参数中配置的允许来源列表进行验证。
##
## @path listeners.ws.$default.websocket.check_origin_enable
## @type boolean()
## check_origin_enable: false
## @doc
## If <code>false</code> and <code>check_origin_enable</code> is <code>true</code>, the server will reject requests that don't have <code>origin</code> HTTP header.
##
## @path listeners.ws.$default.websocket.allow_origin_absence
## @type boolean()
## allow_origin_absence: true
## @doc
## 允许的 origins 列表
##
## @path listeners.ws.$default.websocket
## @type array
## check_origins: []
## @doc
## HTTP 头,用于传递有关客户端 IP 地址的信息。
## 当 EMQX 集群部署在负载平衡器后面时,这一点非常重要。
##
## @path listeners.ws.$default.websocket.proxy_address_header
## @type string()
## proxy_address_header: "x-forwarded-for"
## @doc
## HTTP 头,用于传递有关客户端端口的信息。
## 当 EMQX 集群部署在负载平衡器后面时,这一点非常重要。
##
## @path listeners.ws.$default.websocket.proxy_port_header
## @type string()
## proxy_port_header: "x-forwarded-port"
## deflate_opts {
## @doc 压缩级别
## @path listeners.ws.$default.websocket.deflate_opts.level
## @type enum: none | default | best_compression | best_speed
## level: none
## @doc
## 指定压缩状态的大小</br>
## 较低的值会减少每个连接的内存使用。
##
## @path listeners.ws.$default.websocket.deflate_opts.mem_level
## @type 1..9
## mem_level: 8
## @doc
## 指定压缩策略。
##
## @path listeners.ws.$default.websocket.deflate_opts.strategy
## @type enum: default | filtered | huffman_only | rle
## strategy: default
## @doc 接管意味着在服务器消息之间保留压缩状态。
## @path listeners.ws.$default.websocket.deflate_opts.server_context_takeover
## @type enum: takeover | no_takeover
## server_context_takeover: takeover
## @doc
## 接管意味着在客户端消息之间保留压缩状态。
##
## @path listeners.ws.$default.websocket.deflate_opts.client_context_takeover
## @type enum: takeover | no_takeover
## client_context_takeover: takeover
## @doc
## 指定服务器压缩上下文的大小。
##
## @path listeners.ws.$default.websocket.deflate_opts.server_max_window_bits
## @type 8..15
## server_max_window_bits: 15
## @doc
## 指定客户端压缩上下文的大小。
##
## @path listeners.ws.$default.websocket.deflate_opts.client_max_window_bits
## @type 8..15
## client_max_window_bits: 15
## }
## }
## @doc
## 监听套接字的 IP 地址和端口。
##
## @path listeners.ws.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc 监听器接收池的大小。
## @path listeners.ws.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## 监听器允许的最大并发连接数。
##
## @path listeners.ws.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## 发布或订阅时,请在所有主题前面加上 mountpoint 字符串。
##
## 将消息传递给订阅者时,将从主题名称中删除带前缀的字符串。挂载点是一种用户可以用来实现不同侦听器之间消息路由隔离的方法。
##
## 例如,如果客户机 A 使用 <code>listeners.tcp.<name>.mountpoint</code> 设置为'some_tenant',那么客户端实际上订阅了主题'some_tenant/t'。</br>
## 类似地,如果另一个客户端B(与客户端A连接到同一个侦听器)向主题 't' 发送消息,该消息将路由到所有订阅了'some_租户/t'的客户端,因此客户端 A 将接收主题名为't'的消息</br>
##
## 设置为<code>""</code> 以禁用该功能</br>
##
## mountpoint 字符串中的变量:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.ws.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## 监听器所属的配置组。
##
## @path listeners.ws.$default.zone
## @type atom()
## zone: default
## @doc
## 速率限制类型
##
## @path listeners.ws.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.ws.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc 此监听器的访问控制规则。
## @path listeners.ws.$default
## @type array
## access_rules: ["allow all"]
## @doc
## 如果EMQX集群部署在 HAProxy 或 Nginx 之后,请启用代理协议 V1/2 </br>
## 详情见: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.ws.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## 代理协议超时。如果在超时时间内未收到代理协议数据包,EMQX将关闭TCP连接。
##
## @path listeners.ws.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## 监听器认证重载。
##
## 认证配置可以是单个认证器实例,也可以是一个认证器数组组成的认证链。
## 执行登录验证时(用户名、客户端 ID 等),将按配置的顺序执行</br>
##
## @path listeners.ws.$default
## @type array
## authentication: []
## @path listeners.ws.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc HTTPS websocket 监听器
## @path listeners.wss
## @type map()
## wss:
## $default {
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path listeners.wss.$default.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path listeners.wss.$default.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path listeners.wss.$default.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path listeners.wss.$default.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path listeners.wss.$default.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path listeners.wss.$default.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path listeners.wss.$default.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path listeners.wss.$default.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path listeners.wss.$default.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path listeners.wss.$default.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path listeners.wss.$default.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path listeners.wss.$default.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path listeners.wss.$default.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path listeners.wss.$default.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path listeners.wss.$default.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path listeners.wss.$default.ssl.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path listeners.wss.$default.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path listeners.wss.$default.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path listeners.wss.$default.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path listeners.wss.$default.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path listeners.wss.$default.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path listeners.wss.$default.ssl.dhfile
## @type string()
## dhfile:
## @doc
## TLS/DTLS 服务器与 {verify,verify_peer} 一起使用。
## 如果设置为true,则如果客户端没有要发送的证书,即发送空证书,服务器将失败。
## 如果设置为false,则仅当客户端发送无效证书(空证书被视为有效证书)时才会失败。
##
## @path listeners.wss.$default.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path listeners.wss.$default.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path listeners.wss.$default.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## @doc
## 握手完成所允许的最长时间
##
## @path listeners.wss.$default.ssl.handshake_timeout
## @type emqx_schema:duration()
## handshake_timeout: "15s"
## }
## websocket {
## @doc
## WebSocket 的 MQTT 协议路径。因此,EMQX Broker的WebSocket地址为:
## <code>ws://{ip}:{port}/mqtt</code>
##
## @path listeners.wss.$default.websocket.mqtt_path
## @type string()
## mqtt_path: "/mqtt"
## @doc
## WebSocket消息是否允许包含多个 MQTT 数据包。
##
## @path listeners.wss.$default.websocket.mqtt_piggyback
## @type enum: single | multiple
## mqtt_piggyback: multiple
## @doc
## 如果 <code>true</code>,则使用<code>zlib</code> 压缩 WebSocket 消息</br>
## <code>deflate_opts</code> 下的配置项属于压缩相关参数配置。
##
## @path listeners.wss.$default.websocket.compress
## @type boolean()
## compress: false
## @doc
## 关闭在此间隔内未发送 MQTT CONNECT 消息的客户端的传输层连接。
##
## @path listeners.wss.$default.websocket.idle_timeout
## @type emqx_schema:duration()
## idle_timeout: "15s"
## @doc
## 单个 MQTT 数据包的最大长度。
##
## @path listeners.wss.$default.websocket.max_frame_size
## @type union: infinity | integer()
## max_frame_size: infinity
## @doc
## 如果<code>true</code>,当客户端未携带<code>Sec WebSocket Protocol</code>字段时,服务器将返回一个错误。
## </br>注意:微信小程序需要禁用此验证。
##
## @path listeners.wss.$default.websocket.fail_if_no_subprotocol
## @type boolean()
## fail_if_no_subprotocol: true
## @doc
## 逗号分隔的 subprotocols 支持列表。
##
## @path listeners.wss.$default.websocket.supported_subprotocols
## @type emqx_schema:comma_separated_list()
## supported_subprotocols: "mqtt, mqtt-v3, mqtt-v3.1.1, mqtt-v5"
## @doc
## 如果<code>true</code>,<code>origin</code>HTTP 头将根据<code>check_origins</code>参数中配置的允许来源列表进行验证。
##
## @path listeners.wss.$default.websocket.check_origin_enable
## @type boolean()
## check_origin_enable: false
## @doc
## If <code>false</code> and <code>check_origin_enable</code> is <code>true</code>, the server will reject requests that don't have <code>origin</code> HTTP header.
##
## @path listeners.wss.$default.websocket.allow_origin_absence
## @type boolean()
## allow_origin_absence: true
## @doc
## 允许的 origins 列表
##
## @path listeners.wss.$default.websocket
## @type array
## check_origins: []
## @doc
## HTTP 头,用于传递有关客户端 IP 地址的信息。
## 当 EMQX 集群部署在负载平衡器后面时,这一点非常重要。
##
## @path listeners.wss.$default.websocket.proxy_address_header
## @type string()
## proxy_address_header: "x-forwarded-for"
## @doc
## HTTP 头,用于传递有关客户端端口的信息。
## 当 EMQX 集群部署在负载平衡器后面时,这一点非常重要。
##
## @path listeners.wss.$default.websocket.proxy_port_header
## @type string()
## proxy_port_header: "x-forwarded-port"
## deflate_opts {
## @doc 压缩级别
## @path listeners.wss.$default.websocket.deflate_opts.level
## @type enum: none | default | best_compression | best_speed
## level: none
## @doc
## 指定压缩状态的大小</br>
## 较低的值会减少每个连接的内存使用。
##
## @path listeners.wss.$default.websocket.deflate_opts.mem_level
## @type 1..9
## mem_level: 8
## @doc
## 指定压缩策略。
##
## @path listeners.wss.$default.websocket.deflate_opts.strategy
## @type enum: default | filtered | huffman_only | rle
## strategy: default
## @doc 接管意味着在服务器消息之间保留压缩状态。
## @path listeners.wss.$default.websocket.deflate_opts.server_context_takeover
## @type enum: takeover | no_takeover
## server_context_takeover: takeover
## @doc
## 接管意味着在客户端消息之间保留压缩状态。
##
## @path listeners.wss.$default.websocket.deflate_opts.client_context_takeover
## @type enum: takeover | no_takeover
## client_context_takeover: takeover
## @doc
## 指定服务器压缩上下文的大小。
##
## @path listeners.wss.$default.websocket.deflate_opts.server_max_window_bits
## @type 8..15
## server_max_window_bits: 15
## @doc
## 指定客户端压缩上下文的大小。
##
## @path listeners.wss.$default.websocket.deflate_opts.client_max_window_bits
## @type 8..15
## client_max_window_bits: 15
## }
## }
## @doc
## 监听套接字的 IP 地址和端口。
##
## @path listeners.wss.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc 监听器接收池的大小。
## @path listeners.wss.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## 监听器允许的最大并发连接数。
##
## @path listeners.wss.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## 发布或订阅时,请在所有主题前面加上 mountpoint 字符串。
##
## 将消息传递给订阅者时,将从主题名称中删除带前缀的字符串。挂载点是一种用户可以用来实现不同侦听器之间消息路由隔离的方法。
##
## 例如,如果客户机 A 使用 <code>listeners.tcp.<name>.mountpoint</code> 设置为'some_tenant',那么客户端实际上订阅了主题'some_tenant/t'。</br>
## 类似地,如果另一个客户端B(与客户端A连接到同一个侦听器)向主题 't' 发送消息,该消息将路由到所有订阅了'some_租户/t'的客户端,因此客户端 A 将接收主题名为't'的消息</br>
##
## 设置为<code>""</code> 以禁用该功能</br>
##
## mountpoint 字符串中的变量:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.wss.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## 监听器所属的配置组。
##
## @path listeners.wss.$default.zone
## @type atom()
## zone: default
## @doc
## 速率限制类型
##
## @path listeners.wss.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.wss.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## @doc 此监听器的访问控制规则。
## @path listeners.wss.$default
## @type array
## access_rules: ["allow all"]
## @doc
## 如果EMQX集群部署在 HAProxy 或 Nginx 之后,请启用代理协议 V1/2 </br>
## 详情见: https://www.haproxy.com/blog/haproxy/proxy-protocol/
##
## @path listeners.wss.$default.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc
## 代理协议超时。如果在超时时间内未收到代理协议数据包,EMQX将关闭TCP连接。
##
## @path listeners.wss.$default.proxy_protocol_timeout
## @type emqx_schema:duration()
## proxy_protocol_timeout: "3s"
## @doc
## 监听器认证重载。
##
## 认证配置可以是单个认证器实例,也可以是一个认证器数组组成的认证链。
## 执行登录验证时(用户名、客户端 ID 等),将按配置的顺序执行</br>
##
## @path listeners.wss.$default
## @type array
## authentication: []
## @path listeners.wss.$default.authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## }
## @doc QUIC 监听器
## @path listeners.quic
## @type map()
## quic:
## $default {
## @doc 启用 QUIC 监听器
## @path listeners.quic.$default.enabled
## @type boolean()
## enabled: true
## @doc 证书文件
## @path listeners.quic.$default.certfile
## @type string()
## certfile:
## @doc 私钥文件
## @path listeners.quic.$default.keyfile
## @type string()
## keyfile:
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件,<code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## 注:QUIC 监听器不支持 tlsv1.3 的 ciphers
##
## @path listeners.quic.$default
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256"]
## @doc
## 关闭在此间隔内未发送 MQTT CONNECT 消息的客户端的传输层连接。
##
## @path listeners.quic.$default.idle_timeout
## @type emqx_schema:duration()
## idle_timeout: "15s"
## @doc
## 监听套接字的 IP 地址和端口。
##
## @path listeners.quic.$default.bind
## @type union: emqx_schema:ip_port() | integer()
## bind:
## @doc 监听器接收池的大小。
## @path listeners.quic.$default.acceptors
## @type pos_integer()
## acceptors: 16
## @doc
## 监听器允许的最大并发连接数。
##
## @path listeners.quic.$default.max_connections
## @type union: infinity | pos_integer()
## max_connections: infinity
## @doc
## 发布或订阅时,请在所有主题前面加上 mountpoint 字符串。
##
## 将消息传递给订阅者时,将从主题名称中删除带前缀的字符串。挂载点是一种用户可以用来实现不同侦听器之间消息路由隔离的方法。
##
## 例如,如果客户机 A 使用 <code>listeners.tcp.<name>.mountpoint</code> 设置为'some_tenant',那么客户端实际上订阅了主题'some_tenant/t'。</br>
## 类似地,如果另一个客户端B(与客户端A连接到同一个侦听器)向主题 't' 发送消息,该消息将路由到所有订阅了'some_租户/t'的客户端,因此客户端 A 将接收主题名为't'的消息</br>
##
## 设置为<code>""</code> 以禁用该功能</br>
##
## mountpoint 字符串中的变量:
## - <code>${clientid}</code>: clientid
## - <code>${username}</code>: username
##
## @path listeners.quic.$default.mountpoint
## @type binary()
## mountpoint: ""
## @doc
## 监听器所属的配置组。
##
## @path listeners.quic.$default.zone
## @type atom()
## zone: default
## @doc
## 速率限制类型
##
## @path listeners.quic.$default.limiter
## @type map()
## limiter: {}
## limiter:
## @path listeners.quic.$default.limiter.$ratelimit_name
## @type emqx_limiter_schema:bucket_name()
## $ratelimit_name:
## }
}
## @doc <code>zone</code> 是按<code>name</code> 分组的一组配置。
## 对于灵活的配置映射,可以将 <code>name</code> 设置为侦听器的 <code>zone</code> 配置。
## 注:名为 <code>default</code> 的内置区域是自动创建的,无法删除。
## @doc <code>zone</code> 是按<code>name</code> 分组的一组配置。
## 对于灵活的配置映射,可以将 <code>name</code> 设置为侦听器的 <code>zone</code> 配置。
## 注:名为 <code>default</code> 的内置区域是自动创建的,无法删除。
## @path zones
## @type map()
## zones:
## $my_zone_name {
## mqtt {
## @doc TCP 连接建立后,如果在 <code>idle_timeout</code> 指定的时间内未收到客户端的 MQTT CONNECT 报文,则连接将被断开。
## @path zones.$my_zone_name.mqtt.idle_timeout
## @type union: infinity | emqx_schema:duration()
## idle_timeout:
## @doc 允许的最大 MQTT 报文大小。
## @path zones.$my_zone_name.mqtt.max_packet_size
## @type emqx_schema:bytesize()
## max_packet_size:
## @doc 允许的最大 MQTT Client ID 长度。
## @path zones.$my_zone_name.mqtt.max_clientid_len
## @type 23..65535
## max_clientid_len:
## @doc 允许的最大主题层级。
## @path zones.$my_zone_name.mqtt.max_topic_levels
## @type 1..65535
## max_topic_levels:
## @doc 允许的最大 QoS 等级。
## @path zones.$my_zone_name.mqtt.max_qos_allowed
## @type qos()
## max_qos_allowed:
## @doc 允许的最大主题别名数,0 表示不支持主题别名。
## @path zones.$my_zone_name.mqtt.max_topic_alias
## @type 0..65535
## max_topic_alias:
## @doc 是否启用对 MQTT 保留消息的支持。
## @path zones.$my_zone_name.mqtt.retain_available
## @type boolean()
## retain_available:
## @doc 是否启用对 MQTT 通配符订阅的支持。
## @path zones.$my_zone_name.mqtt.wildcard_subscription
## @type boolean()
## wildcard_subscription:
## @doc 是否启用对 MQTT 共享订阅的支持。
## @path zones.$my_zone_name.mqtt.shared_subscription
## @type boolean()
## shared_subscription:
## @doc 是否为 MQTT v3.1.1/v3.1.0 客户端忽略投递自己发布的消息,类似于 MQTT 5.0 中的 <code>No Local</code> 订阅选项
## @path zones.$my_zone_name.mqtt.ignore_loop_deliver
## @type boolean()
## ignore_loop_deliver:
## @doc 是否以严格模式解析 MQTT 消息。
## 当设置为 true 时,例如客户端 ID、主题名称等中的无效 utf8 字符串将导致客户端断开连接。
## @path zones.$my_zone_name.mqtt.strict_mode
## @type boolean()
## strict_mode:
## @doc 指定返回给客户端的响应信息。如果设置为 "",则禁用此功能。仅适用于使用 MQTT 5.0 协议的客户端。
## @path zones.$my_zone_name.mqtt.response_information
## @type string()
## response_information:
## @doc EMQX 要求客户端使用的保活时间,配置为 <code>disabled</code> 表示将使用客户端指定的保活时间。需要用到 MQTT 5.0 中的 <code>Server Keep Alive</code>,因此仅适用于使用 MQTT 5.0 协议的客户端。
## @path zones.$my_zone_name.mqtt.server_keepalive
## @type union: integer() | disabled
## server_keepalive:
## @doc Broker 判定客户端保活超时使用的退避乘数。如果 EMQX 在 <code>Keep Alive * Backoff * 2</code> 秒内未收到任何报文,EMQX 将关闭当前连接。
## @path zones.$my_zone_name.mqtt.keepalive_backoff
## @type float()
## keepalive_backoff:
## @doc 允许每个客户端建立的最大订阅数量。
## @path zones.$my_zone_name.mqtt.max_subscriptions
## @type union: 1..inf | infinity
## max_subscriptions:
## @doc 投递消息时,是否根据订阅主题时的 QoS 等级来强制提升派发的消息的 QoS 等级。
## @path zones.$my_zone_name.mqtt.upgrade_qos
## @type boolean()
## upgrade_qos:
## @doc 允许在完成应答前同时投递的 QoS 1 和 QoS 2 消息的最大数量。
## @path zones.$my_zone_name.mqtt.max_inflight
## @type 1..65535
## max_inflight:
## @doc QoS 1/2 消息的重新投递间隔。
## @path zones.$my_zone_name.mqtt.retry_interval
## @type emqx_schema:duration()
## retry_interval:
## @doc PUBREL (Client -> Broker) 最大等待队列长度。
## @path zones.$my_zone_name.mqtt.max_awaiting_rel
## @type union: integer() | infinity
## max_awaiting_rel:
## @doc PUBREL (Client -> Broker) 最大等待时间,超时则会被丢弃。
## @path zones.$my_zone_name.mqtt.await_rel_timeout
## @type emqx_schema:duration()
## await_rel_timeout:
## @doc 指定会话将在连接断开后多久过期,仅适用于非 MQTT 5.0 的连接。
## @path zones.$my_zone_name.mqtt.session_expiry_interval
## @type emqx_schema:duration()
## session_expiry_interval:
## @doc 消息队列最大长度。持久客户端断开连接或飞行窗口已满时排队的消息长度。
## @path zones.$my_zone_name.mqtt.max_mqueue_len
## @type union: non_neg_integer() | infinity
## max_mqueue_len:
## @doc 主题优先级。取值范围 [1-255]
## 默认优先级表为空,即所有的主题优先级相同。
##
## 注:优先主题名称中不支持使用逗号和等号。
## 注:不在此列表中的主题,被视为最高/最低优先级,这取决于<code>mqtt.mqueue_default_priority</code> 的配置
##
## 示例:
## 配置 <code>"topic/1" > "topic/2"</code>:
## <code>mqueue_priorities: {"topic/1": 10, "topic/2": 8}</code>
##
## @path zones.$my_zone_name.mqtt.mqueue_priorities
## @type union: map() | disabled
## mqueue_priorities:
## @doc 默认的主题优先级,不在 <code>主题优先级</code>(<code>mqueue_priorities</code>) 中的主题将会使用该优先级。
## @path zones.$my_zone_name.mqtt.mqueue_default_priority
## @type enum: highest | lowest
## mqueue_default_priority: highest
## @doc 指定在连接断开但会话保持期间,是否需要在消息队列中存储 QoS 0 消息。
## @path zones.$my_zone_name.mqtt.mqueue_store_qos0
## @type boolean()
## mqueue_store_qos0:
## @doc 是否使用用户名作为客户端 ID。
## 此设置的作用时间晚于 <code>使用对端证书作为用户名</code>(<code>peer_cert_as_username</code>) 和 <code>使用对端证书作为客户端 ID</code>(<code>peer_cert_as_clientid</code>)。
##
## @path zones.$my_zone_name.mqtt.use_username_as_clientid
## @type boolean()
## use_username_as_clientid:
## @doc 使用对端证书中的 CN, DN 字段或整个证书内容来作为用户名。仅适用于 TLS 连接。
## 目前支持配置为以下内容:
## - <code>cn</code>: 取证书的 CN 字段作为 Username
## - <code>dn</code>: 取证书的 DN 字段作为 Username
## - <code>crt</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容作为 Username
## - <code>pem</code>: 将 <code>DER</code> 证书内容转换为 <code>PEM</code> 格式后作为 Username
## - <code>md5</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容的 MD5 值作为 Username
##
## @path zones.$my_zone_name.mqtt.peer_cert_as_username
## @type enum: disabled | cn | dn | crt | pem | md5
## peer_cert_as_username: disabled
## @doc 使用对端证书中的 CN, DN 字段或整个证书内容来作为客户端 ID。仅适用于 TLS 连接。
## 目前支持配置为以下内容:
## - <code>cn</code>: 取证书的 CN 字段作为 Client ID
## - <code>dn</code>: 取证书的 DN 字段作为 Client ID
## - <code>crt</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容作为 Client ID
## - <code>pem</code>: 将 <code>DER</code> 证书内容转换为 <code>PEM</code> 格式后作为 Client ID
## - <code>md5</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容的 MD5 值作为 Client ID
##
## @path zones.$my_zone_name.mqtt.peer_cert_as_clientid
## @type enum: disabled | cn | dn | crt | pem | md5
## peer_cert_as_clientid: disabled
## }
## stats {
## @doc 启用/禁用统计数据收集功能
## @path zones.$my_zone_name.stats.enable
## @type boolean()
## enable:
## }
## flapping_detect {
## @doc 启用抖动检测功能
## @path zones.$my_zone_name.flapping_detect.enable
## @type boolean()
## enable:
## @doc MQTT 客户端在"窗口"时间内允许的最大断开次数
## @path zones.$my_zone_name.flapping_detect.max_count
## @type integer()
## max_count:
## @doc 抖动检测的时间窗口。
## @path zones.$my_zone_name.flapping_detect.window_time
## @type emqx_schema:duration()
## window_time:
## @doc 抖动的客户端将会被禁止登陆多长时间
## @path zones.$my_zone_name.flapping_detect.ban_time
## @type emqx_schema:duration()
## ban_time:
## }
## force_shutdown {
## @doc 启用 `force_shutdown` 功能
## @path zones.$my_zone_name.force_shutdown.enable
## @type boolean()
## enable:
## @doc 消息队列的最大长度
## @path zones.$my_zone_name.force_shutdown.max_message_queue_len
## @type 0..inf
## max_message_queue_len:
## @doc Heap 的总大小
## @path zones.$my_zone_name.force_shutdown.max_heap_size
## @type emqx_schema:wordsize()
## max_heap_size:
## }
## conn_congestion {
## @doc 启用或者禁用连接阻塞告警功能
## @path zones.$my_zone_name.conn_congestion.enable_alarm
## @type boolean()
## enable_alarm:
## @doc 清除警报前的最短时间。
##
## 只有当队列中没有挂起的数据,并且连接至少被堵塞了 "min_alarm_sustain_duration" 毫秒时,
## 报警才会被清除。这是为了避免太频繁地清除和再次发出警报.
## @path zones.$my_zone_name.conn_congestion.min_alarm_sustain_duration
## @type emqx_schema:duration()
## min_alarm_sustain_duration:
## }
## force_gc {
## @doc 启用强制垃圾回收
## @path zones.$my_zone_name.force_gc.enable
## @type boolean()
## enable:
## @doc 在进程收到多少消息之后,对此进程执行垃圾回收
## @path zones.$my_zone_name.force_gc.count
## @type 0..inf
## count:
## @doc 在进程处理过多少个字节之后,对此进程执行垃圾回收
## @path zones.$my_zone_name.force_gc.bytes
## @type emqx_schema:bytesize()
## bytes:
## }
## overload_protection {
## @doc 是否对系统过载做出反应
## @path zones.$my_zone_name.overload_protection.enable
## @type boolean()
## enable:
## @doc 一些不重要的任务可能会延迟执行,以毫秒为单位设置延迟
## @path zones.$my_zone_name.overload_protection.backoff_delay
## @type 0..inf
## backoff_delay:
## @doc 如有必要,跳过强制GC
## @path zones.$my_zone_name.overload_protection.backoff_gc
## @type boolean()
## backoff_gc:
## @doc 如有必要,跳过进程休眠
## @path zones.$my_zone_name.overload_protection.backoff_hibernation
## @type boolean()
## backoff_hibernation:
## @doc 如有必要,关闭新进来的连接
## @path zones.$my_zone_name.overload_protection.backoff_new_conn
## @type boolean()
## backoff_new_conn:
## }
## }
## @doc 全局的 MQTT 配置项。
## mqtt 下所有的配置作为全局的默认值存在,它可以被 <code>zone</code> 中的配置覆盖。
mqtt {
## @doc TCP 连接建立后,如果在 <code>idle_timeout</code> 指定的时间内未收到客户端的 MQTT CONNECT 报文,则连接将被断开。
## @path mqtt.idle_timeout
## @type union: infinity | emqx_schema:duration()
idle_timeout: "15s"
## @doc 允许的最大 MQTT 报文大小。
## @path mqtt.max_packet_size
## @type emqx_schema:bytesize()
max_packet_size: "1MB"
## @doc 允许的最大 MQTT Client ID 长度。
## @path mqtt.max_clientid_len
## @type 23..65535
max_clientid_len: 65535
## @doc 允许的最大主题层级。
## @path mqtt.max_topic_levels
## @type 1..65535
max_topic_levels: 65535
## @doc 允许的最大 QoS 等级。
## @path mqtt.max_qos_allowed
## @type qos()
max_qos_allowed: 2
## @doc 允许的最大主题别名数,0 表示不支持主题别名。
## @path mqtt.max_topic_alias
## @type 0..65535
max_topic_alias: 65535
## @doc 是否启用对 MQTT 保留消息的支持。
## @path mqtt.retain_available
## @type boolean()
retain_available: true
## @doc 是否启用对 MQTT 通配符订阅的支持。
## @path mqtt.wildcard_subscription
## @type boolean()
wildcard_subscription: true
## @doc 是否启用对 MQTT 共享订阅的支持。
## @path mqtt.shared_subscription
## @type boolean()
shared_subscription: true
## @doc 是否为 MQTT v3.1.1/v3.1.0 客户端忽略投递自己发布的消息,类似于 MQTT 5.0 中的 <code>No Local</code> 订阅选项
## @path mqtt.ignore_loop_deliver
## @type boolean()
ignore_loop_deliver: false
## @doc 是否以严格模式解析 MQTT 消息。
## 当设置为 true 时,例如客户端 ID、主题名称等中的无效 utf8 字符串将导致客户端断开连接。
## @path mqtt.strict_mode
## @type boolean()
strict_mode: false
## @doc 指定返回给客户端的响应信息。如果设置为 "",则禁用此功能。仅适用于使用 MQTT 5.0 协议的客户端。
## @path mqtt.response_information
## @type string()
response_information: []
## @doc EMQX 要求客户端使用的保活时间,配置为 <code>disabled</code> 表示将使用客户端指定的保活时间。需要用到 MQTT 5.0 中的 <code>Server Keep Alive</code>,因此仅适用于使用 MQTT 5.0 协议的客户端。
## @path mqtt.server_keepalive
## @type union: integer() | disabled
server_keepalive: disabled
## @doc Broker 判定客户端保活超时使用的退避乘数。如果 EMQX 在 <code>Keep Alive * Backoff * 2</code> 秒内未收到任何报文,EMQX 将关闭当前连接。
## @path mqtt.keepalive_backoff
## @type float()
keepalive_backoff: 0.75
## @doc 允许每个客户端建立的最大订阅数量。
## @path mqtt.max_subscriptions
## @type union: 1..inf | infinity
max_subscriptions: infinity
## @doc 投递消息时,是否根据订阅主题时的 QoS 等级来强制提升派发的消息的 QoS 等级。
## @path mqtt.upgrade_qos
## @type boolean()
upgrade_qos: false
## @doc 允许在完成应答前同时投递的 QoS 1 和 QoS 2 消息的最大数量。
## @path mqtt.max_inflight
## @type 1..65535
max_inflight: 32
## @doc QoS 1/2 消息的重新投递间隔。
## @path mqtt.retry_interval
## @type emqx_schema:duration()
retry_interval: "30s"
## @doc PUBREL (Client -> Broker) 最大等待队列长度。
## @path mqtt.max_awaiting_rel
## @type union: integer() | infinity
max_awaiting_rel: 100
## @doc PUBREL (Client -> Broker) 最大等待时间,超时则会被丢弃。
## @path mqtt.await_rel_timeout
## @type emqx_schema:duration()
await_rel_timeout: "300s"
## @doc 指定会话将在连接断开后多久过期,仅适用于非 MQTT 5.0 的连接。
## @path mqtt.session_expiry_interval
## @type emqx_schema:duration()
session_expiry_interval: "2h"
## @doc 消息队列最大长度。持久客户端断开连接或飞行窗口已满时排队的消息长度。
## @path mqtt.max_mqueue_len
## @type union: non_neg_integer() | infinity
max_mqueue_len: 1000
## @doc 主题优先级。取值范围 [1-255]
## 默认优先级表为空,即所有的主题优先级相同。
##
## 注:优先主题名称中不支持使用逗号和等号。
## 注:不在此列表中的主题,被视为最高/最低优先级,这取决于<code>mqtt.mqueue_default_priority</code> 的配置
##
## 示例:
## 配置 <code>"topic/1" > "topic/2"</code>:
## <code>mqueue_priorities: {"topic/1": 10, "topic/2": 8}</code>
##
## @path mqtt.mqueue_priorities
## @type union: map() | disabled
mqueue_priorities: disabled
## @doc 默认的主题优先级,不在 <code>主题优先级</code>(<code>mqueue_priorities</code>) 中的主题将会使用该优先级。
## @path mqtt.mqueue_default_priority
## @type enum: highest | lowest
mqueue_default_priority: lowest
## @doc 指定在连接断开但会话保持期间,是否需要在消息队列中存储 QoS 0 消息。
## @path mqtt.mqueue_store_qos0
## @type boolean()
mqueue_store_qos0: true
## @doc 是否使用用户名作为客户端 ID。
## 此设置的作用时间晚于 <code>使用对端证书作为用户名</code>(<code>peer_cert_as_username</code>) 和 <code>使用对端证书作为客户端 ID</code>(<code>peer_cert_as_clientid</code>)。
##
## @path mqtt.use_username_as_clientid
## @type boolean()
use_username_as_clientid: false
## @doc 使用对端证书中的 CN, DN 字段或整个证书内容来作为用户名。仅适用于 TLS 连接。
## 目前支持配置为以下内容:
## - <code>cn</code>: 取证书的 CN 字段作为 Username
## - <code>dn</code>: 取证书的 DN 字段作为 Username
## - <code>crt</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容作为 Username
## - <code>pem</code>: 将 <code>DER</code> 证书内容转换为 <code>PEM</code> 格式后作为 Username
## - <code>md5</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容的 MD5 值作为 Username
##
## @path mqtt.peer_cert_as_username
## @type enum: disabled | cn | dn | crt | pem | md5
peer_cert_as_username: disabled
## @doc 使用对端证书中的 CN, DN 字段或整个证书内容来作为客户端 ID。仅适用于 TLS 连接。
## 目前支持配置为以下内容:
## - <code>cn</code>: 取证书的 CN 字段作为 Client ID
## - <code>dn</code>: 取证书的 DN 字段作为 Client ID
## - <code>crt</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容作为 Client ID
## - <code>pem</code>: 将 <code>DER</code> 证书内容转换为 <code>PEM</code> 格式后作为 Client ID
## - <code>md5</code>: 取 <code>DER</code> 或 <code>PEM</code> 证书的内容的 MD5 值作为 Client ID
##
## @path mqtt.peer_cert_as_clientid
## @type enum: disabled | cn | dn | crt | pem | md5
peer_cert_as_clientid: disabled
}
## @doc 全局 MQTT 监听器的默认认证配置。 为每个监听器配置认证参考监听器器配置中的<code>authentication</code> 配置。
##
## 该配置可以被配置为:
## <ul>
## <li><code>[]</code>: 默认值,允许所以登录请求
## <li>配置为单认证器,例如 <code>{enable:true,backend:"built_in_database",mechanism="password_based"}</code></li>
## <li>配置为认证器数组</li>
## </ul>
##
## 当配置为认证链后,登录凭证会按照配置的顺序进行检查,直到做出<code>allow</code> 或 <code>deny</code>的结果。
##
## 如果在所有的认证器都执行完后,还是没有结果,登录将被拒绝。
##
## @doc 全局 MQTT 监听器的默认认证配置。 为每个监听器配置认证参考监听器器配置中的<code>authentication</code> 配置。
##
## 该配置可以被配置为:
## <ul>
## <li><code>[]</code>: 默认值,允许所以登录请求
## <li>配置为单认证器,例如 <code>{enable:true,backend:"built_in_database",mechanism="password_based"}</code></li>
## <li>配置为认证器数组</li>
## </ul>
##
## 当配置为认证链后,登录凭证会按照配置的顺序进行检查,直到做出<code>allow</code> 或 <code>deny</code>的结果。
##
## 如果在所有的认证器都执行完后,还是没有结果,登录将被拒绝。
##
## @path
## @type array
authentication: []
## @path authentication.$INDEX
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## $INDEX:
## @doc 授权(ACL)。EMQX 支持完整的客户端访问控制(ACL)。</br>
authorization {
## @doc
## 如果用户或客户端不匹配ACL规则,或者从可配置授权源(比如内置数据库、HTTP API 或 PostgreSQL 等。)内未找
## 到此类用户或客户端时,模式的认访问控制操作。
## 在“授权”中查找更多详细信息。
##
## @path authorization.no_match
## @type enum: allow | deny
no_match: allow
## @doc
## 授权检查拒绝操作时的操作。
##
## @path authorization.deny_action
## @type enum: ignore | disconnect
deny_action: ignore
cache {
## @doc
## 启用或禁用授权缓存。
##
## @path authorization.cache.enable
## @type boolean()
enable: true
## @doc
## 缓存项的最大数量。
##
## @path authorization.cache.max_size
## @type 1..1048576
max_size: 32
## @doc
## 缓存数据的生存时间。
##
## @path authorization.cache.ttl
## @type emqx_schema:duration()
ttl: "1m"
}
## @doc
## 鉴权数据源.</br>
## 鉴权(ACL)数据源的列表.
## 它被设计为一个数组,而不是一个散列映射,
## 所以可以作为链式访问控制.</br>
##
## 当授权一个 'publish' 或 'subscribe' 行为时,
## 该配置列表中的所有数据源将按顺序进行检查。
## 如果在某个客户端未找到时(使用 ClientID 或 Username),
## 将会移动到下一个数据源. 直至得到 'allow' 或 'deny' 的结果.</br>
##
## 如果在任何数据源中都未找到对应的客户端信息,
## 配置的默认行为 ('authorization.no_match') 将生效.</br>
##
## 注意:
## 数据源使用 'type' 进行标识.
## 使用同一类型的数据源多于一次不被允许.
##
## @path authorization
## @type array
sources: []
## @path authorization.sources.$INDEX
## @type union: authz:file | authz:http_get | authz:http_post | authz:mnesia | authz:mongo_single | authz:mongo_rs | authz:mongo_sharded | authz:mysql | authz:postgresql | authz:redis_single | authz:redis_sentinel | authz:redis_cluster
## $INDEX:
}
node {
## @doc 节点名。格式为 <name>@<host>。其中 <host> 可以是 IP 地址,也可以是 FQDN。
## 详见 http://erlang.org/doc/reference_manual/distributed.html。
##
## @path node.name
## @type string()
name: "emqx@127.0.0.1"
## @doc 分布式 Erlang 集群使用的 cookie 值。集群间保持一致
## @path node.cookie
## @type string()
cookie: "emqxsecretcookie"
## @doc
## 节点数据存放目录,可能会自动创建的子目录如下:</br>
## - `mnesia/<node_name>`。EMQX的内置数据库目录。例如,`mnesia/emqx@127.0.0.1`。</br>
## 如果节点要被重新命名(例如,`emqx@10.0.1.1`)。旧目录应该首先被删除。</br>
## - `configs`。在启动时生成的配置,以及集群/本地覆盖的配置。</br>
## - `patches`: 热补丁文件将被放在这里。</br>
## - `trace`: 日志跟踪文件。</br>
##
## **注意**: 一个数据dir不能被两个或更多的EMQX节点同时使用。
##
## @path node.data_dir
## @type string()
## data_dir:
## @doc 启动时读取的配置文件列表。后面的配置文件项覆盖前面的文件。
## @path node.config_files
## @type [string()]
## config_files:
## @doc 系统调优参数,设置节点运行多久强制进行一次全局垃圾回收。
## @path node.global_gc_interval
## @type emqx_schema:duration()
global_gc_interval: "15m"
## @doc 设置 Erlang crash_dump 文件的存储路径和文件名。
## @path node.crash_dump_file
## @type emqx_conf_schema:file()
crash_dump_file: "log/erl_crash.dump"
## @doc 保存崩溃文件最大允许时间,如果文件太大,在规则时间内没有保存完成,则会直接结束。
## @path node.crash_dump_seconds
## @type emqx_schema:duration_s()
crash_dump_seconds: "30s"
## @doc 限制崩溃文件的大小,当崩溃时节点内存太大,
## 如果为了保存现场,需要全部存到崩溃文件中,此处限制最多能保存多大的文件。
##
## @path node.crash_dump_bytes
## @type emqx_schema:bytesize()
crash_dump_bytes: "100MB"
## @doc 系统调优参数,此配置将覆盖 vm.args 文件里的 -kernel net_ticktime 参数。当一个节点持续无响应多久之后,认为其已经宕机并断开连接。
##
## @path node.dist_net_ticktime
## @type emqx_schema:duration_s()
dist_net_ticktime: "2m"
## @doc 错误信息中打印的最大堆栈层数
## @path node.backtrace_depth
## @type integer()
backtrace_depth: 23
## @doc 当新EMQX 加入集群时,应重启的Erlang应用程序的列表。
## @path node.applications
## @type emqx_schema:comma_separated_atoms()
applications: []
## @doc <code>etc</code> 存放目录
## @path node.etc_dir
## @type string()
## etc_dir:
cluster_call {
## @doc 当集群间调用出错时,多长时间重试一次。
## @path node.cluster_call.retry_interval
## @type emqx_schema:duration()
retry_interval: "1s"
## @doc 集群间调用最多保留的历史记录数。只用于排错时查看。
## @path node.cluster_call.max_history
## @type 1..500
max_history: 100
## @doc 清理过期事务的时间间隔
## @path node.cluster_call.cleanup_interval
## @type emqx_schema:duration()
cleanup_interval: "5m"
}
}
cluster {
## @doc EMQX集群名称。每个集群都有一个唯一的名称。服务发现时会用于做路径的一部分。
## @path cluster.name
## @type atom()
name: emqxcl
## @doc 集群节点发现方式。可选值为:
## - manual: 手动加入集群</br>
## - static: 配置静态节点。配置几个固定的节点,新节点通过连接固定节点中的某一个来加入集群。</br>
## - mcast: 使用 UDP 多播的方式发现节点。</br>
## - dns: 使用 DNS A 记录的方式发现节点。</br>
## - etcd: 使用 etcd 发现节点。</br>
## - k8s: 使用 Kubernetes 发现节点。</br>
##
## @path cluster.discovery_strategy
## @type enum: manual | static | mcast | dns | etcd | k8s
discovery_strategy: manual
## @doc 指定多久之后从集群中删除离线节点。
## @path cluster.autoclean
## @type emqx_schema:duration()
autoclean: "5m"
## @doc 集群脑裂自动恢复机制开关。
## @path cluster.autoheal
## @type boolean()
autoheal: true
## @doc 分布式 Erlang 集群协议类型。可选值为:
## - inet_tcp: 使用 IPv4 </br>
## - inet6_tcp 使用 IPv6 </br>
## - inet_tls: 使用 TLS,需要与 node.ssl_dist_optfile 配置一起使用。</br>
##
## @path cluster.proto_dist
## @type enum: inet_tcp | inet6_tcp | inet_tls
proto_dist: inet_tcp
static {
## @doc 集群中的EMQX节点名称列表,
## 指定固定的节点列表,多个节点间使用逗号 , 分隔。
## 当 cluster.discovery_strategy 为 static 时,此配置项才有效。
## 适合于节点数量较少且固定的集群。
##
## @path cluster.static
## @type array
seeds: []
}
mcast {
## @doc 指定多播 IPv4 地址。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast.addr
## @type string()
addr: "239.192.0.1"
## @doc 指定多播端口。如有多个端口使用逗号 , 分隔。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast
## @type array
ports: [4369,4370]
## @doc 指定节点发现服务需要绑定到本地 IP 地址。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast.iface
## @type string()
iface: "0.0.0.0"
## @doc 指定多播的 Time-To-Live 值。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast.ttl
## @type 0..255
ttl: 255
## @doc 设置多播的报文是否投递到本地回环地址。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast.loop
## @type boolean()
loop: true
## @doc 外发数据报的内核级缓冲区的大小。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast.sndbuf
## @type emqx_schema:bytesize()
sndbuf: "16KB"
## @doc 接收数据报的内核级缓冲区的大小。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast.recbuf
## @type emqx_schema:bytesize()
recbuf: "16KB"
## @doc 用户级缓冲区的大小。
## 当 cluster.discovery_strategy 为 mcast 时,此配置项才有效。
##
## @path cluster.mcast.buffer
## @type emqx_schema:bytesize()
buffer: "32KB"
}
dns {
## @doc 指定 DNS A 记录的名字。emqx 会通过访问这个 DNS A 记录来获取 IP 地址列表,
## 然后拼接 cluster.dns.app 里指定的 APP 名得到集群中所有节点的列表。
## 当 cluster.discovery_strategy 为 dns 时,此配置项才有效。
##
## @path cluster.dns.name
## @type string()
name: "localhost"
## @doc 用来与从 cluster.dns.name 获取的 IP 列表拼接得到节点名列表。
## 当 cluster.discovery_strategy 为 dns 时,此配置项才有效。
##
## @path cluster.dns.app
## @type string()
app: "emqx"
}
etcd {
## @doc 指定 etcd 服务的地址。如有多个服务使用逗号 , 分隔。
## 当 cluster.discovery_strategy 为 etcd 时,此配置项才有效。
##
## @path cluster.etcd.server
## @type emqx_schema:comma_separated_list()
## server:
## @doc 指定 etcd 路径的前缀。每个节点在 etcd 中都会创建一个路径:
## v2/keys/<prefix>/<cluster.name>/<node.name> </br>
## 当 cluster.discovery_strategy 为 etcd 时,此配置项才有效。
##
## @path cluster.etcd.prefix
## @type string()
prefix: "emqxcl"
## @doc 指定 etcd 中节点信息的过期时间。
## 当 cluster.discovery_strategy 为 etcd 时,此配置项才有效。
##
## @path cluster.etcd.node_ttl
## @type emqx_schema:duration()
node_ttl: "1m"
ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path cluster.etcd.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path cluster.etcd.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path cluster.etcd.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path cluster.etcd.ssl.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path cluster.etcd.ssl.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path cluster.etcd.ssl.depth
## @type integer()
depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path cluster.etcd.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path cluster.etcd.ssl
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path cluster.etcd.ssl
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path cluster.etcd.ssl.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path cluster.etcd.ssl.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc 启用 TLS
## @path cluster.etcd.ssl.enable
## @type boolean()
enable: false
## @doc
## 指定要在 TLS 服务器名称指示扩展中使用的主机名</br>
## 例如,当连接到 "server.example.net" 时,接受连接并执行 TLS 握手的真正服务器可能与 TLS 客户端最初连接到的主机不同,
## 例如,当连接到 IP 地址时,或者当主机具有多个可解析的 DNS 记录时</br>
## 如果未指定,它将默认为使用的主机名字符串
## 建立连接,除非使用 IP 地址</br>
## 然后,主机名也用于对等机的主机名验证
## 证书</br>特殊值'disable'阻止发送服务器名称指示扩展,并禁用主机名验证检查。
##
## @path cluster.etcd.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
}
}
k8s {
## @doc 指定 Kubernetes API Server。如有多个 Server 使用逗号 , 分隔。
## 当 cluster.discovery_strategy 为 k8s 时,此配置项才有效。
##
## @path cluster.k8s.apiserver
## @type string()
## apiserver:
## @doc 指定 Kubernetes 中 EMQX 的服务名。
## 当 cluster.discovery_strategy 为 k8s 时,此配置项才有效。
##
## @path cluster.k8s.service_name
## @type string()
service_name: "emqx"
## @doc 当使用 k8s 方式集群时,address_type 用来从 Kubernetes 接口的应答里获取什么形式的 Host 列表。
## 指定 cluster.k8s.address_type 为 ip,则将从 Kubernetes 接口中获取 emqx 服务的 IP 地址列表:
## - 172.16.122.31 </br>
## - 172.16.122.32 </br>
## - 172.16.122.33 </br>
## 然后与 cluster.k8s.app_name 配置指定的 app name 拼接,得到 emqx 节点列表: </br>
## - emqx@172.16.122.31
## - emqx@172.16.122.32
## - emqx@172.16.122.33
##
## @path cluster.k8s.address_type
## @type enum: ip | dns | hostname
address_type: ip
## @doc app_name 用来跟获取的 Host 列表拼接,得到节点列表。</br>
## 当 cluster.discovery_strategy 为 k8s 时,此配置项才有效。
##
## @path cluster.k8s.app_name
## @type string()
app_name: "emqx"
## @doc 当使用 k8s 方式并且 cluster.k8s.address_type 指定为 dns 类型时,
## 可设置 emqx 节点名的命名空间。与 cluster.k8s.suffix 一起使用用以拼接得到节点名列表。
##
## @path cluster.k8s.namespace
## @type string()
namespace: "default"
## @doc 当使用 k8s 方式并且 cluster.k8s.address_type 指定为 dns 类型时,可设置 emqx 节点名的后缀。
## 与 cluster.k8s.namespace 一起使用用以拼接得到节点名列表。
##
## @path cluster.k8s.suffix
## @type string()
suffix: "pod.local"
}
}
log {
console_handler {
## @doc 启用此日志处理进程。
## @path log.console_handler.enable
## @type boolean()
enable: false
## @doc 设置日志级别。 默认为warning。
## @path log.console_handler.level
## @type emqx_conf_schema:log_level()
level: warning
## @doc 日志格式中的时间戳,使用的时间偏移量。默认使用系统时区system,当为utc为无时间偏移量
## 为具体的N(1-24)数字时,则代表时间偏移量+N。
##
## @path log.console_handler.time_offset
## @type string()
time_offset: "system"
## @doc 设置单个日志消息的最大长度。 如果超过此长度,则日志消息将被截断。最小可设置的长度为100。
## @path log.console_handler.chars_limit
## @type union: unlimited | 100..inf
chars_limit: unlimited
## @doc 选择日志格式。 <code>text</code> 用于纯文本,<code>json</code> 用于结构化日志记录。
## @path log.console_handler.formatter
## @type enum: text | json
formatter: text
## @doc 如果设置为 true,则单行打印日志。 否则,日志消息可能跨越多行。
## @path log.console_handler.single_line
## @type boolean()
single_line: true
## @doc 只要缓冲的日志事件的数量低于这个值,所有的日志事件都会被异步处理。
## 这意味着,日志落地速度不会影响正常的业务进程,因为它们不需要等待日志处理进程的响应。
## 如果消息队列的增长超过了这个值,处理程序开始同步处理日志事件。也就是说,发送事件的客户进程必须等待响应。
## 当处理程序将消息队列减少到低于sync_mode_qlen阈值的水平时,异步操作就会恢复。
## 默认为100条信息,当等待的日志事件大于100条时,就开始同步处理日志。
## @path log.console_handler.sync_mode_qlen
## @type non_neg_integer()
sync_mode_qlen: 100
## @doc 当缓冲的日志事件数大于此值时,新的日志事件将被丢弃。起到过载保护的功能。
## 为了使过载保护算法正常工作必须要:<code> sync_mode_qlen =< drop_mode_qlen =< flush_qlen <\code> 且 drop_mode_qlen > 1
## 要禁用某些模式,请执行以下操作。
## - 如果sync_mode_qlen被设置为0,所有的日志事件都被同步处理。也就是说,异步日志被禁用。
## - 如果sync_mode_qlen被设置为与drop_mode_qlen相同的值,同步模式被禁用。也就是说,处理程序总是以异步模式运行,除非调用drop或flushing。
## - 如果drop_mode_qlen被设置为与flush_qlen相同的值,则drop模式被禁用,永远不会发生。
##
## @path log.console_handler.drop_mode_qlen
## @type pos_integer()
drop_mode_qlen: 3000
## @doc 如果缓冲日志事件的数量增长大于此阈值,则会发生刷新(删除)操作。 日志处理进程会丢弃缓冲的日志消息。
## 来缓解自身不会由于内存瀑涨而影响其它业务进程。日志内容会提醒有多少事件被删除。
## @path log.console_handler.flush_qlen
## @type pos_integer()
flush_qlen: 8000
overload_kill {
## @doc 日志处理进程过载时为保护自己节点其它的业务能正常,强制杀死日志处理进程。
## @path log.console_handler.overload_kill.enable
## @type boolean()
enable: true
## @doc 处理进程允许使用的最大内存。
## @path log.console_handler.overload_kill.mem_size
## @type emqx_schema:bytesize()
mem_size: "30MB"
## @doc 允许的最大队列长度。
## @path log.console_handler.overload_kill.qlen
## @type pos_integer()
qlen: 20000
## @doc 如果处理进程终止,它会在以指定的时间后后自动重新启动。 `infinity` 不自动重启。
## @path log.console_handler.overload_kill.restart_after
## @type union: emqx_schema:duration_ms() | infinity
restart_after: "5s"
}
burst_limit {
## @doc 启用日志限流保护机制。
## @path log.console_handler.burst_limit.enable
## @type boolean()
enable: true
## @doc 在 `window_time` 间隔内处理的最大日志事件数。 达到限制后,将丢弃连续事件,直到 `window_time` 结束。
## @path log.console_handler.burst_limit.max_count
## @type pos_integer()
max_count: 10000
## @doc 参考 `max_count`。
## @path log.console_handler.burst_limit.window_time
## @type emqx_schema:duration()
window_time: "1s"
}
## @doc supervisor 报告的类型。默认为 error 类型。
## - `error`:仅记录 Erlang 进程中的错误。
## - `progress`:除了 error 信息外,还需要记录进程启动的详细信息。
## @path log.console_handler.supervisor_reports
## @type enum: error | progress
supervisor_reports: error
## @doc Erlang 内部格式日志格式化和 Erlang 进程消息队列检查的最大深度。
## @path log.console_handler.max_depth
## @type union: unlimited | non_neg_integer()
max_depth: 100
}
## @doc 需要持久化到文件的日志处理进程列表。默认只有 default 一个处理进程。
## @path log.file_handlers
## @type map()
## file_handlers:
## $name {
## @doc 日志文件路径及名字。
## @path log.file_handlers.$name.file
## @type emqx_conf_schema:file()
## file:
## rotation {
## @doc 启用日志轮换功能。启动后生成日志文件后缀会加上对应的索引数字,比如:log/emqx.log.1。
## 系统会默认生成<code>*.siz/*.idx<code>用于记录日志位置,请不要手动修改这两个文件。
##
## @path log.file_handlers.$name.rotation.enable
## @type boolean()
## enable: true
## @doc 轮换的最大日志文件数。
## @path log.file_handlers.$name.rotation.count
## @type 1..2048
## count: 10
## }
## @doc 此参数控制日志文件轮换。 `infinity` 意味着日志文件将无限增长,否则日志文件将在达到 `max_size`(以字节为单位)时进行轮换。
## 与 rotation count配合使用。如果 counter 为 10,则是10个文件轮换。
##
## @path log.file_handlers.$name.max_size
## @type union: infinity | emqx_schema:bytesize()
## max_size: "50MB"
## @doc 启用此日志处理进程。
## @path log.file_handlers.$name.enable
## @type boolean()
## enable: true
## @doc 设置日志级别。 默认为warning。
## @path log.file_handlers.$name.level
## @type emqx_conf_schema:log_level()
## level: warning
## @doc 日志格式中的时间戳,使用的时间偏移量。默认使用系统时区system,当为utc为无时间偏移量
## 为具体的N(1-24)数字时,则代表时间偏移量+N。
##
## @path log.file_handlers.$name.time_offset
## @type string()
## time_offset: "system"
## @doc 设置单个日志消息的最大长度。 如果超过此长度,则日志消息将被截断。最小可设置的长度为100。
## @path log.file_handlers.$name.chars_limit
## @type union: unlimited | 100..inf
## chars_limit: unlimited
## @doc 选择日志格式。 <code>text</code> 用于纯文本,<code>json</code> 用于结构化日志记录。
## @path log.file_handlers.$name.formatter
## @type enum: text | json
## formatter: text
## @doc 如果设置为 true,则单行打印日志。 否则,日志消息可能跨越多行。
## @path log.file_handlers.$name.single_line
## @type boolean()
## single_line: true
## @doc 只要缓冲的日志事件的数量低于这个值,所有的日志事件都会被异步处理。
## 这意味着,日志落地速度不会影响正常的业务进程,因为它们不需要等待日志处理进程的响应。
## 如果消息队列的增长超过了这个值,处理程序开始同步处理日志事件。也就是说,发送事件的客户进程必须等待响应。
## 当处理程序将消息队列减少到低于sync_mode_qlen阈值的水平时,异步操作就会恢复。
## 默认为100条信息,当等待的日志事件大于100条时,就开始同步处理日志。
## @path log.file_handlers.$name.sync_mode_qlen
## @type non_neg_integer()
## sync_mode_qlen: 100
## @doc 当缓冲的日志事件数大于此值时,新的日志事件将被丢弃。起到过载保护的功能。
## 为了使过载保护算法正常工作必须要:<code> sync_mode_qlen =< drop_mode_qlen =< flush_qlen <\code> 且 drop_mode_qlen > 1
## 要禁用某些模式,请执行以下操作。
## - 如果sync_mode_qlen被设置为0,所有的日志事件都被同步处理。也就是说,异步日志被禁用。
## - 如果sync_mode_qlen被设置为与drop_mode_qlen相同的值,同步模式被禁用。也就是说,处理程序总是以异步模式运行,除非调用drop或flushing。
## - 如果drop_mode_qlen被设置为与flush_qlen相同的值,则drop模式被禁用,永远不会发生。
##
## @path log.file_handlers.$name.drop_mode_qlen
## @type pos_integer()
## drop_mode_qlen: 3000
## @doc 如果缓冲日志事件的数量增长大于此阈值,则会发生刷新(删除)操作。 日志处理进程会丢弃缓冲的日志消息。
## 来缓解自身不会由于内存瀑涨而影响其它业务进程。日志内容会提醒有多少事件被删除。
## @path log.file_handlers.$name.flush_qlen
## @type pos_integer()
## flush_qlen: 8000
## overload_kill {
## @doc 日志处理进程过载时为保护自己节点其它的业务能正常,强制杀死日志处理进程。
## @path log.file_handlers.$name.overload_kill.enable
## @type boolean()
## enable: true
## @doc 处理进程允许使用的最大内存。
## @path log.file_handlers.$name.overload_kill.mem_size
## @type emqx_schema:bytesize()
## mem_size: "30MB"
## @doc 允许的最大队列长度。
## @path log.file_handlers.$name.overload_kill.qlen
## @type pos_integer()
## qlen: 20000
## @doc 如果处理进程终止,它会在以指定的时间后后自动重新启动。 `infinity` 不自动重启。
## @path log.file_handlers.$name.overload_kill.restart_after
## @type union: emqx_schema:duration_ms() | infinity
## restart_after: "5s"
## }
## burst_limit {
## @doc 启用日志限流保护机制。
## @path log.file_handlers.$name.burst_limit.enable
## @type boolean()
## enable: true
## @doc 在 `window_time` 间隔内处理的最大日志事件数。 达到限制后,将丢弃连续事件,直到 `window_time` 结束。
## @path log.file_handlers.$name.burst_limit.max_count
## @type pos_integer()
## max_count: 10000
## @doc 参考 `max_count`。
## @path log.file_handlers.$name.burst_limit.window_time
## @type emqx_schema:duration()
## window_time: "1s"
## }
## @doc supervisor 报告的类型。默认为 error 类型。
## - `error`:仅记录 Erlang 进程中的错误。
## - `progress`:除了 error 信息外,还需要记录进程启动的详细信息。
## @path log.file_handlers.$name.supervisor_reports
## @type enum: error | progress
## supervisor_reports: error
## @doc Erlang 内部格式日志格式化和 Erlang 进程消息队列检查的最大深度。
## @path log.file_handlers.$name.max_depth
## @type union: unlimited | non_neg_integer()
## max_depth: 100
## }
## @doc 让 error_logger 日志处理进程关闭,防止一条异常信息被记录多次。
## @path log.error_logger
## @type atom()
error_logger: silent
}
rpc {
## @doc 在 <code>sync</code> 模式下,发送端等待接收端的 ack信号。
## @path rpc.mode
## @type enum: sync | async
mode: async
## @doc 集群间通信使用的传输协议。
## @path rpc.driver
## @type enum: tcp | ssl
driver: tcp
## @doc 异步模式下,发送的批量消息的最大数量。
## @path rpc.async_batch_size
## @type integer()
async_batch_size: 256
## @doc <code>manual</code>: 通过 <code>tcp_server_port</code> 来发现端口。
## </br><code>stateless</code>: 使用无状态的方式来发现端口,使用如下算法。如果节点名称是 <code>
## emqxN@127.0.0.1</code>, N 是一个数字,那么监听端口就是 5370 + N。
##
## @path rpc.port_discovery
## @type enum: manual | stateless
port_discovery: stateless
## @doc RPC 本地服务使用的 TCP 端口。</br>
## 只有当 rpc.port_discovery 设置为 manual 时,此配置才会生效。
##
## @path rpc.tcp_server_port
## @type integer()
tcp_server_port: 5369
## @doc RPC 本地服务使用的监听SSL端口。</br>
## 只有当 rpc.port_discovery 设置为 manual 且 <code> dirver </code> 设置为 <code>ssl</code>,
## 此配置才会生效。
##
## @path rpc.ssl_server_port
## @type integer()
ssl_server_port: 5369
## @doc 设置本节点与远程节点之间的 RPC 通信通道的最大数量。
## @path rpc.tcp_client_num
## @type 1..256
tcp_client_num: 10
## @doc 建立 RPC 连接的超时时间。
## @path rpc.connect_timeout
## @type emqx_schema:duration()
connect_timeout: "5s"
## @doc TLS 证书文件的路径,用于验证集群节点的身份。
## 只有当 <code>rpc.driver</code> 设置为 <code>ssl</code> 时,此配置才会生效。
##
## @path rpc.certfile
## @type emqx_conf_schema:file()
## certfile:
## @doc <code>rpc.certfile</code> 的私钥文件的路径。</br>
## 注意:此文件内容是私钥,所以需要设置权限为 600。
##
## @path rpc.keyfile
## @type emqx_conf_schema:file()
## keyfile:
## @doc 验证 <code>rpc.certfile</code> 的 CA 证书文件的路径。</br>
## 注意:集群中所有节点的证书必须使用同一个 CA 签发。
##
## @path rpc.cacertfile
## @type emqx_conf_schema:file()
## cacertfile:
## @doc 发送 RPC 请求的超时时间。
## @path rpc.send_timeout
## @type emqx_schema:duration()
send_timeout: "5s"
## @doc 远程节点认证的超时时间。
## @path rpc.authentication_timeout
## @type emqx_schema:duration()
authentication_timeout: "5s"
## @doc 同步 RPC 的回复超时时间。
## @path rpc.call_receive_timeout
## @type emqx_schema:duration()
call_receive_timeout: "15s"
## @doc broker 之间的连接在最后一条消息发送后保持打开的时间。
## @path rpc.socket_keepalive_idle
## @type emqx_schema:duration_s()
socket_keepalive_idle: "7200s"
## @doc keepalive 消息的间隔。
## @path rpc.socket_keepalive_interval
## @type emqx_schema:duration_s()
socket_keepalive_interval: "75s"
## @doc keepalive 探测消息发送失败的次数,直到 RPC 连接被认为已经断开。
## @path rpc.socket_keepalive_count
## @type integer()
socket_keepalive_count: 9
## @doc TCP 调节参数。TCP 发送缓冲区大小。
## @path rpc.socket_sndbuf
## @type emqx_schema:bytesize()
socket_sndbuf: "1MB"
## @doc TCP 调节参数。TCP 接收缓冲区大小。
## @path rpc.socket_recbuf
## @type emqx_schema:bytesize()
socket_recbuf: "1MB"
## @doc TCP 调节参数。用户模式套接字缓冲区大小。
## @path rpc.socket_buffer
## @type emqx_schema:bytesize()
socket_buffer: "1MB"
}
db {
## @doc rlog是默认的数据库,他适用于大规模的集群。
## mnesia是备选数据库,在小集群中提供了很好的性能。
##
## @path db.backend
## @type enum: mnesia | rlog
backend: rlog
## @doc
## 选择节点的角色。</br>
## <code>core</code> 节点提供数据的持久性,并负责写入。建议将核心节点放置在不同的机架或不同的可用区。</br>
## <code>repliant</code> 节点是临时工作节点。 从集群中删除它们,不影响数据库冗余</br>
## 建议复制节点多于核心节点。</br>
## 注意:该参数仅在设置<code>backend</code>时生效到 <code>rlog</code>。
##
## @path db.role
## @type enum: core | replicant
role: core
## @doc 当前节点连接的核心节点列表。</br>
## 注意:该参数仅在设置<code>backend</code>时生效到 <code>rlog</code>
## 并且设置<code>role</code>为<code>replicant</code>时生效。</br>
## 该值需要在手动或静态集群发现机制下设置。</br>
## 如果使用了自动集群发现机制(如<code>etcd</code>),则不需要设置该值。
##
## @path db.core_nodes
## @type emqx_schema:comma_separated_atoms()
core_nodes: []
## @doc 集群间推送事务日志到复制节点使用的协议。
## @path db.rpc_module
## @type enum: gen_rpc | rpc
rpc_module: gen_rpc
## @doc 同步模式下,核心节点等待复制节点的确认信息,然后再发送下一条事务日志。
## @path db.tlog_push_mode
## @type enum: sync | async
tlog_push_mode: async
}
## @doc Broker 相关配置项。
broker {
## @doc 是否启用 Session Registry
## @path broker.enable_session_registry
## @type boolean()
enable_session_registry: true
## @doc Session 在集群中的锁策略。
## - `loca`: 仅锁本节点的 Session
## - `one`: 任选一个其它节点加锁
## - `quorum`: 选择集群中半数以上的节点加锁
## - `all`: 选择所有节点加锁
##
## @path broker.session_locking_strategy
## @type enum: local | leader | quorum | all
session_locking_strategy: quorum
## @doc 共享订阅消息派发策略。
## - `random`: 随机挑选一个共享订阅者派发
## - `round_robin`: 使用 round-robin 策略派发
## - `sticky`: 总是使用上次选中的订阅者派发,直到它断开连接
## - `hash`: 使用发送者的 Client ID 进行 Hash 来选择订阅者
##
## @path broker.shared_subscription_strategy
## @type enum: random | round_robin | sticky | local | hash_topic | hash_clientid
shared_subscription_strategy: round_robin
## @doc 启用/禁用 QoS 1 和 QoS 2 消息的共享派发确认。
## 开启后,允许将消息从未及时回复 ACK 的订阅者 (例如,客户端离线)重新派发给另外一个订阅者。
##
## @path broker.shared_dispatch_ack_enabled
## @type boolean()
shared_dispatch_ack_enabled: false
## @doc 是否开启批量清除路由。
## @path broker.route_batch_clean
## @type boolean()
route_batch_clean: true
perf {
## @doc 通配主题订阅/取消订阅性能调优。
## 建议仅当通配符主题较多时才更改此参数。
##
## 注:当从/更改为 `global` 锁时,它要求集群中的所有节点在更改之前停止。
## - `key`: 为 Mnesia 事务涉及到的每个 key 上锁,建议单节点时使用。
## - `tab`: 为 Mnesia 事务涉及到的表上锁,建议在集群中使用。
## - `global`: 所以更新操作都被全局的锁保护,仅建议在超大规模集群中使用。
##
## @path broker.perf.route_lock_type
## @type enum: key | tab | global
route_lock_type: key
## @doc 是否开启主题表压缩存储。
## 启用它会显着提高通配符主题订阅率,如果通配符主题具有唯一前缀,例如:'sensor/{{id}}/+/',其中每个订阅者的 ID 是唯一的。
## 如果消息主要发布到具有大量级别的主题,则主题匹配性能(发布时)可能会降低。
##
## 注意:这是一个集群范围的配置。 它要求在更改之前停止所有节点。
##
## @path broker.perf.trie_compaction
## @type boolean()
trie_compaction: true
}
## @path broker.shared_subscription_group
## @type map()
## shared_subscription_group:
## $name {
## @path broker.shared_subscription_group.$name.strategy
## @type enum: random | round_robin | sticky | local | hash_topic | hash_clientid
## strategy: random
## }
}
## @doc 系统主题配置。
sys_topics {
## @doc 发送 `$SYS` 主题的间隔时间。
## @path sys_topics.sys_msg_interval
## @type union: disabled | emqx_schema:duration()
sys_msg_interval: "1m"
## @doc 发送心跳系统消息的间隔时间,它包括:
## - `$SYS/brokers/<node>/uptime`
## - `$SYS/brokers/<node>/datetime`
##
## @path sys_topics.sys_heartbeat_interval
## @type union: disabled | emqx_schema:duration()
sys_heartbeat_interval: "30s"
sys_event_messages {
## @doc 是否开启客户端已连接事件消息。
## @path sys_topics.sys_event_messages.client_connected
## @type boolean()
client_connected: true
## @doc 是否开启客户端已断开连接事件消息。
## @path sys_topics.sys_event_messages.client_disconnected
## @type boolean()
client_disconnected: true
## @doc 是否开启客户端已成功订阅主题事件消息。
## @path sys_topics.sys_event_messages.client_subscribed
## @type boolean()
client_subscribed: false
## @doc 是否开启客户端已成功取消订阅主题事件消息。
## @path sys_topics.sys_event_messages.client_unsubscribed
## @type boolean()
client_unsubscribed: false
}
}
force_shutdown {
## @doc 启用 `force_shutdown` 功能
## @path force_shutdown.enable
## @type boolean()
enable: true
## @doc 消息队列的最大长度
## @path force_shutdown.max_message_queue_len
## @type 0..inf
max_message_queue_len: 1000
## @doc Heap 的总大小
## @path force_shutdown.max_heap_size
## @type emqx_schema:wordsize()
max_heap_size: "32MB"
}
overload_protection {
## @doc 是否对系统过载做出反应
## @path overload_protection.enable
## @type boolean()
enable: false
## @doc 一些不重要的任务可能会延迟执行,以毫秒为单位设置延迟
## @path overload_protection.backoff_delay
## @type 0..inf
backoff_delay: 1
## @doc 如有必要,跳过强制GC
## @path overload_protection.backoff_gc
## @type boolean()
backoff_gc: false
## @doc 如有必要,跳过进程休眠
## @path overload_protection.backoff_hibernation
## @type boolean()
backoff_hibernation: true
## @doc 如有必要,关闭新进来的连接
## @path overload_protection.backoff_new_conn
## @type boolean()
backoff_new_conn: true
}
force_gc {
## @doc 启用强制垃圾回收
## @path force_gc.enable
## @type boolean()
enable: true
## @doc 在进程收到多少消息之后,对此进程执行垃圾回收
## @path force_gc.count
## @type 0..inf
count: 16000
## @doc 在进程处理过多少个字节之后,对此进程执行垃圾回收
## @path force_gc.bytes
## @type emqx_schema:bytesize()
bytes: "16MB"
}
conn_congestion {
## @doc 启用或者禁用连接阻塞告警功能
## @path conn_congestion.enable_alarm
## @type boolean()
enable_alarm: false
## @doc 清除警报前的最短时间。
##
## 只有当队列中没有挂起的数据,并且连接至少被堵塞了 "min_alarm_sustain_duration" 毫秒时,
## 报警才会被清除。这是为了避免太频繁地清除和再次发出警报.
## @path conn_congestion.min_alarm_sustain_duration
## @type emqx_schema:duration()
min_alarm_sustain_duration: "1m"
}
stats {
## @doc 启用/禁用统计数据收集功能
## @path stats.enable
## @type boolean()
enable: true
}
sysmon {
vm {
## @doc 定期进程限制检查的时间间隔。
## @path sysmon.vm.process_check_interval
## @type emqx_schema:duration()
process_check_interval: "30s"
## @doc 在发出相应警报之前,本地节点上可以同时存在多少进程的阈值(以进程百分比表示)。
## @path sysmon.vm.process_high_watermark
## @type emqx_schema:percent()
process_high_watermark: "80%"
## @doc 在清除相应警报之前,本地节点上可以同时存在多少进程的阈值(以进程百分比表示)。
## @path sysmon.vm.process_low_watermark
## @type emqx_schema:percent()
process_low_watermark: "60%"
## @doc 启用长垃圾回收监控
## @path sysmon.vm.long_gc
## @type union: disabled | emqx_schema:duration()
## long_gc:
## @doc 启用长调度监控
## @path sysmon.vm.long_schedule
## @type union: disabled | emqx_schema:duration()
long_schedule: "240ms"
## @doc 启用大 heap 监控
## @path sysmon.vm.large_heap
## @type union: disabled | emqx_schema:bytesize()
large_heap: "32MB"
## @doc 启用分布式端口过忙监控
## @path sysmon.vm.busy_dist_port
## @type boolean()
busy_dist_port: true
## @doc 启用端口过忙监控
## @path sysmon.vm.busy_port
## @type boolean()
busy_port: true
}
os {
## @doc 定期 CPU 检查的时间间隔。
## @path sysmon.os.cpu_check_interval
## @type emqx_schema:duration()
cpu_check_interval: "60s"
## @doc 在发出相应警报之前可以使用多少系统 CPU 的阈值,以系统CPU负载的百分比表示。
## @path sysmon.os.cpu_high_watermark
## @type emqx_schema:percent()
cpu_high_watermark: "80%"
## @doc 在解除相应警报之前可以使用多少系统 CPU 的阈值,以系统CPU负载的百分比表示。
## @path sysmon.os.cpu_low_watermark
## @type emqx_schema:percent()
cpu_low_watermark: "60%"
## @doc 定期内存检查的时间间隔。
## @path sysmon.os.mem_check_interval
## @type union: disabled | emqx_schema:duration()
mem_check_interval: "60s"
## @doc 在发出相应报警之前可以分配多少系统内存的阈值,以系统内存的百分比表示。
## @path sysmon.os.sysmem_high_watermark
## @type emqx_schema:percent()
sysmem_high_watermark: "70%"
## @doc 在发出相应警报之前,一个Erlang进程可以分配多少系统内存的阈值,以系统内存的百分比表示。
## @path sysmon.os.procmem_high_watermark
## @type emqx_schema:percent()
procmem_high_watermark: "5%"
}
top {
## @doc 每个监视组的顶级进程数
## @path sysmon.top.num_items
## @type non_neg_integer()
num_items: 10
## @doc 指定应收集进程顶部的频率
## @path sysmon.top.sample_interval
## @type emqx_schema:duration()
sample_interval: "2s"
## @doc 当VM中的进程数超过此值时,停止收集数据
## @path sysmon.top.max_procs
## @type non_neg_integer()
max_procs: 1000000
## @doc 收集数据点的 PostgreSQL 数据库的主机名
## @path sysmon.top.db_hostname
## @type string()
db_hostname: []
## @doc 收集数据点的 PostgreSQL 数据库的端口
## @path sysmon.top.db_port
## @type integer()
db_port: 5432
## @doc PostgreSQL 数据库的用户名
## @path sysmon.top.db_username
## @type string()
db_username: "system_monitor"
## @doc PostgreSQL 数据库的密码
## @path sysmon.top.db_password
## @type binary()
db_password: "system_monitor_password"
## @doc PostgreSQL 数据库的数据库名
## @path sysmon.top.db_name
## @type string()
db_name: "postgres"
}
}
alarm {
## @doc 警报激活时触发的动作。</br>
## 目前,支持以下操作:<code>log</code> 和 <code>publish</code>.
## <code>log</code> 将告警写入日志 (控制台或者文件).
## <code>publish</code> 将告警作为 MQTT 消息发布到系统主题:
## <code>$SYS/brokers/emqx@xx.xx.xx.x/alarms/activate</code> and
## <code>$SYS/brokers/emqx@xx.xx.xx.x/alarms/deactivate</code>
## @path alarm
## @type array
actions: [log, publish]
## @doc 要保留为历史记录的已停用报警的最大总数。当超过此限制时,将删除最旧的停用报警,以限制总数。
## @path alarm.size_limit
## @type 1..3000
size_limit: 1000
## @doc 停用报警的保留时间。报警在停用时不会立即删除,而是在保留时间之后删除。
## @path alarm.validity_period
## @type emqx_schema:duration()
validity_period: "24h"
}
flapping_detect {
## @doc 启用抖动检测功能
## @path flapping_detect.enable
## @type boolean()
enable: false
## @doc MQTT 客户端在"窗口"时间内允许的最大断开次数
## @path flapping_detect.max_count
## @type integer()
max_count: 15
## @doc 抖动检测的时间窗口。
## @path flapping_detect.window_time
## @type emqx_schema:duration()
window_time: "1m"
## @doc 抖动的客户端将会被禁止登陆多长时间
## @path flapping_detect.ban_time
## @type emqx_schema:duration()
ban_time: "5m"
}
persistent_session_store {
## @doc 使用数据库存储有关持久会话的信息。
## 这使得在节点停止时,可以将客户端连接迁移到另一个群集节点。
## @path persistent_session_store.enabled
## @type boolean()
enabled: false
## @doc 将持久会话数据保存在磁盘上。如果为 false 则存储在内存中。
## 如开启, 持久会话数据可在集群重启后恢复。
## 如关闭, 数据仅存储在内存中, 则在整个集群停止后丢失。
## @path persistent_session_store.on_disc
## @type boolean()
on_disc: true
## @doc 在内存中保持一份数据的副本,以便更快地访问。
## @path persistent_session_store.ram_cache
## @type boolean()
ram_cache: false
## @doc 用于存储持久性会话和信息的数据库管理后端
## - `builtin`: 使用内置的数据库(mria)
## @path persistent_session_store.backend
## @type union: broker:persistent_session_builtin
backend:
{
messages {ram_cache = "false"}
session {ram_cache = "true"}
session_messages {ram_cache = "true"}
type = "builtin"
}
## @doc 如果重新启动时处理上一个会话的节点已停止,则未传递到持久会话的消息在垃圾收集之前会被存储。
## @path persistent_session_store.max_retain_undelivered
## @type emqx_schema:duration()
max_retain_undelivered: "1h"
## @doc 将未送达的消息垃圾收集到持久会话的开始间隔。
## 这会影响检查 "max_retain_undelivered"(最大保留未送达)的删除频率。
## @path persistent_session_store.message_gc_interval
## @type emqx_schema:duration()
message_gc_interval: "1h"
## @doc 持久会话消息的临时数据垃圾收集的开始间隔。
## 这不会影响持久会话消息的生命周期长度。
##
## @path persistent_session_store.session_message_gc_interval
## @type emqx_schema:duration()
session_message_gc_interval: "1m"
}
trace {
## @doc
## 确定跟踪文件中有效负载格式的格式</br>
## `text`:基于文本的协议或纯文本协议。
## 建议在有效负载为JSON编码时使用</br>
## `hex`:二进制十六进制编码。当有效负载是自定义二进制协议时,建议使用此选项</br>
## `hidden`:有效负载被模糊化为 `******`
##
## @path trace.payload_encode
## @type enum: hex | text | hidden
payload_encode: text
}
bridges {
## @doc 转发消息到 HTTP 服务器的 HTTP Bridge
## @path bridges.http
## @type map()
## http:
## $name {
## @doc 启用/禁用 Bridge
## @path bridges.http.$name.enable
## @type boolean()
## enable: true
## @doc Bridge 的方向, 必须是 egress
## @path bridges.http.$name.direction
## @type singleton
## direction: egress
## @doc 连接HTTP服务器的超时时间。
## @path bridges.http.$name.connect_timeout
## @type emqx_schema:duration_ms()
## connect_timeout: "15s"
## @doc 请求出错时的最大重试次数。
## @path bridges.http.$name.max_retries
## @type non_neg_integer()
## max_retries: 5
## @doc 重试之间的间隔时间。
## @path bridges.http.$name.retry_interval
## @type emqx_schema:duration()
## retry_interval: "1s"
## @doc 连接池的类型,可用类型有`random`, `hash`。
## @path bridges.http.$name.pool_type
## @type emqx_connector_http:pool_type()
## pool_type: random
## @doc 连接池大小。
## @path bridges.http.$name.pool_size
## @type pos_integer()
## pool_size: 8
## @doc 允许HTTP管道。
## @path bridges.http.$name.enable_pipelining
## @type boolean()
## enable_pipelining: true
## request {
## @doc HTTP 请求方法。
## @path bridges.http.$name.request.method
## @type enum: post | put | get | delete
## method: post
## @doc HTTP请求路径。
## @path bridges.http.$name.request.path
## @type binary()
## path:
## @doc HTTP请求报文主体。
## @path bridges.http.$name.request.body
## @type binary()
## body:
## @doc HTTP 头字段列表。
## @path bridges.http.$name.request.headers
## @type map()
## headers:
## @doc HTTP 请求超时。
## @path bridges.http.$name.request.request_timeout
## @type emqx_schema:duration_ms()
## request_timeout:
## }
## ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path bridges.http.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path bridges.http.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path bridges.http.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path bridges.http.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path bridges.http.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path bridges.http.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path bridges.http.$name.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path bridges.http.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path bridges.http.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path bridges.http.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path bridges.http.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc 启用 TLS
## @path bridges.http.$name.ssl.enable
## @type boolean()
## enable: false
## @doc
## 指定要在 TLS 服务器名称指示扩展中使用的主机名</br>
## 例如,当连接到 "server.example.net" 时,接受连接并执行 TLS 握手的真正服务器可能与 TLS 客户端最初连接到的主机不同,
## 例如,当连接到 IP 地址时,或者当主机具有多个可解析的 DNS 记录时</br>
## 如果未指定,它将默认为使用的主机名字符串
## 建立连接,除非使用 IP 地址</br>
## 然后,主机名也用于对等机的主机名验证
## 证书</br>特殊值'disable'阻止发送服务器名称指示扩展,并禁用主机名验证检查。
##
## @path bridges.http.$name.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
## }
## @doc
## HTTP Bridge 的 URL。</br>
## 路径中允许使用带变量的模板,但是 host, port 不允许使用变量模板。</br>
## 例如,<code> http://localhost:9901/${topic} </code> 是允许的,
## 但是<code> http://${host}:9901/message </code>
## 或 <code> http://localhost:${port}/message </code>
## 不允许。
##
## @path bridges.http.$name.url
## @type binary()
## url:
## @doc
## 发送到 'local_topic' 的消息都会转发到 HTTP 服务器。 </br>
## 注意:如果这个 Bridge 被用作规则(EMQX 规则引擎)的输出,同时也配置了 'local_topic' ,那么这两部分的消息都会被转发到 HTTP 服务器。
##
## @path bridges.http.$name.local_topic
## @type binary()
## local_topic:
## @doc
## HTTP 请求的方法。 所有可用的方法包括:post、put、get、delete。</br>
## 允许使用带有变量的模板。</br>
## @path bridges.http.$name.method
## @type enum: post | put | get | delete
## method: post
## @doc
## HTTP 请求的标头。</br>
## 允许使用带有变量的模板。
##
## @path bridges.http.$name.headers
## @type map()
## headers:
## {
## accept = "application/json"
## "cache-control" = "no-cache"
## connection = "keep-alive"
## "content-type" = "application/json"
## "keep-alive" = "timeout=5"
## }
##
## @doc
## HTTP 请求的正文。</br>
## 允许使用带有变量的模板。
## @path bridges.http.$name.body
## @type binary()
## body: "${payload}"
## @doc HTTP 请求超时
## @path bridges.http.$name.request_timeout
## @type emqx_schema:duration_ms()
## request_timeout: "15s"
## }
## @doc 桥接到另一个 MQTT Broker 的 MQTT Bridge
## @path bridges.mqtt
## @type map()
## mqtt:
## @path bridges.mqtt.$name
## @type union: ingress | egress
## $name:
}
retainer {
## @doc 是否开启消息保留功能
## @path retainer.enable
## @type boolean()
enable: true
## @doc 消息保留时间。0 代表永久保留
## @path retainer.msg_expiry_interval
## @type emqx_schema:duration_ms()
msg_expiry_interval: "0s"
## @doc 消息清理间隔。0 代表不进行清理
## @path retainer.msg_clear_interval
## @type emqx_schema:duration_ms()
msg_clear_interval: "0s"
flow_control {
## @doc 从存储后端批量加载时的每批数量上限,0 代表一次性读取
## @path retainer.flow_control.batch_read_number
## @type non_neg_integer()
batch_read_number: 0
## @doc 批量派发时每批的数量。0 代表一次性全部派发
## @path retainer.flow_control.batch_deliver_number
## @type 0..1000
batch_deliver_number: 0
## @doc 批量发送的限流器的名称。
## 限流器可以用来防止短时间内向客户端发送太多的消息,从而避免过多的消息导致客户端队列堵塞甚至崩溃。
## 这个名称需要是指向 `limiter.batch` 下的一个真实存在的限流器。
## 如果这个字段为空,则不使用限流器。
##
## @path retainer.flow_control.batch_deliver_limiter
## @type emqx_limiter_schema:bucket_name()
## batch_deliver_limiter:
}
## @doc 消息大小最大值
## @path retainer.max_payload_size
## @type emqx_schema:bytesize()
max_payload_size: "1MB"
## @doc 是否不发送保留消息的清理消息,在 MQTT 5.0 中如果一条保留消息的消息体为空,则会清除掉之前存储
## 的对应的保留消息,通过这个值控制是否停止发送清理消息
## @path retainer.stop_publish_clear_msg
## @type boolean()
stop_publish_clear_msg: false
backend {
## @doc 后端类型
## @path retainer.backend.type
## @type enum: built_in_database
type: built_in_database
## @doc 选择消息是存放在磁盘还是内存中
## @path retainer.backend.storage_type
## @type union: ram | disc
storage_type: ram
## @doc 消息保留的数量上限。0 表示无限
## @path retainer.backend.max_retained_messages
## @type non_neg_integer()
max_retained_messages: 0
## @doc Retainer index specifications: list of arrays of positive ascending integers. Each array specifies an index. Numbers in an index specification are 1-based word positions in topics. Words from specified positions will be used for indexing.</br>For example, it is good to have <code>[2, 4]</code> index to optimize <code>+/X/+/Y/...</code> topic wildcard subscriptions.
## @path retainer.backend.index_specs
## @type [[integer()]]
index_specs:
[
[1, 2, 3],
[1, 3],
[2, 3],
[3]
]
}
}
statsd {
## @doc 开启或关闭 Statsd 数据推送
## @path statsd.enable
## @type boolean()
enable: false
## @doc Statsd 服务器地址
## @path statsd.server
## @type emqx_schema:ip_port()
server: "127.0.0.1:8125"
## @doc 数据收集间隔,单位 毫秒
## @path statsd.sample_time_interval
## @type emqx_schema:duration_ms()
sample_time_interval: "10s"
## @doc 数据推送间隔,单位 毫秒
## @path statsd.flush_time_interval
## @type emqx_schema:duration_ms()
flush_time_interval: "10s"
}
auto_subscribe {
## @doc 设备登陆成功之后,通过预设的订阅表示符,为设备自动完成订阅。支持使用占位符。
## @path auto_subscribe
## @type array
topics: []
## $INDEX {
## @doc 订阅标识符,支持使用占位符,例如 client/${clientid}/username/${username}/host/${host}/port/${port}
## 必填,且不可为空字符串
## @path auto_subscribe.topics.$INDEX.topic
## @type binary()
## topic:
## @doc 缺省值为 0,服务质量,
## QoS 0:消息最多传递一次,如果当时客户端不可用,则会丢失该消息。
## QoS 1:消息传递至少 1 次。
## QoS 2:消息仅传送一次。
## @path auto_subscribe.topics.$INDEX.qos
## @type qos()
## qos: 0
## @doc 指定订阅建立时服务端是否向客户端发送保留消息,
## 可选值 0:只要客户端订阅成功,服务端就发送保留消息。
## 可选值 1:客户端订阅成功且该订阅此前不存在,服务端才发送保留消息。毕竟有些时候客户端重新发起订阅可能只是为了改变一下 QoS,并不意味着它想再次接收保留消息。
## 可选值 2:即便客户订阅成功,服务端也不会发送保留消息。
## @path auto_subscribe.topics.$INDEX.rh
## @type 0..2
## rh: 0
## @doc 缺省值为 0,这一选项用来指定服务端向客户端转发消息时是否要保留其中的 RETAIN 标识,注意这一选项不会影响保留消息中的 RETAIN 标识。因此当 Retain As Publish 选项被设置为 0 时,客户端直接依靠消息中的 RETAIN 标识来区分这是一个正常的转发消息还是一个保留消息,而不是去判断消息是否是自己订阅后收到的第一个消息(转发消息甚至可能会先于保留消息被发送,视不同 Broker 的具体实现而定)。
## @path auto_subscribe.topics.$INDEX.rap
## @type 0..1
## rap: 0
## @doc 缺省值为0,
## MQTT v3.1.1:如果设备订阅了自己发布消息的主题,那么将收到自己发布的所有消息。
## MQTT v5:如果设备在订阅时将此选项设置为 1,那么服务端将不会向设备转发自己发布的消息
## @path auto_subscribe.topics.$INDEX.nl
## @type 0..1
## nl: 0
## }
}
delayed {
## @doc 是否开启该功能
## @path delayed.enable
## @type boolean()
enable: true
## @doc 延迟消息的数量上限(0 代表无限)
## @path delayed.max_delayed_messages
## @type integer()
max_delayed_messages: 0
}
telemetry {
## @doc Enable telemetry.
## @path telemetry.enable
## @type boolean()
enable: true
}
## @doc List of topic rewrite rules.
## @doc List of topic rewrite rules.
## @path
## @type array
rewrite: []
## $INDEX {
## @doc 主题重写在哪种操作上生效:
## - `subscribe`:订阅时重写主题;
## - `publish`:发布时重写主题;
## -`all`:全部重写主题
## @path rewrite.$INDEX.action
## @type enum: subscribe | publish | all
## action: subscribe
## @doc 源主题,客户端业务指定的主题
## @path rewrite.$INDEX.source_topic
## @type binary()
## source_topic:
## @doc 目标主题。
## @path rewrite.$INDEX.dest_topic
## @type binary()
## dest_topic:
## @doc 正则表达式
## @path rewrite.$INDEX.re
## @type binary()
## re:
## }
## @doc List of topics whose metrics are reported.
## @doc List of topics whose metrics are reported.
## @path
## @type array
topic_metrics: []
## $INDEX {
## @doc Collect metrics for the topic.
## @path topic_metrics.$INDEX.topic
## @type binary()
## topic:
## }
plugins {
## @doc 一组插件的状态。插件将按照定义的顺序启动
## @path plugins
## @type array
states: []
## $INDEX {
## @doc 插件的名称{name}-{version}。</br>
## 它应该与插件的发布包名称一致,如my_plugin-0.1.0。
## @path plugins.states.$INDEX.name_vsn
## @type string()
## name_vsn:
## @doc 设置为“true”以启用此插件
## @path plugins.states.$INDEX.enable
## @type boolean()
## enable:
## }
## @doc 插件安装包的目录, 不要自己创建, 只能由emqx用户创建与修改
## @path plugins.install_dir
## @type string()
install_dir: "plugins"
## @doc 检查间隔:检查集群中插件的状态是否一致,</br>
## 如果连续3次检查结果不一致,则报警。
##
## @path plugins.check_interval
## @type emqx_schema:duration()
check_interval: "5s"
}
dashboard {
listeners {
http {
## @doc 忽略或启用该监听器配置
## @path dashboard.listeners.http.enable
## @type boolean()
enable: true
## @doc 监听的地址与端口,在dashboard更新此配置时,会重启dashboard服务。
## @path dashboard.listeners.http.bind
## @type union: non_neg_integer() | emqx_schema:ip_port()
bind: 18803
## @doc TCP协议的Socket acceptor池大小
## @path dashboard.listeners.http.num_acceptors
## @type integer()
num_acceptors: 4
## @doc 同时处理的最大连接数
## @path dashboard.listeners.http.max_connections
## @type integer()
max_connections: 512
## @doc 排队等待连接的队列的最大长度
## @path dashboard.listeners.http.backlog
## @type integer()
backlog: 1024
## @doc Socket发送超时时间
## @path dashboard.listeners.http.send_timeout
## @type emqx_schema:duration()
send_timeout: "5s"
## @doc 启用IPv6, 如果机器不支持IPv6,请关闭此选项,否则会导致仪表盘无法使用。
## @path dashboard.listeners.http.inet6
## @type boolean()
inet6: false
## @doc 当开启 inet6 功能的同时禁用 IPv4-to-IPv6 映射。该配置仅在 inet6 功能开启时有效。
## @path dashboard.listeners.http.ipv6_v6only
## @type boolean()
ipv6_v6only: false
}
https {
## @doc 忽略或启用该监听器配置
## @path dashboard.listeners.https.enable
## @type boolean()
enable: false
## @doc 监听的地址与端口,在dashboard更新此配置时,会重启dashboard服务。
## @path dashboard.listeners.https.bind
## @type union: non_neg_integer() | emqx_schema:ip_port()
bind: 18804
## @doc TCP协议的Socket acceptor池大小
## @path dashboard.listeners.https.num_acceptors
## @type integer()
num_acceptors: 4
## @doc 同时处理的最大连接数
## @path dashboard.listeners.https.max_connections
## @type integer()
max_connections: 512
## @doc 排队等待连接的队列的最大长度
## @path dashboard.listeners.https.backlog
## @type integer()
backlog: 1024
## @doc Socket发送超时时间
## @path dashboard.listeners.https.send_timeout
## @type emqx_schema:duration()
send_timeout: "5s"
## @doc 启用IPv6, 如果机器不支持IPv6,请关闭此选项,否则会导致仪表盘无法使用。
## @path dashboard.listeners.https.inet6
## @type boolean()
inet6: false
## @doc 当开启 inet6 功能的同时禁用 IPv4-to-IPv6 映射。该配置仅在 inet6 功能开启时有效。
## @path dashboard.listeners.https.ipv6_v6only
## @type boolean()
ipv6_v6only: false
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path dashboard.listeners.https.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path dashboard.listeners.https.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path dashboard.listeners.https.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path dashboard.listeners.https.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path dashboard.listeners.https.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path dashboard.listeners.https.depth
## @type integer()
depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path dashboard.listeners.https.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path dashboard.listeners.https
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path dashboard.listeners.https
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path dashboard.listeners.https.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path dashboard.listeners.https.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path dashboard.listeners.https.dhfile
## @type string()
## dhfile:
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path dashboard.listeners.https.honor_cipher_order
## @type boolean()
honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path dashboard.listeners.https.client_renegotiation
## @type boolean()
client_renegotiation: true
## @doc
## 握手完成所允许的最长时间
##
## @path dashboard.listeners.https.handshake_timeout
## @type emqx_schema:duration()
handshake_timeout: "15s"
}
}
## @doc 默认的仪表板用户名
## @path dashboard.default_username
## @type binary()
default_username: "admin"
## @doc 默认的仪表板用户密码
## 为了安全,应该尽快修改密码。
## @path dashboard.default_password
## @type binary()
default_password: "public"
## @doc 更新仪表板中显示的指标的时间间隔。必须小于60,且被60的整除。
## @path dashboard.sample_interval
## @type emqx_schema:duration_s()
sample_interval: "10s"
## @doc JWT token 过期时间
## @path dashboard.token_expired_time
## @type emqx_schema:duration()
token_expired_time: "60m"
## @doc 支持跨域资源共享(CORS)
## 允许服务器指示任何来源(域名、协议或端口),除了本服务器之外的任何浏览器应允许加载资源。
## @path dashboard.cors
## @type boolean()
cors: false
## @doc swagger多语言支持
## @path dashboard.i18n_lang
## @type enum: en | zh
i18n_lang: en
}
gateway {
stomp {
frame {
## @doc 允许的 Header 最大数量
## @path gateway.stomp.frame.max_headers
## @type non_neg_integer()
max_headers: 10
## @doc 允许的 Header 字符串的最大长度
## @path gateway.stomp.frame.max_headers_length
## @type non_neg_integer()
max_headers_length: 1024
## @doc 允许的 Stomp 报文 Body 的最大字节数
## @path gateway.stomp.frame.max_body_length
## @type integer()
max_body_length: 65536
}
## @doc
## @path gateway.stomp.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.stomp.listeners.tcp
## @type map()
## tcp:
## $name {
## @doc Acceptor 进程池大小。
## @path gateway.stomp.listeners.tcp.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.stomp.listeners.tcp.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path gateway.stomp.listeners.tcp.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path gateway.stomp.listeners.tcp.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path gateway.stomp.listeners.tcp.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path gateway.stomp.listeners.tcp.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path gateway.stomp.listeners.tcp.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path gateway.stomp.listeners.tcp.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path gateway.stomp.listeners.tcp.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path gateway.stomp.listeners.tcp.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path gateway.stomp.listeners.tcp.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否开启 Proxy Protocol V1/2。当 EMQX 集群部署在 HAProxy 或 Nginx 后需要获取客户端真实 IP 时常用到该选项。参考:https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.stomp.listeners.tcp.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc 接收 Proxy Protocol 报文头的超时时间。如果在超时内没有收到 Proxy Protocol 包,EMQX 将关闭 TCP 连接。
## @path gateway.stomp.listeners.tcp.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc 是否启用该监听器。
## @path gateway.stomp.listeners.tcp.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.stomp.listeners.tcp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.stomp.listeners.tcp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.stomp.listeners.tcp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.stomp.listeners.tcp.$name.authentication
## @link gateway.exproto.listeners.tcp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.stomp.listeners.tcp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.stomp.listeners.tcp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.stomp.listeners.ssl
## @type map()
## ssl:
## $name {
## @doc Acceptor 进程池大小。
## @path gateway.stomp.listeners.ssl.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.stomp.listeners.ssl.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path gateway.stomp.listeners.ssl.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path gateway.stomp.listeners.ssl.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path gateway.stomp.listeners.ssl.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path gateway.stomp.listeners.ssl.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path gateway.stomp.listeners.ssl.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path gateway.stomp.listeners.ssl.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path gateway.stomp.listeners.ssl.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path gateway.stomp.listeners.ssl.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path gateway.stomp.listeners.ssl.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否开启 Proxy Protocol V1/2。当 EMQX 集群部署在 HAProxy 或 Nginx 后需要获取客户端真实 IP 时常用到该选项。参考:https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.stomp.listeners.ssl.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc 接收 Proxy Protocol 报文头的超时时间。如果在超时内没有收到 Proxy Protocol 包,EMQX 将关闭 TCP 连接。
## @path gateway.stomp.listeners.ssl.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc 是否启用该监听器。
## @path gateway.stomp.listeners.ssl.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.stomp.listeners.ssl.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.stomp.listeners.ssl.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.stomp.listeners.ssl.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.stomp.listeners.ssl.$name.authentication
## @link gateway.exproto.listeners.ssl.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.stomp.listeners.ssl.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.stomp.listeners.ssl.$name
## @type array
## access_rules: []
## ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path gateway.stomp.listeners.ssl.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.stomp.listeners.ssl.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.dhfile
## @type string()
## dhfile:
## @doc
## TLS/DTLS 服务器与 {verify,verify_peer} 一起使用。
## 如果设置为true,则如果客户端没有要发送的证书,即发送空证书,服务器将失败。
## 如果设置为false,则仅当客户端发送无效证书(空证书被视为有效证书)时才会失败。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path gateway.stomp.listeners.ssl.$name.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
}
## @doc 是否启用该网关
## @path gateway.stomp.enable
## @type boolean()
enable: true
## @doc 是否开启客户端统计
## @path gateway.stomp.enable_stats
## @type boolean()
enable_stats: true
## @doc 客户端连接过程的空闲时间。该配置用于:
## 1. 一个新创建的客户端进程如果在该时间间隔内没有收到任何客户端请求,将被直接关闭。
## 2. 一个正在运行的客户进程如果在这段时间后没有收到任何客户请求,将进入休眠状态以节省资源。
## @path gateway.stomp.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc username 重写模板
## @path gateway.stomp.clientinfo_override.username
## @type binary()
## username:
## @doc password 重写模板
## @path gateway.stomp.clientinfo_override.password
## @type binary()
## password:
## @doc clientid 重写模板
## @path gateway.stomp.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.stomp.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
mqttsn {
## @doc MQTT-SN 网关 ID。
## 当 <code>broadcast</code> 打开时,MQTT-SN 网关会使用该 ID 来广播 ADVERTISE 消息
## @path gateway.mqttsn.gateway_id
## @type integer()
gateway_id: 1
## @doc 是否周期性广播 ADVERTISE 消息
## @path gateway.mqttsn.broadcast
## @type boolean()
broadcast: false
## @doc 是否允许无连接的客户端发送 QoS 等于 -1 的消息。
## 该功能主要用于支持轻量的 MQTT-SN 客户端实现,它不会向网关建立连接,注册主题,也不会发起订阅;它只使用 QoS 为 -1 来发布消息
## @path gateway.mqttsn.enable_qos3
## @type boolean()
enable_qos3: true
## @doc 在会话被重用后,网关是否主动向客户端注册对已订阅主题名称
## @path gateway.mqttsn.subs_resume
## @type boolean()
subs_resume: false
## @doc 预定义主题列表。
## 预定义的主题列表,是一组 主题 ID 和 主题名称 的映射关系。使用预先定义的主题列表,可以减少 MQTT-SN 客户端和网关对于固定主题的注册请求
## @path gateway.mqttsn
## @type array
predefined: []
## $INDEX {
## @doc 主题 ID。范围:1-65535
## @path gateway.mqttsn.predefined.$INDEX.id
## @type integer()
## id:
## @doc 主题名称。注:不支持通配符
## @path gateway.mqttsn.predefined.$INDEX.topic
## @type binary()
## topic:
## }
## @doc
## @path gateway.mqttsn.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.mqttsn.listeners.udp
## @link gateway.coap.listeners.udp
## @type map()
## @doc
## @path gateway.mqttsn.listeners.dtls
## @link gateway.coap.listeners.dtls
## @type map()
}
## @doc 是否启用该网关
## @path gateway.mqttsn.enable
## @type boolean()
enable: true
## @doc 是否开启客户端统计
## @path gateway.mqttsn.enable_stats
## @type boolean()
enable_stats: true
## @doc 客户端连接过程的空闲时间。该配置用于:
## 1. 一个新创建的客户端进程如果在该时间间隔内没有收到任何客户端请求,将被直接关闭。
## 2. 一个正在运行的客户进程如果在这段时间后没有收到任何客户请求,将进入休眠状态以节省资源。
## @path gateway.mqttsn.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc username 重写模板
## @path gateway.mqttsn.clientinfo_override.username
## @type binary()
## username:
## @doc password 重写模板
## @path gateway.mqttsn.clientinfo_override.password
## @type binary()
## password:
## @doc clientid 重写模板
## @path gateway.mqttsn.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.mqttsn.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
coap {
## @doc CoAP 网关要求客户端的最小心跳间隔时间。
## 当 <code>connection_required</code> 开启后,该参数用于检查客户端连接是否存活
## @path gateway.coap.heartbeat
## @type emqx_gateway_schema:duration()
heartbeat: "30s"
## @doc 是否开启连接模式。
## 连接模式是非标准协议的功能。它维护 CoAP 客户端上线、认证、和连接状态的保持
## @path gateway.coap.connection_required
## @type boolean()
connection_required: false
## @doc 投递给 CoAP 客户端的通知消息类型。当客户端 Observe 一个资源(或订阅某个主题)时,网关会向客户端推送新产生的消息。其消息类型可设置为:
## - non: 不需要客户端返回确认消息;
## - con: 需要客户端返回一个确认消息;
## - qos: 取决于消息的 QoS 等级; QoS 0 会以 `non` 类型下发,QoS 1/2 会以 `con` 类型下发
##
## @path gateway.coap.notify_type
## @type union: non | con | qos
notify_type: qos
## @doc 客户端订阅请求的默认 QoS 等级。
## 当 CoAP 客户端发起订阅请求时,如果未携带 `qos` 参数则会使用该默认值。默认值可设置为:
## - qos0, qos1, qos2: 设置为固定的 QoS 等级
## - coap: 依据订阅操作的 CoAP 报文类型来动态决定
## * 当订阅请求为 `non-confirmable` 类型时,取值为 qos0
## * 当订阅请求为 `confirmable` 类型时,取值为 qos1
##
## @path gateway.coap.subscribe_qos
## @type enum: qos0 | qos1 | qos2 | coap
subscribe_qos: coap
## @doc 客户端发布请求的默认 QoS 等级。
## 当 CoAP 客户端发起发布请求时,如果未携带 `qos` 参数则会使用该默认值。默认值可设置为:
## - qos0, qos1, qos2: 设置为固定的 QoS 等级
## - coap: 依据发布操作的 CoAP 报文类型来动态决定
## * 当发布请求为 `non-confirmable` 类型时,取值为 qos0
## * 当发布请求为 `confirmable` 类型时,取值为 qos1
##
## @path gateway.coap.publish_qos
## @type enum: qos0 | qos1 | qos2 | coap
publish_qos: coap
## @doc
## @path gateway.coap.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.coap.listeners.udp
## @type map()
## udp:
## $name {
## udp {
## @doc 为 Socket 指定 {active, N} 选项。
## 参见:https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.coap.listeners.udp.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Socket 在内核空间接收缓冲区的大小。
## @path gateway.coap.listeners.udp.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Socket 在内核空间发送缓冲区的大小。
## @path gateway.coap.listeners.udp.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Socket 在用户空间的缓冲区大小。
## @path gateway.coap.listeners.udp.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc 允许重用本地处于 TIME_WAIT 的端口号
## @path gateway.coap.listeners.udp.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否启用该监听器。
## @path gateway.coap.listeners.udp.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.coap.listeners.udp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.coap.listeners.udp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.coap.listeners.udp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.coap.listeners.udp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.coap.listeners.udp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.coap.listeners.udp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.coap.listeners.dtls
## @type map()
## dtls:
## $name {
## @doc Acceptor 进程池大小。
## @path gateway.coap.listeners.dtls.$name.acceptors
## @type integer()
## acceptors: 16
## udp {
## @doc 为 Socket 指定 {active, N} 选项。
## 参见:https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.coap.listeners.dtls.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Socket 在内核空间接收缓冲区的大小。
## @path gateway.coap.listeners.dtls.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Socket 在内核空间发送缓冲区的大小。
## @path gateway.coap.listeners.dtls.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Socket 在用户空间的缓冲区大小。
## @path gateway.coap.listeners.dtls.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc 允许重用本地处于 TIME_WAIT 的端口号
## @path gateway.coap.listeners.dtls.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否启用该监听器。
## @path gateway.coap.listeners.dtls.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.coap.listeners.dtls.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.coap.listeners.dtls.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.coap.listeners.dtls.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.coap.listeners.dtls.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.coap.listeners.dtls.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.coap.listeners.dtls.$name
## @type array
## access_rules: []
## dtls {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path gateway.coap.listeners.dtls.$name.dtls.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path gateway.coap.listeners.dtls.$name.dtls.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path gateway.coap.listeners.dtls.$name.dtls.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path gateway.coap.listeners.dtls.$name.dtls.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path gateway.coap.listeners.dtls.$name.dtls.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path gateway.coap.listeners.dtls.$name.dtls.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path gateway.coap.listeners.dtls.$name.dtls.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path gateway.coap.listeners.dtls.$name.dtls
## @type array
## versions: [dtlsv1.2, dtlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.coap.listeners.dtls.$name.dtls
## @type array
## ciphers: ["ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path gateway.coap.listeners.dtls.$name.dtls.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path gateway.coap.listeners.dtls.$name.dtls.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path gateway.coap.listeners.dtls.$name.dtls.dhfile
## @type string()
## dhfile:
## @doc
## TLS/DTLS 服务器与 {verify,verify_peer} 一起使用。
## 如果设置为true,则如果客户端没有要发送的证书,即发送空证书,服务器将失败。
## 如果设置为false,则仅当客户端发送无效证书(空证书被视为有效证书)时才会失败。
##
## @path gateway.coap.listeners.dtls.$name.dtls.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path gateway.coap.listeners.dtls.$name.dtls.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path gateway.coap.listeners.dtls.$name.dtls.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
}
## @doc 是否启用该网关
## @path gateway.coap.enable
## @type boolean()
enable: true
## @doc 是否开启客户端统计
## @path gateway.coap.enable_stats
## @type boolean()
enable_stats: true
## @doc 客户端连接过程的空闲时间。该配置用于:
## 1. 一个新创建的客户端进程如果在该时间间隔内没有收到任何客户端请求,将被直接关闭。
## 2. 一个正在运行的客户进程如果在这段时间后没有收到任何客户请求,将进入休眠状态以节省资源。
## @path gateway.coap.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc username 重写模板
## @path gateway.coap.clientinfo_override.username
## @type binary()
## username:
## @doc password 重写模板
## @path gateway.coap.clientinfo_override.password
## @type binary()
## password:
## @doc clientid 重写模板
## @path gateway.coap.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.coap.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
lwm2m {
## @doc LwM2M Resource 定义的 XML 文件目录路径
## @path gateway.lwm2m.xml_dir
## @type binary()
xml_dir: "etc/lwm2m_xml"
## @doc 允许 LwM2M 客户端允许设置的心跳最小值
## @path gateway.lwm2m.lifetime_min
## @type emqx_gateway_schema:duration()
lifetime_min: "15s"
## @doc 允许 LwM2M 客户端允许设置的心跳最大值
## @path gateway.lwm2m.lifetime_max
## @type emqx_gateway_schema:duration()
lifetime_max: "86400s"
## @doc 在QMode模式下,LwM2M网关认为网络链接有效的时间窗口的值。
## 例如,在收到客户端的更新信息后,在这个时间窗口内的任何信息都会直接发送到LwM2M客户端,而超过这个时间窗口的所有信息都会暂时储存在内存中
## @path gateway.lwm2m.qmode_time_window
## @type emqx_gateway_schema:duration_s()
qmode_time_window: "22s"
## @doc 自动 Observe REGISTER 数据包的 Object 列表
## @path gateway.lwm2m.auto_observe
## @type boolean()
auto_observe: false
## @doc 发布UPDATE事件消息的策略。
## - always: 只要收到 UPDATE 请求,就发送更新事件。
## - contains_object_list: 仅当 UPDATE 请求携带 Object 列表时才发送更新事件
##
## @path gateway.lwm2m.update_msg_publish_condition
## @type union: always | contains_object_list
update_msg_publish_condition: "contains_object_list"
translators {
command {
## @doc 主题名称
## @path gateway.lwm2m.translators.command.topic
## @type binary()
## topic:
## @doc QoS 等级
## @path gateway.lwm2m.translators.command.qos
## @type qos()
qos: 0
}
response {
## @doc 主题名称
## @path gateway.lwm2m.translators.response.topic
## @type binary()
## topic:
## @doc QoS 等级
## @path gateway.lwm2m.translators.response.qos
## @type qos()
qos: 0
}
notify {
## @doc 主题名称
## @path gateway.lwm2m.translators.notify.topic
## @type binary()
## topic:
## @doc QoS 等级
## @path gateway.lwm2m.translators.notify.qos
## @type qos()
qos: 0
}
register {
## @doc 主题名称
## @path gateway.lwm2m.translators.register.topic
## @type binary()
## topic:
## @doc QoS 等级
## @path gateway.lwm2m.translators.register.qos
## @type qos()
qos: 0
}
update {
## @doc 主题名称
## @path gateway.lwm2m.translators.update.topic
## @type binary()
## topic:
## @doc QoS 等级
## @path gateway.lwm2m.translators.update.qos
## @type qos()
qos: 0
}
}
## @doc
## @path gateway.lwm2m.mountpoint
## @type binary()
mountpoint: "lwm2m/${endpoint_name}/"
listeners {
## @doc
## @path gateway.lwm2m.listeners.udp
## @link gateway.coap.listeners.udp
## @type map()
## @doc
## @path gateway.lwm2m.listeners.dtls
## @link gateway.coap.listeners.dtls
## @type map()
}
## @doc 是否启用该网关
## @path gateway.lwm2m.enable
## @type boolean()
enable: true
## @doc 是否开启客户端统计
## @path gateway.lwm2m.enable_stats
## @type boolean()
enable_stats: true
## @doc 客户端连接过程的空闲时间。该配置用于:
## 1. 一个新创建的客户端进程如果在该时间间隔内没有收到任何客户端请求,将被直接关闭。
## 2. 一个正在运行的客户进程如果在这段时间后没有收到任何客户请求,将进入休眠状态以节省资源。
## @path gateway.lwm2m.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc username 重写模板
## @path gateway.lwm2m.clientinfo_override.username
## @type binary()
## username:
## @doc password 重写模板
## @path gateway.lwm2m.clientinfo_override.password
## @type binary()
## password:
## @doc clientid 重写模板
## @path gateway.lwm2m.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.lwm2m.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
exproto {
server {
## @doc 服务监听地址和端口。
## @path gateway.exproto.server.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path gateway.exproto.server.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path gateway.exproto.server.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path gateway.exproto.server.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path gateway.exproto.server.ssl.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path gateway.exproto.server.ssl.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path gateway.exproto.server.ssl.depth
## @type integer()
depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path gateway.exproto.server.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path gateway.exproto.server.ssl
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.server.ssl
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path gateway.exproto.server.ssl.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path gateway.exproto.server.ssl.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path gateway.exproto.server.ssl.dhfile
## @type string()
## dhfile:
## @doc
## TLS/DTLS 服务器与 {verify,verify_peer} 一起使用。
## 如果设置为true,则如果客户端没有要发送的证书,即发送空证书,服务器将失败。
## 如果设置为false,则仅当客户端发送无效证书(空证书被视为有效证书)时才会失败。
##
## @path gateway.exproto.server.ssl.fail_if_no_peer_cert
## @type boolean()
fail_if_no_peer_cert: false
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path gateway.exproto.server.ssl.honor_cipher_order
## @type boolean()
honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path gateway.exproto.server.ssl.client_renegotiation
## @type boolean()
client_renegotiation: true
## @doc
## 握手完成所允许的最长时间
##
## @path gateway.exproto.server.ssl.handshake_timeout
## @type emqx_schema:duration()
handshake_timeout: "15s"
}
}
handler {
## @doc 对端 gRPC 服务器地址。
## @path gateway.exproto.handler.address
## @type binary()
## address:
ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path gateway.exproto.handler.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path gateway.exproto.handler.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path gateway.exproto.handler.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path gateway.exproto.handler.ssl.verify
## @type enum: verify_peer | verify_none
verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path gateway.exproto.handler.ssl.reuse_sessions
## @type boolean()
reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path gateway.exproto.handler.ssl.depth
## @type integer()
depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path gateway.exproto.handler.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path gateway.exproto.handler.ssl
## @type array
versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.handler.ssl
## @type array
ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path gateway.exproto.handler.ssl.user_lookup_fun
## @type string()
user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path gateway.exproto.handler.ssl.secure_renegotiate
## @type boolean()
secure_renegotiate: true
## @doc 启用 TLS
## @path gateway.exproto.handler.ssl.enable
## @type boolean()
enable: false
## @doc
## 指定要在 TLS 服务器名称指示扩展中使用的主机名</br>
## 例如,当连接到 "server.example.net" 时,接受连接并执行 TLS 握手的真正服务器可能与 TLS 客户端最初连接到的主机不同,
## 例如,当连接到 IP 地址时,或者当主机具有多个可解析的 DNS 记录时</br>
## 如果未指定,它将默认为使用的主机名字符串
## 建立连接,除非使用 IP 地址</br>
## 然后,主机名也用于对等机的主机名验证
## 证书</br>特殊值'disable'阻止发送服务器名称指示扩展,并禁用主机名验证检查。
##
## @path gateway.exproto.handler.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
}
}
## @doc
## @path gateway.exproto.mountpoint
## @type binary()
mountpoint: ""
listeners {
## @doc
## @path gateway.exproto.listeners.tcp
## @type map()
## tcp:
## $name {
## @doc Acceptor 进程池大小。
## @path gateway.exproto.listeners.tcp.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.exproto.listeners.tcp.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path gateway.exproto.listeners.tcp.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path gateway.exproto.listeners.tcp.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path gateway.exproto.listeners.tcp.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path gateway.exproto.listeners.tcp.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path gateway.exproto.listeners.tcp.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path gateway.exproto.listeners.tcp.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path gateway.exproto.listeners.tcp.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path gateway.exproto.listeners.tcp.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path gateway.exproto.listeners.tcp.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否开启 Proxy Protocol V1/2。当 EMQX 集群部署在 HAProxy 或 Nginx 后需要获取客户端真实 IP 时常用到该选项。参考:https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.exproto.listeners.tcp.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc 接收 Proxy Protocol 报文头的超时时间。如果在超时内没有收到 Proxy Protocol 包,EMQX 将关闭 TCP 连接。
## @path gateway.exproto.listeners.tcp.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc 是否启用该监听器。
## @path gateway.exproto.listeners.tcp.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.exproto.listeners.tcp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.exproto.listeners.tcp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.exproto.listeners.tcp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.exproto.listeners.tcp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.exproto.listeners.tcp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.tcp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.exproto.listeners.ssl
## @type map()
## ssl:
## $name {
## @doc Acceptor 进程池大小。
## @path gateway.exproto.listeners.ssl.$name.acceptors
## @type integer()
## acceptors: 16
## tcp {
## @doc
## 为此套接字指定{active,N}选项</br>
## See: https://erlang.org/doc/man/inet.html#setopts-2
##
## @path gateway.exproto.listeners.ssl.$name.tcp.active_n
## @type integer()
## active_n: 100
## @doc
## TCP backlog 定义了挂起连接队列可以增长到的最大长度。
##
## @path gateway.exproto.listeners.ssl.$name.tcp.backlog
## @type integer()
## backlog: 1024
## @doc
## 连接的TCP发送超时。
##
## @path gateway.exproto.listeners.ssl.$name.tcp.send_timeout
## @type emqx_schema:duration()
## send_timeout: "15s"
## @doc
## 如果发送超时,则关闭连接。
##
## @path gateway.exproto.listeners.ssl.$name.tcp.send_timeout_close
## @type boolean()
## send_timeout_close: true
## @doc
## 连接的 TCP 接收缓冲区(OS内核)。
##
## @path gateway.exproto.listeners.ssl.$name.tcp.recbuf
## @type emqx_schema:bytesize()
## recbuf:
## @doc
## 连接的 TCP 发送缓冲区(OS内核)。
##
## @path gateway.exproto.listeners.ssl.$name.tcp.sndbuf
## @type emqx_schema:bytesize()
## sndbuf:
## @doc
## 驱动程序使用的用户空间缓冲区的大小。
##
## @path gateway.exproto.listeners.ssl.$name.tcp.buffer
## @type emqx_schema:bytesize()
## buffer:
## @doc
## 当 VM 套接字实现内部排队的数据量达到此限制时,套接字将设置为忙碌状态。
##
## @path gateway.exproto.listeners.ssl.$name.tcp.high_watermark
## @type emqx_schema:bytesize()
## high_watermark: "1MB"
## @doc
## 连接的 TCP_NODELAY 标识
##
## @path gateway.exproto.listeners.ssl.$name.tcp.nodelay
## @type boolean()
## nodelay: false
## @doc
## 连接的 SO_REUSEADDR 标识
##
## @path gateway.exproto.listeners.ssl.$name.tcp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否开启 Proxy Protocol V1/2。当 EMQX 集群部署在 HAProxy 或 Nginx 后需要获取客户端真实 IP 时常用到该选项。参考:https://www.haproxy.com/blog/haproxy/proxy-protocol/
## @path gateway.exproto.listeners.ssl.$name.proxy_protocol
## @type boolean()
## proxy_protocol: false
## @doc 接收 Proxy Protocol 报文头的超时时间。如果在超时内没有收到 Proxy Protocol 包,EMQX 将关闭 TCP 连接。
## @path gateway.exproto.listeners.ssl.$name.proxy_protocol_timeout
## @type emqx_gateway_schema:duration()
## proxy_protocol_timeout: "15s"
## @doc 是否启用该监听器。
## @path gateway.exproto.listeners.ssl.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.exproto.listeners.ssl.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.exproto.listeners.ssl.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.exproto.listeners.ssl.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.exproto.listeners.ssl.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.exproto.listeners.ssl.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.ssl.$name
## @type array
## access_rules: []
## ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path gateway.exproto.listeners.ssl.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.listeners.ssl.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.dhfile
## @type string()
## dhfile:
## @doc
## TLS/DTLS 服务器与 {verify,verify_peer} 一起使用。
## 如果设置为true,则如果客户端没有要发送的证书,即发送空证书,服务器将失败。
## 如果设置为false,则仅当客户端发送无效证书(空证书被视为有效证书)时才会失败。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path gateway.exproto.listeners.ssl.$name.ssl.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
## @doc
## @path gateway.exproto.listeners.udp
## @type map()
## udp:
## $name {
## udp {
## @doc 为 Socket 指定 {active, N} 选项。
## 参见:https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.exproto.listeners.udp.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Socket 在内核空间接收缓冲区的大小。
## @path gateway.exproto.listeners.udp.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Socket 在内核空间发送缓冲区的大小。
## @path gateway.exproto.listeners.udp.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Socket 在用户空间的缓冲区大小。
## @path gateway.exproto.listeners.udp.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc 允许重用本地处于 TIME_WAIT 的端口号
## @path gateway.exproto.listeners.udp.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否启用该监听器。
## @path gateway.exproto.listeners.udp.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.exproto.listeners.udp.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.exproto.listeners.udp.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.exproto.listeners.udp.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.exproto.listeners.udp.$name.authentication
## @link gateway.coap.listeners.udp.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.exproto.listeners.udp.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.udp.$name
## @type array
## access_rules: []
## }
## @doc
## @path gateway.exproto.listeners.dtls
## @type map()
## dtls:
## $name {
## @doc Acceptor 进程池大小。
## @path gateway.exproto.listeners.dtls.$name.acceptors
## @type integer()
## acceptors: 16
## udp {
## @doc 为 Socket 指定 {active, N} 选项。
## 参见:https://erlang.org/doc/man/inet.html#setopts-2
## @path gateway.exproto.listeners.dtls.$name.udp.active_n
## @type integer()
## active_n: 100
## @doc Socket 在内核空间接收缓冲区的大小。
## @path gateway.exproto.listeners.dtls.$name.udp.recbuf
## @type emqx_gateway_schema:bytesize()
## recbuf:
## @doc Socket 在内核空间发送缓冲区的大小。
## @path gateway.exproto.listeners.dtls.$name.udp.sndbuf
## @type emqx_gateway_schema:bytesize()
## sndbuf:
## @doc Socket 在用户空间的缓冲区大小。
## @path gateway.exproto.listeners.dtls.$name.udp.buffer
## @type emqx_gateway_schema:bytesize()
## buffer:
## @doc 允许重用本地处于 TIME_WAIT 的端口号
## @path gateway.exproto.listeners.dtls.$name.udp.reuseaddr
## @type boolean()
## reuseaddr: true
## }
## @doc 是否启用该监听器。
## @path gateway.exproto.listeners.dtls.$name.enable
## @type boolean()
## enable: true
## @doc 监听器绑定的 IP 地址或端口。
## @path gateway.exproto.listeners.dtls.$name.bind
## @type union: emqx_gateway_schema:ip_port() | integer()
## bind:
## @doc 监听器支持的最大连接数。
## @path gateway.exproto.listeners.dtls.$name.max_connections
## @type integer()
## max_connections: 1024
## @doc 监听器支持的最大连接速率。
## @path gateway.exproto.listeners.dtls.$name.max_conn_rate
## @type integer()
## max_conn_rate: 1000
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.exproto.listeners.dtls.$name.authentication
## @link gateway.coap.listeners.dtls.$name.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
## @doc 发布或订阅时,在所有主题前增加前缀字符串。
## 当消息投递给订阅者时,前缀字符串将从主题名称中删除。挂载点是用户可以用来实现不同监听器之间的消息路由隔离的一种方式。
## 例如,如果客户端 A 在 `listeners.tcp.<name>.mountpoint` 设置为 `some_tenant` 的情况下订阅 `t`,则客户端实际上订阅了 `some_tenant/t` 主题。 类似地,如果另一个客户端 B(连接到与客户端 A 相同的侦听器)向主题 `t` 发送消息,则该消息被路由到所有订阅了 `some_tenant/t` 的客户端,因此客户端 A 将收到该消息,带有 主题名称`t`。 设置为 `""` 以禁用该功能。
## 挂载点字符串中可用的变量:
## - <code>${clientid}</code>:clientid
## - <code>${username}</code>:用户名
##
## @path gateway.exproto.listeners.dtls.$name.mountpoint
## @type binary()
## mountpoint:
## @doc 配置监听器的访问控制规则。
## 见:https://github.com/emqtt/esockd#allowdeny
## @path gateway.exproto.listeners.dtls.$name
## @type array
## access_rules: []
## dtls {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path gateway.exproto.listeners.dtls.$name.dtls
## @type array
## versions: [dtlsv1.2, dtlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path gateway.exproto.listeners.dtls.$name.dtls
## @type array
## ciphers: ["ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc
## 如果协商使用Diffie-Hellman密钥交换的密码套件,则服务器将使用包含PEM编码的Diffie-Hellman参数的文件的路径。如果未指定,则使用默认参数</br>
##
## 注意:TLS 1.3不支持<code>dhfile</code>选项。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.dhfile
## @type string()
## dhfile:
## @doc
## TLS/DTLS 服务器与 {verify,verify_peer} 一起使用。
## 如果设置为true,则如果客户端没有要发送的证书,即发送空证书,服务器将失败。
## 如果设置为false,则仅当客户端发送无效证书(空证书被视为有效证书)时才会失败。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.fail_if_no_peer_cert
## @type boolean()
## fail_if_no_peer_cert: false
## @doc
## 一个重要的安全设置,它强制根据服务器指定的顺序而不是客户机指定的顺序设置密码,从而强制服务器管理员执行(通常配置得更正确)安全顺序。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.honor_cipher_order
## @type boolean()
## honor_cipher_order: true
## @doc
## 在支持客户机发起的重新协商的协议中,这种操作的资源成本对于服务器来说高于客户机。
## 这可能会成为拒绝服务攻击的载体。
## SSL 应用程序已经采取措施来反击此类尝试,但通过将此选项设置为 false,可以严格禁用客户端发起的重新协商。
## 默认值为 true。请注意,由于基础密码套件可以加密的消息数量有限,禁用重新协商可能会导致长期连接变得不可用。
##
## @path gateway.exproto.listeners.dtls.$name.dtls.client_renegotiation
## @type boolean()
## client_renegotiation: true
## }
## }
}
## @doc 是否启用该网关
## @path gateway.exproto.enable
## @type boolean()
enable: true
## @doc 是否开启客户端统计
## @path gateway.exproto.enable_stats
## @type boolean()
enable_stats: true
## @doc 客户端连接过程的空闲时间。该配置用于:
## 1. 一个新创建的客户端进程如果在该时间间隔内没有收到任何客户端请求,将被直接关闭。
## 2. 一个正在运行的客户进程如果在这段时间后没有收到任何客户请求,将进入休眠状态以节省资源。
## @path gateway.exproto.idle_timeout
## @type emqx_gateway_schema:duration()
idle_timeout: "30s"
clientinfo_override {
## @doc username 重写模板
## @path gateway.exproto.clientinfo_override.username
## @type binary()
## username:
## @doc password 重写模板
## @path gateway.exproto.clientinfo_override.password
## @type binary()
## password:
## @doc clientid 重写模板
## @path gateway.exproto.clientinfo_override.clientid
## @type binary()
## clientid:
}
## @doc 网关的认证器配置,对该网关下所以的监听器生效。如果每个监听器需要配置不同的认证器,需要配置监听器下的 <code>authentication</code> 字段
## @path gateway.exproto.authentication
## @type union: authn-builtin_db:authentication | authn-mysql:authentication | authn-postgresql:authentication | authn-mongodb:standalone | authn-mongodb:replica-set | authn-mongodb:sharded-cluster | authn-redis:standalone | authn-redis:cluster | authn-redis:sentinel | authn-http:get | authn-http:post | authn-jwt:hmac-based | authn-jwt:public-key | authn-jwt:jwks | authn-scram-builtin_db:authentication
## authentication:
}
}
prometheus {
## @doc Prometheus 服务器地址
## @path prometheus.push_gateway_server
## @type string()
push_gateway_server: "http://127.0.0.1:9091"
## @doc 数据推送间隔,单位 毫秒
## @path prometheus.interval
## @type emqx_schema:duration_ms()
interval: "15s"
## @doc 开启或关闭 Prometheus 数据推送
## @path prometheus.enable
## @type boolean()
enable: false
}
rule_engine {
## @doc 当设置为“true”(默认)时,规则引擎将忽略发布到 $SYS 主题的消息。
## @path rule_engine.ignore_sys_message
## @type boolean()
ignore_sys_message: true
## @doc 规则
## @path rule_engine.rules
## @type map()
rules: {}
## rules:
## $id {
## @doc 规则名字
## @path rule_engine.rules.$id.name
## @type binary()
## name: ""
## @doc
## 用于处理消息的 SQL 。
## 示例:<code>SELECT * FROM "test/topic" WHERE payload.x = 1</code>
##
## @path rule_engine.rules.$id.sql
## @type binary()
## sql:
## @doc
## 规则的动作列表。
## 动作可以是指向 EMQX bridge 的引用,也可以是一个指向函数的对象。
## 我们支持一些内置函数,如“republish”和“console”,我们还支持用户提供的函数,它的格式为:“{module}:{function}”。
## 列表中的动作按顺序执行。这意味着如果其中一个动作执行缓慢,则以下所有动作都不会被执行直到它返回。
## 如果其中一个动作崩溃,在它之后的所有动作仍然会被按照原始顺序执行。
## 如果运行动作时出现任何错误,则会出现错误消息,并且相应的计数器会增加。
##
## @path rule_engine.rules.$id
## @type array
## outputs: []
## @path rule_engine.rules.$id.outputs.$INDEX
## @type union: binary() | rule_engine:builtin_output_republish | rule_engine:builtin_output_console | rule_engine:user_provided_function
## $INDEX:
## @doc 启用或禁用规则引擎
## @path rule_engine.rules.$id.enable
## @type boolean()
## enable: true
## @doc 规则的描述
## @path rule_engine.rules.$id.description
## @type binary()
## description: ""
## }
## @doc 规则引擎内建函数 `jq` 默认时间限制
## @path rule_engine.jq_function_default_timeout
## @type emqx_schema:duration_ms()
jq_function_default_timeout: "10s"
}
exhook {
## @doc ExHook 服务器列表
## @path exhook
## @type array
servers: []
## $INDEX {
## @doc ExHook 服务器名称
## @path exhook.servers.$INDEX.name
## @type binary()
## name:
## @doc 开启这个 Exhook 服务器
## @path exhook.servers.$INDEX.enable
## @type boolean()
## enable: true
## @doc gRPC 服务器地址
## @path exhook.servers.$INDEX.url
## @type binary()
## url:
## @doc gRPC 服务器请求超时时间
## @path exhook.servers.$INDEX.request_timeout
## @type emqx_exhook_schema:duration()
## request_timeout: "5s"
## @doc 当 gRPC 请求失败后的操作
## @path exhook.servers.$INDEX.failed_action
## @type enum: deny | ignore
## failed_action: deny
## ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path exhook.servers.$INDEX.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path exhook.servers.$INDEX.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path exhook.servers.$INDEX.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path exhook.servers.$INDEX.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path exhook.servers.$INDEX.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path exhook.servers.$INDEX.ssl.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path exhook.servers.$INDEX.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path exhook.servers.$INDEX.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path exhook.servers.$INDEX.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path exhook.servers.$INDEX.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc 启用 TLS
## @path exhook.servers.$INDEX.ssl.enable
## @type boolean()
## enable: false
## @doc
## 指定要在 TLS 服务器名称指示扩展中使用的主机名</br>
## 例如,当连接到 "server.example.net" 时,接受连接并执行 TLS 握手的真正服务器可能与 TLS 客户端最初连接到的主机不同,
## 例如,当连接到 IP 地址时,或者当主机具有多个可解析的 DNS 记录时</br>
## 如果未指定,它将默认为使用的主机名字符串
## 建立连接,除非使用 IP 地址</br>
## 然后,主机名也用于对等机的主机名验证
## 证书</br>特殊值'disable'阻止发送服务器名称指示扩展,并禁用主机名验证检查。
##
## @path exhook.servers.$INDEX.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
## }
## @doc 自动重连到 gRPC 服务器的设置。
## 当 gRPC 服务器不可用时,Exhook 将会按照这里设置的间隔时间进行重连,并重新初始化注册的钩子
## @path exhook.servers.$INDEX.auto_reconnect
## @type union: false | emqx_exhook_schema:duration()
## auto_reconnect: "60s"
## @doc gRPC 客户端进程池大小
## @path exhook.servers.$INDEX.pool_size
## @type pos_integer()
## pool_size: 8
## }
}
psk_authentication {
## @doc 是否开启 TLS PSK 支持
## @path psk_authentication.enable
## @type boolean()
enable: false
## @doc 如果设置了初始化文件,EMQX 将在启动时从初始化文件中导入 PSK 信息到内建数据库中。
## 这个文件需要按行进行组织,每一行必须遵守如下格式: <code>PSKIdentity:SharedSecret</code>
## 例如: <code>mydevice1:c2VjcmV0</code>
## @path psk_authentication.init_file
## @type binary()
## init_file:
## @doc PSK 文件中 <code>PSKIdentity</code> 和 <code>SharedSecret</code> 之间的分隔符
## @path psk_authentication.separator
## @type binary()
separator: ":"
## @doc 将 PSK 文件导入到内建数据时每个块的大小
## @path psk_authentication.chunk_size
## @type integer()
chunk_size: 50
}
limiter {
bytes_in {
## @doc 是否开启
## @path limiter.bytes_in.enable
## @type boolean()
enable: true
## @doc 桶的令牌生成速率
## @path limiter.bytes_in.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc 突发速率。
## 突发速率允许短时间内速率超过设置的速率值,突发速率 + 速率 = 当前桶能达到的最大速率值
## @path limiter.bytes_in.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc 桶的配置
## @path limiter.bytes_in.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
message_in {
## @doc 是否开启
## @path limiter.message_in.enable
## @type boolean()
enable: true
## @doc 桶的令牌生成速率
## @path limiter.message_in.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc 突发速率。
## 突发速率允许短时间内速率超过设置的速率值,突发速率 + 速率 = 当前桶能达到的最大速率值
## @path limiter.message_in.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc 桶的配置
## @path limiter.message_in.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
connection {
## @doc 是否开启
## @path limiter.connection.enable
## @type boolean()
enable: true
## @doc 桶的令牌生成速率
## @path limiter.connection.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc 突发速率。
## 突发速率允许短时间内速率超过设置的速率值,突发速率 + 速率 = 当前桶能达到的最大速率值
## @path limiter.connection.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc 桶的配置
## @path limiter.connection.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
message_routing {
## @doc 是否开启
## @path limiter.message_routing.enable
## @type boolean()
enable: true
## @doc 桶的令牌生成速率
## @path limiter.message_routing.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc 突发速率。
## 突发速率允许短时间内速率超过设置的速率值,突发速率 + 速率 = 当前桶能达到的最大速率值
## @path limiter.message_routing.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc 桶的配置
## @path limiter.message_routing.bucket
## @link limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
}
batch {
## @doc 是否开启
## @path limiter.batch.enable
## @type boolean()
enable: true
## @doc 桶的令牌生成速率
## @path limiter.batch.rate
## @type emqx_limiter_schema:rate()
rate: "infinity"
## @doc 突发速率。
## 突发速率允许短时间内速率超过设置的速率值,突发速率 + 速率 = 当前桶能达到的最大速率值
## @path limiter.batch.burst
## @type emqx_limiter_schema:burst_rate()
burst: 0
## @doc 桶的配置
## @path limiter.batch.bucket
## @type map()
bucket:
{
default {}
}
## bucket:
## $bucket_name {
## @doc 桶的令牌生成速率
## @path limiter.batch.bucket.$bucket_name.rate
## @type emqx_limiter_schema:rate()
## rate: "infinity"
## @doc 该令牌桶的容量
## @path limiter.batch.bucket.$bucket_name.capacity
## @type emqx_limiter_schema:capacity()
## capacity: "infinity"
## @doc 桶中的初始令牌数
## @path limiter.batch.bucket.$bucket_name.initial
## @type emqx_limiter_schema:initial()
## initial: "0"
## per_client {
## @doc 桶的令牌生成速率
## @path limiter.batch.bucket.$bucket_name.per_client.rate
## @type emqx_limiter_schema:rate()
## rate: "infinity"
## @doc 桶中的初始令牌数
## @path limiter.batch.bucket.$bucket_name.per_client.initial
## @type emqx_limiter_schema:initial()
## initial: "0"
## @doc 当桶中剩余的令牌数低于这个值,即使令牌申请成功了,也会被强制暂停一会儿
## @path limiter.batch.bucket.$bucket_name.per_client.low_watermark
## @type emqx_limiter_schema:initial()
## low_watermark: "0"
## @doc 每个使用者的令牌容量上限
## @path limiter.batch.bucket.$bucket_name.per_client.capacity
## @type emqx_limiter_schema:capacity()
## capacity: "infinity"
## @doc 申请的令牌数是否可以被分割
## @path limiter.batch.bucket.$bucket_name.per_client.divisible
## @type boolean()
## divisible: false
## @doc 申请失败后,尝试重新申请的时长最大值
## @path limiter.batch.bucket.$bucket_name.per_client.max_retry_time
## @type emqx_schema:duration()
## max_retry_time: "10s"
## @doc 当所有的重试都失败后的处理策略
## @path limiter.batch.bucket.$bucket_name.per_client.failure_strategy
## @type emqx_limiter_schema:failure_strategy()
## failure_strategy: force
## }
## }
}
}
connectors {
## @doc MQTT bridges。
## @path connectors.mqtt
## @type map()
## mqtt:
## $name {
## @doc
## MQTT 桥的模式。 可用的类型有“cluster_singleton”,“cluster_shareload”。</br>
##
## - cluster_singleton:在 emqx 集群内创建唯一的 MQTT 连接。</br>
## 在“cluster_singleton”节点中,所有发往远程代理的消息都通过相同的MQTT 连接。</br>
##
## - cluster_shareload:在 emqx 集群的每个节点上创建一个 MQTT 连接。</br>
## 在“cluster_shareload”模式下,来自远程代理的传入负载通过共享订阅的方式接收。</br>
## 请注意,“clientid”以节点名称为后缀,这是为了避免不同节点之间的clientid冲突。
## 而且对于入口连接的“remote_topic”,我们只能使用共享订阅主题过滤器。
##
## @path connectors.mqtt.$name.mode
## @type enum: cluster_shareload
## mode: cluster_shareload
## @doc 远程 MQTT Broker的主机和端口。
## @path connectors.mqtt.$name.server
## @type emqx_schema:ip_port()
## server:
## @doc Reconnect interval. Delay for the MQTT bridge to retry establishing the connection in case of transportation failure. Time interval is a string that contains a number followed by time unit:</br>
## - `ms` for milliseconds,
## - `s` for seconds,
## - `m` for minutes,
## - `h` for hours;
## </br>or combination of whereof: `1h5m0s`
## @path connectors.mqtt.$name.reconnect_interval
## @type string()
## reconnect_interval: "15s"
## @doc MQTT 协议版本
## @path connectors.mqtt.$name.proto_ver
## @type enum: v3 | v4 | v5
## proto_ver: v4
## @doc
## 是否启用 Bridge Mode。
## 注意:此设置只针对 MQTT 协议版本 < 5.0 有效,并且需要远程 MQTT Broker 支持 Bridge Mode。
##
## @path connectors.mqtt.$name.bridge_mode
## @type boolean()
## bridge_mode: false
## @doc MQTT 协议的用户名
## @path connectors.mqtt.$name.username
## @type binary()
## username: "emqx"
## @doc MQTT 协议的密码
## @path connectors.mqtt.$name.password
## @type binary()
## password: "emqx"
## @doc MQTT 清除会话
## @path connectors.mqtt.$name.clean_start
## @type boolean()
## clean_start: true
## @doc MQTT Keepalive. Time interval is a string that contains a number followed by time unit:</br>
## - `ms` for milliseconds,
## - `s` for seconds,
## - `m` for minutes,
## - `h` for hours;
## </br>or combination of whereof: `1h5m0s`
## @path connectors.mqtt.$name.keepalive
## @type string()
## keepalive: "300s"
## @doc Message retry interval. Delay for the MQTT bridge to retry sending the QoS1/QoS2 messages in case of ACK not received. Time interval is a string that contains a number followed by time unit:</br>
## - `ms` for milliseconds,
## - `s` for seconds,
## - `m` for minutes,
## - `h` for hours;
## </br>or combination of whereof: `1h5m0s`
## @path connectors.mqtt.$name.retry_interval
## @type string()
## retry_interval: "15s"
## @doc MQTT 协议的最大飞行(已发送但未确认)消息
## @path connectors.mqtt.$name.max_inflight
## @type non_neg_integer()
## max_inflight: 32
## replayq {
## @doc
## replayq 文件保存的目录。</br>
## 设置为 'false' 会禁用 replayq 功能。
##
## @path connectors.mqtt.$name.replayq.dir
## @type union: boolean() | string()
## dir:
## @doc
## 单个段的大小(以字节为单位)。</br>
## 一个段映射到 replayq 目录中的一个文件。 如果当前段已满,则新段(文件)将被打开写入。
##
## @path connectors.mqtt.$name.replayq.seg_bytes
## @type emqx_schema:bytesize()
## seg_bytes: "100MB"
## @doc
## 在Offload模式下,磁盘队列仅用于卸载队列尾段。</br>
## 消息首先缓存在内存中,然后写入replayq文件。内存缓大小为“seg_bytes” 指定的值。
##
## @path connectors.mqtt.$name.replayq.offload
## @type boolean()
## offload: false
## }
## ssl {
## @doc
## 受信任的PEM格式CA证书捆绑文件</br>
## 此文件中的证书用于验证TLS对等方的证书。
## 如果要信任新CA,请将新证书附加到文件中。
## 无需重启EMQX即可加载更新的文件,因为系统会定期检查文件是否已更新(并重新加载)</br>
## 注意:从文件中失效(删除)证书不会影响已建立的连接。
##
## @path connectors.mqtt.$name.ssl.cacertfile
## @type binary()
## cacertfile:
## @doc
## PEM格式证书链文件</br>
## 此文件中的证书应与证书颁发链的顺序相反。也就是说,主机的证书应该放在文件的开头,然后是直接颁发者证书,依此类推。
## 虽然根CA证书是可选的,但它应该放在
## 如果要添加文件,请将其删除。
##
## @path connectors.mqtt.$name.ssl.certfile
## @type binary()
## certfile:
## @doc
## PEM格式的私钥文件。
##
## @path connectors.mqtt.$name.ssl.keyfile
## @type binary()
## keyfile:
## @doc
## 启用或禁用对等验证。
##
## @path connectors.mqtt.$name.ssl.verify
## @type enum: verify_peer | verify_none
## verify: verify_none
## @doc
## 启用 TLS 会话重用。
##
## @path connectors.mqtt.$name.ssl.reuse_sessions
## @type boolean()
## reuse_sessions: true
## @doc
## 在有效的证书路径中,可以跟随对等证书的非自颁发中间证书的最大数量。因此,如果深度为0,则对等方必须由受信任的根CA直接签名;如果1,路径可以是PEER、CA、ROOT-CA;如果是2,则路径可以是PEER、CA、CA、ROOT-CA等等。默认值为10。
##
## @path connectors.mqtt.$name.ssl.depth
## @type integer()
## depth: 10
## @doc
## 包含用户密码的字符串。
## 仅在私钥文件受密码保护时使用。
##
## @path connectors.mqtt.$name.ssl.password
## @type string()
## password:
## @doc
## 支持所有TLS/DTLS版本</br>
##
## 注:PSK 的 Ciphers 无法在 <code>tlsv1.3</code> 中使用,如果打算使用 PSK 密码套件,请确保这里配置为 <code>["tlsv1.2","tlsv1.1"]</code>。
##
## @path connectors.mqtt.$name.ssl
## @type array
## versions: [tlsv1.3, tlsv1.2, tlsv1.1, tlsv1]
## @doc
## 此配置保存由逗号分隔的 TLS 密码套件名称,或作为字符串数组。例如
## <code>"TLS_AES_256_GCM_SHA384,TLS_AES_128_GCM_SHA256"</code>或
## <code>["TLS_AES_256_GCM_SHA384","TLS_AES_128_GCM_SHA256"]</code>。
## </br>
## 密码(及其顺序)定义了客户端和服务器通过网络连接加密信息的方式。
## 选择一个好的密码套件对于应用程序的数据安全性、机密性和性能至关重要。
##
## 名称应为 OpenSSL 字符串格式(而不是 RFC 格式)。
## EMQX 配置文档提供的所有默认值和示例都是 OpenSSL 格式</br>
## 注意:某些密码套件仅与特定的 TLS <code>版本</code>兼容('tlsv1.1'、'tlsv1.2'或'tlsv1.3')。
## 不兼容的密码套件将被自动删除。
##
## 例如,如果只有 <code>versions</code> 仅配置为 <code>tlsv1.3</code>。为其他版本配置密码套件将无效。
##
## </br>
## 注:PSK 的 Ciphers 不支持 tlsv1.3</br>
## 如果打算使用PSK密码套件 <code>tlsv1.3</code>。应在<code>ssl.versions</code>中禁用。
##
## </br>
## PSK 密码套件:
## <code>"RSA-PSK-AES256-GCM-SHA384,RSA-PSK-AES256-CBC-SHA384,
## RSA-PSK-AES128-GCM-SHA256,RSA-PSK-AES128-CBC-SHA256,
## RSA-PSK-AES256-CBC-SHA,RSA-PSK-AES128-CBC-SHA,
## RSA-PSK-DES-CBC3-SHA,RSA-PSK-RC4-SHA"</code></br>
##
## @path connectors.mqtt.$name.ssl
## @type array
## ciphers: ["TLS_AES_256_GCM_SHA384", "TLS_AES_128_GCM_SHA256", "TLS_CHACHA20_POLY1305_SHA256", "TLS_AES_128_CCM_SHA256", "TLS_AES_128_CCM_8_SHA256", "ECDHE-ECDSA-AES256-GCM-SHA384", "ECDHE-RSA-AES256-GCM-SHA384", "ECDHE-ECDSA-AES256-SHA384", "ECDHE-RSA-AES256-SHA384", "ECDH-ECDSA-AES256-GCM-SHA384", "ECDH-RSA-AES256-GCM-SHA384", "ECDH-ECDSA-AES256-SHA384", "ECDH-RSA-AES256-SHA384", "DHE-DSS-AES256-GCM-SHA384", "DHE-DSS-AES256-SHA256", "AES256-GCM-SHA384", "AES256-SHA256", "ECDHE-ECDSA-AES128-GCM-SHA256", "ECDHE-RSA-AES128-GCM-SHA256", "ECDHE-ECDSA-AES128-SHA256", "ECDHE-RSA-AES128-SHA256", "ECDH-ECDSA-AES128-GCM-SHA256", "ECDH-RSA-AES128-GCM-SHA256", "ECDH-ECDSA-AES128-SHA256", "ECDH-RSA-AES128-SHA256", "DHE-DSS-AES128-GCM-SHA256", "DHE-DSS-AES128-SHA256", "AES128-GCM-SHA256", "AES128-SHA256", "ECDHE-ECDSA-AES256-SHA", "ECDHE-RSA-AES256-SHA", "DHE-DSS-AES256-SHA", "ECDH-ECDSA-AES256-SHA", "ECDH-RSA-AES256-SHA", "ECDHE-ECDSA-AES128-SHA", "ECDHE-RSA-AES128-SHA", "DHE-DSS-AES128-SHA", "ECDH-ECDSA-AES128-SHA", "ECDH-RSA-AES128-SHA", "RSA-PSK-AES256-GCM-SHA384", "RSA-PSK-AES256-CBC-SHA384", "RSA-PSK-AES128-GCM-SHA256", "RSA-PSK-AES128-CBC-SHA256", "RSA-PSK-AES256-CBC-SHA", "RSA-PSK-AES128-CBC-SHA"]
## @doc
## 用于查找预共享密钥(PSK)标识的 EMQX 内部回调。
##
## @path connectors.mqtt.$name.ssl.user_lookup_fun
## @type string()
## user_lookup_fun: "emqx_tls_psk:lookup"
## @doc
## SSL 参数重新协商是一种允许客户端和服务器动态重新协商 SSL 连接参数的功能。
## RFC 5746 定义了一种更安全的方法。通过启用安全的重新协商,您就失去了对不安全的重新协商的支持,从而容易受到 MitM 攻击。
##
## @path connectors.mqtt.$name.ssl.secure_renegotiate
## @type boolean()
## secure_renegotiate: true
## @doc 启用 TLS
## @path connectors.mqtt.$name.ssl.enable
## @type boolean()
## enable: false
## @doc
## 指定要在 TLS 服务器名称指示扩展中使用的主机名</br>
## 例如,当连接到 "server.example.net" 时,接受连接并执行 TLS 握手的真正服务器可能与 TLS 客户端最初连接到的主机不同,
## 例如,当连接到 IP 地址时,或者当主机具有多个可解析的 DNS 记录时</br>
## 如果未指定,它将默认为使用的主机名字符串
## 建立连接,除非使用 IP 地址</br>
## 然后,主机名也用于对等机的主机名验证
## 证书</br>特殊值'disable'阻止发送服务器名称指示扩展,并禁用主机名验证检查。
##
## @path connectors.mqtt.$name.ssl.server_name_indication
## @type union: disable | string()
## server_name_indication:
## }
## }
}
slow_subs {
## @doc 开启慢订阅
## @path slow_subs.enable
## @type boolean()
enable: false
## @doc 慢订阅统计的阈值
## @path slow_subs.threshold
## @type emqx_schema:duration_ms()
threshold: "500ms"
## @doc 慢订阅记录的有效时间
## @path slow_subs.expire_interval
## @type emqx_schema:duration_ms()
expire_interval: "300s"
## @doc 慢订阅统计表的记录数量上限
## @path slow_subs.top_k_num
## @type pos_integer()
top_k_num: 10
## @doc 慢订阅的统计类型
## @path slow_subs.stats_type
## @type enum: whole | internal | response
stats_type: whole
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment