Skip to content

Commit

Permalink
Add support for new REST API endpoint for bulk lookup of Tweets by ID
Browse files Browse the repository at this point in the history
  • Loading branch information
sferik committed Apr 25, 2014
1 parent 8547449 commit 0d23c5e
Show file tree
Hide file tree
Showing 3 changed files with 29 additions and 33 deletions.
30 changes: 14 additions & 16 deletions lib/twitter/rest/tweets.rb
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ module REST
module Tweets
include Twitter::REST::Utils
include Twitter::Utils
MAX_TWEETS_PER_REQUEST = 100

# Returns up to 100 of the first retweets of a given tweet
#
Expand Down Expand Up @@ -62,19 +63,24 @@ def status(tweet, options = {})

# Returns Tweets
#
# @see https://dev.twitter.com/docs/api/1.1/get/statuses/show/:id
# @see https://dev.twitter.com/docs/api/1.1/get/statuses/lookup
# @rate_limited Yes
# @authentication Requires user context
# @raise [Twitter::Error::Unauthorized] Error raised when supplied user credentials are not valid.
# @authentication Required
# @return [Array<Twitter::Tweet>] The requested Tweets.
# @overload statuses(*tweets)
# @param tweets [Enumerable<Integer, String, URI, Twitter::Tweet>] A collection of Tweet IDs, URIs, or objects.
# @overload statuses(*tweets, options)
# @param tweets [Enumerable<Integer, String, URI, Twitter::Tweet>] A collection of Tweet IDs, URIs, or objects.
# @param options [Hash] A customizable set of options.
# @option options [Symbol, String] :method Requests users via a GET request instead of the standard POST request if set to ':get'.
# @option options [Boolean] :include_entities The tweet entities node will be disincluded when set to false.
# @option options [Boolean, String, Integer] :trim_user Each tweet returned in a timeline will include a user object with only the author's numerical ID when set to true, 't' or 1.
def statuses(*args)
parallel_tweets_from_response(:get, '/1.1/statuses/show', args)
arguments = Twitter::Arguments.new(args)
request_method = arguments.options.delete(:method) || :post
flat_pmap(arguments.each_slice(MAX_TWEETS_PER_REQUEST)) do |tweets|
perform_with_objects(request_method, '/1.1/statuses/lookup.json', arguments.options.merge(:id => tweets.collect { |u| extract_id(u) }.join(',')), Twitter::Tweet)
end
end

# Destroys the specified Tweets
Expand All @@ -92,7 +98,10 @@ def statuses(*args)
# @param options [Hash] A customizable set of options.
# @option options [Boolean, String, Integer] :trim_user Each tweet returned in a timeline will include a user object with only the author's numerical ID when set to true, 't' or 1.
def destroy_status(*args)
parallel_tweets_from_response(:post, '/1.1/statuses/destroy', args)
arguments = Twitter::Arguments.new(args)
pmap(arguments) do |tweet|
perform_with_object(:post, "/1.1/statuses/destroy/#{extract_id(tweet)}.json", arguments.options, Twitter::Tweet)
end
end
alias_method :destroy_tweet, :destroy_status
deprecate_alias :status_destroy, :destroy_status
Expand Down Expand Up @@ -289,17 +298,6 @@ def retweeters_ids(*args)

private

# @param request_method [Symbol]
# @param path [String]
# @param args [Array]
# @return [Array<Twitter::Tweet>]
def parallel_tweets_from_response(request_method, path, args)
arguments = Twitter::Arguments.new(args)
pmap(arguments) do |tweet|
perform_with_object(request_method, path + "/#{extract_id(tweet)}.json", arguments.options, Twitter::Tweet)
end
end

def post_retweet(tweet, options)
response = post("/1.1/statuses/retweet/#{extract_id(tweet)}.json", options).body
Twitter::Tweet.new(response)
Expand Down
2 changes: 1 addition & 1 deletion lib/twitter/rest/users.rb
Original file line number Diff line number Diff line change
Expand Up @@ -214,7 +214,7 @@ def unblock(*args)
#
# @see https://dev.twitter.com/docs/api/1.1/get/users/lookup
# @rate_limited Yes
# @authentication Requires user context
# @authentication Required
# @raise [Twitter::Error::Unauthorized] Error raised when supplied user credentials are not valid.
# @return [Array<Twitter::User>] The requested users.
# @overload users(*users)
Expand Down
30 changes: 14 additions & 16 deletions spec/twitter/rest/tweets_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -135,36 +135,34 @@

describe '#statuses' do
before do
stub_get('/1.1/statuses/show/25938088801.json').to_return(:body => fixture('status.json'), :headers => {:content_type => 'application/json; charset=utf-8'})
stub_post('/1.1/statuses/lookup.json').with(:body => {:id => '25938088801,91151181040201728'}).to_return(:body => fixture('statuses.json'), :headers => {:content_type => 'application/json; charset=utf-8'})
end
it 'requests the correct resource' do
@client.statuses(25_938_088_801)
expect(a_get('/1.1/statuses/show/25938088801.json')).to have_been_made
@client.statuses(25_938_088_801, 91_151_181_040_201_728)
expect(a_post('/1.1/statuses/lookup.json').with(:body => {:id => '25938088801,91151181040201728'})).to have_been_made
end
it 'returns an array of Tweets' do
tweets = @client.statuses(25_938_088_801)
tweets = @client.statuses(25_938_088_801, 91_151_181_040_201_728)
expect(tweets).to be_an Array
expect(tweets.first).to be_a Twitter::Tweet
expect(tweets.first.text).to eq("The problem with your code is that it's doing exactly what you told it to do.")
expect(tweets.first.text).to eq('Happy Birthday @imdane. Watch out for those @rally pranksters!')
end
context 'with a URI object passed' do
context 'with URI objects passed' do
it 'requests the correct resource' do
tweet = URI.parse('https://twitter.com/sferik/status/25938088801')
@client.statuses(tweet)
expect(a_get('/1.1/statuses/show/25938088801.json')).to have_been_made
@client.statuses(URI.parse('https://twitter.com/sferik/status/25938088801'), URI.parse('https://twitter.com/sferik/status/91151181040201728'))
expect(a_post('/1.1/statuses/lookup.json').with(:body => {:id => '25938088801,91151181040201728'})).to have_been_made
end
end
context 'with a URI string passed' do
context 'with URI strings passed' do
it 'requests the correct resource' do
@client.statuses('https://twitter.com/sferik/status/25938088801')
expect(a_get('/1.1/statuses/show/25938088801.json')).to have_been_made
@client.statuses('https://twitter.com/sferik/status/25938088801', 'https://twitter.com/sferik/status/91151181040201728')
expect(a_post('/1.1/statuses/lookup.json').with(:body => {:id => '25938088801,91151181040201728'})).to have_been_made
end
end
context 'with a Tweet passed' do
context 'with Tweets passed' do
it 'requests the correct resource' do
tweet = Twitter::Tweet.new(:id => 25_938_088_801)
@client.statuses(tweet)
expect(a_get('/1.1/statuses/show/25938088801.json')).to have_been_made
@client.statuses(Twitter::Tweet.new(:id => 25_938_088_801), Twitter::Tweet.new(:id => 91_151_181_040_201_728))
expect(a_post('/1.1/statuses/lookup.json').with(:body => {:id => '25938088801,91151181040201728'})).to have_been_made
end
end
end
Expand Down

0 comments on commit 0d23c5e

Please sign in to comment.