viki 0.0.5 → 1.0.0

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
@@ -7,23 +7,30 @@ Installation
7
7
  ----------
8
8
  Manually `gem install viki` or add `gem 'viki'` to Gemfile
9
9
 
10
- How to use
11
- ----------
12
- Add to your .rb
10
+ Usage
11
+ -----
12
+ Add where necessary
13
13
 
14
14
  require 'viki'
15
15
 
16
16
  Initialization
17
17
 
18
- viki = Viki.new('your_client_id', 'your_client_secret')
18
+ client = Viki.new('your_client_id', 'your_client_secret')
19
+
20
+ Client is a `Viki::Client` object. When you make a method call, for example `client.movies`, the client will return a `Viki::Request` object - which you will be using to make requests. You may chain methods on the request object. The actual call to the API will only be made when you call `.get` on the request object.
19
21
 
22
+ viki = client.movies #returns a Viki::Request object
23
+ results = viki.get #hits the API and returns a Viki::APIObject
20
24
 
21
- Responses will be returned in a `Viki::APIObject`.
25
+ APIObject Methods
26
+ -----------------
22
27
 
23
- For results that are paginated. You can use the `APIObject`'s `next` and `prev` methods to retrieve the next and previous 25 records respectively.
28
+ Responses will be returned in a `Viki::APIObject`. See below
29
+
30
+ For results that are paginated, you may use the `APIObject`'s `next` and `prev` methods to retrieve the next and previous 25 records respectively.
24
31
 
