2014-04-11 16 views
5

Tôi đang sử dụng omniauth để cho phép mọi người đăng ký/đăng nhập bằng Facebook và hoạt động tốt của nó! Nhưng tôi muốn thêm đá quý omniauth-twitter để cho phép họ kết nối với Twitter.Rails: Cookie tràn với omniauth twitter đăng ký

Tôi làm theo các bước tương tự so với khi tôi thiết lập Facebook kết nối: https://github.com/plataformatec/devise/wiki/OmniAuth:-Overview

Nhưng khi tôi đăng ký/trong tôi nhận được lỗi sau:

ActionDispatch::Cookies::CookieOverflow in OmniauthCallbacksController#twitter 

tại URL sau:

http://localhost:3000/users/auth/twitter/callback?oauth_token=HRjON8J4bj9EcbjiELHcpHmSXo0cPd0wCHyuWG8ATZU&oauth_verifier=ZiZb1FAKZmNML1gVu5RKBLEGzbeAPPzC80QCpPDGU 

tôi đã cố gắng điều khác nhau đề nghị trên bài viết tương tự nhưng không ai trong số những hoạt động :(

Dưới đây là cấu hình của tôi:

omniauth_callbacks_controller.rb => app/controllers/omniauth_callbacks_controller.rb

def twitter 
    # You need to implement the method below in your model (e.g. app/models/user.rb) 
    @user = User.find_for_twitter_oauth(request.env["omniauth.auth"]) 

    if @user.persisted? 
     sign_in_and_redirect @user, :event => :authentication #this will throw if @user is not activated 
     set_flash_message(:notice, :success, :kind => "twitter") if is_navigational_format? 
    else 
     session["devise.twitter_data"] = request.env["omniauth.auth"] 
     redirect_to new_user_registration_url 
    end 
    end 

user.rb => app/models/user.rb

def self.find_for_twitter_oauth(auth) 
    where(auth.slice(:provider, :uid)).first_or_create do |user| 
    user.provider = auth.provider 
    user.uid = auth.uid 
    user.email = auth.info.email 
    user.password = Devise.friendly_token[0,20] 
    user.name = auth.info.name # assuming the user model has a name 
    end 
end 

def self.new_with_session(params, session) 
    super.tap do |user| 
     if data = session["devise.twitter_data"] && session["devise.twitter_data"]["extra"]["raw_info"] 
     user.email = data["email"] if user.email.blank? 
     end 
    end 
    end 

devise.rb => app/config/initializers/devise.rb

Rails.application.config.middleware.use OmniAuth::Builder do 
provider :twitter, "KEY, "KEYPASSWORD 
end 

Bất kỳ ý tưởng gì sai?

+1

Bạn đặt 'request.env [" omniauth.auth "]' là một băm lớn vào phiên. Bạn cần thêm câu trả lời nào? –

+0

Mẹo chuyên nghiệp: chỉ cắt những phần bạn CẦN và đặt những phần đó trong phiên. –

+0

Kiến thức về mã của tôi rất hạn chế, khi tôi bắt đầu học mã từ đầu tháng trước, vì vậy tôi không thực sự bây giờ ý nghĩa của hàm băm này. Tôi chỉ cần đặt nó bởi vì tôi đã có nó với mô hình omniauth của tôi cho facebook authentification và nó đã làm việc - Bạn có ý nghĩa gì bởi nó là một băm lớn? là nó không cần thiết? – zacchj

Trả lời

7

Như Michael nói trong nhận xét, bạn đang lưu trữ một băm lớn trong phiên và quá lớn (bạn đang sử dụng mặc định CookieStore và cookie chỉ có thể chứa 4KB dữ liệu). Hàm băm do omniauth cung cấp có tất cả dữ liệu được trả về bởi twitter, có thể khá nhiều. Ví dụ: xem README: https://github.com/arunagw/omniauth-twitter#authentication-hash

Nếu mã trong câu hỏi của bạn là tất cả mã liên quan đến đăng nhập twitter, có vẻ như bạn chỉ cần giữ email trong phiên vì đó là tất cả những gì được bạn sử dụng new_with_session mã. Vì vậy, dòng của bạn trong else trong twitter đó là:

session["devise.twitter_data"] = request.env["omniauth.auth"] 

có thể là một cái gì đó như:

session["devise.twitter_data"] = request.env["omniauth.auth"].select { |k, v| k == "email" } 

Tuy nhiên các lỗ hổng lớn với điều này là rằng twitter không trả lại một địa chỉ email cho một người dùng, vì vậy dữ liệu ["email"] sẽ luôn luôn là nil trong new_with_session anyway! Vì vậy, nó là vô nghĩa giữ bất cứ điều gì trong phiên họp nếu bạn chỉ sau này quan tâm đến email mà không bao giờ được trả lại bởi twitter. Có lẽ bạn muốn lấy một tên để giúp điền vào mẫu đăng ký thay vì địa chỉ email. Trong trường hợp này, bạn chỉ có thể giữ nó trong băm từ omniauth. Nếu bạn muốn giữ một vài điều trong băm, sau đó thay vì chọn tất cả chúng để đưa vào phiên giao dịch, bạn có thể làm một cái gì đó như:

session["devise.twitter_data"] = request.env["omniauth.auth"].delete_if("extra") 

đó sẽ loại bỏ các "thêm" băm lồng nhau có thể giúp tất cả mọi thứ khác để phù hợp trong phiên.Để có một giải pháp hoàn chỉnh, bạn sẽ phải xem xét các tình huống lộn xộn như đối phó với những người đã đăng nhập bằng Facebook và sau đó đến và đăng nhập bằng Twitter và muốn sử dụng cùng một địa chỉ email và kết hợp với tài khoản hiện có của họ trên máy tính của bạn. hệ thống.

Trong mọi trường hợp, lưu ý rằng nếu bạn đang sử dụng Rails 3 thì cookie phiên không được mã hóa để người dùng hoặc bất kỳ ai có quyền truy cập vào máy tính của họ có thể đọc nội dung của cookie với bất kỳ dữ liệu nào từ twitter mà bạn kết thúc đó. Nếu bạn đang sử dụng Rails 4, thì cookie sẽ được mã hóa để bảo vệ chống lại điều đó.

Các vấn đề liên quan