fleakr 0.4.1 → 0.4.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -1 +1,3 @@
1
- require 'fleakr/core_ext/hash'
1
+ require 'fleakr/core_ext/hash'
2
+ require 'fleakr/core_ext/false_class'
3
+ require 'fleakr/core_ext/true_class'
@@ -0,0 +1,7 @@
1
+ class FalseClass # :nodoc:
2
+
3
+ def to_i
4
+ 0
5
+ end
6
+
7
+ end
@@ -0,0 +1,7 @@
1
+ class TrueClass # :nodoc:
2
+
3
+ def to_i
4
+ 1
5
+ end
6
+
7
+ end
@@ -17,22 +17,39 @@ module Fleakr
17
17
 
18
18
  flickr_attribute :value, :from => 'auth/token'
19
19
  flickr_attribute :permissions, :from => 'auth/perms'
20
+ flickr_attribute :user_id, :from => 'auth/user@nsid'
21
+ flickr_attribute :user_name, :from => 'auth/user@username'
22
+ flickr_attribute :full_name, :from => 'auth/user@fullname'
20
23
 
21
24
  # Retrieve a full authentication token from the supplied mini-token (e.g. 123-456-789)
22
25
  #
23
- def self.from_mini_token(token)
24
- parameters = {:mini_token => token, :sign? => true}
25
- response = Fleakr::Api::MethodRequest.with_response!('auth.getFullToken', parameters)
26
-
27
- self.new(response.body)
26
+ def self.from_mini_token(mini_token)
27
+ from :mini_token, mini_token
28
28
  end
29
29
 
30
30
  # Retrieve a full authentication token from the supplied auth_token string
31
31
  # (e.g. 45-76598454353455)
32
32
  #
33
- def self.from_auth_token(token)
34
- parameters = {:auth_token => token, :sign? => true}
35
- response = Fleakr::Api::MethodRequest.with_response!('auth.checkToken', parameters)
33
+ def self.from_auth_token(auth_token)
34
+ from :auth_token, auth_token
35
+ end
36
+
37
+ # Retrieve a full authentication token from the supplied frob
38
+ def self.from_frob(frob)
39
+ from :frob, frob
40
+ end
41
+
42
+ def self.from(thing, value) # :nodoc:
43
+ api_methods = {
44
+ :mini_token => 'getFullToken',
45
+ :auth_token => 'checkToken',
46
+ :frob => 'getToken'
47
+ }
48
+
49
+ method = "auth.#{api_methods[thing]}"
50
+
51
+ parameters = {thing => value, :authenticate? => false}
52
+ response = Fleakr::Api::MethodRequest.with_response!(method, parameters)
36
53
 
37
54
  self.new(response.body)
38
55
  end
@@ -3,6 +3,9 @@ module Fleakr
3
3
 
4
4
  # = Photo
5
5
  #
6
+ # Handles both the retrieval of Photo objects from various associations (e.g. User / Set) as
7
+ # well as the ability to upload images to the Flickr site.
8
+ #
6
9
  # == Attributes
7
10
  #
8
11
  # [id] The ID for this photo
@@ -59,20 +62,32 @@ module Fleakr
59
62
 
60
63
  has_many :images
61
64
 
62
- # Upload the photo specified by <tt>filename</tt> to the user's Flickr account. This
63
- # call requires authentication.
65
+ # Upload the photo specified by <tt>filename</tt> to the user's Flickr account. When uploading,
66
+ # there are several options available (none are required):
67
+ #
68
+ # [:title] The title for this photo. Any string is allowed.
69
+ # [:description] The description for this photo. Any string is allowed.
70
+ # [:tags] A collection of tags for this photo. This can be a string or array of strings.
71
+ # [:viewable_by] Who can view this photo? Acceptable values are one of <tt>:everyone</tt>,
72
+ # <tt>:friends</tt> or <tt>:family</tt>. This can also take an array of values
73
+ # (e.g. <tt>[:friends, :family]</tt>) to make it viewable by friends and family.
74
+ # [:level] The safety level of this photo. Acceptable values are one of <tt>:safe</tt>,
75
+ # <tt>:moderate</tt>, or <tt>:restricted</tt>.
76
+ # [:type] The type of image this is. Acceptable values are one of <tt>:photo</tt>,
77
+ # <tt>:screenshot</tt>, or <tt>:other</tt>.
78
+ # [:hide?] Should this photo be hidden from public searches? Takes a boolean.
64
79
  #