25
32
  ```
26
- viki.movies
33
+ viki = client.movies #returns a Viki::Request
27
34
  movies = viki.get #return records in a Viki::APIObject
28
35
 
29
36
  movies.content #content of the API call in JSON format
@@ -37,8 +44,9 @@ For results that are paginated. You can use the `APIObject`'s `next` and `prev`
37
44
  Examples
38
45
  ----------
39
46
  * Results will always be returned in JSON format.
47
+ * This gem simply converts Ruby methods to API endpoints. Each URL namespace is a method. This means that if there is a `/series/` url namespace, the gem's request object will have an equivalent `.series` method. See examples below for an illustration of this behaviour.
48
+ * Refer to the [API V3 documentation](http://dev.viki.com/api "Viki API V3 Docs") for complete documentation for all Viki API endpoints.
40
49
  * All URL endpoints in the following examples should include an `access_token` parameter.
41
- * Refer to the [API V3 documentation](http://dev.viki.com/api "Viki API V3 Docs") for all endpoints.
42
50
 
43
51
  ### List Movies
44
52
  URL
@@ -51,8 +59,8 @@ URL
51
59
 
52
60
  Your ruby application
53
61
 
54
- viki.movies.get #without parameter filters
55
- viki.movies(genre: 2).get #with parameter filters
62
+ client.movies.get #without parameter filters
63
+ client.movies(genre: 2).get #with parameter filters
56
64
 
57
65
  ### Show Movie
58
66
  URL
@@ -61,7 +69,7 @@ URL
61
69
 
62
70
  Your ruby application
63
71
 
64
- viki.movies(71459).get
72
+ client.movies(71459).get
65
73
 
66
74
  ### Subtitles
67
75
  URL
@@ -70,7 +78,7 @@ URL
70
78
 
71
79
  Your ruby application
72
80
 
73
- viki.movies(71459).subtitles('en').get
81
+ client.movies(71459).subtitles('en').get
74
82
 
75
83
  ### Show Episode
76
84
  URL
@@ -79,7 +87,7 @@ URL
79
87
 
80
88
  Your ruby application
81
89
 
82
- viki.series(6004).episodes(61168).get
90
+ client.series(6004).episodes(61168).get
83
91
 
84
92
  ### List Newscasts
85
93
 
@@ -93,11 +101,11 @@ URL
93
101
 
94
102
  Your ruby application
95
103
 
96
- viki.newscasts.get #without parameter filter
97
- viki.newscasts(language: 'ko').get #with parameter filter
104
+ client.newscasts.get #without parameter filter
105
+ client.newscasts(language: 'ko').get #with parameter filter
98
106
 
99
107
  RSpec Testing
100
- ----------
108
+ -------------
101
109
  To run the tests, create a spec_config.rb file from the sample file.
102
110
 
103
- Add your client id and client secret into the file.
111
+ Add your client id and client secret into this file.
data/lib/viki/client.rb CHANGED
@@ -1,14 +1,12 @@
1
1
  require 'httparty'
2
2
  require 'viki/api_object'
3
+ require 'viki/transport'
3
4
  require 'viki/request'
4
5
  require 'multi_json'
5
6
 
6
7
  module Viki
7
8
  class Client
8
- Dir[File.expand_path('../client/*.rb', __FILE__)].each { |f| require f }
9
- URL_NAMESPACES = [:movies, :series, :episodes, :music_videos, :newscasts, :newsclips,
10
- :artists, :featured, :coming_soon, :subtitles, :hardsubs, :genres, :countries,
11
- :search, :languages]
9
+ include Viki::Transport
12
10
 
13
11
  def initialize(client_id, client_secret)
14
12
  @client_id = client_id
@@ -18,36 +16,12 @@ module Viki
18
16
 
19
17
  attr_reader :access_token
20
18
 
21
- include Viki::Request
22
-
23
- def get
24
- current_chain = @call_chain
25
- @call_chain = []
26
- request(current_chain)
27
- end
28
-
29
- def reset_access_token
30
- @access_token = auth_request(@client_id, @client_secret)
31
- end
32
-
33
19
  private
34
20
  def method_missing(name, *args)
35
- @call_chain ||= []
36
- raise NoMethodError if not URL_NAMESPACES.include? name
37
-
38
- curr_call = { name: name }
39
-
40
- first_arg, second_arg = args[0], args[1]
41
-
42
- if args.length == 1
43
- first_arg.is_a?(Hash) ? curr_call.merge!({ params: first_arg }) : curr_call.merge!({ resource: first_arg })
44
- elsif args.length == 2
45
- curr_call.merge!({ resource: first_arg })
46
- curr_call.merge!({ params: second_arg })
47
- end
48
-
49
- @call_chain.push(curr_call)
50
- self
21
+ raise NoMethodError if not URL_NAMESPACES.include? name
22
+ Viki::Request.new({client_id: @client_id,
23
+ client_secret: @client_secret,
24
+ access_token: @access_token}, name, *args)
51
25
  end
52
26
 
53
27
  end
data/lib/viki/request.rb CHANGED
@@ -1,57 +1,51 @@
1
- require 'uri'
2
- require 'httparty'
3
- require 'multi_json'
4
- require 'viki/utilities'
5
-
6
1
  module Viki
7
- module Request
8
- include Viki::Utilities
2
+ class Request
3
+ def initialize(auth_data, name, *args)
4
+ @access_token = auth_data[:access_token]
5
+ @client_id = auth_data[:client_id]
6
+ @client_secret = auth_data[:client_secret]
9
7
 
10
- private
11
- HOST = "http://www.viki.com/api/v3/"
12
-
13
- def auth_request(client_id, client_secret)
14
- params = {
15
- :grant_type => 'client_credentials',
16
- :client_id => client_id,
17
- :client_secret => client_secret
18
- }
19
- response = HTTParty.post('http://viki.com/oauth/token', query: params)
20
- json = MultiJson.load(response.body)
21
- raise Viki::Error.new(response.header.code, json["error_description"]) if response.header.code != "200"
22
- json["access_token"]
8
+ build_call_chain(name, *args)
23
9
  end
24
10
 
25
- def request(call_chain)
26
- path, params = build_url(call_chain)
27
- request_url = HOST + path.chop + ".json"
11
+ attr_reader :access_token
28
12
 
29
- response = HTTParty.get(request_url, :query => params)
13
+ include Viki::Transport
30
14
 
31
- if response.header.code == "401"
32
- self.reset_access_token
33
- params.merge!({ access_token: self.access_token })
34
- response = HTTParty.get(request_url, :query => params)
35
- end
36
-
37
- capture response
15
+ def get
16
+ current_chain = @call_chain
17
+ @call_chain = []
18
+ request(current_chain)
19
+ end
38
20
 
39
- APIObject.new(response.body, self.access_token)
21
+ def reset_access_token
22
+ @access_token = auth_request(@client_id, @client_secret)
40
23
  end
41
24
 
42
25
  private
26
+ def method_missing(name, *args)
27
+ build_call_chain(name, *args)
28
+ self
29
+ end
30
+
31
+ def build_call_chain(name, *args)
32
+ @call_chain ||= []
33
+ raise NoMethodError if not URL_NAMESPACES.include? name
34
+
35
+ curr_call = { name: name }
43
36
 
44
- def build_url(call_chain)
45
- path = ""
46
- params = { access_token: self.access_token }
37
+ first_arg, second_arg = args[0], args[1]
47
38
 
48
- call_chain.each do |c|
49
- path += "#{c[:name]}/"
50
- path += "#{c[:resource]}/" if c.has_key?(:resource)
51
- params.merge!(c[:params]) if c.has_key?(:params)
39
+ if args.length == 1
40
+ first_arg.is_a?(Hash) ? curr_call.merge!({ params: first_arg }) : curr_call.merge!({ resource: first_arg })
41
+ elsif args.length == 2
42
+ curr_call.merge!({ resource: first_arg })
43
+ curr_call.merge!({ params: second_arg })
52
44
  end
53
45
 
54
- return path, params
46
+ @call_chain.push(curr_call)
55
47
  end
48
+
56
49
  end
57
50
  end
51
+
@@ -0,0 +1,55 @@
1
+ require 'uri'
2
+ require 'httparty'
3
+ require 'multi_json'
4
+ require 'viki/utilities'
5
+
6
+ module Viki
7
+ module Transport
8
+ include Viki::Utilities
9
+
10
+ private
11
+ HOST = "http://www.viki.com/api/v3/"
12
+
13
+ def auth_request(client_id, client_secret)
14
+ params = {
15
+ :grant_type => 'client_credentials',
16
+ :client_id => client_id,
17
+ :client_secret => client_secret
18
+ }
19
+ response = HTTParty.post('http://viki.com/oauth/token', query: params)
20
+ json = MultiJson.load(response.body)
21
+ raise Viki::Error.new(response.header.code, json["error_description"]) if response.header.code != "200"
22
+ json["access_token"]
23
+ end
24
+
25
+ def request(call_chain)
26
+ path, params = build_url(call_chain)
27
+ request_url = HOST + path.chop + ".json"
28
+
29
+ response = HTTParty.get(request_url, :query => params)
30
+
31
+ if response.header.code == "401"
32
+ self.reset_access_token
33
+ params.merge!({ access_token: self.access_token })
34
+ response = HTTParty.get(request_url, :query => params)
35
+ end
36
+
37
+ capture response
38
+
39
+ APIObject.new(response.body, self.access_token)
40
+ end
41
+
42
+ def build_url(call_chain)
43
+ path = ""
44
+ params = { access_token: self.access_token }
45
+
46
+ call_chain.each do |c|
47
+ path += "#{c[:name]}/"
48
+ path += "#{c[:resource]}/" if c.has_key?(:resource)
49
+ params.merge!(c[:params]) if c.has_key?(:params)
50
+ end
51
+
52
+ return path, params
53
+ end
54
+ end
55
+ end
@@ -1,5 +1,8 @@
1
1
  module Viki
2
2
  module Utilities
3
+ URL_NAMESPACES = [:movies, :series, :episodes, :music_videos, :newscasts, :newsclips,
4
+ :artists, :featured, :coming_soon, :subtitles, :hardsubs, :genres, :countries,
5
+ :search, :languages]
3
6
  private
4
7
 
5
8
  def capture(response)
data/lib/viki/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module Viki
2
- VERSION = "0.0.5"
2
+ VERSION = "1.0.0"
3
3
  end
@@ -2,25 +2,19 @@ require 'spec_helper'
2
2
 
3
3
  describe Viki::Client do
4
4
 
5
- describe "#get" do
5
+ describe "method delegation" do
6
6
  before { Viki::Client.any_instance.stub(:auth_request) }
7
- subject { Viki::Client.new('chickenrice', 'soronerychickenrice') }
8
7
 
9
- it "should perform a request to the right url given a call chain" do
10
- subject.movies(1234).subtitles('en')
11
- subject.should_receive(:request).with([{ :name => :movies, :resource => 1234 },
12
- { :name => :subtitles, :resource => "en" }])
13
- subject.get
8
+ def client
9
+ Viki::Client.new('chickenrice', 'soronerychickenrice')
14
10
  end
15
11
 
16
- it "should perform a request with the right params given a call chain" do
17
- subject.movies(1234, {genre: 2})
18
- subject.should_receive(:request).with([{ :name => :movies, :resource => 1234, :params => {genre: 2}}])
19
- subject.get
12
+ it "should raise NoMethodError error if part of the call chain is not part of the URL_NAMESPACES list" do
13
+ expect { client.methodwrong.subtitles('en') }.to raise_error(NoMethodError)
20
14
  end
21
15
 
22
- it "should raise NoMethodError error if part of the call chain is not part of the URL_NAMESPACES list" do
23
- expect { subject.methodwrong.subtitles('en') }.to raise_error(NoMethodError)
16
+ it "should return a request object when method_missing is called" do
17
+ client.movies(1234).should be_an_instance_of(Viki::Request)
24
18
  end
25
19
  end
26
20
  end
@@ -0,0 +1,31 @@
1
+ require 'spec_helper'
2
+
3
+ describe Viki::Request do
4
+ describe "#get" do
5
+ before do
6
+ Viki::Client.any_instance.stub(:auth_request)
7
+ Viki::Request.any_instance.stub(:request) { Viki::APIObject }
8
+ end
9
+
10
+ def client
11
+ Viki.new('chickenrice', 'soronerychickenrice')
12
+ end
13
+
14
+ it "should perform a request to the right url given a call chain" do
15
+ req = client.movies(1234).subtitles('en')
16
+ req.should_receive(:request).with([{ :name => :movies, :resource => 1234 },
17
+ { :name => :subtitles, :resource => "en" }])
18
+ req.get
19
+ end
20
+
21
+ it "should perform a request with the right params given a call chain" do
22
+ req = client.movies(1234, { genre: 2 })
23
+ req.should_receive(:request).with([{ :name => :movies, :resource => 1234, :params => { genre: 2 } }])
24
+ req.get
25
+ end
26
+
27
+ it "should raise NoMethodError error if part of the call chain is not part of the URL_NAMESPACES list" do
28
+ expect { client.methodwrong.subtitles('en') }.to raise_error(NoMethodError)
29
+ end
30
+ end
31
+ end
@@ -128,7 +128,7 @@ describe "Viki" do
128
128
  end
129
129
  end
130
130
 
131
- describe "Renew Expired Access Token" do
131
+ describe "Access token renewal" do
132
132
  it "should request a new access token when an endpoint returns 401 and client currently has an access_token" do
133
133
  VCR.use_cassette "auth/expired_access_token" do
134
134
  client.access_token.should_not be_empty
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: viki
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.5
4
+ version: 1.0.0
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -11,11 +11,11 @@ authors:
11
11
  autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
- date: 2012-07-04 00:00:00.000000000Z
14
+ date: 2012-07-10 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: rspec
18
- requirement: &70100608348400 !ruby/object:Gem::Requirement
18
+ requirement: !ruby/object:Gem::Requirement
19
19
  none: false
20
20
  requirements:
21
21
  - - ~>
@@ -23,10 +23,15 @@ dependencies:
23
23
  version: 2.10.0
24
24
  type: :development
25
25
  prerelease: false
26
- version_requirements: *70100608348400
26
+ version_requirements: !ruby/object:Gem::Requirement
27
+ none: false
28
+ requirements:
29
+ - - ~>
30
+ - !ruby/object:Gem::Version
31
+ version: 2.10.0
27
32
  - !ruby/object:Gem::Dependency
28
33
  name: vcr
29
- requirement: &70100608347900 !ruby/object:Gem::Requirement
34
+ requirement: !ruby/object:Gem::Requirement
30
35
  none: false
31
36
  requirements:
32
37
  - - ~>
@@ -34,10 +39,15 @@ dependencies:
34
39
  version: 2.2.2
35
40
  type: :development
36
41
  prerelease: false
37
- version_requirements: *70100608347900
42
+ version_requirements: !ruby/object:Gem::Requirement
43
+ none: false
44
+ requirements:
45
+ - - ~>
46
+ - !ruby/object:Gem::Version
47
+ version: 2.2.2
38
48
  - !ruby/object:Gem::Dependency
39
49
  name: webmock
40
- requirement: &70100608347440 !ruby/object:Gem::Requirement
50
+ requirement: !ruby/object:Gem::Requirement
41
51
  none: false
42
52
  requirements:
43
53
  - - ~>
@@ -45,10 +55,15 @@ dependencies:
45
55
  version: 1.8.7
46
56
  type: :development
47
57
  prerelease: false
48
- version_requirements: *70100608347440
58
+ version_requirements: !ruby/object:Gem::Requirement
59
+ none: false
60
+ requirements:
61
+ - - ~>
62
+ - !ruby/object:Gem::Version
63
+ version: 1.8.7
49
64
  - !ruby/object:Gem::Dependency
50
65
  name: excon
51
- requirement: &70100608346980 !ruby/object:Gem::Requirement
66
+ requirement: !ruby/object:Gem::Requirement
52
67
  none: false
53
68
  requirements:
54
69
  - - ~>
@@ -56,10 +71,15 @@ dependencies:
56
71
  version: 0.9.6
57
72
  type: :development
58
73
  prerelease: false
59
- version_requirements: *70100608346980
74
+ version_requirements: !ruby/object:Gem::Requirement
75
+ none: false
76
+ requirements:
77
+ - - ~>
78
+ - !ruby/object:Gem::Version
79
+ version: 0.9.6
60
80
  - !ruby/object:Gem::Dependency
61
81
  name: httparty
62
- requirement: &70100608346520 !ruby/object:Gem::Requirement
82
+ requirement: !ruby/object:Gem::Requirement
63
83
  none: false
64
84
  requirements:
65
85
  - - ~>
@@ -67,10 +87,15 @@ dependencies:
67
87
  version: 0.8.3
68
88
  type: :runtime
69
89
  prerelease: false
70
- version_requirements: *70100608346520
90
+ version_requirements: !ruby/object:Gem::Requirement
91
+ none: false
92
+ requirements:
93
+ - - ~>
94
+ - !ruby/object:Gem::Version
95
+ version: 0.8.3
71
96
  - !ruby/object:Gem::Dependency
72
97
  name: multi_json
73
- requirement: &70100608346060 !ruby/object:Gem::Requirement
98
+ requirement: !ruby/object:Gem::Requirement
74
99
  none: false
75
100
  requirements:
76
101
  - - ~>
@@ -78,7 +103,12 @@ dependencies:
78
103
  version: 1.3.6
79
104
  type: :runtime
80
105
  prerelease: false
81
- version_requirements: *70100608346060
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ none: false
108
+ requirements:
109
+ - - ~>
110
+ - !ruby/object:Gem::Version
111
+ version: 1.3.6
82
112
  description: Viki-gem is an official wrapper gem for the Viki V3 API.
83
113
  email:
84
114
  - engineering@viki.com
@@ -97,11 +127,13 @@ files:
97
127
  - lib/viki/client.rb
98
128
  - lib/viki/error.rb
99
129
  - lib/viki/request.rb
130
+ - lib/viki/transport.rb
100
131
  - lib/viki/utilities.rb
101
132
  - lib/viki/version.rb
102
133
  - spec/lib/client_spec.rb
103
134
  - spec/lib/error_spec.rb
104
- - spec/requests/request_spec.rb
135
+ - spec/lib/request_spec.rb
136
+ - spec/requests/request_integration_spec.rb
105
137
  - spec/spec_config.rb.sample
106
138
  - spec/spec_helper.rb
107
139
  - spec/support/filter_shared_examples_spec.rb
@@ -127,14 +159,15 @@ required_rubygems_version: !ruby/object:Gem::Requirement
127
159
  version: '0'
128
160
  requirements: []
129
161
  rubyforge_project: viki
130
- rubygems_version: 1.8.6
162
+ rubygems_version: 1.8.24
131
163
  signing_key:
132
164
  specification_version: 3
133
165
  summary: A thin wrapper around the Viki V3 API
134
166
  test_files:
135
167
  - spec/lib/client_spec.rb
136
168
  - spec/lib/error_spec.rb
137
- - spec/requests/request_spec.rb
169
+ - spec/lib/request_spec.rb
170
+ - spec/requests/request_integration_spec.rb
138
171
  - spec/spec_config.rb.sample
139
172
  - spec/spec_helper.rb
140
173
  - spec/support/filter_shared_examples_spec.rb