Приложение и actioncable не будут делиться cookie

Я использую devise для аутентификации, но когда я реализовал ваш метод, я получил сообщение "Неавторизованная попытка подключения была отклонена"

После нескольких часов поисков я узнал, что:

cookies.signed['user.id']

возвращает ноль В следующем блоке кода.

def find_verified_user
  if verified_user = User.find_by(id: cookies.signed['user.id'])
    verified_user
  else
    reject_unauthorized_connection
  end
end

Я проверил и определенно есть cookie, но он не содержит данных cookie, установленных Devise.

Чтобы проверить, действительно ли установлен 'user.id', я поднимаю его в представлении. Это, как исключение, возвращает идентификатор пользователя

Signed in as @#{cookies.signed[:username]}.
- raise(cookies.signed['user.id'].inspect)
%br/
%br/
#messages
%br/
%br/
= form_for :message, url: messages_path, remote: true, id: 'messages-form' do |f|
 = f.label :body, 'Enter a message:'
 %br/
 = f.text_field :body
 %br/
 = f.submit 'Send message'

Мой вопрос / проблема:

Кажется, что cookie не доступен на сервере actioncable.
Есть ли способ поделиться файлом cookie, установленным Devise, с кабельным сервером?

https://github.com/stsc3000/actioncable-chat.git

2 ответа

Проверьте клиентский файл JavaScript, который подключается к вашему серверу Action Cable. В некоторых руководствах вы поместили это в 'app/assets/javascripts/application_cable.coffee', а другие в 'app/assets/javascripts/channel /index.coffee', но это выглядит так:

#= require cable

@App = {}
App.cable = Cable.createConsumer("ws://cable.example.com:28080")

Вам нужен адрес WebSocket, указывающий на ваш кабель-сервер, и этот адрес должен предоставить пространство имен файлов cookie остальной части вашего приложения. Скорее всего, ваш указывает на неправильное место, поэтому, например, если вы работаете над этим локально, вам нужно изменить:

App.cable = Cable.createConsumer("ws://cable.example.com:28080")

в

App.cable = Cable.createConsumer("ws://localhost:28080")

при условии, конечно, что ваш сервер Cable работает на порту 28080 (указан в исполняемом файле bin / cable). Также обязательно очистите кеш браузера, чтобы обновленный файл использовался браузером.

Не уверен, что он уже запущен, но у меня была та же проблема с Rails 5.0.0.beta3. Я не перешел на следующую строку:

App.cable = Cable.createConsumer("ws://localhost:3000")

Я сохранил это как было раньше

 @App ||= {}
 App.cable = ActionCable.createConsumer()

Но то, что я сделал, было связано с Cookies. Несмотря ни на что Файл cookie для моего user_id не будет отображаться. Так что я обошел вокруг. Вместо этого я получил файл cookie для сохранения имени пользователя, а затем, наконец, смог увидеть его в вызове функции find_verified_user.

Когда пользователь входит в систему (Sessions#create), я вызываю вспомогательную функцию:

sessions_helper.rb
 def set_cookie(user)
    the_username = user.username.to_s
    cookies.permanent.signed[:username] = the_username
  end

Новый find_verified_user

  def find_verified_user
    if current_user = User.find_by_username(cookies.signed[:username])
      current_user
    else
      reject_unauthorized_connection
    end
  end

Это может или не может быть лучшим решением, но после часов путаницы и разочарования это сработало для моей ситуации. Я надеюсь, что это может помочь кому-то

Настроить нужно в config/initializers/session_store.rb

# using cookie store
if Rails.env.production?
#  to share across subdomains
    Rails.application.config.session_store :cookie_store, 
                      key: '_app_name_session', domain: ".example.com"
else
# to share with any domain
    Rails.application.config.session_store :cookie_store, 
                      key: '_app_name_session', domain: :all, tld_length: 2
end

#for redis store
elsif Rails.env.production?
#  to share across subdomains
    Rails.application.config.session_store :redis_store, {
       servers: [
        { host: YourRedisHost, port: YourRedisPort},
      ],
      key: '_app_name_session',
      expire_after: 1.day,
      domain: '.example.com'
    }

else
# to share with any domain
    Rails.application.config.session_store :redis_store, {
       servers: [
        { host: YourRedisHost, port: YourRedisPort},
      ],
      key: '_app_name_session',
      expire_after: 1.day,
      domain: :all, 
      tld_length: 2
    }
end 

Проблема , которую я обнаружил, состоит в следующем: у меня есть 2 разных пользователя, вошедших в систему. Один вошел в систему на 127.0.0.1, а другой вошел в систему на локальном хосте. поэтому, когда я захожу на свой веб-сайт с использованием 127.0.0.1:3000, но мой кабель настроен для работы на локальном хосте следующим образом:

  config.action_cable.url = "ws://localhost:3000/cable"

в config/environment /development.rb

пользователь, вошедший в систему на 127.0.0.1, делает запрос кабеля к "ws://localhost:3000/cable" (согласно конфигурации), но таким образом отправляется файл cookie, сохраненный для localhost, хотя я делаю запрос с 127.0. 0.1, который является другим пользователем (или вообще без пользователя).

Таким образом, нижний корень - это то, на что указывает Pwnrar, конфигурация адреса кабеля и способ доступа к вашему веб-сайту.

Таким образом, чтобы решить эту проблему, всегда заходите на свой веб-сайт, используя адрес сервера, настроенный для вашего кабеля, в противном случае файлы cookie будут смешаны.

Другие вопросы по тегам