65
- def self.upload(filename)
66
- response = Fleakr::Api::UploadRequest.with_response!(filename)
80
+ def self.upload(filename, options = {})
81
+ response = Fleakr::Api::UploadRequest.with_response!(filename, :create, options)
67
82
  photo = Photo.new(response.body)
68
- Photo.find_by_id(photo.id, :authenticate? => true)
83
+ Photo.find_by_id(photo.id)
69
84
  end
70
85
 
71
86
  # Replace the current photo's image with the one specified by filename. This
72
87
  # call requires authentication.
73
88
  #
74
89
  def replace_with(filename)
75
- response = Fleakr::Api::UploadRequest.with_response!(filename, :photo_id => self.id, :type => :update)
90
+ response = Fleakr::Api::UploadRequest.with_response!(filename, :update, :photo_id => self.id)
76
91
  self.populate_from(response.body)
77
92
  self
78
93
  end
@@ -33,8 +33,10 @@ module Fleakr
33
33
  target_class = options[:class_name].nil? ? self.name : "Fleakr::Objects::#{options[:class_name]}"
34
34
 
35
35
  class_eval <<-CODE
36
- def self.find_all_#{condition}(value)
37
- response = Fleakr::Api::MethodRequest.with_response!('#{options[:call]}', :#{attribute} => value)
36
+ def self.find_all_#{condition}(value, options = {})
37
+ options.merge!(:#{attribute} => value)
38
+
39
+ response = Fleakr::Api::MethodRequest.with_response!('#{options[:call]}', options)
38
40
  (response.body/'rsp/#{options[:path]}').map {|e| #{target_class}.new(e) }
39
41
  end
40
42
  CODE
@@ -3,7 +3,7 @@ module Fleakr
3
3
 
4
4
  MAJOR = 0
5
5
  MINOR = 4
6
- TINY = 1
6
+ TINY = 2
7
7
 
8
8
  def self.to_s
9
9
  [MAJOR, MINOR, TINY].join('.')
@@ -0,0 +1,8 @@
1
+ <?xml version="1.0" encoding="utf-8"?>
2
+ <rsp stat="ok">
3
+ <auth>
4
+ <token>abc-123</token>
5
+ <perms>delete</perms>
6
+ <user nsid="31066442@N69" fullname="Sir Froot Pants" username="frootpantz"></user>
7
+ </auth>
8
+ </rsp>
@@ -26,16 +26,6 @@ module Fleakr::Api
26
26
  request.parameters[:method].value.should == 'flickr.people.findByUsername'
27
27
  end
28
28
 
29
- it "should know that it needs to sign the request" do
30
- ParameterList.expects(:new).with(:sign? => true).returns(stub(:<< => nil))
31
- request = MethodRequest.new('people.findByUsername', :sign? => true)
32
- end
33
-
34
- it "should know that it needs to authenticate the request" do
35
- ParameterList.expects(:new).with(:authenticate? => true).returns(stub(:<< => nil))
36
- request = MethodRequest.new('activity.userPhotos', :authenticate? => true)
37
- end
38
-
39
29
  it "should know the endpoint with full parameters" do
40
30
  query_parameters = 'foo=bar'
41
31
 
@@ -0,0 +1,179 @@
1
+ require File.dirname(__FILE__) + '/../../../test_helper'
2
+
3
+ module Fleakr::Api
4
+
5
+ class OptionTest < Test::Unit::TestCase
6
+
7
+ def self.should_know_the_class_for(type, options)
8
+ it "should know the class for the :#{type} type" do
9
+ Option.class_for(type).should == options[:is]
10
+ end
11
+ end
12
+
13
+ describe "The Option class" do
14
+ should_know_the_class_for :title, :is => Fleakr::Api::SimpleOption
15
+ should_know_the_class_for :description, :is => Fleakr::Api::SimpleOption
16
+ should_know_the_class_for :tags, :is => Fleakr::Api::TagOption
17
+ should_know_the_class_for :viewable_by, :is => Fleakr::Api::ViewOption
18
+ should_know_the_class_for :level, :is => Fleakr::Api::LevelOption
19
+ should_know_the_class_for :type, :is => Fleakr::Api::TypeOption
20
+ should_know_the_class_for :hide?, :is => Fleakr::Api::HiddenOption
21
+
22
+ it "should be able to create an option for a type" do
23
+ option = stub()
24
+
25
+ Option.expects(:class_for).with(:title).returns(Fleakr::Api::SimpleOption)
26
+ Fleakr::Api::SimpleOption.expects(:new).with(:title, 'blip').returns(option)
27
+
28
+ Option.for(:title, 'blip').should == option
29
+ end
30
+ end
31
+
32
+ end
33
+
34
+ class SimpleOptionTest < Test::Unit::TestCase
35
+
36
+ describe "An instance of the SimpleOption class" do
37
+ it "should have a type" do
38
+ so = SimpleOption.new(:title, 'blip')
39
+ so.type.should == :title
40
+ end
41
+
42
+ it "should have a value" do
43
+ so = SimpleOption.new(:title, 'blip')
44
+ so.value.should == 'blip'
45
+ end
46
+
47
+ it "should be able to generate a hash representation of itself" do
48
+ so = SimpleOption.new(:title, 'blip')
49
+ so.to_hash.should == {:title => 'blip'}
50
+ end
51
+ end
52
+
53
+ end
54
+
55
+ class TagOptionTest < Test::Unit::TestCase
56
+
57
+ describe "An instance of the TagOption class" do
58
+
59
+ it "should normalize the input value to an array" do
60
+ to = TagOption.new(:tags, 'blip')
61
+ to.value.should == ['blip']
62
+ end
63
+
64
+ it "should be able to generate a hash representation of itself with tags joined on spaces" do
65
+ to = TagOption.new(:tags, %w(bop bip))
66
+ to.to_hash.should == {:tags => '"bop" "bip"'}
67
+ end
68
+
69
+ it "should quote tag values with spaces" do
70
+ to = TagOption.new(:tags, ['tag', 'one with spaces'])
71
+ to.to_hash.should == {:tags => '"tag" "one with spaces"'}
72
+ end
73
+ end
74
+
75
+ end
76
+
77
+ class ViewOptionTest < Test::Unit::TestCase
78
+
79
+ describe "An instance of the ViewOption class" do
80
+ it "should be able to generate a hash representation for viewing by :everyone" do
81
+ vo = ViewOption.new(:viewable_by, :everyone)
82
+ vo.to_hash.should == {:is_public => 1, :is_family => 0, :is_friend => 0}
83
+ end
84
+
85
+ it "should be able to generate a hash representation for viewing by :family" do
86
+ vo = ViewOption.new(:viewable_by, :family)
87
+ vo.to_hash.should == {:is_public => 0, :is_family => 1, :is_friend => 0}
88
+ end
89
+
90
+ it "should be able to generate a hash representation for viewing by :friends" do
91
+ vo = ViewOption.new(:viewable_by, :friends)
92
+ vo.to_hash.should == {:is_public => 0, :is_family => 0, :is_friend => 1}
93
+ end
94
+
95
+ it "should know the visibility is public if value is set to :everyone" do
96
+ vo = ViewOption.new(:viewable_by, :everyone)
97
+ vo.public?.should be(true)
98
+ end
99
+
100
+ it "should know the visibility is not public if :everyone is not the only value" do
101
+ vo = ViewOption.new(:viewable_by, [:everyone, :family])
102
+ vo.public?.should be(false)
103
+ end
104
+
105
+ it "should know that its visible to friends and family if specified as such" do
106
+ vo = ViewOption.new(:viewable_by, [:friends, :family])
107
+ vo.friends?.should be(true)
108
+ vo.family?.should be(true)
109
+ end
110
+
111
+ end
112
+
113
+ end
114
+
115
+ class LevelOptionTest < Test::Unit::TestCase
116
+
117
+ describe "An instance of the LevelOption class" do
118
+
119
+ it "should be able to generate a hash representation for the :safe level" do
120
+ lo = LevelOption.new(:level, :safe)
121
+ lo.to_hash.should == {:safety_level => 1}
122
+ end
123
+
124
+ it "should be able to generate a hash representation for the :moderate level" do
125
+ lo = LevelOption.new(:level, :moderate)
126
+ lo.to_hash.should == {:safety_level => 2}
127
+ end
128
+
129
+ it "should be able to generate a hash representation for the :restricted level" do
130
+ lo = LevelOption.new(:level, :restricted)
131
+ lo.to_hash.should == {:safety_level => 3}
132
+ end
133
+
134
+ end
135
+
136
+ end
137
+
138
+ class TypeOptionTest < Test::Unit::TestCase
139
+
140
+ describe "An instance of the TypeOption class" do
141
+
142
+ it "should be able to generate a hash representation for the :photo type" do
143
+ to = TypeOption.new(:type, :photo)
144
+ to.to_hash.should == {:content_type => 1}
145
+ end
146
+
147
+ it "should be able to generate a hash representation for the :screenshot type" do
148
+ to = TypeOption.new(:type, :screenshot)
149
+ to.to_hash.should == {:content_type => 2}
150
+ end
151
+
152
+ it "should be able to generate a hash representation for the :other type" do
153
+ to = TypeOption.new(:type, :other)
154
+ to.to_hash.should == {:content_type => 3}
155
+ end
156
+
157
+ end
158
+
159
+ end
160
+
161
+ class HiddenOptionTest < Test::Unit::TestCase
162
+
163
+ describe "An instance of the HiddenOption class" do
164
+
165
+ it "should be able to generate a hash representation when set to true" do
166
+ ho = HiddenOption.new(:hide?, true)
167
+ ho.to_hash.should == {:hidden => 2}
168
+ end
169
+
170
+ it "should be able to generate a hash representation when set to false" do
171
+ ho = HiddenOption.new(:hide?, false)
172
+ ho.to_hash.should == {:hidden => 1}
173
+ end
174
+
175
+ end
176
+
177
+ end
178
+
179
+ end
@@ -9,7 +9,6 @@ module Fleakr::Api
9
9
  @api_key = 'key'
10
10
  @secret = 'foobar'
11
11
 
12
- Fleakr.stubs(:shared_secret).with().returns(@secret)
13
12
  Fleakr.stubs(:api_key).with().returns(@api_key)
14
13
  @parameter_list = ParameterList.new
15
14
  end
@@ -24,7 +23,7 @@ module Fleakr::Api
24
23
  parameter_list = ParameterList.new(:one => 'two')
25
24
  parameter_list[:one].value.should == 'two'
26
25
  end
27
-
26
+
28
27
  it "should be able to add parameters to its list" do
29
28
  parameter = ValueParameter.new('foo', 'bar')
30
29
 
@@ -47,11 +46,15 @@ module Fleakr::Api
47
46
  end
48
47
 
49
48
  it "should be able to calculate the signature of the parameters" do
49
+ Fleakr.stubs(:shared_secret).with().returns(@secret)
50
+
50
51
  @parameter_list << ValueParameter.new('foo', 'bar')
51
52
  @parameter_list.signature.should == Digest::MD5.hexdigest("#{@secret}api_key#{@api_key}foobar")
52
53
  end
53
54
 
54
55
  it "should use the correct order when signing a list of multiple parameters" do
56
+ Fleakr.stubs(:shared_secret).with().returns(@secret)
57
+
55
58
  @parameter_list << ValueParameter.new('z', 'a')
56
59
  @parameter_list << ValueParameter.new('a', 'z')
57
60
 
@@ -59,6 +62,8 @@ module Fleakr::Api
59
62
  end
60
63
 
61
64
  it "should ignore the parameters that aren't included in the signature" do
65
+ Fleakr.stubs(:shared_secret).with().returns(@secret)
66
+
62
67
  @parameter_list << ValueParameter.new('foo', 'bar')
63
68
  @parameter_list << ValueParameter.new('yes', 'no', false)
64
69
 
@@ -76,15 +81,30 @@ module Fleakr::Api
76
81
  @parameter_list.sign?.should be(false)
77
82
  end
78
83
 
79
- it "should know that it needs to sign the request when asked" do
80
- parameter_list = ParameterList.new(:sign? => true)
81
- parameter_list.sign?.should be(true)
84
+ it "should know that it needs to sign the request when a shared secret is available" do
85
+ Fleakr.expects(:shared_secret).with().returns(@secret)
86
+ @parameter_list.sign?.should be(true)
82
87
  end
83
88
 
84
89
  it "should know that it doesn't need to authenticate the request by default" do
85
90
  @parameter_list.authenticate?.should be(false)
86
91
  end
87
92
 
93
+ it "should know to authenticate the request when a token is available" do
94
+ Fleakr.stubs(:token).with().returns(stub(:value => 'toke'))
95
+ parameter_list = ParameterList.new
96
+
97
+ parameter_list.authenticate?.should be(true)
98
+ end
99
+
100
+ it "should not authenticate the request if it's been specifically told not to" do
101
+ Fleakr.expects(:token).with().never
102
+
103
+ parameter_list = ParameterList.new(:authenticate? => false)
104
+ parameter_list.authenticate?.should be(false)
105
+ end
106
+
107
+
88
108
  it "should know to authenticate the request when asked" do
89
109
  Fleakr.expects(:token).with().returns(stub(:value => 'toke'))
90
110
 
@@ -103,15 +123,10 @@ module Fleakr::Api
103
123
  auth_param.include_in_signature?.should be(true)
104
124
  end
105
125
 
106
- it "should know that it needs to sign the request when it is to be authenticated" do
107
- Fleakr.expects(:token).with().returns(stub(:value => 'toke'))
108
-
109
- parameter_list = ParameterList.new(:authenticate? => true)
110
- parameter_list.sign?.should be(true)
111
- end
112
-
113
126
  it "should include the signature in the list of parameters if the request is to be signed" do
114
- parameter_list = ParameterList.new(:sign? => true)
127
+ parameter_list = ParameterList.new
128
+
129
+ parameter_list.stubs(:sign?).with().returns(true)
115
130
  parameter_list.stubs(:signature).with().returns('sig')
116
131
 
117
132
  signature_param = parameter_list[:api_sig]
@@ -122,24 +137,24 @@ module Fleakr::Api
122
137
  end
123
138
 
124
139
  context "with associated parameters" do
125
-
140
+
126
141
  before do
127
142
  @p1 = ValueParameter.new('a', 'b')
128
143
  @p2 = ValueParameter.new('c', 'd')
129
-
144
+
130
145
  @p1.stubs(:to_query).with().returns('q1')
131
146
  @p1.stubs(:to_form).with().returns('f1')
132
147
 
133
148
  @p2.stubs(:to_query).with().returns('q2')
134
149
  @p2.stubs(:to_form).with().returns('f2')
135
-
150
+
136
151
  @parameter_list.stubs(:list).with().returns('a' => @p1, 'c' => @p2)
137
152
  end
138
-
153
+
139
154
  it "should be able to generate a query representation of itself" do
140
155
  @parameter_list.to_query.should == 'q1&q2'
141
156
  end
142
-
157
+
143
158
  it "should be able to represent a form representation of itself" do
144
159
  @parameter_list.stubs(:boundary).returns('bound')
145
160