kappa 0.1.3.pre → 0.1.4.pre

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/README.md CHANGED
@@ -1,9 +1,14 @@
1
- # <img src="http://static-cdn.jtvnw.net/jtv_user_pictures/chansub-global-emoticon-ddc6e3a8732cb50f-25x28.png" /> Kappa
1
+ # <img src="https://raw.github.com/schmich/kappa/master/assets/kappa.png" /> Kappa
2
2
 
3
- Kappa is a Ruby library for interfacing with the [Twitch.tv Kraken API](https://github.com/justintv/Twitch-API).
3
+ Kappa is a Ruby library for interfacing with the [Twitch.tv API](https://github.com/justintv/Twitch-API).
4
+
5
+ [![Gem Version](https://badge.fury.io/rb/kappa.png)](https://badge.fury.io/rb/kappa.png)
6
+ [![Build Status](https://secure.travis-ci.org/schmich/tome.png)](http://travis-ci.org/schmich/tome)
7
+ [![Dependency Status](https://gemnasium.com/schmich/kappa.png)](https://gemnasium.com/schmich/kappa)
8
+ [![Coverage Status](https://coveralls.io/repos/schmich/kappa/badge.png?branch=master)](https://coveralls.io/r/schmich/kappa?branch=master)
9
+ [![Code Climate](https://codeclimate.com/github/schmich/kappa.png)](https://codeclimate.com/github/schmich/kappa)
4
10
 
5
11
  ## Getting Started
6
- ============
7
12
 
8
13
  `gem install kappa --pre`
9
14
 
@@ -12,15 +17,65 @@ require 'kappa'
12
17
 
13
18
  include Kappa::V2
14
19
 
15
- grubby = Channel.new('followgrubby')
20
+ grubby = Channel.get('followgrubby')
16
21
  puts grubby.streaming?
17
22
  ```
18
23
 
19
- ## API
20
- ============
24
+ ## Examples
25
+
26
+ ### Channels
27
+
28
+ Channels serve as the home location for a [user's](#users) content. Channels have a [stream](#streams), can run commercials, store [videos](#videos), display information and status, and have a customized page including banners and backgrounds.
29
+
30
+ ```ruby
31
+ c = Channel.get('destiny')
32
+
33
+ c.nil? # Does the requested channel not exist? (ex: false)
34
+ c.name # Unique Twitch name (ex: "destiny")
35
+ c.display_name # Display name, e.g. name used for page title (ex: "Destiny")
36
+ c.stream # The currently live stream for this channel (ex: #<Kappa::V2::Stream> object)
37
+ c.url # The URL for the channel's main page (ex: "http://www.twitch.tv/destiny")
38
+ c.status # Current status (ex: "Destiny - Diamond I ADC - Number 1 Draven player in the entire Omaha (NE) metro area -watch from http://www.destiny.gg")
39
+ c.streaming? # Is the channel currently streaming? (ex: true)
40
+ c.game_name # Name of the primary game for this channel (ex: "League of Legends")
41
+ c.mature? # Does the channel have mature content? (ex: true)
42
+ c.id # Unique Twitch ID (ex: 18074328)
43
+ c.created_at # When the channel was created (ex: #<DateTime: 2010-11-22T04:14:56+00:00 ((2455523j,15296s,0n),+0s,2299161j)>)
44
+ c.updated_at # When the channel was last updated, e.g. last stream time (ex: #<DateTime: 2013-05-11T19:57:29+00:00 ((2456424j,71849s,0n),+0s,2299161j)>)
45
+ c.background_url # URL for background image (ex: "http://static-cdn.jtvnw.net/jtv_user_pictures/destiny-channel_background_image-ab706db77853e079.jpeg")
46
+ c.banner_url # URL for banner image (ex: "http://static-cdn.jtvnw.net/jtv_user_pictures/destiny-channel_header_image-d2b9b2452f67ec00-640x125.jpeg")
47
+ c.logo_url # URL for logo image (ex: "http://static-cdn.jtvnw.net/jtv_user_pictures/destiny-profile_image-168e66661c484c5e-300x300.jpeg")
48
+ c.video_banner_url # URL for the image shown when the stream is offline (ex: "http://static-cdn.jtvnw.net/jtv_user_pictures/destiny-channel_offline_image-7a21fd1bd88c4ac3-640x360.jpeg")
49
+
50
+ c.videos
51
+ c.teams
52
+ c.subscribers
53
+ c.editors
54
+ c.followers
55
+ c.has_subscriber?
56
+ ```
57
+
58
+ ### Streams
59
+
60
+ Streams are video broadcasts that are currently live. They have a [broadcaster](#users) and are part of a [channel](#channels).
61
+
62
+ ### Users
63
+
64
+ These are members of the Twitch community who have a Twitch account. If broadcasting, they can own a [stream](#streams) that they can broadcast on their [channel](#channels). If mainly viewing, they might follow or subscribe to channels.
65
+
66
+ ### Videos
67
+
68
+ Videos are broadcasts or highlights owned by a [channel](#channels). Broadcasts are unedited videos that are saved after a streaming session. Highlights are videos edited from broadcasts by the channel's owner.
69
+
70
+ ### Teams
71
+
72
+ Teams are an organization of [channels](#channels).
73
+
74
+ ### Games
75
+
76
+ Games are categories (e.g. League of Legends, Diablo 3) used by [streams](#streams) and [channels](#channels). Games can be searched for by query.
21
77
 
22
78
  ## Contributing
23
- ============
24
79
 
25
80
  ## License
26
81
 
data/lib/kappa.rb CHANGED
@@ -8,7 +8,6 @@ require 'kappa/team'
8
8
  require 'kappa/user'
9
9
  require 'kappa/images'
10
10
  require 'kappa/twitch'
11
- require 'kappa/base'
12
11
  require 'kappa/version'
13
12
 
14
13
  # TODO
data/lib/kappa/channel.rb CHANGED
@@ -1,49 +1,73 @@
1
+ require 'cgi'
2
+
1
3
  module Kappa
4
+ # @private
2
5
  class ChannelBase
3
6
  include IdEquality
4
7
 
5
- def initialize(arg, connection)
6
- @connection = connection
7
-
8
- case arg
9
- when Hash
10
- parse(arg)
11
- when String
12
- json = @connection.get("channels/#{arg}")
13
- parse(json)
14
- else
15
- raise ArgumentError
8
+ def self.get(channel_name)
9
+ encoded_name = CGI.escape(channel_name)
10
+ json = connection.get("channels/#{encoded_name}")
11
+ if !json || json['status'] == 404
12
+ nil
13
+ else
14
+ new(json)
16
15
  end
17
16
  end
18
17
  end
19
18
  end
20
19
 
21
20
  module Kappa::V2
22
- # TODO:
23
- # c.subscriptions
24
- # c.start_commercial
25
- # c.reset_stream_key
26
- # c.foo = 'bar' ; c.save!
27
- # Current user's channel
28
21
  class Channel < Kappa::ChannelBase
29
- def initialize(arg, connection = Connection.instance)
30
- super(arg, connection)
22
+ # TODO:
23
+ # c.subscriptions
24
+ # c.start_commercial
25
+ # c.reset_stream_key
26
+ # c.foo = 'bar' ; c.save!
27
+ # Current user's channel
28
+ include Connection
29
+
30
+ def initialize(hash)
31
+ @id = hash['_id']
32
+ @background_url = hash['background']
33
+ @banner_url = hash['banner']
34
+ @created_at = DateTime.parse(hash['created_at'])
35
+ @display_name = hash['display_name']
36
+ @game_name = hash['game']
37
+ @logo_url = hash['logo']
38
+ @mature = hash['mature'] || false
39
+ @name = hash['name']
40
+ @status = hash['status']
41
+ @updated_at = DateTime.parse(hash['updated_at'])
42
+ @url = hash['url']
43
+ @video_banner_url = hash['video_banner']
44
+
45
+ @teams = []
46
+ teams = hash['teams']
47
+ teams.each do |team_json|
48
+ @teams << Team.new(team_json)
49
+ end
31
50
  end
32
51
 
52
+ # This flag is specified by the owner of the channel.
53
+ # @return [Boolean] `true` if the channel has mature content, `false` otherwise.
33
54
  def mature?
34
55
  @mature
35
56
  end
36
57
 
37
- # TODO: Move these into derived classes?
58
+ # Get the live stream associated with this channel.
59
+ # @return [Stream] Live stream object for this channel, or `nil` if the channel is not currently streaming.
60
+ # @see #streaming?
38
61
  def stream
39
- # TODO: Use _links instead of hard-coding.
40
- json = @connection.get("streams/#{@name}")
41
- stream_json = json['stream']
42
- Stream.new(stream_json, @connection)
62
+ Stream.get(@name)
43
63
  end
44
64
 
65
+ # This makes a separate request to get the channel's stream. If you want to actually use
66
+ # the stream object, you should call `#stream` instead.
67
+ # @return [Boolean] `true` if the channel currently has a live stream, `false` otherwise.
68
+ # @see #stream
45
69
  def streaming?
46
- stream.live?
70
+ !stream.nil?
47
71
  end
48
72
 
49
73
  #
@@ -67,29 +91,25 @@ module Kappa::V2
67
91
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/channels.md#get-channelschannelfollows
68
92
  # TODO: Warning: this set can be very large, this can run for very long time, recommend using :limit/:offset.
69
93
  #
70
- def followers(params = {})
71
- limit = params[:limit] || 0
72
-
73
- followers = []
74
- ids = Set.new
75
-
76
- @connection.paginated("channels/#{@name}/follows", params) do |json|
77
- current_followers = json['follows']
78
- current_followers.each do |follow_json|
79
- user_json = follow_json['user']
80
- user = User.new(user_json, @connection)
81
- if ids.add?(user.id)
82
- followers << user
83
- if followers.count == limit
84
- return followers
85
- end
86
- end
87
- end
88
-
89
- !current_followers.empty?
94
+ def followers(args = {})
95
+ params = {}
96
+
97
+ limit = args[:limit]
98
+ if limit && (limit < 100)
99
+ params[:limit] = limit
100
+ else
101
+ params[:limit] = 100
102
+ limit = 0
90
103
  end
91
104
 
92
- followers
105
+ return connection.accumulate(
106
+ :path => "channels/#{@name}/follows",
107
+ :params => params,
108
+ :json => 'follows',
109
+ :sub_json => 'user',
110
+ :class => User,
111
+ :limit => limit
112
+ )
93
113
  end
94
114
 
95
115
  # TODO: Requires authentication.
@@ -105,36 +125,42 @@ module Kappa::V2
105
125
  # Support User object or username (string)
106
126
  end
107
127
 
128
+ # @return [Fixnum] Unique Twitch ID.
108
129
  attr_reader :id
130
+
131
+ # @return [String] URL for background image.
109
132
  attr_reader :background_url
133
+
134
+ # @return [String] URL for banner image.
110
135
  attr_reader :banner_url
136
+
137
+ # @return [DateTime] When the channel was created.
111
138
  attr_reader :created_at
112
- attr_reader :stream_delay_sec
139
+
140
+ # @return [String] Display name, e.g. name used for page title.
113
141
  attr_reader :display_name
142
+
143
+ # @return [String] Name of the primary game for this channel.
114
144
  attr_reader :game_name
145
+
146
+ # @return [String] URL for the logo image.
115
147
  attr_reader :logo_url
148
+
149
+ # @return [String] Unique Twitch name.
116
150
  attr_reader :name
151
+
152
+ # @return [String] Current status.
117
153
  attr_reader :status
154
+
155
+ # @return [DateTime] When the channel was last updated, e.g. last stream time.
118
156
  attr_reader :updated_at
157
+
158
+ # @return [String] The URL for the channel's main page.
119
159
  attr_reader :url
160
+
161
+ # @return [String] URL for the image shown when the stream is offline.
120
162
  attr_reader :video_banner_url
121
163
 
122
- private
123
- def parse(hash)
124
- @id = hash['_id']
125
- @background_url = hash['background']
126
- @banner_url = hash['banner']
127
- @created_at = DateTime.parse(hash['created_at'])
128
- @stream_delay_sec = hash['delay']
129
- @display_name = hash['display_name']
130
- @game_name = hash['game']
131
- @logo_url = hash['logo']
132
- @mature = hash['mature'] || false
133
- @name = hash['name']
134
- @status = hash['status']
135
- @updated_at = DateTime.parse(hash['updated_at'])
136
- @url = hash['url']
137
- @video_banner_url = hash['video_banner']
138
- end
164
+ attr_reader :teams
139
165
  end
140
166
  end
@@ -2,8 +2,11 @@ require 'httparty'
2
2
  require 'addressable/uri'
3
3
  require 'securerandom'
4
4
  require 'json'
5
+ require 'singleton'
6
+ require 'set'
5
7
 
6
8
  module Kappa
9
+ # @private
7
10
  class ConnectionBase
8
11
  include HTTParty
9
12
 
@@ -17,12 +20,6 @@ module Kappa
17
20
  @last_request_time = Time.now - RATE_LIMIT_SEC
18
21
  end
19
22
 
20
- def self.instance
21
- @connection ||= self.class_eval do
22
- self.new
23
- end
24
- end
25
-
26
23
  def get(path, query = nil)
27
24
  request_url = @base_url + path
28
25
 
@@ -42,6 +39,36 @@ module Kappa
42
39
  return JSON.parse(json)
43
40
  end
44
41
 
42
+ def accumulate(args)
43
+ path = args[:path]
44
+ params = args[:params]
45
+ json = args[:json]
46
+ sub_json = args[:sub_json]
47
+ klass = args[:class]
48
+ limit = args[:limit]
49
+
50
+ objects = []
51
+ ids = Set.new
52
+
53
+ paginated(path, params) do |response_json|
54
+ current_objects = response_json[json]
55
+ current_objects.each do |object_json|
56
+ object_json = object_json[sub_json] if sub_json
57
+ object = klass.new(object_json)
58
+ if ids.add?(object.id)
59
+ objects << object
60
+ if objects.count == limit
61
+ return objects
62
+ end
63
+ end
64
+ end
65
+
66
+ !current_objects.empty?
67
+ end
68
+
69
+ return objects
70
+ end
71
+
45
72
  def paginated(path, params = {})
46
73
  limit = [params[:limit] || 100, 100].min
47
74
  offset = params[:offset] || 0
@@ -100,19 +127,29 @@ module Kappa
100
127
  end
101
128
 
102
129
  module Kappa::V2
103
- class Connection < Kappa::ConnectionBase
104
- private
105
- def custom_headers
106
- { 'Accept' => 'application/vnd.twitchtv.v2+json' }
130
+ # @private
131
+ module Connection
132
+ class Impl < Kappa::ConnectionBase
133
+ include Singleton
134
+
135
+ private
136
+ def custom_headers
137
+ { 'Accept' => 'application/vnd.twitchtv.v2+json' }
138
+ end
107
139
  end
108
- end
109
- end
110
140
 
111
- module Kappa::V3
112
- class Connection < Kappa::ConnectionBase
113
- private
114
- def custom_headers
115
- { 'Accept' => 'application/vnd.twitchtv.v3+json' }
141
+ def self.included(base)
142
+ base.extend(ClassMethods)
143
+ end
144
+
145
+ def connection
146
+ Impl.instance
147
+ end
148
+
149
+ module ClassMethods
150
+ def connection
151
+ Impl.instance
152
+ end
116
153
  end
117
154
  end
118
155
  end
data/lib/kappa/game.rb CHANGED
@@ -1,43 +1,18 @@
1
1
  module Kappa
2
+ # @private
2
3
  class GameBase
3
4
  include IdEquality
4
-
5
- def initialize(arg)
6
- case arg
7
- when Hash
8
- parse(arg)
9
- else
10
- raise ArgumentError
11
- end
12
- end
13
5
  end
14
6
 
7
+ # @private
15
8
  class GameSuggestionBase
16
9
  include IdEquality
17
-
18
- def initialize(arg)
19
- case arg
20
- when Hash
21
- parse(arg)
22
- else
23
- raise ArgumentError
24
- end
25
- end
26
10
  end
27
11
  end
28
12
 
29
13
  module Kappa::V2
30
14
  class Game < Kappa::GameBase
31
- attr_reader :id
32
- attr_reader :name
33
- attr_reader :giantbomb_id
34
- attr_reader :box_images
35
- attr_reader :logo_images
36
- attr_reader :channel_count
37
- attr_reader :viewer_count
38
-
39
- private
40
- def parse(hash)
15
+ def initialize(hash)
41
16
  @channel_count = hash['channels']
42
17
  @viewer_count = hash['viewers']
43
18
 
@@ -48,18 +23,18 @@ module Kappa::V2
48
23
  @box_images = Images.new(game['box'])
49
24
  @logo_images = Images.new(game['logo'])
50
25
  end
51
- end
52
26
 
53
- class GameSuggestion < Kappa::GameSuggestionBase
54
27
  attr_reader :id
55
28
  attr_reader :name
56
29
  attr_reader :giantbomb_id
57
- attr_reader :popularity
58
30
  attr_reader :box_images
59
31
  attr_reader :logo_images
32
+ attr_reader :channel_count
33
+ attr_reader :viewer_count
34
+ end
60
35
 
61
- private
62
- def parse(hash)
36
+ class GameSuggestion < Kappa::GameSuggestionBase
37
+ def initialize(hash)
63
38
  @id = hash['_id']
64
39
  @name = hash['name']
65
40
  @giantbomb_id = hash['giantbomb_id']
@@ -67,47 +42,54 @@ module Kappa::V2
67
42
  @box_images = Images.new(hash['box'])
68
43
  @logo_images = Images.new(hash['logo'])
69
44
  end
45
+
46
+ attr_reader :id
47
+ attr_reader :name
48
+ attr_reader :giantbomb_id
49
+ attr_reader :popularity
50
+ attr_reader :box_images
51
+ attr_reader :logo_images
70
52
  end
71
53
 
72
54
  class Games
55
+ include Connection
56
+
73
57
  #
74
58
  # GET /games/top
75
59
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/games.md#get-gamestop
76
60
  #
77
- def top(params = {})
78
- limit = params[:limit] || 0
79
-
80
- games = []
81
- ids = Set.new
61
+ def self.top(args = {})
62
+ params = {}
82
63
 
83
- @conn.paginated('games/top', params) do |json|
84
- current_games = json['top']
85
- current_games.each do |game_json|
86
- game = Game.new(game_json)
87
- if ids.add?(game.id)
88
- games << game
89
- if games.count == limit
90
- return games
91
- end
92
- end
93
- end
64
+ limit = args[:limit]
65
+ if limit && (limit < 100)
66
+ params[:limit] = limit
67
+ else
68
+ params[:limit] = 100
69
+ limit = 0
94
70
  end
95
71
 
96
- games
72
+ return connection.accumulate(
73
+ :path => 'games/top',
74
+ :params => params,
75
+ :json => 'top',
76
+ :class => Game,
77
+ :limit => limit
78
+ )
97
79
  end
98
80
 
99
81
  #
100
82
  # GET /search/games
101
83
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/search.md#get-searchgames
102
84
  #
103
- def search(params = {})
85
+ def self.search(params = {})
104
86
  live = params[:live] || false
105
87
  name = params[:name]
106
88
 
107
89
  games = []
108
90
  ids = Set.new
109
91
 
110
- json = @conn.get('search/games', :query => name, :type => 'suggest', :live => live)
92
+ json = connection.get('search/games', :query => name, :type => 'suggest', :live => live)
111
93
  all_games = json['games']
112
94
  all_games.each do |game_json|
113
95
  game = GameSuggestion.new(game_json)
@@ -1,4 +1,5 @@
1
1
  module Kappa
2
+ # @private
2
3
  module IdEquality
3
4
  def hash
4
5
  @id.hash
data/lib/kappa/images.rb CHANGED
@@ -1,33 +1,19 @@
1
- module Kappa
2
- class ImagesBase
3
- def initialize(arg)
4
- case arg
5
- when Hash
6
- parse(arg)
7
- else
8
- raise ArgumentError
9
- end
1
+ module Kappa::V2
2
+ class Images
3
+ def initialize(hash)
4
+ @large_url = hash['large']
5
+ @medium_url = hash['medium']
6
+ @small_url = hash['small']
7
+ @template_url = hash['template']
10
8
  end
11
- end
12
- end
13
9
 
14
- module Kappa::V2
15
- class Images < Kappa::ImagesBase
16
10
  def url(width, height)
17
- @template_url.gsub('{width}', width.to_s, '{height}', height.to_s)
11
+ @template_url.gsub('{width}', width.to_s).gsub('{height}', height.to_s)
18
12
  end
19
13
 
20
14
  attr_reader :large_url
21
15
  attr_reader :medium_url
22
16
  attr_reader :small_url
23
17
  attr_reader :template_url
24
-
25
- private
26
- def parse(hash)
27
- @large_url = hash['large']
28
- @medium_url = hash['medium']
29
- @small_url = hash['small']
30
- @template_url = hash['template']
31
- end
32
18
  end
33
19
  end
data/lib/kappa/stream.rb CHANGED
@@ -1,54 +1,46 @@
1
- require 'set'
2
-
3
1
  module Kappa
2
+ # @private
4
3
  class StreamBase
5
4
  include IdEquality
6
5
 
7
- def initialize(hash, connection = self.class.default_connection)
8
- @connection = connection
9
- parse(hash)
10
- end
11
-
12
- def self.get(stream_name, connection = default_connection)
6
+ def self.get(stream_name)
13
7
  json = connection.get("streams/#{stream_name}")
14
8
  stream = json['stream']
15
9
  if json['status'] == 404 || !stream
16
10
  nil
17
11
  else
18
- new(stream, connection)
12
+ new(stream)
19
13
  end
20
14
  end
21
-
22
- private
23
- def self.default_connection
24
- self.class.module_class(:Connection).instance
25
- end
26
15
  end
27
16
  end
28
17
 
29
18
  module Kappa::V2
30
19
  class Stream < Kappa::StreamBase
31
- attr_reader :id
32
- attr_reader :broadcaster
33
- attr_reader :game_name
34
- attr_reader :name
35
- attr_reader :viewer_count
36
- attr_reader :preview_url
37
- attr_reader :channel
20
+ include Connection
38
21
 
39
- private
40
- def parse(hash)
22
+ def initialize(hash)
41
23
  @id = hash['_id']
42
24
  @broadcaster = hash['broadcaster']
43
25
  @game_name = hash['game']
44
26
  @name = hash['name']
45
27
  @viewer_count = hash['viewers']
46
28
  @preview_url = hash['preview']
47
- @channel = Channel.new(hash['channel'], @connection)
29
+ @channel = Channel.new(hash['channel'])
48
30
  end
31
+
32
+ attr_reader :id
33
+ attr_reader :broadcaster
34
+ attr_reader :game_name
35
+ attr_reader :name
36
+ attr_reader :viewer_count
37
+ attr_reader :preview_url
38
+ attr_reader :channel
49
39
  end
50
40
 
51
41
  class Streams
42
+ include Connection
43
+
52
44
  def self.all
53
45
  end
54
46
 
@@ -76,76 +68,45 @@ module Kappa::V2
76
68
  end
77
69
 
78
70
  limit = args[:limit]
79
- if limit && (limit < 25)
71
+ if limit && (limit < 100)
80
72
  params[:limit] = limit
81
73
  else
82
- params[:limit] = 25
74
+ params[:limit] = 100
83
75
  limit = 0
84
76
  end
85
77
 
86
- streams = []
87
- ids = Set.new
88
-
89
- connection = Connection.instance
90
- connection.paginated('streams', params) do |json|
91
- current_streams = json['streams']
92
- current_streams.each do |stream_json|
93
- stream = Stream.new(stream_json, connection)
94
- if ids.add?(stream.id)
95
- streams << stream
96
- if streams.count == limit
97
- return streams
98
- end
99
- end
100
- end
101
-
102
- !current_streams.empty?
103
- end
104
-
105
- streams
78
+ return connection.accumulate(
79
+ :path => 'streams',
80
+ :params => params,
81
+ :json => 'streams',
82
+ :class => Stream,
83
+ :limit => limit
84
+ )
106
85
  end
107
86
 
108
87
  #
109
88
  # GET /streams/featured
110
89
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/streams.md#get-streamsfeatured
111
90
  #
112
- def self.featured(params = {})
113
- limit = params[:limit] || 0
114
-
115
- streams = []
116
- ids = Set.new
117
-
118
- connection = Connection.instance
119
- connection.paginated('streams/featured', params) do |json|
120
- current_streams = json['featured']
121
- current_streams.each do |featured_json|
122
- # TODO: Capture more information from the featured_json structure (need a FeaturedStream class?)
123
- stream_json = featured_json['stream']
124
- stream = Stream.new(stream_json, connection)
125
- if ids.add?(stream.id)
126
- streams << stream
127
- if streams.count == limit
128
- return streams
129
- end
130
- end
131
- end
91
+ def self.featured(args = {})
92
+ params = {}
132
93
 
133
- !current_streams.empty?
94
+ limit = args[:limit]
95
+ if limit && (limit < 100)
96
+ params[:limit] = limit
97
+ else
98
+ params[:limit] = 100
99
+ limit = 0
134
100
  end
135
101
 
136
- streams
137
- end
138
- end
139
- end
140
-
141
- module Kappa::V3
142
- class Stream < Kappa::StreamBase
143
- def initialize(arg, connection = Connection.instance)
144
- super(arg, connection)
145
- end
146
-
147
- private
148
- def parse(hash)
102
+ return connection.accumulate(
103
+ :path => 'streams/featured',
104
+ :params => params,
105
+ :json => 'featured',
106
+ :sub_json => 'stream',
107
+ :class => Stream,
108
+ :limit => limit
109
+ )
149
110
  end
150
111
  end
151
112
  end
data/lib/kappa/team.rb CHANGED
@@ -1,17 +1,18 @@
1
1
  module Kappa
2
+ # @private
2
3
  class TeamBase
3
4
  include IdEquality
4
5
 
5
- def initialize(arg, connection)
6
- @connection = connection
7
-
8
- case arg
9
- when Hash
10
- parse(arg)
11
- when String
12
- json = @connection.get("teams/#{arg}")
13
- else
14
- raise ArgumentError
6
+ #
7
+ # GET /teams/:team
8
+ # https://github.com/justintv/Twitch-API/blob/master/v2_resources/teams.md#get-teamsteam
9
+ #
10
+ def self.get(team_name)
11
+ json = connection.get("teams/#{team_name}")
12
+ if json['status'] == 404
13
+ nil
14
+ else
15
+ new(json)
15
16
  end
16
17
  end
17
18
  end
@@ -19,26 +20,9 @@ end
19
20
 
20
21
  module Kappa::V2
21
22
  class Team < Kappa::TeamBase
22
- #
23
- # GET /teams/:team
24
- # https://github.com/justintv/Twitch-API/blob/master/v2_resources/teams.md#get-teamsteam
25
- #
26
- def intialize(arg, connection = Connection.instance)
27
- super(arg, connection)
28
- end
29
-
30
- attr_reader :id
31
- attr_reader :info
32
- attr_reader :background_url
33
- attr_reader :banner_url
34
- attr_reader :logo_url
35
- attr_reader :name
36
- attr_reader :display_name
37
- attr_reader :updated_at
38
- attr_reader :created_at
23
+ include Connection
39
24
 
40
- private
41
- def parse(hash)
25
+ def initialize(hash)
42
26
  @id = hash['_id']
43
27
  @info = hash['info']
44
28
  @background_url = hash['background']
@@ -49,35 +33,43 @@ module Kappa::V2
49
33
  @updated_at = DateTime.parse(hash['updated_at'])
50
34
  @created_at = DateTime.parse(hash['created_at'])
51
35
  end
36
+
37
+ attr_reader :id
38
+ attr_reader :info
39
+ attr_reader :background_url
40
+ attr_reader :banner_url
41
+ attr_reader :logo_url
42
+ attr_reader :name
43
+ attr_reader :display_name
44
+ attr_reader :updated_at
45
+ attr_reader :created_at
52
46
  end
53
47
 
54
48
  class Teams
49
+ include Connection
50
+
55
51
  #
56
52
  # GET /teams
57
53
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/teams.md#get-teams
58
54
  #
59
- def all(params = {})
60
- limit = params[:limit] || 0
61
-
62
- teams = []
63
- ids = Set.new
64
-
65
- @conn.paginated('teams', params) do |json|
66
- teams_json = json['teams']
67
- teams_json.each do |team_json|
68
- team = Team.new(team_json, @conn)
69
- if ids.add?(team.id)
70
- teams << team
71
- if teams.count == limit
72
- return teams
73
- end
74
- end
75
- end
55
+ def self.all(args = {})
56
+ params = {}
76
57
 
77
- !teams_json.empty?
58
+ limit = args[:limit]
59
+ if limit && (limit < 100)
60
+ params[:limit] = limit
61
+ else
62
+ params[:limit] = 100
63
+ limit = 0
78
64
  end
79
65
 
80
- teams
66
+ return connection.accumulate(
67
+ :path => 'teams',
68
+ :params => params,
69
+ :json => 'teams',
70
+ :class => Team,
71
+ :limit => limit
72
+ )
81
73
  end
82
74
  end
83
75
  end
data/lib/kappa/user.rb CHANGED
@@ -1,34 +1,37 @@
1
1
  module Kappa
2
+ # @private
2
3
  class UserBase
3
4
  include IdEquality
4
5
 
5
- def initialize(hash, connection = self.class.default_connection)
6
- @connection = connection
7
- parse(hash)
8
- end
9
-
10
6
  #
11
7
  # GET /users/:user
12
8
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/users.md#get-usersuser
13
9
  #
14
- def self.get(user_name, connection = default_connection)
10
+ def self.get(user_name)
15
11
  json = connection.get("users/#{user_name}")
16
12
  if json['status'] == 404
17
13
  nil
18
14
  else
19
- new(json, connection)
15
+ new(json)
20
16
  end
21
17
  end
22
-
23
- private
24
- def self.default_connection
25
- self.class.module_class(:Connection).instance
26
- end
27
18
  end
28
19
  end
29
20
 
30
21
  module Kappa::V2
31
22
  class User < Kappa::UserBase
23
+ include Connection
24
+
25
+ def initialize(hash)
26
+ @id = hash['_id']
27
+ @created_at = DateTime.parse(hash['created_at'])
28
+ @display_name = hash['display_name']
29
+ @logo_url = hash['logo']
30
+ @name = hash['name']
31
+ @staff = hash['staff'] || false
32
+ @updated_at = DateTime.parse(hash['updated_at'])
33
+ end
34
+
32
35
  def channel
33
36
  # TODO
34
37
  end
@@ -54,28 +57,24 @@ module Kappa::V2
54
57
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/follows.md#get-usersuserfollowschannels
55
58
  #
56
59
  def following(params = {})
57
- limit = params[:limit] || 0
58
-
59
- channels = []
60
- ids = Set.new
61
-
62
- @connection.paginated("users/#{@name}/follows/channels", params) do |json|
63
- current_channels = json['follows']
64
- current_channels.each do |follow_json|
65
- channel_json = follow_json['channel']
66
- channel = Channel.new(channel_json, @connection)
67
- if ids.add?(channel.id)
68
- channels << channel
69
- if channels.count == limit
70
- return channels
71
- end
72
- end
73
- end
60
+ params = {}
74
61
 
75
- !current_channels.empty?
62
+ limit = args[:limit]
63
+ if limit && (limit < 100)
64
+ params[:limit] = limit
65
+ else
66
+ params[:limit] = 100
67
+ limit = 0
76
68
  end
77
69
 
78
- channels
70
+ return connection.accumulate(
71
+ :path => "users/#{@name}/follows/channels",
72
+ :params => params,
73
+ :json => 'follows',
74
+ :sub_json => 'channel',
75
+ :class => Channel,
76
+ :limit => limit
77
+ )
79
78
  end
80
79
 
81
80
  #
@@ -83,7 +82,7 @@ module Kappa::V2
83
82
  # https://github.com/justintv/Twitch-API/blob/master/v2_resources/follows.md#get-usersuserfollowschannelstarget
84
83
  #
85
84
  def following?(channel_name)
86
- json = @connection.get("users/#{@name}/follows/channels/#{channel_name}")
85
+ json = connection.get("users/#{@name}/follows/channels/#{channel_name}")
87
86
  status = json['status']
88
87
  return !status || (status != 404)
89
88
  end
@@ -98,16 +97,5 @@ module Kappa::V2
98
97
  # TODO: Authenticated user attributes.
99
98
  # attr_reader :email
100
99
  # def partnered?
101
-
102
- private
103
- def parse(hash)
104
- @id = hash['_id']
105
- @created_at = DateTime.parse(hash['created_at'])
106
- @display_name = hash['display_name']
107
- @logo_url = hash['logo']
108
- @name = hash['name']
109
- @staff = hash['staff'] || false
110
- @updated_at = DateTime.parse(hash['updated_at'])
111
- end
112
100
  end
113
101
  end
data/lib/kappa/version.rb CHANGED
@@ -1 +1 @@
1
- $version = '0.1.3.pre'
1
+ $version = '0.1.4.pre'
data/lib/kappa/video.rb CHANGED
@@ -1,31 +1,35 @@
1
1
  module Kappa
2
+ # @private
2
3
  class VideoBase
3
4
  include IdEquality
4
5
 
5
- def initialize(arg, connection)
6
- @connection = connection
7
-
8
- case arg
9
- when Hash
10
- parse(arg)
11
- when String
12
- json = @connection.get("videos/#{arg}")
13
- parse(json)
14
- else
15
- raise ArgumentError
16
- end
6
+ def self.get(id)
7
+ json = connection.get("videos/#{id}")
8
+ new(json)
17
9
  end
18
10
  end
19
11
  end
20
12
 
21
13
  module Kappa::V2
22
14
  class Video < Kappa::VideoBase
23
- def initialize(arg)
24
- super(arg, Connection.instance)
15
+ include Connection
16
+
17
+ def initialize(hash)
18
+ @id = hash['id']
19
+ @title = hash['title']
20
+ @recorded_at = DateTime.parse(hash['recorded_at'])
21
+ @url = hash['url']
22
+ @view_count = hash['views']
23
+ @description = hash['description']
24
+ @length_sec = hash['length']
25
+ @game_name = hash['game']
26
+ @preview_url = hash['preview']
27
+ @channel_name = hash['channel']['name']
28
+ # @channel_display_name = json['channel']['display_name']
25
29
  end
26
30
 
27
31
  def channel
28
- Channel.new(@conn.get("channels/#{@channel_name}"), @conn)
32
+ Channel.new(connection.get("channels/#{@channel_name}"))
29
33
  end
30
34
 
31
35
  attr_reader :id
@@ -40,23 +44,6 @@ module Kappa::V2
40
44
  attr_reader :preview_url
41
45
  # TODO: Move this under "v.channel.name" and force the query if other attributes are requested.
42
46
  attr_reader :channel_name
43
-
44
- private
45
- def parse(hash)
46
- @conn = conn
47
-
48
- @id = hash['id']
49
- @title = hash['title']
50
- @recorded_at = DateTime.parse(hash['recorded_at'])
51
- @url = hash['url']
52
- @view_count = hash['views']
53
- @description = hash['description']
54
- @length_sec = hash['length']
55
- @game_name = hash['game']
56
- @preview_url = hash['preview']
57
- @channel_name = hash['channel']['name']
58
- # @channel_display_name = json['channel']['display_name']
59
- end
60
47
  end
61
48
 
62
49
  class Videos
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: kappa
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.3.pre
4
+ version: 0.1.4.pre
5
5
  prerelease: 6
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2013-05-09 00:00:00.000000000 Z
12
+ date: 2013-05-12 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: httparty
@@ -91,6 +91,22 @@ dependencies:
91
91
  - - ! '>='
92
92
  - !ruby/object:Gem::Version
93
93
  version: 2.13.0
94
+ - !ruby/object:Gem::Dependency
95
+ name: coveralls
96
+ requirement: !ruby/object:Gem::Requirement
97
+ none: false
98
+ requirements:
99
+ - - ! '>='
100
+ - !ruby/object:Gem::Version
101
+ version: '0'
102
+ type: :development
103
+ prerelease: false
104
+ version_requirements: !ruby/object:Gem::Requirement
105
+ none: false
106
+ requirements:
107
+ - - ! '>='
108
+ - !ruby/object:Gem::Version
109
+ version: '0'
94
110
  description: ! " A Ruby library for interfacing with the Twitch.tv Kraken API\n
95
111
  \ including users, channels, streams, and followers.\n"
96
112
  email: schmch@gmail.com
@@ -98,7 +114,6 @@ executables: []
98
114
  extensions: []
99
115
  extra_rdoc_files: []
100
116
  files:
101
- - lib/kappa/base.rb
102
117
  - lib/kappa/channel.rb
103
118
  - lib/kappa/connection.rb
104
119
  - lib/kappa/game.rb
@@ -137,3 +152,4 @@ signing_key:
137
152
  specification_version: 3
138
153
  summary: Ruby library for interfacing with the Twitch.tv Kraken API.
139
154
  test_files: []
155
+ has_rdoc:
data/lib/kappa/base.rb DELETED
@@ -1,9 +0,0 @@
1
- class Class
2
- def module_class(sym)
3
- parts = name.split('::')
4
- parts[-1] = sym
5
- parts.inject(Kernel) { |const, part|
6
- const.const_get(part)
7
- }
8
- end
9
- end