zoopla 0.2.0 → 0.2.2

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.
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- zoopla (0.2.0)
4
+ zoopla (0.2.2)
5
5
  curb (~> 0.7.12)
6
6
  hashie (~> 1.0.0)
7
7
  json (~> 1.4.3)
@@ -1,9 +1,13 @@
1
1
  # Zoopla API Wrapper
2
2
 
3
- Use this gem to access real estate data using zoopla.co.uk API from ruby code:
3
+ Use this gem to access real estate data using zoopla.co.uk API from ruby code.
4
4
 
5
5
  * property listings with addresses, prices, agent details etc
6
- * more to come
6
+ * request parameters are chained: `sales.in{:area => "Camden, London"}.for(200000..250000).each{|listing| puts listing.price}`
7
+ * transparent pagination: just pass a block to process listings
8
+ * error handling
9
+ * Zed-index
10
+ * integers, dates and lat/lon parameters are parsed
7
11
 
8
12
  **This gem is pre-alpha, therefore it's missing important features and it not production ready. Also, the interface may change considerably in the future**
9
13
 
@@ -38,6 +42,73 @@ To search for rentals, do a similar query:
38
42
 
39
43
  The input and output parameters for property listings are described in the [Zoopla documentation](http://developer.zoopla.com/docs/read/Property_listings)
40
44
 
45
+ ### Disambiguation
46
+
47
+ If an ambiguous area is specified, a `Zoopla::DisambiguationError` will be raised
48
+
49
+ begin
50
+ zoopla.sales.in({:area => "Whitechapel"}).each{|listing| puts l.price}
51
+ rescue Zoopla::DisambiguationError => e
52
+ puts "Which of the following did you mean?"
53
+ e.areas.each{|area| puts area} # areas is an Array of Strings
54
+ end
55
+
56
+ The output will be
57
+
58
+ Which of the following did you mean?
59
+ Whitechapel, Devon
60
+ Whitechapel, Lancashire
61
+ Whitechapel, London
62
+
63
+ ### Unknown locations
64
+
65
+ If an unknown location is specified, a `Zoopla::UnknownLocationError` will be raised. If the API can provide a spelling suggestion,
66
+ it will be available in `e.suggestion`
67
+
68
+ begin
69
+ zoopla.sales.in({:area => "Stok, Devon"}).each{|listing| puts l.price}
70
+ rescue Zoopla::UnknownLocationError => e
71
+ puts "Did you mean #{e.suggestion}" if e.suggestion
72
+ end
73
+
74
+ The output will be
75
+
76
+ Did you mean stoke, Devon
77
+
78
+ ### Zed-index
79
+
80
+ To find out the [Zed-index](http://www.zoopla.co.uk/property/estimate/about/) of a place do
81
+
82
+ $ index_set = zoopla.zed_index.in({:area => 'London', :output_type => "town"})
83
+ $ puts index_set.latest # 427646
84
+ $ puts index_set.zed_index # 427646
85
+ $ puts index_set.zed_index_3month # 430923
86
+
87
+ The full list of possible fields can be found in the [documentation](http://developer.zoopla.com/docs/read/Zed_Index_API)
88
+
89
+ ### Area value graphs
90
+
91
+ To get the list of graphs do
92
+
93
+ $ graphs = zoopla.area_value_graphs.in({:postcode => "SW1A"})
94
+ $ puts graphs.average_values_graph_url # http://www.zoopla.co.uk/dynimgs/graph/average_prices/SW1A?width=400&height=212
95
+
96
+ To specify the size, chain the methods
97
+
98
+ $ graphs = zoopla.area_value_graphs.large.in({:postcode => "SW1A"})
99
+ $ puts graphs.average_values_graph_url # http://www.zoopla.co.uk/dynimgs/graph/average_prices/SW1A?width=600&height=318
100
+
101
+ The full list of possible fields can be found in the [documentation](http://developer.zoopla.com/docs/read/Area_Value_Graphs)
102
+
103
+ ### Property rich list
104
+
105
+ In line with all other methods
106
+
107
+ $ list = zoopla.rich_list.in({:area => 'NW1', :output_type => :outcode, :area_type => :streets })
108
+ $ list.url # "http://www.zoopla.co.uk/property/richlist/london/NW1/camden-town-regents-park-marylebone-north"
109
+ $ list.lowest.first.name # "Wrotham Road, London NW1"
110
+
111
+ Valid combinations of `output_type`/`area_type` are described in the [documentation](http://developer.zoopla.com/docs/read/Property_Rich_List)
41
112
 
42
113
  ## Contributing to zoopla
43
114
 
@@ -4,8 +4,12 @@ require 'cgi'
4
4
  require 'hashie'
5
5
 
6
6
  require File.expand_path('../zoopla/version', __FILE__)
7
+ require File.expand_path('../zoopla/errors', __FILE__)
7
8
  require File.expand_path('../zoopla/api', __FILE__)
8
9
  require File.expand_path('../zoopla/listings', __FILE__)
10
+ require File.expand_path('../zoopla/zed_index', __FILE__)
11
+ require File.expand_path('../zoopla/area_value_graphs', __FILE__)
12
+ require File.expand_path('../zoopla/property_rich_list', __FILE__)
9
13
 
10
14
  class Zoopla
11
15
 
@@ -25,4 +29,23 @@ class Zoopla
25
29
  Sales.new(@api_key)
26
30
  end
27
31
 
32
+ # Delegates to the ZedIndex class
33
+ # @return [ZedIndex]
34
+ def zed_index
35
+ ZedIndex.new(@api_key)
36
+ end
37
+
38
+ # Delegates to the AreaValueGraphs class
39
+ # @return [AreaValueGraphs]
40
+ def area_value_graphs
41
+ AreaValueGraphs.new(@api_key)
42
+ end
43
+
44
+ # Delegates to the PropertyRichList class
45
+ # @return [PropertyRichList]
46
+ def property_rich_list
47
+ PropertyRichList.new(@api_key)
48
+ end
49
+ alias_method :rich_list, :property_rich_list
50
+
28
51
  end
@@ -1,43 +1,82 @@
1
1
  class Zoopla
2
2
 
3
- # Raised when Zoopla returns the HTTP status code 400
4
- class BadRequestError < StandardError; end
5
-
6
- # Raised when Zoopla returns the HTTP status code 401
7
- class UnauthorizedRequestError < StandardError; end
8
-
9
- # Raised when Zoopla returns the HTTP status code 403
10
- class ForbiddenError < StandardError; end
11
-
12
- # Raised when Zoopla returns the HTTP status code 404
13
- class NotFoundError < StandardError; end
14
-
15
- # Raised when Zoopla returns the HTTP status code 405
16
- class MethodNotAllowedError < StandardError; end
17
-
18
- # Raised when Zoopla returns the HTTP status code 500
19
- class InternalServerError < StandardError; end
20
-
21
- class API # abstract
3
+ # Abstract class that understands how to talk to the API
4
+ class API
22
5
 
23
6
  def initialize(api_key)
24
7
  @key = api_key
8
+ reset!
9
+ end
10
+
11
+ # Resets all parameters except the API key
12
+ # @return [Rentals, Sales]
13
+ def reset!
14
+ @request = default_parameters
15
+ @actual_location = nil
16
+ self
17
+ end
18
+
19
+ # Holds standard output parameters for the call to the server, if any
20
+ def actual_location
21
+ return @actual_location if @actual_location
22
+ fetch_data(@request)
25
23
  end
26
24
 
27
25
  private
28
26
 
27
+ def valid_output_types
28
+ %w(postcode street town outcode area county country)
29
+ end
30
+
31
+ def check_output_type(location)
32
+ raise InvalidOutputTypeError.new("Invalid output type: #{location[:output_type]}") unless valid_output_types.include? location[:output_type].to_s or location[:output_type].nil?
33
+ end
34
+
35
+ def extract_actual_location(reply)
36
+ @actual_location = Hashie::Mash.new
37
+ %w(area_name street town postcode county country).each {|field|
38
+ @actual_location[field] = reply[field]
39
+ }
40
+ @actual_location.bounding_box = parse_values_if_possible(reply.bounding_box)
41
+ end
42
+
43
+ def raise_error_if_necessary(code, body)
44
+ case code
45
+ when 400 then raise BadRequestError.new "Not enough parameters to produce a valid response."
46
+ when 401 then raise UnauthorizedRequestError.new "The API key could not be recognised and the request is not authorized."
47
+ when 403 then raise ForbiddenError.new "The requested method is not available for the API key specified (the API key is invalid?)."
48
+ when 404 then raise NotFoundError.new "A method was requested that is not available in the API version specified."
49
+ when 405 then raise MethodNotAllowedError.new "The HTTP request that was made requested an API method that can not process the HTTP method used."
50
+ when 500 then raise InternalServerError.new "Internal Server Error"
51
+ else
52
+ raise_api_specific_error_if_necessary(body)
53
+ end
54
+ end
55
+
56
+ def raise_api_specific_error_if_necessary(body)
57
+ return unless body && body.error_code
58
+ case body.error_code.to_i
59
+ when -1 then raise DisambiguationError.new(body.disambiguation)
60
+ when 1 then raise InsufficientArgumentsError.new(body.error_string)
61
+ when 5 then raise InvalidRequestedDataError.new(body.error_string)
62
+ when 7 then raise UnknownLocationError.new(body.suggestion)
63
+ end
64
+ end
65
+
29
66
  def fetch_data(params)
30
67
  response_code, body = call(url(params))
31
- return preprocess(body) if response_code == 200
32
- raise case response_code
33
- when 400 then BadRequestError.new "Not enough parameters to produce a valid response."
34
- when 401 then UnauthorizedRequestError.new "The API key could not be recognised and the request is not authorized."
35
- when 403 then ForbiddenError.new "The requested method is not available for the API key specified (the API key is invalid?)."
36
- when 404 then NotFoundError.new "A method was requested that is not available in the API version specified."
37
- when 405 then MethodNotAllowedError.new "The HTTP request that was made requested an API method that can not process the HTTP method used."
38
- when 500 then InternalServerError.new "Internal Server Error"
39
- else StandardError.new "Unexpected HTTP error"
40
- end
68
+ body = parse body if body
69
+ raise_error_if_necessary response_code, body
70
+ extract_actual_location(body)
71
+ preprocess body
72
+ end
73
+
74
+ def preprocess(reply)
75
+ reply
76
+ end
77
+
78
+ def default_parameters
79
+ {}
41
80
  end
42
81
 
43
82
  def call(url)
@@ -53,7 +92,11 @@ class Zoopla
53
92
  end
54
93
 
55
94
  def tryParsingInteger(field, value)
56
- (value.to_i rescue 0) if %w(price listing_id num_bathrooms num_bedrooms num_floors num_recepts).include? field
95
+ (value.to_i rescue 0) if %w(zed_index price listing_id num_bathrooms num_bedrooms num_floors num_recepts).include? field
96
+ end
97
+
98
+ def tryParsingFloat(field, value)
99
+ (value.to_f rescue 0.0) if %w(longitude_min longitude_max latitude_min latitude_max).include? field
57
100
  end
58
101
 
59
102
  def tryParsingDate(field, value)
@@ -69,10 +112,15 @@ class Zoopla
69
112
  end
70
113
 
71
114
  def parse_values_if_possible(reply)
72
- return reply if reply.is_a? String
115
+ return reply unless reply.is_a? Hash
73
116
  reply.each_pair do |field, value|
74
- reply[field] = tryParsingHash(field, value) || tryParsingArray(field, value) || tryParsingInteger(field, value) || tryParsingDate(field, value) || value
117
+ reply[field] = tryParsingHash(field, value) || tryParsingArray(field, value) || tryParsingInteger(field, value) ||tryParsingFloat(field, value) || tryParsingDate(field, value) || value
75
118
  end
119
+ reply
120
+ end
121
+
122
+ def parse(reply)
123
+ Hashie::Mash.new.deep_update(parse_values_if_possible(JSON.parse reply))
76
124
  end
77
125
 
78
126
  end
@@ -0,0 +1,57 @@
1
+ class Zoopla
2
+
3
+ class AreaValueGraphs < API
4
+
5
+ # Defines the search area. All possible params are described at http://developer.zoopla.com/docs/
6
+ # @param [Hash] Location hash
7
+ # @return [AreaValueGraphs]
8
+ def in(location)
9
+ check_output_type location
10
+ @request.merge! location
11
+ reply = fetch_data(@request)
12
+ fields = %w(area_values_url home_values_graph_url value_trend_graph_url value_ranges_graph_url average_values_graph_url)
13
+ filtered = fields.inject({}) do |result, field|
14
+ result[field] = reply[field]
15
+ result
16
+ end
17
+ Hashie::Mash.new.update filtered
18
+ end
19
+
20
+ # Sets the size of the returned images to small
21
+ # @return AreaValueGraphs
22
+ def small
23
+ @request[:size] = 'small'
24
+ self
25
+ end
26
+
27
+ # Sets the size of the returned images to medium
28
+ # @return AreaValueGraphs
29
+ def medium
30
+ @request[:size] = 'medium'
31
+ self
32
+ end
33
+
34
+ # Sets the size of the returned images to large
35
+ # @return AreaValueGraphs
36
+ def large
37
+ @request[:size] = 'large'
38
+ self
39
+ end
40
+
41
+ private
42
+
43
+ def api_call
44
+ 'area_value_graphs'
45
+ end
46
+
47
+ def default_parameters
48
+ {:output_type => 'outcode'}
49
+ end
50
+
51
+ def valid_output_types
52
+ %w(outcode)
53
+ end
54
+
55
+ end
56
+
57
+ end
@@ -0,0 +1,54 @@
1
+ class Zoopla
2
+
3
+ # Raised when Zoopla returns the HTTP status code 400
4
+ class BadRequestError < StandardError; end
5
+
6
+ # Raised when Zoopla returns the HTTP status code 401
7
+ class UnauthorizedRequestError < StandardError; end
8
+
9
+ # Raised when Zoopla returns the HTTP status code 403
10
+ class ForbiddenError < StandardError; end
11
+
12
+ # Raised when Zoopla returns the HTTP status code 404
13
+ class NotFoundError < StandardError; end
14
+
15
+ # Raised when Zoopla returns the HTTP status code 405
16
+ class MethodNotAllowedError < StandardError; end
17
+
18
+ # Raised when Zoopla returns the HTTP status code 500
19
+ class InternalServerError < StandardError; end
20
+
21
+ # Raised when there are insufficient arguments for the API to return a result
22
+ class InsufficientArgumentsError < StandardError; end
23
+
24
+ # Raised under mysterious circumstances
25
+ class InvalidRequestedDataError < StandardError; end
26
+
27
+ # Raised when an invalid output type is specified
28
+ class InvalidOutputTypeError < StandardError; end
29
+
30
+ # Raised when an ambiguous area name is given, e.g. Whitechapel (is it in London? Devon? Lancashire?)
31
+ class DisambiguationError < StandardError
32
+
33
+ # Array of possible locations (Strings)
34
+ attr_reader :areas
35
+
36
+ def initialize(areas)
37
+ @areas = areas
38
+ end
39
+
40
+ end
41
+
42
+ # Raised when an unknown location is searched for, e.g. Stok
43
+ class UnknownLocationError < StandardError
44
+
45
+ # String, a spelling suggestion, may be nil
46
+ attr_reader :suggestion
47
+
48
+ def initialize(suggestion)
49
+ @suggestion = suggestion
50
+ end
51
+
52
+ end
53
+
54
+ end
@@ -7,6 +7,7 @@ class Zoopla
7
7
  # @param [Hash] Location hash
8
8
  # @return [Sales, Rentals]
9
9
  def in(location)
10
+ check_output_type location
10
11
  @request.merge! location
11
12
  self
12
13
  end
@@ -130,6 +131,7 @@ class Zoopla
130
131
 
131
132
  # Iterates over the results. Possible fields are described at http://developer.zoopla.com/docs/read/Property_listings
132
133
  # @yield [Hashie::Mash] a listing with data, e.g. sales.each{|listing| puts listing.price }
134
+ # @raise Zoopla::DisambiguationError if an ambiguous area is specified. Always expect this exception
133
135
  def each
134
136
  fetched_so_far, number_of_results = 0, 0
135
137
  @request[:page_number] = 1
@@ -142,14 +144,7 @@ class Zoopla
142
144
  end
143
145
  end while fetched_so_far < number_of_results
144
146
  end
145
-
146
- # Resets all parameters except the API key
147
- # @return [Rentals, Sales]
148
- def reset!
149
- @request = default_parameters
150
- self
151
- end
152
-
147
+
153
148
  private
154
149
 
155
150
  def set_limiting_value(limit, attribute, value)
@@ -173,13 +168,8 @@ class Zoopla
173
168
  end
174
169
 
175
170
  def preprocess(reply)
176
- reply = JSON.parse reply
177
- number_of_results = reply["result_count"] || 0
178
- listings = reply["listing"].inject([]) do |memo, listing|
179
- parse_values_if_possible(listing)
180
- memo << Hashie::Mash.new.update(listing)
181
- end
182
- [number_of_results, listings]
171
+ number_of_results = reply.result_count || 0
172
+ [number_of_results, reply.listing]
183
173
  end
184
174
 
185
175
  def api_call
@@ -4,12 +4,7 @@ class Zoopla
4
4
  class Rentals < API
5
5
 
6
6
  include Zoopla::Listing
7
-
8
- def initialize(*args)
9
- super(*args)
10
- reset!
11
- end
12
-
7
+
13
8
  # Include property listings that are already rented in the results
14
9
  # @return [Rentals]
15
10
  def include_rented
@@ -5,11 +5,6 @@ class Zoopla
5
5
 
6
6
  include Zoopla::Listing
7
7
 
8
- def initialize(*args)
9
- super(*args)
10
- reset!
11
- end
12
-
13
8
  # Whether to include property listings that are already sold in the results
14
9
  # @return [Sales]
15
10
  def include_sold
@@ -0,0 +1,37 @@
1
+ class Zoopla
2
+
3
+ class PropertyRichList < API
4
+
5
+ # Defines the search area. All possible params are described at http://developer.zoopla.com/docs/
6
+ # @param [Hash] Location hash
7
+ # @return [PropertyRichList]
8
+ def in(location)
9
+ check_output_type location
10
+ # check_area_type location
11
+ @request.merge! location
12
+ reply = fetch_data(@request)
13
+ result = Hashie::Mash.new
14
+ result.richlist_url = result.url = reply.richlist_url
15
+ result.highest = reply.highest
16
+ result.lowest = reply.lowest
17
+ result
18
+ end
19
+
20
+ private
21
+
22
+ def api_call
23
+ 'richlist'
24
+ end
25
+
26
+ def default_parameters
27
+ {:output_type => 'outcode'}
28
+ end
29
+
30
+ def valid_output_types
31
+ %w(outcode area town county country)
32
+ end
33
+
34
+
35
+ end
36
+
37
+ end
@@ -3,7 +3,7 @@ class Zoopla
3
3
  module Version
4
4
  MAJOR = 0
5
5
  MINOR = 2
6
- PATCH = 0
6
+ PATCH = 2
7
7
 
8
8
  STRING = [MAJOR, MINOR, PATCH].compact.join('.')
9
9
  end
@@ -0,0 +1,37 @@
1
+ class Zoopla
2
+
3
+ class ZedIndex < API
4
+
5
+ # Defines the search area. All possible params are described at http://developer.zoopla.com/docs/
6
+ # @param [Hash] Location hash
7
+ # @return [ZedIndex]
8
+ def in(location)
9
+ check_output_type location
10
+ @request.merge! location
11
+ reply = fetch_data(@request)
12
+ fields = %w(area_url zed_index zed_index_3month zed_index_6month zed_index_1year zed_index_2year zed_index_3year zed_index_4year zed_index_5year)
13
+ filtered = fields.inject({:latest => reply["zed_index"].to_i}) do |result, field|
14
+ reply[field] = reply[field].to_i if field =~ /zed_index/ && reply[field]
15
+ result[field] = reply[field]
16
+ result
17
+ end
18
+ Hashie::Mash.new.update filtered
19
+ end
20
+
21
+ private
22
+
23
+ def api_call
24
+ 'zed_index'
25
+ end
26
+
27
+ def default_parameters
28
+ {:output_type => 'outcode'}
29
+ end
30
+
31
+ def valid_output_types
32
+ %w(town outcode county country)
33
+ end
34
+
35
+ end
36
+
37
+ end
@@ -0,0 +1 @@
1
+ {"country":"England","area_name":null,"longitude":-0.146927,"street":null,"town":"","average_values_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/average_prices/NW1?width=400&height=212","latitude":51.5330895,"value_ranges_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/price_bands/NW1?width=400&height=212","value_trend_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/local_type_trends/NW1?width=400&height=212","county":"London","bounding_box":{"latitude_min":"51.518085","longitude_min":"-0.170917","longitude_max":"-0.122937","latitude_max":"51.548094"},"area_values_url":"http://www.zoopla.co.uk/home-values/london/NW1/camden-town-regents-park-marylebone-north","postcode":"NW1","home_values_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/home_value/oc/NW1?width=400&height=212"}
@@ -0,0 +1 @@
1
+ {"country":"England","area_name":null,"longitude":-0.146927,"street":null,"town":"","average_values_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/average_prices/NW1?width=600&height=318","latitude":51.5330895,"value_ranges_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/price_bands/NW1?width=600&height=318","value_trend_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/local_type_trends/NW1?width=600&height=318","county":"London","bounding_box":{"latitude_min":"51.518085","longitude_min":"-0.170917","longitude_max":"-0.122937","latitude_max":"51.548094"},"area_values_url":"http://www.zoopla.co.uk/home-values/london/NW1/camden-town-regents-park-marylebone-north","postcode":"NW1","home_values_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/home_value/oc/NW1?width=600&height=318"}
@@ -0,0 +1 @@
1
+ {"country":"England","area_name":null,"longitude":-0.146927,"street":null,"town":"","average_values_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/average_prices/NW1?width=200&height=106","latitude":51.5330895,"value_ranges_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/price_bands/NW1?width=200&height=106","value_trend_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/local_type_trends/NW1?width=200&height=106","county":"London","bounding_box":{"latitude_min":"51.518085","longitude_min":"-0.170917","longitude_max":"-0.122937","latitude_max":"51.548094"},"area_values_url":"http://www.zoopla.co.uk/home-values/london/NW1/camden-town-regents-park-marylebone-north","postcode":"NW1","home_values_graph_url":"http://www.zoopla.co.uk/dynimgs/graph/home_value/oc/NW1?width=200&height=106"}
@@ -0,0 +1 @@
1
+ {"disambiguation":["Whitechapel, Devon","Whitechapel, Lancashire","Whitechapel, London"],"error_string":"Disambiguation required.","error_code":-1}
@@ -0,0 +1 @@
1
+ {"error_string":"Insufficient arguments","error_code":"1"}
@@ -0,0 +1 @@
1
+ {"error_string":"Requested data is invalid, please refer to documentation","error_code":"5"}
@@ -0,0 +1 @@
1
+ {"error_string":"Unknown location entered.","error_code":"7"}
@@ -0,0 +1 @@
1
+ {"country":"England","area_name":null,"longitude":-0.146927,"highest":[{"zed_index":"5174714","name":"Park Square East, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/park-square-east"},{"zed_index":"3980577","name":"Cambridge Gate, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/cambridge-gate"},{"zed_index":"3909518","name":"Chester Terrace, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/chester-terrace"},{"zed_index":"2899292","name":"Gloucester Gate, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/gloucester-gate"},{"zed_index":"2719681","name":"Regents Park Terrace, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/regents-park-terrace"},{"zed_index":"2698449","name":"Kent Terrace, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/kent-terrace"},{"zed_index":"2463170","name":"Park Village West, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/park-village-west"},{"zed_index":"1917504","name":"Brunswick Place, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/brunswick-place-nw1"},{"zed_index":"1907749","name":"Chester Place, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/chester-place"},{"zed_index":"1881067","name":"York Terrace West, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/york-terrace-west"},{"zed_index":"1800075","name":"Chagford Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/chagford-street"},{"zed_index":"1779054","name":"York Terrace East, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/york-terrace-east"},{"zed_index":"1745053","name":"Cumberland Terrace, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/cumberland-terrace"},{"zed_index":"1737473","name":"Rothwell Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/rothwell-street"},{"zed_index":"1717895","name":"Prince Albert Road, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/prince-albert-road-nw1"},{"zed_index":"1668805","name":"St. Marks Crescent, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/st-marks-crescent"},{"zed_index":"1628394","name":"Chamberlain Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/chamberlain-street"},{"zed_index":"1622213","name":"Berkley Road, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/berkley-road"},{"zed_index":"1614178","name":"Chalcot Crescent, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/chalcot-crescent"},{"zed_index":"1396558","name":"Park Square Mews, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/park-square-mews"}],"street":null,"town":"","lowest":[{"zed_index":"200353","name":"Wrotham Road, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/wrotham-road-nw1"},{"zed_index":"209635","name":"Varndell Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/varndell-street"},{"zed_index":"217475","name":"Maiden Lane, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/maiden-lane-nw1"},{"zed_index":"226860","name":"Pancras Road, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/pancras-road"},{"zed_index":"231922","name":"Augustus Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/augustus-street"},{"zed_index":"236737","name":"Ferdinand Place, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/ferdinand-place"},{"zed_index":"237750","name":"Hampstead Road, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/hampstead-road"},{"zed_index":"239249","name":"Phoenix Road, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/phoenix-road-nw1"},{"zed_index":"240097","name":"George Mews, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/george-mews-nw1"},{"zed_index":"240484","name":"Penfold Place, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/penfold-place"},{"zed_index":"241605","name":"Werrington Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/werrington-street"},{"zed_index":"244254","name":"Purchese Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/purchese-street"},{"zed_index":"244336","name":"Harrington Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/harrington-street"},{"zed_index":"245213","name":"Stanhope Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/stanhope-street"},{"zed_index":"249274","name":"Bridgeway Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/bridgeway-street"},{"zed_index":"251384","name":"Ossulston Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/ossulston-street"},{"zed_index":"252863","name":"Mornington Place, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/mornington-place"},{"zed_index":"253139","name":"Osnaburgh Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/osnaburgh-street"},{"zed_index":"253787","name":"Barker Drive, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/barker-drive"},{"zed_index":"256284","name":"Farrier Street, London NW1","details_url":"http://www.zoopla.co.uk/home-values/london/farrier-street"}],"richlist_url":"http://www.zoopla.co.uk/property/richlist/london/NW1/camden-town-regents-park-marylebone-north","latitude":51.5330895,"county":"London","postcode":"NW1","bounding_box":{"latitude_min":"51.518085","longitude_min":"-0.170917","longitude_max":"-0.122937","latitude_max":"51.548094"}}
@@ -0,0 +1 @@
1
+ {"suggestion":"stoke","error_string":"Unknown location entered.","error_code":"7"}
@@ -0,0 +1 @@
1
+ {"area_url":"http://www.zoopla.co.uk/home-values/london","zed_index_1year":449379,"street":null,"zed_index":"427646","town":"","zed_index_2year":376536,"zed_index_3year":474942,"latitude":51.523591,"postcode":"","zed_index_6month":459057,"country":"England","area_name":null,"longitude":-0.105602,"zed_index_4year":463594,"zed_index_3month":430923,"county":"London","bounding_box":{"latitude_min":"51.363621","longitude_min":"-0.34844","longitude_max":"0.137236","latitude_max":"51.683561"},"zed_index_5year":416328}
@@ -6,8 +6,104 @@ class TestAPI < Test::Unit::TestCase
6
6
  @rentals = Zoopla.new('my_api_key').rentals
7
7
  end
8
8
 
9
+ def test_invalid_output_type
10
+ assert_raise Zoopla::InvalidOutputTypeError do
11
+ @rentals.in({:output_type => :block})
12
+ end
13
+ assert_nothing_raised { @rentals.in({:output_type => "street"}) }
14
+ assert_nothing_raised { @rentals.in({:output_type => :street}) }
15
+ assert_nothing_raised { @rentals.in({:output_type => :postcode}) }
16
+ assert_nothing_raised { @rentals.in({:output_type => :outcode}) }
17
+ assert_nothing_raised { @rentals.in({:output_type => :town}) }
18
+ assert_nothing_raised { @rentals.in({:output_type => :county}) }
19
+ assert_nothing_raised { @rentals.in({:output_type => :country}) }
20
+ assert_nothing_raised { @rentals.in({:output_type => :area}) }
21
+ end
22
+
23
+ def test_disambiguation
24
+ e = assert_raise Zoopla::DisambiguationError do
25
+ @rentals.send(:raise_error_if_necessary, 200, @rentals.send(:parse, api_reply('disambiguation')))
26
+ end
27
+ assert_equal ["Whitechapel, Devon", "Whitechapel, Lancashire", "Whitechapel, London"], e.areas
28
+ end
29
+
30
+ def test_insufficient_argumetns
31
+ assert_raise Zoopla::InsufficientArgumentsError do
32
+ @rentals.send(:raise_error_if_necessary, 200, @rentals.send(:parse, api_reply('insufficient_arguments')))
33
+ end
34
+ end
35
+
36
+ def test_unknown_location_with_suggestion
37
+ e = assert_raise Zoopla::UnknownLocationError do
38
+ @rentals.send(:raise_error_if_necessary, 200, @rentals.send(:parse, api_reply('suggestion')))
39
+ end
40
+ assert_equal 'stoke', e.suggestion
41
+ end
42
+
43
+ def test_unknown_location_without_suggestion
44
+ e = assert_raise Zoopla::UnknownLocationError do
45
+ @rentals.send(:raise_error_if_necessary, 200, @rentals.send(:parse, api_reply('no_suggestion')))
46
+ end
47
+ assert_nil e.suggestion
48
+ end
49
+
50
+ def test_actual_location
51
+ @rentals.send(:extract_actual_location, @rentals.send(:parse, api_reply('postcode')))
52
+ location = @rentals.actual_location
53
+ assert_equal 'London', location.county
54
+ assert_equal 'England', location.country
55
+ assert_equal 'E1W 3TJ', location.postcode
56
+ assert_equal 51.506390, location.bounding_box.latitude_min
57
+ assert_equal 51.506390, location.bounding_box.latitude_max
58
+ assert_equal -0.054738, location.bounding_box.longitude_max
59
+ assert_equal -0.054738, location.bounding_box.longitude_min
60
+ end
61
+
62
+ def test_actual_location_fallback
63
+ @rentals.expects(:fetch_data)
64
+ @rentals.actual_location
65
+ end
66
+
67
+ def test_actual_location_fallback
68
+ @rentals.send(:extract_actual_location, @rentals.send(:parse, api_reply('postcode')))
69
+ @rentals.expects(:fetch_data).never
70
+ @rentals.actual_location
71
+ end
72
+
73
+ def test_deep_parsing_the_reply
74
+ reply = @rentals.send(:parse, api_reply('postcode'))
75
+ listing = reply.listing.first
76
+ assert_equal 11695072, listing.listing_id
77
+ assert_equal 'rent', listing.listing_status
78
+ assert_equal 275, listing.price
79
+ assert_equal 'Atkinson Mcleod', listing.agent_name
80
+ assert_equal '135 Leman Street, Aldgate', listing.agent_address
81
+ assert_equal 'http://static.zoopla.co.uk/zoopla_static_agent_logo_(26302).gif', listing.agent_logo
82
+ assert_match(/^Charming one double bedroom apartment .+Our Ref: rpl\/iupload\/CTL070029$/m, listing.description)
83
+ assert_equal 'http://www.zoopla.co.uk/to-rent/details/11695072', listing.details_url
84
+ assert_equal 'Prospect Place, Wapping Wall, Wapping, London E1W', listing.displayable_address
85
+ assert_equal 'http://content.zoopla.co.uk/18d7d607146d3f0ea8cd46c48b5984084613a8ce.jpg', listing.floor_plan.first
86
+ assert_equal 'Picture No.05', listing.image_caption
87
+ assert_equal 'http://images.zoopla.co.uk/f03d30a35c97bf20825af1db8f9e52e1c936dd42_354_255.jpg', listing.image_url
88
+ assert_equal 51.50639, listing.latitude
89
+ assert_equal(-0.054738, listing.longitude)
90
+ assert_equal 0, listing.num_bathrooms
91
+ assert_equal 1, listing.num_bedrooms
92
+ assert_equal 0, listing.num_floors
93
+ assert_equal 0, listing.num_recepts
94
+ assert_equal 'E1W', listing.outcode
95
+ assert_equal 'London', listing.post_town
96
+ assert_equal 265, listing.price_change.first.price
97
+ assert_equal Date.parse('2010-07-23 19:12:46'), listing.price_change.first.date
98
+ assert_equal 275, listing.price_change.last.price
99
+ assert_equal Date.parse('2011-01-06 19:00:45'), listing.price_change.last.date
100
+ assert_equal 'Flat', listing.property_type
101
+ assert_equal 'Wapping Wall Wapping London', listing.street_name
102
+ assert_equal 'http://images.zoopla.co.uk/f03d30a35c97bf20825af1db8f9e52e1c936dd42_80_60.jpg', listing.thumbnail_url
103
+ end
104
+
9
105
  def test_no_results_returned
10
- number_of_results, reply = @rentals.send(:preprocess, api_reply('empty'))
106
+ number_of_results, reply = @rentals.send(:preprocess, @rentals.send(:parse, api_reply('empty')))
11
107
  assert_equal 0, number_of_results
12
108
  assert_equal [], reply
13
109
  end
@@ -0,0 +1,41 @@
1
+ require 'helper'
2
+
3
+ class TestAreaValueGraphs < Test::Unit::TestCase
4
+
5
+ def setup
6
+ @area_value_graphs = Zoopla.new('my_api_key').area_value_graphs
7
+ end
8
+
9
+ def test_in
10
+ @area_value_graphs.stubs(:fetch_data).returns(@area_value_graphs.send(:parse, api_reply('area_value_graphs')))
11
+ index_set = @area_value_graphs.medium.in({:postcode => 'NW1'})
12
+ assert_equal 'http://www.zoopla.co.uk/home-values/london/NW1/camden-town-regents-park-marylebone-north', index_set.area_values_url
13
+ assert_equal 'http://www.zoopla.co.uk/dynimgs/graph/home_value/oc/NW1?width=400&height=212', index_set.home_values_graph_url
14
+ assert_equal 'http://www.zoopla.co.uk/dynimgs/graph/local_type_trends/NW1?width=400&height=212', index_set.value_trend_graph_url
15
+ assert_equal 'http://www.zoopla.co.uk/dynimgs/graph/price_bands/NW1?width=400&height=212', index_set.value_ranges_graph_url
16
+ assert_equal 'http://www.zoopla.co.uk/dynimgs/graph/average_prices/NW1?width=400&height=212', index_set.average_values_graph_url
17
+ end
18
+
19
+ def test_small_size
20
+ @area_value_graphs.stubs(:fetch_data).returns(@area_value_graphs.send(:parse, api_reply('area_value_graphs_small')))
21
+ index_set = @area_value_graphs.small.in({:postcode => 'NW1'})
22
+ assert_equal 'http://www.zoopla.co.uk/dynimgs/graph/home_value/oc/NW1?width=200&height=106', index_set.home_values_graph_url
23
+ end
24
+
25
+ def test_larse_size
26
+ @area_value_graphs.stubs(:fetch_data).returns(@area_value_graphs.send(:parse, api_reply('area_value_graphs_large')))
27
+ index_set = @area_value_graphs.large.in({:postcode => 'NW1'})
28
+ assert_equal 'http://www.zoopla.co.uk/dynimgs/graph/home_value/oc/NW1?width=600&height=318', index_set.home_values_graph_url
29
+ end
30
+
31
+ def test_invalid_output_type
32
+ assert_raise Zoopla::InvalidOutputTypeError do
33
+ @area_value_graphs.send(:check_output_type, {:output_type => :postcode})
34
+ end
35
+ assert_raise Zoopla::InvalidOutputTypeError do
36
+ @area_value_graphs.send(:check_output_type, {:output_type => :area})
37
+ end
38
+ assert_nothing_raised { @area_value_graphs.send(:check_output_type, {:output_type => :outcode}) }
39
+ end
40
+
41
+ end
@@ -140,6 +140,7 @@ class TestZooplaListings < Test::Unit::TestCase
140
140
  end
141
141
 
142
142
  def test_furnished
143
+ listing_parameter_test(:furnished, 'furnished', {:furnished => 'furnished'})
143
144
  listing_parameter_test(:furnished, 'furnished', {:furnished => 'furnished'})
144
145
  listing_parameter_test(:furnished, 'unfurnished', {:furnished => 'unfurnished'})
145
146
  listing_parameter_test(:furnished, 'part-furnished', {:furnished => 'part-furnished'})
@@ -216,46 +217,14 @@ class TestZooplaListings < Test::Unit::TestCase
216
217
  def test_requesting_multiple_results_pages_transparently
217
218
  mock = mock();
218
219
  mock.expects(:process_listing).times(12);
219
- page1 = @rentals.send :preprocess, api_reply('big_request_page1')
220
- page2 = @rentals.send :preprocess, api_reply('big_request_page2')
220
+ page1 = @rentals.send(:preprocess, @rentals.send(:parse, api_reply('big_request_page1')))
221
+ page2 = @rentals.send(:preprocess, @rentals.send(:parse, api_reply('big_request_page2')))
221
222
  @rentals.stubs(:fetch_data).returns(page1, page2)
222
223
  @rentals.in({:postcode => 'E1W 3TJ'}).within(0.1).price(300..400).each {|listing|
223
224
  mock.process_listing
224
225
  }
225
226
  end
226
227
 
227
- def test_deep_parsing_the_reply
228
- _, reply = @rentals.send(:preprocess, api_reply('postcode'))
229
- listing = reply.first
230
- assert_equal 11695072, listing.listing_id
231
- assert_equal 'rent', listing.listing_status
232
- assert_equal 275, listing.price
233
- assert_equal 'Atkinson Mcleod', listing.agent_name
234
- assert_equal '135 Leman Street, Aldgate', listing.agent_address
235
- assert_equal 'http://static.zoopla.co.uk/zoopla_static_agent_logo_(26302).gif', listing.agent_logo
236
- assert_match(/^Charming one double bedroom apartment .+Our Ref: rpl\/iupload\/CTL070029$/m, listing.description)
237
- assert_equal 'http://www.zoopla.co.uk/to-rent/details/11695072', listing.details_url
238
- assert_equal 'Prospect Place, Wapping Wall, Wapping, London E1W', listing.displayable_address
239
- assert_equal 'http://content.zoopla.co.uk/18d7d607146d3f0ea8cd46c48b5984084613a8ce.jpg', listing.floor_plan.first
240
- assert_equal 'Picture No.05', listing.image_caption
241
- assert_equal 'http://images.zoopla.co.uk/f03d30a35c97bf20825af1db8f9e52e1c936dd42_354_255.jpg', listing.image_url
242
- assert_equal 51.50639, listing.latitude
243
- assert_equal(-0.054738, listing.longitude)
244
- assert_equal 0, listing.num_bathrooms
245
- assert_equal 1, listing.num_bedrooms
246
- assert_equal 0, listing.num_floors
247
- assert_equal 0, listing.num_recepts
248
- assert_equal 'E1W', listing.outcode
249
- assert_equal 'London', listing.post_town
250
- assert_equal 265, listing.price_change.first.price
251
- assert_equal Date.parse('2010-07-23 19:12:46'), listing.price_change.first.date
252
- assert_equal 275, listing.price_change.last.price
253
- assert_equal Date.parse('2011-01-06 19:00:45'), listing.price_change.last.date
254
- assert_equal 'Flat', listing.property_type
255
- assert_equal 'Wapping Wall Wapping London', listing.street_name
256
- assert_equal 'http://images.zoopla.co.uk/f03d30a35c97bf20825af1db8f9e52e1c936dd42_80_60.jpg', listing.thumbnail_url
257
- end
258
-
259
228
  private
260
229
 
261
230
  def listing_parameter_test(param, value, result)
@@ -0,0 +1,26 @@
1
+ require 'helper'
2
+
3
+ class TestPropertyRichList < Test::Unit::TestCase
4
+
5
+ def setup
6
+ @list = Zoopla.new('my_api_key').rich_list
7
+ end
8
+
9
+ def test_list
10
+ @list.stubs(:fetch_data).returns(@list.send(:parse, api_reply('richlist')))
11
+ richlist = @list.in({:area => 'NW1', :output_type => :outcode, :area_type => :streets })
12
+ assert_equal 'http://www.zoopla.co.uk/property/richlist/london/NW1/camden-town-regents-park-marylebone-north', richlist.richlist_url
13
+ assert_equal 'http://www.zoopla.co.uk/property/richlist/london/NW1/camden-town-regents-park-marylebone-north', richlist.url
14
+ highest = richlist.highest
15
+ lowest = richlist.lowest
16
+ assert_equal 20, highest.length
17
+ assert_equal 'Park Square East, London NW1', highest.first.name
18
+ assert_equal 5174714, highest.first.zed_index
19
+ assert_equal 'http://www.zoopla.co.uk/home-values/london/park-square-east', highest.first.details_url
20
+ assert_equal 20, lowest.length
21
+ assert_equal 'Wrotham Road, London NW1', lowest.first.name
22
+ assert_equal 200353, lowest.first.zed_index
23
+ assert_equal 'http://www.zoopla.co.uk/home-values/london/wrotham-road-nw1', lowest.first.details_url
24
+ end
25
+
26
+ end
@@ -0,0 +1,41 @@
1
+ require 'helper'
2
+
3
+ class TestZedIndex < Test::Unit::TestCase
4
+
5
+ def setup
6
+ @zed_index = Zoopla.new('my_api_key').zed_index
7
+ end
8
+
9
+ def test_in
10
+ @zed_index.stubs(:fetch_data).returns(@zed_index.send(:parse, api_reply('zed_index')))
11
+ index_set = @zed_index.in({:area => 'London', :output_type => "town"})
12
+ assert_equal 'http://www.zoopla.co.uk/home-values/london', index_set.area_url
13
+ assert_equal 427646, index_set.latest
14
+ assert_equal 427646, index_set.zed_index
15
+ assert_equal 430923, index_set.zed_index_3month
16
+ assert_equal 459057, index_set.zed_index_6month
17
+ assert_equal 449379, index_set.zed_index_1year
18
+ assert_equal 376536, index_set.zed_index_2year
19
+ assert_equal 474942, index_set.zed_index_3year
20
+ assert_equal 463594, index_set.zed_index_4year
21
+ assert_equal 416328, index_set.zed_index_5year
22
+ end
23
+
24
+ def test_invalid_output_type
25
+ assert_raise Zoopla::InvalidOutputTypeError do
26
+ @zed_index.send(:check_output_type, {:output_type => :street})
27
+ end
28
+ assert_raise Zoopla::InvalidOutputTypeError do
29
+ @zed_index.send(:check_output_type, {:output_type => :postcode})
30
+ end
31
+ assert_raise Zoopla::InvalidOutputTypeError do
32
+ @zed_index.send(:check_output_type, {:output_type => :area})
33
+ end
34
+ assert_nothing_raised { @zed_index.send(:check_output_type, {:output_type => :outcode}) }
35
+ assert_nothing_raised { @zed_index.send(:check_output_type, {:output_type => :town}) }
36
+ assert_nothing_raised { @zed_index.send(:check_output_type, {:output_type => :county}) }
37
+ assert_nothing_raised { @zed_index.send(:check_output_type, {:output_type => :country}) }
38
+ end
39
+
40
+
41
+ end
metadata CHANGED
@@ -2,7 +2,7 @@
2
2
  name: zoopla
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease:
5
- version: 0.2.0
5
+ version: 0.2.2
6
6
  platform: ruby
7
7
  authors:
8
8
  - Evgeny Shadchnev
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
12
 
13
- date: 2011-03-04 00:00:00 +00:00
13
+ date: 2011-03-06 00:00:00 +00:00
14
14
  default_executable:
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
@@ -75,18 +75,35 @@ files:
75
75
  - Rakefile
76
76
  - lib/zoopla.rb
77
77
  - lib/zoopla/api.rb
78
+ - lib/zoopla/area_value_graphs.rb
79
+ - lib/zoopla/errors.rb
78
80
  - lib/zoopla/listings.rb
79
81
  - lib/zoopla/listings/listing.rb
80
82
  - lib/zoopla/listings/rentals.rb
81
83
  - lib/zoopla/listings/sales.rb
84
+ - lib/zoopla/property_rich_list.rb
82
85
  - lib/zoopla/version.rb
86
+ - lib/zoopla/zed_index.rb
87
+ - test/api_replies/area_value_graphs.js
88
+ - test/api_replies/area_value_graphs_large.js
89
+ - test/api_replies/area_value_graphs_small.js
83
90
  - test/api_replies/big_request_page1.js
84
91
  - test/api_replies/big_request_page2.js
92
+ - test/api_replies/disambiguation.js
85
93
  - test/api_replies/empty.js
94
+ - test/api_replies/insufficient_arguments.js
95
+ - test/api_replies/invalid_data.js
96
+ - test/api_replies/no_suggestion.js
86
97
  - test/api_replies/postcode.js
98
+ - test/api_replies/richlist.js
99
+ - test/api_replies/suggestion.js
100
+ - test/api_replies/zed_index.js
87
101
  - test/helper.rb
88
102
  - test/test_api.rb
89
- - test/test_zoopla_listings.rb
103
+ - test/test_area_value_graphs.rb
104
+ - test/test_listings.rb
105
+ - test/test_property_rich_list.rb
106
+ - test/test_zed_index.rb
90
107
  - zoopla.gemspec
91
108
  has_rdoc: true
92
109
  homepage: http://github.com/shadchnev/zoopla
@@ -117,10 +134,23 @@ signing_key:
117
134
  specification_version: 3
118
135
  summary: Access zoopla.co.uk API from ruby scripts
119
136
  test_files:
137
+ - test/api_replies/area_value_graphs.js
138
+ - test/api_replies/area_value_graphs_large.js
139
+ - test/api_replies/area_value_graphs_small.js
120
140
  - test/api_replies/big_request_page1.js
121
141
  - test/api_replies/big_request_page2.js
142
+ - test/api_replies/disambiguation.js
122
143
  - test/api_replies/empty.js
144
+ - test/api_replies/insufficient_arguments.js
145
+ - test/api_replies/invalid_data.js
146
+ - test/api_replies/no_suggestion.js
123
147
  - test/api_replies/postcode.js
148
+ - test/api_replies/richlist.js
149
+ - test/api_replies/suggestion.js
150
+ - test/api_replies/zed_index.js
124
151
  - test/helper.rb
125
152
  - test/test_api.rb
126
- - test/test_zoopla_listings.rb
153
+ - test/test_area_value_graphs.rb
154
+ - test/test_listings.rb
155
+ - test/test_property_rich_list.rb
156
+ - test/test_zed_index.rb