tweetstream 0.1.0

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of tweetstream might be problematic. Click here for more details.

data/.document ADDED
@@ -0,0 +1,5 @@
1
+ README.rdoc
2
+ lib/**/*.rb
3
+ bin/*
4
+ features/**/*.feature
5
+ LICENSE
data/.gitignore ADDED
@@ -0,0 +1,5 @@
1
+ *.sw?
2
+ .DS_Store
3
+ coverage
4
+ rdoc
5
+ pkg
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2009 Intridea, Inc.
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.rdoc ADDED
@@ -0,0 +1,77 @@
1
+ = TweetStream
2
+
3
+ TweetStream provides simple Ruby access to Twitter's Streaming API
4
+ (http://apiwiki.twitter.com/Streaming-API-Documentation).
5
+
6
+ == Installation
7
+
8
+ The TweetStream gem is available on GitHub and Gemcutter. To get the
9
+ latest gem from GitHub:
10
+
11
+ gem sources -a http://gems.github.com/
12
+ gem install intridea-tweetstream
13
+
14
+ To install from Gemcutter:
15
+
16
+ gem sources -a http://gemcutter.org/
17
+ gem install tweetstream
18
+
19
+ == Usage
20
+
21
+ Using TweetStream is quite simple:
22
+
23
+ require 'rubygems'
24
+ require 'tweetstream'
25
+
26
+ # This will pull a sample of all tweets based on
27
+ # your Twitter account's Streaming API role.
28
+ TweetStream::Client.new('username','password').sample do |status|
29
+ # The status object is a special Hash with
30
+ # method access to its keys.
31
+ puts "#{status.text}"
32
+ end
33
+
34
+ You can also use it to track keywords or follow a given set of
35
+ user ids:
36
+
37
+ # Use 'track' to track a list of single-word keywords
38
+ TweetStream::Client.new('username','password').track('term1', 'term2') do |status|
39
+ puts "#{status.text}"
40
+ end
41
+
42
+ # Use 'follow' to follow a group of user ids (integers, not screen names)
43
+ TweetStream::Client.new('username','password').follow(14252, 53235) do |status|
44
+ puts "#{status.text}"
45
+ end
46
+
47
+ The methods available to TweetStream::Client will be kept in parity
48
+ with the methods available on the Streaming API wiki page.
49
+
50
+ == Daemonizing
51
+
52
+ It is also possible to create a daemonized script quite easily
53
+ using the TweetStream library:
54
+
55
+ # The third argument is an optional process name
56
+ TweetStream::Client.new('username','password', 'tracker').track('term1', 'term2') do |status|
57
+ # do something in the background
58
+ end
59
+
60
+ If you put the above into a script and run the script with <tt>ruby scriptname.rb</tt>, you will see a list of daemonization commands such
61
+ as start, stop, and run.
62
+
63
+ == Note on Patches/Pull Requests
64
+
65
+ * Fork the project.
66
+ * Make your feature addition or bug fix.
67
+ * Add tests for it. This is important so I don't break it in a future version unintentionally.
68
+ * Commit, do not mess with rakefile, version, or history. (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
69
+ * Send me a pull request. Bonus points for topic branches.
70
+
71
+ == Contributors
72
+
73
+ * Michael Bleigh (initial gem)
74
+
75
+ == Copyright
76
+
77
+ Copyright (c) 2009 Intridea, Inc. (http://www.intridea.com/). See LICENSE for details.
data/Rakefile ADDED
@@ -0,0 +1,50 @@
1
+ require 'rubygems'
2
+ require 'rake'
3
+
4
+ begin
5
+ require 'jeweler'
6
+ Jeweler::Tasks.new do |gem|
7
+ gem.name = "tweetstream"
8
+ gem.summary = %Q{TweetStream is a simple wrapper for consuming the Twitter Streaming API.}
9
+ gem.description = %Q{TweetStream allows you to easily consume the Twitter Streaming API utilizing the YAJL Ruby gem.}
10
+ gem.email = "michael@intridea.com"
11
+ gem.homepage = "http://github.com/intridea/tweetstream"
12
+ gem.authors = ["Michael Bleigh"]
13
+ gem.add_development_dependency "rspec"
14
+ gem.add_dependency 'yajl-ruby', '>= 0.6.3'
15
+ gem.add_dependency 'daemons'
16
+ # gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
17
+ end
18
+ rescue LoadError
19
+ puts "Jeweler (or a dependency) not available. Install it with: sudo gem install jeweler"
20
+ end
21
+
22
+ require 'spec/rake/spectask'
23
+ Spec::Rake::SpecTask.new(:spec) do |spec|
24
+ spec.libs << 'lib' << 'spec'
25
+ spec.spec_files = FileList['spec/**/*_spec.rb']
26
+ end
27
+
28
+ Spec::Rake::SpecTask.new(:rcov) do |spec|
29
+ spec.libs << 'lib' << 'spec'
30
+ spec.pattern = 'spec/**/*_spec.rb'
31
+ spec.rcov = true
32
+ end
33
+
34
+ task :spec => :check_dependencies
35
+
36
+ task :default => :spec
37
+
38
+ require 'rake/rdoctask'
39
+ Rake::RDocTask.new do |rdoc|
40
+ if File.exist?('VERSION')
41
+ version = File.read('VERSION')
42
+ else
43
+ version = ""
44
+ end
45
+
46
+ rdoc.rdoc_dir = 'rdoc'
47
+ rdoc.title = "tweetstream #{version}"
48
+ rdoc.rdoc_files.include('README*')
49
+ rdoc.rdoc_files.include('lib/**/*.rb')
50
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.1.0
data/lib/tracker.log ADDED
File without changes
data/lib/tracker.rb ADDED
@@ -0,0 +1,12 @@
1
+ require 'rubygems'
2
+ require 'tweetstream'
3
+ require 'logger'
4
+
5
+ File.open('tracker.log', File::WRONLY | File::APPEND | File::CREAT) do |file|
6
+ log = Logger.new(file)
7
+
8
+ TweetStream::Daemon.new('mbleigh','hotmail', 'tracker').track('fail') do |status|
9
+ log.info "[#{status.user.screen_name}] #{status.text}"
10
+ puts "[#{status.user.screen_name}] #{status.text}"
11
+ end
12
+ end
@@ -0,0 +1,5 @@
1
+ require 'tweetstream/client'
2
+ require 'tweetstream/hash'
3
+ require 'tweetstream/status'
4
+ require 'tweetstream/user'
5
+ require 'tweetstream/daemon'
@@ -0,0 +1,109 @@
1
+ require 'uri'
2
+ require 'cgi'
3
+ require 'yajl'
4
+ require 'yajl/http_stream'
5
+
6
+ module TweetStream
7
+ # Provides simple access to the Twitter Streaming API (http://apiwiki.twitter.com/Streaming-API-Documentation)
8
+ # for Ruby scripts that need to create a long connection to
9
+ # Twitter for tracking and other purposes.
10
+ #
11
+ # Basic usage of the library is to call one of the provided
12
+ # methods and provide a block that will perform actions on
13
+ # a yielded TweetStream::Status. For example:
14
+ #
15
+ # TweetStream::Client.new('user','pass').track('fail') do |status|
16
+ # puts "[#{status.user.screen_name}] #{status.text}"
17
+ # end
18
+ #
19
+ # For information about a daemonized TweetStream client,
20
+ # view the TweetStream::Daemon class.
21
+ class Client
22
+ attr_accessor :username, :password
23
+
24
+ # Create a new client with the Twitter credentials
25
+ # of the account you want to be using its API quota.
26
+ def initialize(user, pass)
27
+ self.username = user
28
+ self.password = pass
29
+ end
30
+
31
+ # Returns all public statuses. The Firehose is not a generally
32
+ # available resource. Few applications require this level of access.
33
+ # Creative use of a combination of other resources and various access
34
+ # levels can satisfy nearly every application use case.
35
+ def firehose(query_parameters = {}, &block)
36
+ start('statuses/firehose', query_parameters, &block)
37
+ end
38
+
39
+ # Returns all retweets. The retweet stream is not a generally available
40
+ # resource. Few applications require this level of access. Creative
41
+ # use of a combination of other resources and various access levels
42
+ # can satisfy nearly every application use case. As of 9/11/2009,
43
+ # the site-wide retweet feature has not yet launched,
44
+ # so there are currently few, if any, retweets on this stream.
45
+ def retweet(query_parameters = {}, &block)
46
+ start('statuses/retweet', query_parameters, &block)
47
+ end
48
+
49
+ # Returns a random sample of all public statuses. The default access level
50
+ # provides a small proportion of the Firehose. The "Gardenhose" access
51
+ # level provides a proportion more suitable for data mining and
52
+ # research applications that desire a larger proportion to be statistically
53
+ # significant sample.
54
+ def sample(query_parameters = {}, &block)
55
+ start('statuses/sample', query_parameters, &block)
56
+ end
57
+
58
+ # Specify keywords to track. Queries are subject to Track Limitations,
59
+ # described in Track Limiting and subject to access roles, described in
60
+ # the statuses/filter method. Track keywords are case-insensitive logical
61
+ # ORs. Terms are exact-matched, and also exact-matched ignoring
62
+ # punctuation. Phrases, keywords with spaces, are not supported.
63
+ # Keywords containing punctuation will only exact match tokens.
64
+ # Query parameters may be passed as the last argument.
65
+ def track(*keywords, &block)
66
+ query_params = keywords.pop if keywords.last.is_a?(::Hash)
67
+ query_params ||= {}
68
+ start('statuses/filter', query_params.merge(:track => keywords.join(',')), &block)
69
+ end
70
+
71
+ # Returns public statuses from or in reply to a set of users. Mentions
72
+ # ("Hello @user!") and implicit replies ("@user Hello!" created without
73
+ # pressing the reply "swoosh") are not matched. Requires integer user
74
+ # IDs, not screen names. Query parameters may be passed as the last argument.
75
+ def follow(*user_ids, &block)
76
+ query_params = user_ids.pop if user_ids.last.is_a?(::Hash)
77
+ query_params ||= {}
78
+ start('statuses/filter', query_params.merge(:follow => user_ids.join(',')), &block)
79
+ end
80
+
81
+ #:nodoc:
82
+ def start(path, query_parameters = {}, &block)
83
+ uri = build_uri(path, query_parameters)
84
+
85
+ Yajl::HttpStream.get(uri, :symbolize_keys => true) do |hash|
86
+ yield TweetStream::Status.new(hash)
87
+ end
88
+ end
89
+
90
+ protected
91
+
92
+ #:nodoc:
93
+ def build_uri(path, query_parameters = {})
94
+ URI.parse("http://#{self.username}:#{self.password}@stream.twitter.com/1/#{path}.json#{build_query_parameters(query_parameters)}")
95
+ end
96
+
97
+ #:nodoc:
98
+ def build_query_parameters(query)
99
+ return '' unless query && query.is_a?(::Hash) && query.size > 0
100
+ pairs = []
101
+
102
+ query.each_pair do |k,v|
103
+ pairs << "#{k.to_s}=#{CGI.escape(v.to_s)}"
104
+ end
105
+
106
+ "?#{pairs.join('&')}"
107
+ end
108
+ end
109
+ end
@@ -0,0 +1,40 @@
1
+ require 'daemons'
2
+
3
+ # A daemonized TweetStream client that will allow you to
4
+ # create backgroundable scripts for application specific
5
+ # processes. For instance, if you create a script called
6
+ # <tt>tracker.rb</tt> and fill it with this:
7
+ #
8
+ # require 'rubygems'
9
+ # require 'tweetstream'
10
+ #
11
+ # TweetStream::Daemon.new('user','pass', 'tracker').track('intridea') do |status|
12
+ # # do something here
13
+ # end
14
+ #
15
+ # And then you call this from the shell:
16
+ #
17
+ # ruby tracker.rb start
18
+ #
19
+ # A daemon process will spawn that will automatically
20
+ # run the code in the passed block whenever a new tweet
21
+ # matching your search term ('intridea' in this case)
22
+ # is posted.
23
+ #
24
+ class TweetStream::Daemon < TweetStream::Client
25
+ # Initialize a Daemon with the credentials of the
26
+ # Twitter account you wish to use. The daemon has
27
+ # an optional process name for use when querying
28
+ # running processes.
29
+ def initialize(user, pass, app_name=nil)
30
+ @app_name = app_name
31
+ super(user, pass)
32
+ end
33
+
34
+ #:nodoc:
35
+ def start(path, query_parameters = {}, &block)
36
+ Daemons.run_proc(@app_name || 'tweetstream', :multiple => true) do
37
+ super(path, query_parameters, &block)
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,16 @@
1
+ #:nodoc:
2
+ class TweetStream::Hash < ::Hash
3
+ def initialize(other_hash)
4
+ other_hash.keys.each do |key|
5
+ self[key.to_sym] = other_hash[key]
6
+ end
7
+ end
8
+
9
+ def method_missing(method_name, *args)
10
+ if key?(method_name.to_sym)
11
+ self[method_name.to_sym]
12
+ else
13
+ super
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,8 @@
1
+ # A simple Hash wrapper that gives you method-based
2
+ # access to the properties of a Twitter status.
3
+ class TweetStream::Status < TweetStream::Hash
4
+ def initialize(hash)
5
+ super
6
+ self[:user] = TweetStream::User.new(self[:user])
7
+ end
8
+ end
@@ -0,0 +1,5 @@
1
+ # A simple Hash wrapper that gives you method-based
2
+ # access to user properties returned by the streamer.
3
+ class TweetStream::User < TweetStream::Hash
4
+
5
+ end
@@ -0,0 +1 @@
1
+ {"favorited":false,"text":"listening to Where U Headed by Universal Playaz. http://iLike.com/s/9zpOZ #musicmonday something for the ladies","in_reply_to_user_id":null,"in_reply_to_screen_name":null,"source":"<a href=\"http://www.iLike.com\" rel=\"nofollow\">iLike</a>","truncated":false,"created_at":"Tue Sep 22 01:29:13 +0000 2009","user":{"statuses_count":378,"favourites_count":1,"profile_text_color":"666666","location":"Atlanta, Ga","profile_background_image_url":"http://a3.twimg.com/profile_background_images/36516125/Universal_Playaz.jpg","profile_link_color":"2FC2EF","description":"Paper Chaser","following":null,"verified":false,"notifications":null,"profile_sidebar_fill_color":"252429","profile_image_url":"http://a1.twimg.com/profile_images/413331530/DIESELSTATScopy_normal.jpg","url":"http://www.myspace.com/DieselDtheg","profile_sidebar_border_color":"181A1E","screen_name":"DieselD2143","profile_background_tile":true,"followers_count":75,"protected":false,"time_zone":"Eastern Time (US & Canada)","created_at":"Thu Jun 18 15:56:32 +0000 2009","name":"Diesel D","friends_count":119,"profile_background_color":"1A1B1F","id":48392351,"utc_offset":-18000},"in_reply_to_status_id":null,"id":4161231023} {"favorited":false,"text":"David Bowie and Nine Inch Nails perform \"Hurt\" http://bit.ly/AOaWG #musicmonday #nineinchnails #nin","in_reply_to_user_id":null,"in_reply_to_screen_name":null,"source":"web","truncated":false,"created_at":"Tue Sep 22 01:29:16 +0000 2009","user":{"statuses_count":668,"favourites_count":25,"profile_text_color":"445d85","location":"S\u00e3o Paulo, Brazil","profile_background_image_url":"http://a3.twimg.com/profile_background_images/38174991/GeorgeRomero-oil-400.jpg","profile_link_color":"555757","description":"You think I ain't worth a dollar, but I feel like a millionaire","following":null,"verified":false,"notifications":null,"profile_sidebar_fill_color":"a3a7ad","profile_image_url":"http://a1.twimg.com/profile_images/96034368/n1076431955_30001395_7912_normal.jpg","url":null,"profile_sidebar_border_color":"c7d1ed","screen_name":"RenatonMiranda","profile_background_tile":true,"followers_count":111,"protected":false,"time_zone":"Santiago","created_at":"Sat Mar 14 15:03:59 +0000 2009","name":"Renato Miranda","friends_count":143,"profile_background_color":"287356","id":24379310,"utc_offset":-14400},"in_reply_to_status_id":null,"id":4161232008} {"favorited":false,"text":"#musicmonday ,time to download some songs today!! :)","in_reply_to_user_id":null,"in_reply_to_screen_name":null,"source":"web","truncated":false,"created_at":"Tue Sep 22 01:29:19 +0000 2009","user":{"statuses_count":188,"favourites_count":0,"profile_text_color":"3D1957","location":"under the water","profile_background_image_url":"http://s.twimg.com/a/1253562286/images/themes/theme10/bg.gif","profile_link_color":"FF0000","description":"ask me ","following":null,"verified":false,"notifications":null,"profile_sidebar_fill_color":"7AC3EE","profile_image_url":"http://a1.twimg.com/profile_images/421281292/twit_pic_normal.jpg","url":"http://www.exploretalent.com/contest_video.php?talentnum=2053105&cm_id=3398","profile_sidebar_border_color":"65B0DA","screen_name":"julieanne11343","profile_background_tile":true,"followers_count":9,"protected":false,"time_zone":"Pacific Time (US & Canada)","created_at":"Mon Jul 20 21:08:22 +0000 2009","name":"Julieanne","friends_count":17,"profile_background_color":"642D8B","id":58591151,"utc_offset":-28800},"in_reply_to_status_id":null,"id":4161233120} {"text":"#Musicmonday \"Dont be tardy f0r the party\"","truncated":false,"source":"<a href=\"http://twitterhelp.blogspot.com/2008/05/twitter-via-mobile-web-mtwittercom.html\" rel=\"nofollow\">mobile web</a>","in_reply_to_status_id":null,"favorited":false,"created_at":"Tue Sep 22 01:29:19 +0000 2009","user":{"verified":false,"notifications":null,"profile_sidebar_fill_color":"e0ff92","location":"Dope Girl Island","profile_sidebar_border_color":"87bc44","description":"","following":null,"profile_background_tile":false,"followers_count":29,"profile_image_url":"http://a3.twimg.com/profile_images/217487577/badbad_normal.jpg","time_zone":"Eastern Time (US & Canada)","url":null,"friends_count":65,"profile_background_color":"9ae4e8","screen_name":"SwagGirlOnDeck","protected":false,"statuses_count":847,"favourites_count":0,"created_at":"Fri May 01 16:59:15 +0000 2009","profile_text_color":"000000","name":"Mariah Reta","id":36987168,"profile_background_image_url":"http://s.twimg.com/a/1253301564/images/themes/theme1/bg.png","utc_offset":-18000,"profile_link_color":"0000ff"},"in_reply_to_user_id":null,"id":4161233317,"in_reply_to_screen_name":null}
data/spec/spec.opts ADDED
@@ -0,0 +1,2 @@
1
+ --colour
2
+ --format progress
@@ -0,0 +1,24 @@
1
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
2
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
3
+
4
+ require 'rubygems'
5
+ require 'tweetstream'
6
+ require 'spec'
7
+ require 'spec/autorun'
8
+ require 'yajl'
9
+
10
+ def sample_tweets
11
+ if @tweets
12
+ @tweets
13
+ else
14
+ @tweets = []
15
+ Yajl::Parser.parse(File.open(File.dirname(__FILE__) + '/data/statuses.json', 'r')) do |hash|
16
+ @tweets << hash
17
+ end
18
+ @tweets
19
+ end
20
+ end
21
+
22
+ Spec::Runner.configure do |config|
23
+
24
+ end
@@ -0,0 +1,122 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+
3
+ describe TweetStream::Client do
4
+ it 'should set the username and password from the initializers' do
5
+ @client = TweetStream::Client.new('abc','def')
6
+ @client.username.should == 'abc'
7
+ @client.password.should == 'def'
8
+ end
9
+
10
+ describe '#build_uri' do
11
+ before do
12
+ @client = TweetStream::Client.new('abc','def')
13
+ end
14
+
15
+ it 'should return a URI' do
16
+ @client.send(:build_uri, '').is_a?(URI).should be_true
17
+ end
18
+
19
+ it 'should contain the auth information from the client' do
20
+ @client.send(:build_uri, '').user.should == 'abc'
21
+ @client.send(:build_uri, '').password.should == 'def'
22
+ end
23
+
24
+ it 'should have the specified path with the version prefix and a json extension' do
25
+ @client.send(:build_uri, 'awesome').path.should == '/1/awesome.json'
26
+ end
27
+
28
+ it 'should add on a query string if such parameters are specified' do
29
+ @client.send(:build_uri, 'awesome', :q => 'abc').query.should == 'q=abc'
30
+ end
31
+ end
32
+
33
+ describe '#build_query_parameters' do
34
+ before do
35
+ @client = TweetStream::Client.new('abc','def')
36
+ end
37
+
38
+ it 'should return a blank string if passed a nil value' do
39
+ @client.send(:build_query_parameters, nil).should == ''
40
+ end
41
+
42
+ it 'should return a blank string if passed an empty hash' do
43
+ @client.send(:build_query_parameters, {}).should == ''
44
+ end
45
+
46
+ it 'should add a query parameter for a key' do
47
+ @client.send(:build_query_parameters, {:query => 'abc'}).should == '?query=abc'
48
+ end
49
+
50
+ it 'should escape characters in the value' do
51
+ @client.send(:build_query_parameters, {:query => 'awesome guy'}).should == '?query=awesome+guy'
52
+ end
53
+
54
+ it 'should join multiple pairs together' do
55
+ ['?a=b&c=d','?c=d&a=b'].include?(@client.send(:build_query_parameters, {:a => 'b', :c => 'd'})).should be_true
56
+ end
57
+ end
58
+
59
+ describe '#start' do
60
+ before do
61
+ @client = TweetStream::Client.new('abc','def')
62
+ end
63
+
64
+ it 'should make a call to Yajl::HttpStream' do
65
+ Yajl::HttpStream.should_receive(:get).once.with(URI.parse('http://abc:def@stream.twitter.com/1/cool.json'), :symbolize_keys => true).and_return({})
66
+ @client.start('cool')
67
+ end
68
+
69
+ it 'should yield a TwitterStream::Status for each update' do
70
+ Yajl::HttpStream.should_receive(:get).once.with(URI.parse('http://abc:def@stream.twitter.com/1/statuses/filter.json?track=musicmonday'), :symbolize_keys => true).and_yield(sample_tweets[0])
71
+ @client.track('musicmonday') do |status|
72
+ status.is_a?(TweetStream::Status).should be_true
73
+ @yielded = true
74
+ end
75
+ @yielded.should be_true
76
+ end
77
+ end
78
+
79
+ describe ' API methods' do
80
+ before do
81
+ @client = TweetStream::Client.new('abc','def')
82
+ end
83
+
84
+ %w(firehose retweet sample).each do |method|
85
+ it "##{method} should make a call to start with \"statuses/#{method}\"" do
86
+ @client.should_receive(:start).once.with('statuses/' + method, {})
87
+ @client.send(method)
88
+ end
89
+ end
90
+
91
+ it '#track should make a call to start with "statuses/filter" and a track query parameter' do
92
+ @client.should_receive(:start).once.with('statuses/filter', :track => 'test')
93
+ @client.track('test')
94
+ end
95
+
96
+ it '#track should comma-join multiple arguments' do
97
+ @client.should_receive(:start).once.with('statuses/filter', :track => 'foo,bar,baz')
98
+ @client.track('foo', 'bar', 'baz')
99
+ end
100
+
101
+ it '#follow should make a call to start with "statuses/filter" and a follow query parameter' do
102
+ @client.should_receive(:start).once.with('statuses/filter', :follow => '123')
103
+ @client.follow(123)
104
+ end
105
+
106
+ it '#follow should comma-join multiple arguments' do
107
+ @client.should_receive(:start).once.with('statuses/filter', :follow => '123,456')
108
+ @client.follow(123, 456)
109
+ end
110
+ end
111
+
112
+ describe '#track' do
113
+ before do
114
+ @client = TweetStream::Client.new('abc','def')
115
+ end
116
+
117
+ it 'should call #start with "statuses/filter" and the provided queries' do
118
+ @client.should_receive(:start).once.with('statuses/filter', :track => 'rock')
119
+ @client.track('rock')
120
+ end
121
+ end
122
+ end
@@ -0,0 +1,19 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+
3
+ describe TweetStream::Hash do
4
+ it 'should be initialized by passing in an existing hash' do
5
+ TweetStream::Hash.new(:abc => 123)[:abc].should == 123
6
+ end
7
+
8
+ it 'should symbolize incoming keys' do
9
+ TweetStream::Hash.new('abc' => 123)[:abc].should == 123
10
+ end
11
+
12
+ it 'should allow access via method calls' do
13
+ TweetStream::Hash.new(:abc => 123).abc.should == 123
14
+ end
15
+
16
+ it 'should still throw NoMethod for non-existent keys' do
17
+ lambda{TweetStream::Hash.new({}).akabi}.should raise_error(NoMethodError)
18
+ end
19
+ end
@@ -0,0 +1,9 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+
3
+ describe TweetStream::Status do
4
+ it 'should modify the :user key into a TweetStream::User object' do
5
+ @status = TweetStream::Status.new(:user => {:screen_name => 'bob'})
6
+ @status.user.is_a?(TweetStream::User).should be_true
7
+ @status.user.screen_name.should == 'bob'
8
+ end
9
+ end
@@ -0,0 +1,5 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe TweetStream do
4
+
5
+ end
metadata ADDED
@@ -0,0 +1,109 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: tweetstream
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Michael Bleigh
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2009-09-22 00:00:00 -04:00
13
+ default_executable:
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: rspec
17
+ type: :development
18
+ version_requirement:
19
+ version_requirements: !ruby/object:Gem::Requirement
20
+ requirements:
21
+ - - ">="
22
+ - !ruby/object:Gem::Version
23
+ version: "0"
24
+ version:
25
+ - !ruby/object:Gem::Dependency
26
+ name: yajl-ruby
27
+ type: :runtime
28
+ version_requirement:
29
+ version_requirements: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: 0.6.3
34
+ version:
35
+ - !ruby/object:Gem::Dependency
36
+ name: daemons
37
+ type: :runtime
38
+ version_requirement:
39
+ version_requirements: !ruby/object:Gem::Requirement
40
+ requirements:
41
+ - - ">="
42
+ - !ruby/object:Gem::Version
43
+ version: "0"
44
+ version:
45
+ description: TweetStream allows you to easily consume the Twitter Streaming API utilizing the YAJL Ruby gem.
46
+ email: michael@intridea.com
47
+ executables: []
48
+
49
+ extensions: []
50
+
51
+ extra_rdoc_files:
52
+ - LICENSE
53
+ - README.rdoc
54
+ files:
55
+ - .document
56
+ - .gitignore
57
+ - LICENSE
58
+ - README.rdoc
59
+ - Rakefile
60
+ - VERSION
61
+ - lib/tracker.log
62
+ - lib/tracker.rb
63
+ - lib/tweetstream.rb
64
+ - lib/tweetstream/client.rb
65
+ - lib/tweetstream/daemon.rb
66
+ - lib/tweetstream/hash.rb
67
+ - lib/tweetstream/status.rb
68
+ - lib/tweetstream/user.rb
69
+ - spec/data/statuses.json
70
+ - spec/spec.opts
71
+ - spec/spec_helper.rb
72
+ - spec/tweetstream/client_spec.rb
73
+ - spec/tweetstream/hash_spec.rb
74
+ - spec/tweetstream/status_spec.rb
75
+ - spec/tweetstream_spec.rb
76
+ has_rdoc: true
77
+ homepage: http://github.com/intridea/tweetstream
78
+ licenses: []
79
+
80
+ post_install_message:
81
+ rdoc_options:
82
+ - --charset=UTF-8
83
+ require_paths:
84
+ - lib
85
+ required_ruby_version: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: "0"
90
+ version:
91
+ required_rubygems_version: !ruby/object:Gem::Requirement
92
+ requirements:
93
+ - - ">="
94
+ - !ruby/object:Gem::Version
95
+ version: "0"
96
+ version:
97
+ requirements: []
98
+
99
+ rubyforge_project:
100
+ rubygems_version: 1.3.5
101
+ signing_key:
102
+ specification_version: 3
103
+ summary: TweetStream is a simple wrapper for consuming the Twitter Streaming API.
104
+ test_files:
105
+ - spec/spec_helper.rb
106
+ - spec/tweetstream/client_spec.rb
107
+ - spec/tweetstream/hash_spec.rb
108
+ - spec/tweetstream/status_spec.rb
109
+ - spec/tweetstream_spec.rb