ruby - Google API 服务器到服务器通信不起作用(Ruby 实现)
问题描述
我已按照所有步骤设置域范围的授权(https://developers.google.com/admin-sdk/reports/v1/guides/delegation)并点击此链接(https://developers .google.com/identity/protocols/OAuth2ServiceAccount#delegatingauthority),我最终在 Ruby 中创建了这个类。
class Gsuite::ServiceAccount
def initialize(person: nil)
end
def authorized_client
Google::Auth::ServiceAccountCredentials.make_creds(
authorizer = Google::Auth::ServiceAccountCredentials.make_creds(
json_key_io: StringIO.new(File.read AppConfig[:gsuite_service_account]
[:credentials_file]),
scope: AppConfig[:gsuite_service_account][:scope])
client = authorizer.fetch_access_token!
end
end
这个类返回我这个哈希
{"access_token"=>"a_long_token_string_here", "expires_in"=>3600, "token_type"=>"Bearer"}
然后,我创建了这个方法(在我的 Admin 类中)来连接到 Gmail 服务
def gsuite_client_access
@client ||= Gsuite::ServiceAccount.new(person: self.email.to_s).authorized_client
authorized_client = Google::Apis::GmailV1::GmailService.new
authorized_client.authorization = @client
authorized_client
end
因此,当我尝试在代码的另一部分中使用此行列出我的 Gmail 邮件时
inbox = current_admin.gsuite_client_access.list_user_messages('me', max_results: 10)
我收到以下错误消息 =>
Sending HTTP get https://www.googleapis.com/gmail/v1/users/me/messages?maxResults=10
401
#<Hurley::Response GET https://www.googleapis.com/gmail/v1/users/me/messages?maxResults=10 == 401 (238 bytes) 645ms>
Caught error Unauthorized
Error - #<Google::Apis::AuthorizationError: Unauthorized>
Retrying after authentication failure
Google::Apis::AuthorizationError: Unauthorized
任何想法这里缺少什么?
解决方案
最后,我让它工作了。事实证明,您需要使用此行来使用 sub 方法来“模拟用户”才能连接。
authorizer.sub = @person
而且,为了您的高兴,这里是用于阅读 Gmail 邮件的更新测试代码,因此您可以按照自己的意愿使用它。只需记住将 credentials.json 文件保存在您的项目文件夹中以使其工作并使用您在 GSuite 仪表板中添加的相同范围。
class Gsuite::ServiceAccount
def initialize(person: nil)
@person = person
end
def read_messages
client = service_account_access
inbox = client.list_user_messages(@person, max_results: 5, label_ids: "INBOX" )
if inbox.result_size_estimate.nonzero?
inbox.messages.each do |message|
response = client.get_user_message(@person, message.id)
end
end
end
private
def service_account_access
token = authorized_client
client = Signet::OAuth2::Client.new(access_token: token['access_token'])
client.expires_in = Time.current + token["expires_in"]
auth_client = Google::Apis::GmailV1::GmailService.new
auth_client.authorization = client
auth_client
end
def authorized_client
authorizer = Google::Auth::ServiceAccountCredentials.make_creds(
json_key_io: StringIO.new(File.read AppConfig[:credentials_file]),
scope: AppConfig[:gsuite_scope]).dup
authorizer.sub = @person
authorizer.fetch_access_token!
end
end
推荐阅读
- python - 更改 matplotlib 中图例中的标签格式
- python - 如何找出矩阵中大于某个阈值的值?
- python - 向量化 Pandas 列
- typescript - TypeScript:联合类型分布的条件类型数组
- python - 使用 ctypes 调用带有指针参数的 C++ 函数
- java - 在分布式计算期间防止死锁
- javascript - 为什么 AngularJS $onChanges 没有注意到数组发生了变化?
- android - 未找到可绘制资源,但它们存在于可绘制文件夹中
- wpf - 如何在 WPF 中编辑完整的 ToggleButton 模板的副本?缺少一些触发器
- angular - Angular 无法连接到 docker compose 中的 Spring Boot 端点