omn​​iauth-facebook test with devise

时间:2016-08-04 12:18:56

标签: ruby-on-rails devise rspec-rails omniauth-facebook

我开始使用omniauth和设计用户模型。整合效果很好,但案例失败了。 这是来自omniauth回调控制器的相关代码:

class OmniauthCallbacksController < Devise::OmniauthCallbacksController
  before_action :find_user, only: [:facebook]
  def facebook
    process_omniauth_response('Facebook', request.env['omniauth.auth'], @user)
  end
  def failure
    redirect_to root_path, flash: { error: 'Authentication \
      failed, please try again!' }
  end

  private

  def find_user
    @user = User.from_omniauth(request.env['omniauth.auth'])
  end

  def process_omniauth_response(provider, env_data, user)
    if user.persisted?
      sign_in_and_redirect user, event: :authentication
      set_flash_message(:notice, :success,
                        kind: provider) if is_navigational_format?
    else
      session["devise.#{provider.downcase}_data"] = env_data
      redirect_to new_user_registration_url
    end
  end
end

用户模型方法:

def self.from_omniauth(auth)
   where(provider: auth.provider, uid: auth.uid).first_or_create do |user|
     info = auth.info
     user.email = info.email
     user.remote_profile_picture_url = info.image
     user.name = info.name
     user.password = Devise.friendly_token[0, 20]
   end
end

def self.new_with_session(params, session)
 super.tap do |user|
   auth_data =
     session['devise.facebook_data'] || session['devise.twitter_data']
   fill_with_omniauth_data(user, auth_data) if auth_data
 end
end

def self.fill_with_omniauth_data(user, auth_data)
 data_info = auth_data['info']
 user.email = data_info['email'] if user.email.blank?
 user.name = data_info['name'] if user.name.blank?
 ...
end

所以一切正常,即如果新用户点击Facebook登录,经过Facebook认证后,他将来到预先填写数据的注册页面,但是在下面这种情况下,它将在omniauth回调后登录页面动作:

context 'when facebook email doesn\'t exist in the system' do
  before(:each) do
    stub_env_for_omniauth
    get :facebook
  end

  it { response.should redirect_to new_user_registration_path }

  it 'should create authentication with facebook id' do
    authentication = User.where(provider: 'facebook', uid: '1234').first
    puts authentication.inspect
    authentication.should_not be_nil
  end
end

存根方法:

def stub_env_for_omniauth
  request.env['devise.mapping'] = Devise.mappings[:user]
  request.env['omniauth.auth'] = OmniAuth::AuthHash.new(
    provider: 'facebook', uid: '1234', info: {
      email: 'ghost@nobody.com', name: 'mock user'
    },
    extra: { raw_info: { age: 23 } }
  ) 
end

我收到了这条消息:

  

预期回复是重定向到http://test.host/users/sign_up,但重定向到http://test.host/users/sign_in

从调试开始,我得到的用户对象是新的,当我在控制器的'find_user'方法中检查它时没有持久化,但是在spec的情况下它是持久的。

我将不胜感激任何帮助。 谢谢

0 个答案:

没有答案