diff --git a/lib/action_cable_client.rb b/lib/action_cable_client.rb index b682b0a..b8bf1d8 100644 --- a/lib/action_cable_client.rb +++ b/lib/action_cable_client.rb @@ -22,7 +22,7 @@ class Commands attr_reader :_message_factory # The queue should store entries in the format: # [ action, data ] - attr_accessor :message_queue, :_subscribed, :_subscribed_callaback, :_pinged_callback + attr_accessor :message_queue, :_subscribed, :_subscribed_callback, :_pinged_callback, :_connected_callback def_delegator :_websocket_client, :onerror, :errored def_delegator :_websocket_client, :send, :send_msg @@ -91,7 +91,7 @@ def received # # do things after the client is connected to the server # end def connected - _websocket_client.onopen do + self._connected_callback = Proc.new do subscribe yield end @@ -111,7 +111,7 @@ def connected # # do things after successful subscription confirmation # end def subscribed(&block) - self._subscribed_callaback = block + self._subscribed_callback = block end # @return [Boolean] is the client subscribed to the channel? @@ -147,6 +147,8 @@ def handle_received_message(message) if is_ping?(json) _pinged_callback&.call(json) + elsif is_welcome?(json) + _connected_callback&.call(json) elsif !subscribed? check_for_subscribe_confirmation(json) else @@ -162,7 +164,7 @@ def check_for_subscribe_confirmation(message) return unless Message::TYPE_CONFIRM_SUBSCRIPTION == message_type self._subscribed = true - _subscribed_callaback&.call + _subscribed_callback&.call end # {"identifier" => "_ping","message" => 1460201942} @@ -172,6 +174,12 @@ def is_ping?(message) Message::IDENTIFIER_PING == message_identifier end + # {"type" => "welcome"} + def is_welcome?(message) + message_identifier = message[Message::TYPE_KEY] + Message::IDENTIFIER_WELCOME == message_identifier + end + def subscribe msg = _message_factory.create(Commands::SUBSCRIBE) send_msg(msg.to_json) diff --git a/lib/action_cable_client/message.rb b/lib/action_cable_client/message.rb index 576f457..e3703d3 100644 --- a/lib/action_cable_client/message.rb +++ b/lib/action_cable_client/message.rb @@ -4,6 +4,7 @@ class ActionCableClient class Message IDENTIFIER_KEY = 'identifier' IDENTIFIER_PING = 'ping' + IDENTIFIER_WELCOME = 'welcome' # Type is never sent, but is received # TODO: find a better place for this constant TYPE_KEY = 'type' diff --git a/spec/unit/action_cable_client_spec.rb b/spec/unit/action_cable_client_spec.rb index 895fc20..d4f41a7 100644 --- a/spec/unit/action_cable_client_spec.rb +++ b/spec/unit/action_cable_client_spec.rb @@ -99,9 +99,9 @@ context '#subscribed' do it 'sets the callback' do - expect(@client._subscribed_callaback).to eq nil + expect(@client._subscribed_callback).to eq nil @client.subscribed {} - expect(@client._subscribed_callaback).to_not eq nil + expect(@client._subscribed_callback).to_not eq nil end it 'once the callback is set, receiving a subscription confirmation invokes the callback' do @@ -110,7 +110,7 @@ callback_called = true end - expect(@client).to receive(:_subscribed_callaback).and_call_original + expect(@client).to receive(:_subscribed_callback).and_call_original message = { 'identifier' => 'ping', 'type' => 'confirm_subscription' } @client.send(:check_for_subscribe_confirmation, message) expect(callback_called).to eq true @@ -118,6 +118,14 @@ end context '#connected' do + it 'sets the callback' do + expect(@client._connected_callback).to eq(nil) + + @client.connected {} + + expect(@client._connected_callback).to_not eq(nil) + end + it 'subscribes' do # TODO: how do I stub a method chain that takes a block? # allow{ |b| @client._websocket_client.callback }.to yield_with_no_args