[英]Getting “The Authorization server does not support this response type” from doorkeeper
[英]Getting authorization from iNaturalist for API
我正在尝试通过Ruby on Rails使用iNaturalist的API。 我是Ruby的新手,而iNaturalist的文档很少。 第一步,我需要弄清楚如何从他们的网站获得授权。
iNaturalist提供以下示例代码。 我使用iNaturalist设置了一个项目,并尝试使用自己的凭据在Rails Console中运行示例代码。 将以下行中的#{url}替换为用户应该登录到iNat所要使用的URL:放置“转到#{url},批准该应用,您应该重定向到您的“ +“ redirect_uri。在此处复制并粘贴“代码”参数。”
我转到生成的网址并登录: https : //www.inaturalist.org/oauth/authorize? client_id= [我的客户ID]&redirect_uri = https://ruby_on_rails--timrobinson41199691.codeanyapp.com/login/&response_type=码
iNaturalist回复“包含的重定向uri无效”。
如果我忽略&response_type = code,它将以“授权服务器不支持此响应类型”的形式响应。
我的网站在codeanywhere.com上。 主页的URL是“ https://ruby_on_rails--timrobinson41199691.codeanyapp.com/ ”。 问题的部分原因是我不了解应该为redirect_uri创建哪种页面,因为我对此仍然很陌生。
require 'rubygems'
require 'rest_client'
require 'json'
site = "https://www.inaturalist.org"
app_id = 'YOUR APP ID'
app_secret = 'YOUR APP SECRET'
redirect_uri = 'YOUR APP REDIRECT URI' # you can set this to some URL you control for testing
# REQUEST AN AUTHORIZATION CODE
# Your web app should redirect the user to this url. They should see a screen
# offering them the choice to authorize your app. If they aggree, they will be
# redirected to your redirect_uri with a "code" parameter
url = "#{site}/oauth/authorize?client_id=#{app_id}&redirect_uri=#{redirect_uri}&response_type=code"
# REQUEST AN AUTH TOKEN
# Once your app has that code parameter, you can exchange it for an access token:
puts "Go to #{url}, approve the app, and you should be redirected to your " +
"redirect_uri. Copy and paste the 'code' param here."
print "Code: "
auth_code = gets.strip
puts
payload = {
:client_id => app_id,
:client_secret => app_secret,
:code => auth_code,
:redirect_uri => redirect_uri,
:grant_type => "authorization_code"
}
puts "POST #{site}/oauth/token, payload: #{payload.inspect}"
puts response = RestClient.post("#{site}/oauth/token", payload)
puts
# response will be a chunk of JSON looking like
# {
# "access_token":"xxx",
# "token_type":"bearer",
# "expires_in":null,
# "refresh_token":null,
# "scope":"write"
# }
# Store the token (access_token) in your web app. You can now use it to make authorized
# requests on behalf of the user, like retrieving profile data:
token = JSON.parse(response)["access_token"]
headers = {"Authorization" => "Bearer #{token}"}
puts "GET /users/edit.json, headers: #{headers.inspect}"
puts RestClient.get("#{site}/users/edit.json", headers)
puts
用户登录到iNat后,应使用数据中提供的授权代码将其重定向回到我的网站。 在routes.rb中,我的登录路由设置为:
post '/login', to: 'organisms#login'
我也尝试过使用get。
iNat返回上面提到的错误,并且未重定向回我的网站。
首先,OAuth可能有些令人生畏。 该指南实际上仅显示了使用cURL测试您的API的等效功能。
在实际的应用程序中,当提供程序从授权重定向回时, redirect_uri
是应用程序中处理响应的任何端点。
因此,让我们设置一个最小的真实Rails应用程序。
注册一个新的应用程序或编辑您现有的应用程序。 使用http://localhost:3000/oauth/inaturalist/callback
作为回调URL(根据需要调整主机)。
将窗口保持打开状态,因为稍后您将需要client_id和secret。
# /config/routes.rb
Rails.application.routes.draw do
# just make sure you have a root path defined.
root to: 'pages#home'
namespace :oauth do
namespace :inaturalist, controller: :callbacks do
# This is just a simple redirect route
get '/', action: :passthru, as: :authorize
# This is the route that handles the actual callback
get 'callback'
end
end
end
您实际上可以在没有重定向路由的情况下执行此操作,而只需在视图中添加指向https://www.inaturalist.org/oauth/authorize...
url的链接。 但是拥有它可以将您的应用程序与OAuth的疯狂以及OmniAuth的工作方式隔离开来。
在Rails 5中,使用加密的凭据存储您的client_id和密码。
从您的外壳运行$ bin/rails credentials:edit
。
inaturalist:
client_id: <from the inaturalist site>
secret: <from the inaturalist site>
在早期版本中,请使用ENV变量。
# Place this in your gemfile outside any groups
gem 'oauth2', '~> 1.4', '>= 1.4.1'
然后运行bundle install
。
# app/controllers/oauth/inaturalist/callbacks_controller.rb
require 'oauth2'
module Oauth
module Inaturalist
class CallbacksController < ::ActionController::Base
# GET /oauth/inaturalist
def passthru
redirect_to client.auth_code.authorize_url
end
# This endpoint is where the provider redirects the user back to
# after authorization.
# GET /oauth/inaturalist/callback
def callback
# Fetch an auth token from the access code
token = client.auth_code.get_token(params[:code])
# Perform an authenticated request to get the users data
api_response = token.get("/users/edit.json")
@user_data = JSON.parse(api_response.body)
# This is just an example of how you can use the user data from
# the provider
@user = {
uid: @user_data["id"],
nickname: @user_data["nickname"]
}
session[:user_id] = @user[:uid]
session[:token] = token.to_hash
redirect_to root_path, success: "Hello #{@user[:nickname]}"
end
private
# Change this if you are not using Rails 5 credentials.
def client
OAuth2::Client.new(
credentials.fetch(:client_id),
credentials.fetch(:secret),
site: "https://www.inaturalist.org",
redirect_uri: oauth_inaturalist_callback_url
)
end
def credentials
Rails.application.credentials.fetch(:inaturalist)
end
end
end
end
token
实际上是一个新的OAuth2::AccessToken
实例,可以使用获取的凭据调用该实例以调用端点。
本示例将令牌存储在会话中。 您可以使用以下命令在后续请求中检索它:
token = OAuth2::AccessToken.from_hash( session[:token] )
文档中提到将oauth访问令牌替换为api.inaturalist.org的api令牌。 但是细节有点稀疏。
<%= link_to 'Sign in to iNaturalist.org', oauth_inaturalist_authorize_path %>
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.