2

У меня есть приложение Rails, которое использует SSO Google для входа/выхода пользователей. Он отлично работает в Safari, но в Chrome я получаю эту ошибку:Rails/Google SSO - всплывающее окно auth: заблокировано кадр с источником

Blocked a frame with origin "[domain]" from accessing a frame with origin "https://accounts.google.com". Protocols, domains, and ports must match. 

Ранее я использовал это «решение», чтобы решить: https://github.com/zquestz/omniauth-google-oauth2/issues/122#issuecomment-60510241

Но недавно я заметил, что он вдруг перестал работать для Safari с приведенным выше решением.

Моя текущая реализация выглядит следующим образом (кофе сценария):

$(document).ready -> 
    $.ajax 
    url: 'https://apis.google.com/js/client:plus.js?onload=gpAsyncInit' 
    dataType: 'script' 
    cache: false 

window.gpAsyncInit = -> 

    $('.googleplus-login').click (e) -> 
    e.preventDefault() 

    gapi.auth.authorize { 
    immediate: false 
    response_type: 'code' 
    cookie_policy: 'single_host_origin' 
    client_id: '[id]' 
    scope: 'email profile' 
    }, (response) -> 
    if response and !response.error 
     # google authentication succeed, now post data to server and handle data securely 
     jQuery.ajax 
     type: 'POST' 
     url: '/auth/google_oauth2/callback' 
     dataType: 'json' 
     data: response 
     success: (json) -> 
      # response from server 
      [this doesn't happen] 

      return 
    else 
     # google authentication failed 

Я не видел эту ошибку, описанную в любом месте в документации Google, так что я не совсем уверен, как это исправить.

Я уверен, что у меня есть тот же протокол https, так что это должно быть что-то еще. Я догадываюсь о домене.

Я видел, что другие сайты (например, Stack-overflow) используют другой поток, в котором всплывающее окно не отображается, но вместо этого пользователь перенаправляется на другую страницу. Интересно, может ли это быть решением (и/или) рекомендуемым способом сделать это, чтобы избежать моей ошибки.

В этом случае, где я могу найти документацию для этого в джунглях документации Google?

Update

Это соответствующие части моего кода контроллера.

def google_authentication 

    respond_to do |format| 

    code = params[:code] 

    unless code.blank? 

     [..] 

     load = { code: code, client_id: client_id, client_secret: client_secret, grant_type: grant_type, redirect_uri: redirect_uri } 
     url = "https://www.googleapis.com/oauth2/v3/token/" 
     response = HTTParty.post(url, :query => load, headers: { "content-type" => "application/x-www-form-urlencoded"}) 
     json = JSON.parse(response.body) 

     unless json.nil? 

     unless json["error"].present? 

      [..] 

      email = decoded_hash["email"] 
      user = User.find_by_email(email) 

      if user 
      sign_in_existing_user(user) 
      format.json { render :json => {:status => "Success", user_id: "# {user.id}"} } 
      else 
      # Create user 
      [..] 
      format.html { redirect_to current_user, notice: "Welcome #{current_user.name}!" } 
      format.json { render :json => {:status => "Success", user_id: "#{current_user.id}"} } 

      end 
     else 
      #format.html { redirect_to root_path, error: "Could not sign up/in" } 
      format.json { head :no_content } 
     end 
     end 
    end 
    end 
end 

Я обновил мой JS на основе ответа ниже по @EugZol, чтобы:

data: {access_token: response['access_token'], error: response['error'], expires_in: response['expires_in']} 

И я в настоящее время получаю следующее сообщение об ошибке:

Started POST "/auth/google_oauth2/callback" [..] 
Processing by UsersController#google_authentication as JSON 
Parameters: {"expires_in"=>"86400", "provider"=>"google_oauth2"} 
Completed 406 Not Acceptable in 1ms (ActiveRecord: 0.0ms) 

ActionController::UnknownFormat (ActionController::UnknownFormat): 
app/controllers/users_controller.rb:237:in `google_authentication' 

ответ

1

Единственное Я мог предположить, что здесь, когда вы пытаетесь сделать запрос на свой собственный сервер:

data: response 

... ваш код обращается косвенным образом к кадру, созданному GAPI. I.e., response ссылки на объекты в одном из своих внутренних полей, которые кадр, и jQuery пытается сериализовать это.

Решение выбрать необходимые поля вручную:

data: { 
    state: response['state'], 
    code: response['code'], 
    scope: response['scope'], 
    client_id: response['client_id'], 
    g_user_cookie_policy: response['g_user_cookie_policy'] 
} 
+0

Спасибо! Когда я попробовал это, я получаю следующую ошибку: «Начал POST»/auth/google_oauth2/callback »[...] Обработка по UserController # google_authentication как JSON Параметры: {" expires_in "=>" [exp] "," провайдер "=>" google_oauth2 "} Завершено 406 Не допускается в 1 мс (ActiveRecord: 0.0ms) ActionController :: UnknownFormat (ActionController :: UnknownFormat): app/контроллеры/users_controller.rb: 237: в google_authentication''. Будет ли обновлять мой вопрос с помощью соответствующего кода контроллера, будет очень благодарен, если вы тоже сможете его рассмотреть! – Anders

+0

Вам, похоже, нужно передать параметр «code». Добавьте '{code: response ['code'], ...}' в «данные» Javascript. – EugZol

+0

Спасибо! Теперь это, наконец, работает! Это параметры, которые я фактически использовал (токен доступа для меня здесь не существует) 'data: {state: response ['state'], code: response ['code'], scope: response ['scope'], client_id : response ['client_id'], g_user_cookie_policy: response ['g_user_cookie_policy']} '. – Anders