Class: Slack::RealTime::Client

Inherits:
Object
  • Object
show all
Includes:
Api::Message, Api::MessageId, Api::Ping, Api::Typing
Defined in:
lib/slack/real_time/client.rb

Defined Under Namespace

Classes: ClientAlreadyStartedError, ClientNotStartedError

Class Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Api::Typing

#typing

Methods included from Api::Message

#message

Methods included from Api::Ping

#ping

Constructor Details

#initialize(options = {}) ⇒ Client

Returns a new instance of Client.



24
25
26
27
28
29
30
31
32
# File 'lib/slack/real_time/client.rb', line 24

def initialize(options = {})
  @callbacks = Hash.new { |h, k| h[k] = [] }
  Slack::RealTime::Config::ATTRIBUTES.each do |key|
    send("#{key}=", options.key?(key) ? options[key] : Slack::RealTime.config.send(key))
  end
  @token ||= Slack.config.token
  @logger ||= (Slack::Config.logger || Slack::Logger.default)
  @web_client = Slack::Web::Client.new(token: token, logger: logger)
end

Class Attribute Details

.eventsObject

Returns the value of attribute events.



17
18
19
# File 'lib/slack/real_time/client.rb', line 17

def events
  @events
end

Class Method Details

.configObject



75
76
77
# File 'lib/slack/real_time/client.rb', line 75

def config
  Config
end

.configureObject



71
72
73
# File 'lib/slack/real_time/client.rb', line 71

def configure
  block_given? ? yield(config) : config
end

Instance Method Details

#keep_alive?Boolean

Ensure the server is running, and ping the remote server if no other messages were sent.

Returns:

  • (Boolean)


106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
# File 'lib/slack/real_time/client.rb', line 106

def keep_alive?
  # We can't ping the remote server if we aren't connected.
  return false if @socket.nil? || !@socket.connected?

  time_since_last_message = @socket.time_since_last_message

  # If the server responded within the specified time, we are okay:
  return true if time_since_last_message < websocket_ping

  # If the server has not responded for a while:
  return false if time_since_last_message > (websocket_ping * 2)

  # Kick off the next ping message:
  ping

  true
end

#on(type, &block) ⇒ Object



40
41
42
43
# File 'lib/slack/real_time/client.rb', line 40

def on(type, &block)
  type = type.to_s
  callbacks[type] << block
end

#run_loopObject



80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
# File 'lib/slack/real_time/client.rb', line 80

def run_loop
  @socket.connect! do |driver|
    driver.on :open do |event|
      logger.debug("#{self}##{__method__}") { event.class.name }
      open_event(event)
      callback(event, :open)
    end

    driver.on :message do |event|
      logger.debug("#{self}##{__method__}") { "#{event.class}, #{event.data}" }
      dispatch(event)
    end

    driver.on :close do |event|
      logger.debug("#{self}##{__method__}") { event.class.name }
      callback(event, :close)
      close(event)
      callback(event, :closed)
    end

    # This must be called last to ensure any events are registered before invoking user code.
    @callback&.call(driver)
  end
end

#run_ping!Object

Check if the remote server is responsive, and if not, restart the connection.



125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
# File 'lib/slack/real_time/client.rb', line 125

def run_ping!
  return if keep_alive?

  logger.warn(to_s) { 'is offline' }

  restart_async
rescue Slack::Web::Api::Errors::SlackError => e
  # stop pinging if bot was uninstalled
  case e.message
  when 'account_inactive', 'invalid_auth'
    logger.warn(to_s) { e.message }
    raise e
  end
  logger.debug("#{self}##{__method__}") { e }
rescue StandardError => e
  # disregard all ping worker failures, keep pinging
  logger.debug("#{self}##{__method__}") { e }
end

#run_ping?Boolean

Returns:

  • (Boolean)


144
145
146
# File 'lib/slack/real_time/client.rb', line 144

def run_ping?
  !websocket_ping.nil? && websocket_ping.positive?
end

#start!(&block) ⇒ Object

Start RealTime client and block until it disconnects.



46
47
48
49
50
# File 'lib/slack/real_time/client.rb', line 46

def start!(&block)
  @callback = block if block_given?
  build_socket
  @socket.start_sync(self)
end

#start_async(&block) ⇒ Object

Start RealTime client and return immediately. The RealTime::Client will run in the background.



54
55
56
57
58
# File 'lib/slack/real_time/client.rb', line 54

def start_async(&block)
  @callback = block if block_given?
  build_socket
  @socket.start_async(self)
end

#started?Boolean

Returns:

  • (Boolean)


66
67
68
# File 'lib/slack/real_time/client.rb', line 66

def started?
  @socket&.connected?
end

#stop!Object



60
61
62
63
64
# File 'lib/slack/real_time/client.rb', line 60

def stop!
  raise ClientNotStartedError unless started?

  @socket&.disconnect!
end

#to_sObject



152
153
154
155
156
157
158
# File 'lib/slack/real_time/client.rb', line 152

def to_s
  if store&.team
    "id=#{store.team.id}, name=#{store.team.name}, domain=#{store.team.domain}"
  else
    super
  end
end

#websocket_ping_timerObject



148
149
150
# File 'lib/slack/real_time/client.rb', line 148

def websocket_ping_timer
  websocket_ping / 2
end