Class: SteamCondenser::Servers::SourceServer

Inherits:
Object
  • Object
show all
Includes:
Logging, GameServer
Defined in:
lib/steam-condenser/servers/source_server.rb

Overview

This class represents a Source game server and can be used to query information about and remotely execute commands via RCON on the server

A Source game server is an instance of the Source Dedicated Server (SrcDS) running games using Valve's Source engine, like Counter-Strike: Source, Team Fortress 2 or Left4Dead.

See Also:

Author:

  • Sebastian Staudt

Instance Attribute Summary

Attributes included from BaseServer

#host_names, #ip_addresses

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Logging

formatter=, included, level=, #log, logdev=

Methods included from GameServer

#handle_response_for_request, #init, #ping, player_status_attributes, #players, #rcon_authenticated?, #reply, #rules, #send_request, #server_info, split_player_status, #to_s, #update_challenge_number, #update_ping, #update_players, #update_rules, #update_server_info

Methods included from BaseServer

#failsafe, #rotate_ip

Constructor Details

#initialize(address, port = 27015) ⇒ SourceServer

Creates a new instance of a server object representing a Source server, i.e. SrcDS instance

Parameters:

  • address (String)

    Either an IP address, a DNS name or one of them combined with the port number. If a port number is given, e.g. 'server.example.com:27016' it will override the second argument.

  • port (Fixnum) (defaults to: 27015)

    The port the server is listening on

Raises:

  • (Error)

    if an host name cannot be resolved


51
52
53
# File 'lib/steam-condenser/servers/source_server.rb', line 51

def initialize(address, port = 27015)
  super
end

Class Method Details

.masterMasterServer

Returns a master server instance for the default master server for Source games

Returns:


39
40
41
# File 'lib/steam-condenser/servers/source_server.rb', line 39

def self.master
  MasterServer.new *MasterServer::SOURCE_MASTER_SERVER
end

Instance Method Details

#disconnectObject

Disconnects the TCP-based channel used for RCON commands

See Also:

  • RCONSocket#close

58
59
60
# File 'lib/steam-condenser/servers/source_server.rb', line 58

def disconnect
  @rcon_socket.close
end

#init_socketObject

Initializes the sockets to communicate with the Source server

See Also:

  • RCONSocket
  • SourceSocket

66
67
68
69
# File 'lib/steam-condenser/servers/source_server.rb', line 66

def init_socket
  @rcon_socket = Sockets::RCONSocket.new @ip_address, @port
  @socket      = Sockets::SourceSocket.new @ip_address, @port
end

#rcon_auth(password) ⇒ Boolean

Authenticates the connection for RCON communication with the server

Parameters:

  • password (String)

    The RCON password of the server

Returns:

  • (Boolean)

    whether authentication was successful

Raises:

See Also:


77
78
79
80
81
82
83
84
85
86
# File 'lib/steam-condenser/servers/source_server.rb', line 77

def rcon_auth(password)
  @rcon_request_id = rand 2**16

  @rcon_socket.send Packets::RCON::RCONAuthRequest.new @rcon_request_id, password

  reply = @rcon_socket.reply
  raise Error::RCONBan if reply.nil?
  reply = @rcon_socket.reply
  @rcon_authenticated = reply.request_id == @rcon_request_id
end

#rcon_exec(command) ⇒ String

Remotely executes a command on the server via RCON

Parameters:

  • command (String)

    The command to execute on the server via RCON

Returns:

  • (String)

    The output of the executed command

Raises:

  • (RCONBanException)

    if the IP of the local machine has been banned on the game server

  • (RCONNoAuthException)

    if not authenticated with the server

See Also:


96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
# File 'lib/steam-condenser/servers/source_server.rb', line 96

def rcon_exec(command)
  raise Error::RCONNoAuth unless @rcon_authenticated

  @rcon_socket.send Packets::RCON::RCONExecRequest.new(@rcon_request_id, command)

  is_multi = false
  response = []
  begin
    response_packet = @rcon_socket.reply

    if response_packet.nil? || response_packet.is_a?(Packets::RCON::RCONAuthResponse)
      @rcon_authenticated = false
      raise Error::RCONNoAuth
    end

    if !is_multi && response_packet.response.size > 0
      is_multi = true
      @rcon_socket.send Packets::RCON::RCONTerminator.new(@rcon_request_id)
    end

    response << response_packet.response
  end while is_multi && !(response[-2] == '' && response[-1] == '')

  response.join('').strip
end