新手问题 好吧,实在搞不出来.devise (2.1.2)+omniauth (1.1.0)

jialezhang · 2012年08月14日 · 最后由 jialezhang 回复于 2012年08月15日 · 5093 次阅读

首先,插入图片了,界面很点丑,请大家见谅

本想利用 devise+omniauth 设置第三方的认证,但是看几个教程和视频之后,发现要么是单独的 ominuth,要么不是用 devise 内置支持 omniauth 的那种方法,终于在 devise 的 github/wiki 里面找到一个,但是还是没太懂。

devise 是怎么去管理认证这个过程的 在 user.rb 中添加 devise:omniauthable 之后新增两个路由 ,我在申请的时候之这样填的 ,这个时候访问/users/auth/github 之后显示 github 询问的画面,然后就返回 No route matches [GET] "/users/auth/callback" ,当然我自己也知道这样写肯定找不到,但是不知道 CallbackUrl 该怎么去写才能正确的将东西交由/users/omniauht_callback_controller.rb 去处理 PS:敢问流程是不是这样 链接到 user_omniauth_authorize(:provider),相当在地址栏输入/users/auth/github =====> /users/omniauht_callback_controller.rb ====>用户 allowed 之后 ====> 返到我在申请的时候 callback 的地址上面 (这个时候我出现了报错,应该就是 callback-url 填错了,日志写的是 (github) Authentication failure! invalid_credentials:). 大神们,伸出手帮帮忙吧!

参考过https://github.com/plataformatec/devise/wiki/OmniAuth%3A-Overview https://gist.github.com/993566

Github 这个是你服务器上面没有 Github 的 SSL 证书,之前 Ruby China 也遇到过,后面为了省事情,直接跳过证书验证了

https://github.com/ruby-china/ruby-china/blob/master/config/initializers/devise.rb#L2

#1 楼 @huacnlee 额,有想过证书的问题,但是我现在最主要的 (如上),是因为不知道CallBack Url改怎么去写才可以指向/users/auth/:actino/callback然后交由某个文件处理 (设置如上),日志还没有涉及到 ssl 的问题额,求老大指点啊

这是 Ruby China 的配置,你对比源代码看看吧

#3 楼 @zhangjingqiang 啊,之前都没有搜到这篇教程啊。求问 CallbackUrl 是怎么写的,貌似这个蛮关键啊

#5 楼 @jialezhang 嗯嗯,如果对于单一的第三方这种写法的确是没有问题的,但是如果我还有其他的如微博,QQ,这样写就很有问题的了吧

#3 楼 @zhangjingqiang 嗯嗯,差不多的,但是想知道普适的 callback 写法

#4 楼 @huacnlee 2 了,不同的认证应该去不同的地方写

#7 楼 @jialezhang 这个例子是这样处理的: app/models/user.rb

def self.find_for_facebook_oauth(access_token, signed_in_resource=nil)
  data = access_token.extra.raw_info
  if user = self.find_by_email(data.email)
    user
  else # Create a user with a stub password.
    self.create!(:email => data.email, :password => Devise.friendly_token[0,20])
  end
end

app/controllers/users/omniauth_callbacks_controller.rb

def facebook
  # You need to implement the method below in your model
  @user = User.find_for_facebook_oauth(request.env["omniauth.auth"], current_user)

  if @user.persisted?
    flash[:notice] = I18n.t "devise.omniauth_callbacks.success", :kind => "Facebook"
    sign_in_and_redirect @user, :event => :authentication
  else
    session["devise.facebook_data"] = request.env["omniauth.auth"]
    redirect_to new_user_registration_url
  end
end

写共通方法的我没试过,但这个例子很好(twitter+facebook+google): /app/models/user.rb

class User < ActiveRecord::Base
  def self.from_omniauth(auth)
    find_by_provider_and_uid(auth["provider"], auth["uid"]) || create_with_omniauth(auth)
  end

  def self.create_with_omniauth(auth)
    create! do |user|
      user.provider = auth["provider"]
      user.uid = auth["uid"]
      user.name = auth["info"]["name"]
    end
  end
end

/app/controllers/sessions_controller.rb

def create
  user = User.from_omniauth(env["omniauth.auth"])
  session[:user_id] = user.id
  redirect_to root_url, notice: "Signed in!"
end

(来自:http://railscasts.com/episodes/304-omniauth-identity?view=asciicast

需要 登录 后方可回复, 如果你还没有账号请 注册新账号