1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89
|
# -*- coding: utf-8 -*-
require_relative "basic"
require_relative "utils"
require_relative "authentication_failed_action"
require_relative "rate_limiting"
require "oauth"
# OAuth関連
module MikuTwitter::Connect
INVALID_REQUEST = 32
PAGE_DOES_NOT_EXIST = 34
BASIC_AUTHENTICATION_IS_NOT_SUPPORTED = 53
RATE_LIMIT_EXCEEDED = 88
INVALID_OR_EXPIRED_TOKEN = 89
OVER_CAPACITY = 130
INTERNAL_ERROR = 131
TIMESTAMP_TOOLATE = 135
BAD_AUTHENTICATION_DATA = 215
IDENTITY_SEED = 'r.A3%Z83n84GDw@KyN-mH-%+_&TnTJ2/'.freeze
attr_accessor :consumer_key, :consumer_secret, :a_token, :a_secret, :oauth_url
def initialize(*a, &b)
@oauth_url = 'https://twitter.com'
super(*a, &b)
end
# キャッシュのキーなどで使う、アカウント毎の一意なID
def account_identity
Digest::MD5.hexdigest([consumer_key, consumer_secret, a_token, a_secret, IDENTITY_SEED].join) end
def consumer(url=oauth_url)
OAuth::Consumer.new(consumer_key, consumer_secret,
:site => url) end
def access_token(url=@oauth_url)
OAuth::AccessToken.new(consumer(url), a_token, a_secret) end
def request_oauth_token
consumer.get_request_token end
# OAuth経由でurlを叩く
# ==== Args
# [method] メソッド。:get, :post, :put, :delete の何れか
# [url] 叩くURL
# [options]
# API引数。ただし、以下のキーは特別扱いされ、API引数からは除外される
# :head :: HTTPリクエストヘッダ(Hash)
# ==== Return
# 戻り値(HTTPResponse)
# ==== Exceptions
# TimeoutError
def query_with_oauth!(method, url, options = {})
if [:get, :delete].include? method
path = url + get_args(options)
res = access_token.__send__(method, path, options[:head])
else
path = url
query_args = options.melt
head = options[:head]
query_args.delete(:head)
res = access_token.__send__(method, path, query_args, head) end
if res.is_a? Net::HTTPResponse
case res.code
when '200'
when '401'
begin
errors = (JSON.parse(res.body)["errors"] rescue nil)
errors.each { |error|
if [INVALID_OR_EXPIRED_TOKEN].include? error["code"]
atoken = authentication_failed_action(method, url, options, res)
return query_with_oauth!(method, url, options) if atoken end }
rescue Exception => e
warn e end
when '429'
raise MikuTwitter::RateLimitError.new("Rate limit #{url}", nil)
end
end
res
end
end
class MikuTwitter; include MikuTwitter::Connect end
|