나는 이것을 추한 해킹으로 해결할 수있었습니다. 이러한 모듈의 내부 동작에 대해 더 많은 지식을 가진 사람이이를 수행 할 수있는 적절한 방법을 제안한다면 좋을 것입니다. 깨끗한 구현을 제공하기에 충분하지 않은 많은 방법이 있습니다. 나는 원숭이가 서명 된 요청에서 oauth 토큰을 가져 오기 위해 oauth 도우미를 패치했습니다. 아직 구현을 완료하지 못했기 때문에 더 많은 문제가 발생할 수 있습니다. 이것은 그래프 api를 호출하는 대신 서명 된 요청에 포함 된 user_id (facebook uid)를 활용할 수도 있습니다. json으로 개체가 USER_ID 매개 변수를 포함하지 않는 경우
http://developers.facebook.com/docs/authentication/
", 리디렉션해야합니다 사용자가 아직 승인되지 않은 경우 여기에 설명 된대로
나는 리디렉션을 포함하려면이 업데이트되었습니다 일반 OAuth 2.0 웹 애플리케이션 흐름에 따라 애플리케이션 승인 화면으로 이동합니다. "
그러나이 대신에 그 URL에 대한 링크가있는 페이스 북 로고가 표시되고 사용자가 iframe에서 튀어 나오게됩니다. 나는 거기에 없어야한다고 생각하는 페이스 북으로 iframe을 패배시킵니다.
module Devise
module Oauth
module InternalHelpers
def callback_action
access_token = nil
if params[:signed_request]
signed_data = FacebookSignedRequest.new(params[:signed_request]).valid?
if signed_data['oauth_token']
access_token = oauth_config.access_token_by_token(signed_data['oauth_token'])
else
return redirect_to oauth_config.authorize_url(:redirect_uri => oauth_redirect_uri)
end
elsif params[:code]
access_token = oauth_config.access_token_by_code(params[:code], oauth_redirect_uri)
else
return redirect_to oauth_config.authorize_url(:redirect_uri => oauth_redirect_uri)
end
self.resource = resource_class.send(oauth_model_callback, access_token, signed_in_resource) if access_token
if resource && resource.persisted? && resource.errors.empty?
set_oauth_flash_message :notice, :success
sign_in_and_redirect resource_name, resource, :event => :authentication
else
session[oauth_session_key] = access_token.token
clean_up_passwords(resource)
render_for_oauth
end
end
def valid_oauth_callback?
return !!params[:signed_request]
end
end
end
end
### For parsing the signed request
require 'base64'
require 'json'
require 'openssl'
# the code is copied from
# http://forum.developers.facebook.net/viewtopic.php?pid=250261
class FacebookSignedRequest
attr_reader :signed_request
def initialize(signed_request)
@signed_request = signed_request
end
def base64_url_decode str
encoded_str = str.gsub('-','+').gsub('_','/')
encoded_str += '=' while !(encoded_str.size % 4).zero?
Base64.decode64(encoded_str)
end
def valid?
secret = "facebook-secret"
#decode data
encoded_sig, payload = signed_request.split('.')
sig = base64_url_decode(encoded_sig).unpack("H*")[0]
data = JSON.parse base64_url_decode(payload)
if data['algorithm'].to_s.upcase != 'HMAC-SHA256'
# Rails.logger.error 'Unknown algorithm. Expected HMAC-SHA256'
return false
end
#check sig
expected_sig = OpenSSL::HMAC.hexdigest('sha256', secret, payload)
if expected_sig != sig
# Rails.logger.error 'Bad Signed JSON signature!'
return false
end
data
end
end