Source Remote Console (RCON)¶
Source remote console (or RCON) provides a way for server operators to
administer and interact with their servers remotely in the same manner as
the console provided by srcds. The
provides an implementation of the RCON protocol.
RCON is a simple, TCP-based request-response protocol with support for basic authentication. The RCON client initiates a connection to a server and attempts to authenticate by submitting a password. If authentication succeeds then the client is free to send further requests. These subsequent requests are interpreted the same way as if you were to type them into the srcds console.
Passwords and console commands are sent in plain text. Tunneling the connection through a secure channel may be advisable where possible.
Multiple RCON authentication failures in a row from a single host will result in the Source server automatically banning that IP, preventing any subsequent connection attempts.
valve.rcon module provides a number of ways to interact with
RCON servers. The simplest is the
execute() function which executes
a single command on the server and returns the response as a string.
In many cases this may be sufficient but it’s important to consider that
execute() will create a new, temporary connection for every command.
If order to reuse a connection the
RCON class should be used
execute(address, password, command)¶
Execute a command on an RCON server.
This is a very high-level interface which connects to the given RCON server using the provided credentials and executes a command.
- address – the address of the server to connect to as a tuple containing the host as a string and the port as an integer.
- password (str) – the password to use to authenticate the connection.
- command (str) – the command to execute on the server.
- UnicodeDecodeError – if the response could not be decoded into Unicode.
- RCONCommunicationError – if a connection to the RCON server could not be made.
- RCONAuthenticationError – if authentication failed, either due to being banned or providing the wrong password.
- RCONMessageError – if the response body couldn’t be decoded into a Unicode string.
the response to the command as a Unicode string.
Representing RCON Messages¶
Each RCON message, whether a request or a response, is represented by an
instance of the
RCONMessage class. Each message has three fields:
the message ID, type and contents or body. The message ID of a request is
reflected back to the client when the server returns a response but is
otherwise unsued by this implementation. The type is one of four constants
(represented by three distinct values) which signifies the semantics of the
message’s ID and body. The body it self is an opaque string; its value
depends on the type of message.
RCONMessage(id_, type_, body_or_text)¶
Represents a RCON request or response.
Decode a message from a bytestring.
This will attempt to decode a single message from the start of the given buffer. If the buffer contains more than a single message then this must be called multiple times.
Raises: MessageError – if the buffer doesn’t contain a valid message. Returns: a tuple containing the decoded
RCONMessageand the remnants of the buffer. If the buffer contained exactly one message then the remaning buffer will be empty.
Encode message to a bytestring.
Get the body of the message as Unicode.
Raises: UnicodeDecodeError – if the body cannot be decoded as ASCII. Returns: the body of the message as a Unicode string.
It has been reported that some servers may not return valid ASCII as they’re documented to do so. Therefore you should always handle the potential
If the correct encoding is known you can manually decode
bodyfor your self.
Unicode and String Encoding¶
The type of the body field of RCON messages is documented as being a
double null-terminated, ASCII-encoded string. At the Python level though
both Unicode strings and raw byte string interfaces are provided by
In Python you are encouraged to deal with text (a.k.a. Unicode strings)
in preference to raw byte strings unless strictly neccessary. However,
it has been reported that under some conditions RCON servers may return
invalid ASCII sequences in the response body. Therefore it is possible
that the textual representation of the body cannot be determined and
attempts to access
RCONMessage.text will fail with a
UnicodeDecodeError being raised.
It appears – but is not conclusively determined – that RCON servers in fact return UTF-8-encoded message bodies, hence why ASCII seems to to work in most cases. Until this can be categorically proven as the behaviour that should be expected Python-valve will continue to attempt to process ASCII strings.
If you come across
UnicodeDecodeError whilst accessing response
bodies you will instead have to make-do and handle the raw byte strings
manually. For example:
response = rcon.execute("command") response_text = response.body.decode("utf-8")
If this is undesirable it is also possible to globally set the encoding
RCONMessage but this not particularly encouraged:
import valve.rcon valve.rcon.RCONMessage.ENCODING = "utf-8"
Creating RCON Connections¶
RCON(address, password, timeout=None)¶
Represents an RCON connection.
Invoke a command.
This is a higher-level version of
execute()that always blocks and only returns the response body.
Raises: RCONMessageError – if the response body couldn’t be decoded into a Unicode string. Returns: the response to the command as a Unicode string.
Authenticate with the server.
This sends an authentication message to the connected server containing the password. If the password is correct the server sends back an acknowledgement and will allow all subsequent commands to be executed.
However, if the password is wrong the server will either notify the client or immediately drop the connection depending on whether the client IP has been banned or not. In either case, the client connection will be closed and an exception raised.
Client banning IP banning happens automatically after a few failed attempts at authentication. Assuming you can direct access to the server’s console you can unban the client IP using the
Banning xxx.xxx.xxx.xx for rcon hacking attempts ] removeip xxx.xxx.xxx.xxx removeip: filter removed for xxx.xxx.xxx.xxx
param timeout: the number of seconds to wait for a response. If not given the connection-global timeout is used. raises RCONAuthenticationError: if authentication failed, either due to being banned or providing the wrong password. raises RCONTimeoutError: if the server takes too long to respond. The connection will be closed in this case as well. Raises:
- RCONError – if closed.
- RCONError – if not connected.
Determine if the connection is authenticated.
Close connection to a server.
Determine if the connection has been closed.
Create a connection to a server.
- RCONError – if closed.
- RCONError – if connected.
Determine if a connection has been made.
Strictly speaking this does not guarantee that any subsequent attempt to execute a command will succeed as the underlying socket may be closed by the server at any time. It merely indicates that a previous call to
Get all ConVars for an RCON connection.
This will issue a
cvarlistcommand to it in order to enumerate all available ConVars.
Returns: an iterator of :class:`ConVar`s which may be empty.
execute(command, block=True, timeout=None)¶
Invoke a command.
Invokes the given command on the conncted server. By default this will block (up to the timeout) for a response. This can be disabled if you don’t care about the response.
param str command: the command to execute. param bool block: whether or not to wait for a response. param timeout: the number of seconds to wait for a response. If not given the connection-global timeout is used. raises RCONCommunicationError: if the socket is closed or in any other erroneous state whilst issuing the request or receiving the response. raises RCONTimeoutError: if the timeout is reached waiting for a response. This doesn’t close the connection but the response is lost. returns: the response to the command as a
Nonedepending on whether
- RCONError – if not authenticated.
- RCONError – if not connected.
import valve.rcon address = ("rcon.example.com", 27015) password = "top-secrect-password" with valve.rcon.RCON(address, password) as rcon: response = rcon.execute("echo Hello, world!") print(response.text)
As well as providing means to programatically interact with RCON servers,
valve.rcon module also provides an interactive, command-line
client. A client shell can be started by calling
shell() or running
A simple interactive RCON shell.
This will connect to the server identified by the given address using the given password. If a password is not given then the shell will prompt for it. If no address is given, then no connection will be made automatically and the user will have to do it manually using
Once connected the shell simply dispatches commands and prints the response to stdout.
- address – a network address tuple containing the host and port of the RCON server.
- password (str) – the password for the server. This is ignored if
addressis not given.
Using the RCON Shell¶
shell() is executed, an interactive RCON shell is created. This
shell reads commands from stdin, passes them to a connected RCON server
then prints the response to stdout in a conventional read-eval-print pattern.
By default, commands are treated as plain RCON commmands and are passed directly to the connected server for evaluation. However, commands prefixed with an exclamation mark are interpreted by the shell it self:
Connect to an RCON server. This command accepts two space-separated arguments: the address of the server and the corresponding password; the latter is optional. If the password is not given the user is prompted for it.
If the shell is already connected to a server then it will disconnect first before connecting to the new one.
- Disconnect from the current RCON server.
- Shutdown the RCON server. This actually just sends an
exitcommand to the server. This must be used instead of
exitas its behaviour could prove confusing with
- Exit the shell. This does not shutdown the RCON server.
Help is available via the
help command. When connected, an optional
argument can be provided which is the RCON command to show help for.
When connected to a server, command completions are provided via the tab key.
valve.rcon module is runnable. When ran with no arguments its the
same as calling
shell() with defaults. As with
address and password can be provided as a part of the invoking command:
$ python -m valve.rcon $ python -m valve.rcon rcon.example.com:27015 $ python -m valve.rcon rcon.example.com:27015 --password TOP-SECRET
Passing sensitive information via command-line arguments, such as your RCON password, can be dangerous. For example, it can show up in ps output.
Executing a Single Command¶
When ran, the module has two modes of execution: the default, which will
spawn an interactive RCON shell and the single command execution mode.
When passed the
--execute argument, python -m valve.rcon
will run the given command and exit with a status code of zero upon
completion. The command response is printed to stdout.
This can be useful for simple scripting of RCON commands outside of a Python environment, such as in a shell script.
$ python -m valve.rcon rcon.example.com:27015 \ --password TOP-SECRET --execute "echo Hello, world!"