From 0c8b942fb482285195f2554d7e523e24cfa87627 Mon Sep 17 00:00:00 2001 From: Edward Samuel Pasaribu Date: Wed, 23 Sep 2015 21:54:00 +0800 Subject: [PATCH 1/5] Support JRuby 9.0.0.0 --- .travis.yml | 5 ++++- CHANGELOG.md | 4 ++++ Gemfile | 20 ++++++++++++++++++++ Rakefile | 13 ++++++++----- google_maps_service.gemspec | 10 +--------- 5 files changed, 37 insertions(+), 15 deletions(-) diff --git a/.travis.yml b/.travis.yml index daa651c..38bb10c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,5 +1,8 @@ language: ruby rvm: + - ruby-head - 2.2 - 2.1 - - 2.0.0 \ No newline at end of file + - 2.0.0 + - jruby-head + - jruby-9000 \ No newline at end of file diff --git a/CHANGELOG.md b/CHANGELOG.md index 36138f6..a7a692d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,9 @@ # Changelog +## HEAD + +* Support JRuby 9.0.0.0 + ## 0.4.0 * Use required positional and optional named parameters (_breaking changes_) diff --git a/Gemfile b/Gemfile index a240910..0395ba2 100644 --- a/Gemfile +++ b/Gemfile @@ -2,3 +2,23 @@ source 'https://rubygems.org' # Specify your gem's dependencies in google_maps_service.gemspec gemspec + +group :development do + gem 'bundler', '~> 1.6' + gem 'rake', '~> 10.0' + gem 'rspec', '~> 3.3' + gem 'simplecov', '~> 0.10' + gem 'coveralls', '~> 0.8.2' + gem 'webmock', '~> 1.21' +end + +platforms :ruby do + group :development do + gem 'yard', '~> 0.8' + gem 'redcarpet', '~> 3.2' + end +end + +if ENV['RAILS_VERSION'] + gem 'rails', ENV['RAILS_VERSION'] +end diff --git a/Rakefile b/Rakefile index 79705c4..b8cba83 100644 --- a/Rakefile +++ b/Rakefile @@ -1,12 +1,15 @@ -require "bundler/gem_tasks" -require "rspec/core/rake_task" -require "yard" +require 'bundler/gem_tasks' +require 'rspec/core/rake_task' RSpec::Core::RakeTask.new task :default => :spec task :test => :spec -YARD::Rake::YardocTask.new do |t| - t.files = ['lib/**/*.rb'] +unless defined?(JRUBY_VERSION) + require 'yard' + + YARD::Rake::YardocTask.new do |t| + t.files = ['lib/**/*.rb'] + end end \ No newline at end of file diff --git a/google_maps_service.gemspec b/google_maps_service.gemspec index d3ae90a..ce59ce1 100644 --- a/google_maps_service.gemspec +++ b/google_maps_service.gemspec @@ -20,13 +20,5 @@ Gem::Specification.new do |spec| spec.add_runtime_dependency 'multi_json', '~> 1.11' spec.add_runtime_dependency 'hurley', '~> 0.1' - spec.add_runtime_dependency 'retriable', '~> 2.0', '>= 2.0.2' - spec.add_development_dependency 'bundler', '~> 1.7' - spec.add_development_dependency 'rake', '~> 10.0' - spec.add_development_dependency 'yard', '~> 0.8.7.6' - spec.add_development_dependency 'redcarpet', '~> 3.3' - spec.add_development_dependency 'rspec', '~> 3.3' - spec.add_development_dependency 'simplecov', '~> 0.10.0' - spec.add_development_dependency 'coveralls', '~> 0.8.2' - spec.add_development_dependency 'webmock', '~> 1.21', '>= 1.21.0' + spec.add_runtime_dependency 'retriable', '~> 2.0' end From 6bf1e880159383300baaf4482d37ccdec11aeeab Mon Sep 17 00:00:00 2001 From: Edward Samuel Pasaribu Date: Wed, 23 Sep 2015 22:32:08 +0800 Subject: [PATCH 2/5] Add more documentation --- lib/google_maps_service.rb | 2 ++ lib/google_maps_service/apis/roads.rb | 2 +- lib/google_maps_service/client.rb | 5 ++++- lib/google_maps_service/errors.rb | 3 +++ 4 files changed, 10 insertions(+), 2 deletions(-) diff --git a/lib/google_maps_service.rb b/lib/google_maps_service.rb index dc0c106..f96003b 100644 --- a/lib/google_maps_service.rb +++ b/lib/google_maps_service.rb @@ -42,6 +42,8 @@ class << self # @return [Object] attr_accessor :connection + # Configure global parameters. + # @yield [config] def configure yield self true diff --git a/lib/google_maps_service/apis/roads.rb b/lib/google_maps_service/apis/roads.rb index 9d05fd2..770b98c 100644 --- a/lib/google_maps_service/apis/roads.rb +++ b/lib/google_maps_service/apis/roads.rb @@ -126,7 +126,7 @@ def extract_roads_body(response) # Check response body for error status. # - # @param [Hurley::Response] body Response object. + # @param [Hurley::Response] response Response object. # @param [Hash] body Response body. def check_roads_body_error(response, body) error = body[:error] diff --git a/lib/google_maps_service/client.rb b/lib/google_maps_service/client.rb index 83863a9..5c10be8 100644 --- a/lib/google_maps_service/client.rb +++ b/lib/google_maps_service/client.rb @@ -199,6 +199,7 @@ def get(path, params, base_url: DEFAULT_BASE_URL, accepts_client_id: true, custo # # @param [String] path The path portion of the URL. # @param [Hash] params URL parameters. + # @param [Boolean] accepts_client_id Sign the request using API {#keys} instead of {#client_id}. # # @return [String] def generate_auth_url(path, params, accepts_client_id) @@ -260,8 +261,10 @@ def check_response_status_code(response) # Check response body for error status. # - # @param [Hurley::Response] body Response object. + # @param [Hurley::Response] response Response object. # @param [Hash] body Response body. + # + # @return [void] def check_body_error(response, body) case body[:status] when 'OK', 'ZERO_RESULTS' diff --git a/lib/google_maps_service/errors.rb b/lib/google_maps_service/errors.rb index 36302de..642ba0b 100644 --- a/lib/google_maps_service/errors.rb +++ b/lib/google_maps_service/errors.rb @@ -7,6 +7,9 @@ class BaseError < StandardError # @return [Hurley::Response] attr_reader :response + # Initialize error + # + # @param [Hurley::Response] response HTTP response. def initialize(response = nil) @response = response end From 600a2a922eb961e8ae8ce6cb51dc60bff0da927c Mon Sep 17 00:00:00 2001 From: Edward Samuel Pasaribu Date: Wed, 23 Sep 2015 22:49:28 +0800 Subject: [PATCH 3/5] Refactoring --- lib/google_maps_service/client.rb | 59 +++++++++++++++++-------------- 1 file changed, 33 insertions(+), 26 deletions(-) diff --git a/lib/google_maps_service/client.rb b/lib/google_maps_service/client.rb index 5c10be8..0a6e634 100644 --- a/lib/google_maps_service/client.rb +++ b/lib/google_maps_service/client.rb @@ -94,8 +94,6 @@ class Client # connection: Hurley::HttpCache.new(HurleyExcon::Connection.new) # ) # - # - # # @option options [String] :key Secret key for accessing Google Maps Web Service. # Can be obtained at https://developers.google.com/maps/documentation/geocoding/get-api-key#key. # @option options [String] :client_id Client id for using Maps API for Work services. @@ -111,17 +109,13 @@ class Client # By default, the default Hurley's HTTP client connection (Net::Http) will be used. # See https://github.com/lostisland/hurley/blob/master/README.md#connections. def initialize(**options) - @key = options[:key] || GoogleMapsService.key - @client_id = options[:client_id] || GoogleMapsService.client_id - @client_secret = options[:client_secret] || GoogleMapsService.client_secret - @retry_timeout = options[:retry_timeout] || GoogleMapsService.retry_timeout || 60 - @queries_per_second = options[:queries_per_second] || GoogleMapsService.queries_per_second - @request_options = options[:request_options] || GoogleMapsService.request_options - @ssl_options = options[:ssl_options] || GoogleMapsService.ssl_options - @connection = options[:connection] || GoogleMapsService.connection - - # - initialize_qps if @queries_per_second + [:key, :client_id, :client_secret, + :retry_timeout, :queries_per_second, + :request_options, :ssl_options, :connection].each do |key| + self.instance_variable_set("@#{key}".to_sym, options[key] || GoogleMapsService.instance_variable_get("@#{key}")) + end + + initialize_query_tickets end # Get the current HTTP client. @@ -133,10 +127,12 @@ def client protected # Initialize QPS queue. QPS queue is a "tickets" for calling API - def initialize_qps - @qps_queue = SizedQueue.new @queries_per_second - @queries_per_second.times do - @qps_queue << 0 + def initialize_query_tickets + if @queries_per_second + @qps_queue = SizedQueue.new @queries_per_second + @queries_per_second.times do + @qps_queue << 0 + end end end @@ -175,18 +171,11 @@ def get(path, params, base_url: DEFAULT_BASE_URL, accepts_client_id: true, custo url = base_url + generate_auth_url(path, params, accepts_client_id) Retriable.retriable timeout: @retry_timeout, on: RETRIABLE_ERRORS do |try| - # Get/wait the request "ticket" if QPS is configured - # Check for previous request time, it must be more than a second ago before calling new request - if @qps_queue - elapsed_since_earliest = Time.now - @qps_queue.pop - sleep(1 - elapsed_since_earliest) if elapsed_since_earliest.to_f < 1 - end - begin + request_query_ticket response = client.get url ensure - # Release request "ticket" - @qps_queue << Time.now if @qps_queue + release_query_ticket end return custom_response_decoder.call(response) if custom_response_decoder @@ -194,6 +183,24 @@ def get(path, params, base_url: DEFAULT_BASE_URL, accepts_client_id: true, custo end end + # Get/wait the request "ticket" if QPS is configured. + # Check for previous request time, it must be more than a second ago before calling new request. + # + # @return [void] + def request_query_ticket + if @qps_queue + elapsed_since_earliest = Time.now - @qps_queue.pop + sleep(1 - elapsed_since_earliest) if elapsed_since_earliest.to_f < 1 + end + end + + # Release request "ticket". + # + # @return [void] + def release_query_ticket + @qps_queue << Time.now if @qps_queue + end + # Returns the path and query string portion of the request URL, # first adding any necessary parameters. # From 72cbe2bb6d1e96ee6fa19d77598da8777c1936ee Mon Sep 17 00:00:00 2001 From: Edward Samuel Pasaribu Date: Wed, 23 Sep 2015 23:20:42 +0800 Subject: [PATCH 4/5] Add more test coverage --- lib/google_maps_service/client.rb | 7 ++-- spec/google_maps_service/client_spec.rb | 55 +++++++++++++++++++++++++ 2 files changed, 58 insertions(+), 4 deletions(-) diff --git a/lib/google_maps_service/client.rb b/lib/google_maps_service/client.rb index 0a6e634..4c98c89 100644 --- a/lib/google_maps_service/client.rb +++ b/lib/google_maps_service/client.rb @@ -140,13 +140,14 @@ def initialize_query_tickets # @return [Hurley::Client] def new_client client = Hurley::Client.new + client.request_options.query_class = Hurley::Query::Flat + client.request_options.redirection_limit = 0 + client.header[:user_agent] = user_agent client.connection = @connection if @connection @request_options.each_pair {|key, value| client.request_options[key] = value } if @request_options @ssl_options.each_pair {|key, value| client.ssl_options[key] = value } if @ssl_options - client.request_options.query_class = Hurley::Query::Flat - client.header[:user_agent] = user_agent client end @@ -261,8 +262,6 @@ def check_response_status_code(response) raise GoogleMapsService::Error::ClientError.new(response), 'Invalid request' when 500..600 raise GoogleMapsService::Error::ServerError.new(response), 'Server error' - else - raise ArgumentError, 'Invalid response status code' end end diff --git a/spec/google_maps_service/client_spec.rb b/spec/google_maps_service/client_spec.rb index c5cdb01..2933386 100644 --- a/spec/google_maps_service/client_spec.rb +++ b/spec/google_maps_service/client_spec.rb @@ -107,6 +107,17 @@ end end + context 'with unknown api error' do + before(:example) do + stub_request(:get, /https:\/\/maps.googleapis.com\/maps\/api\/geocode\/.*/) + .to_return(:status => 200, headers: { 'Content-Type' => 'application/json' }, body: '{"status":"UNKNOWN_ERROR"}') + end + + it 'should raise GoogleMapsService::Error::ApiError' do + expect { client.geocode('Sydney') }.to raise_error GoogleMapsService::Error::ApiError + end + end + context 'with server error and then success' do before(:example) do stub_request(:get, /https:\/\/maps.googleapis.com\/maps\/api\/geocode\/.*/) @@ -120,6 +131,50 @@ end end + context 'with server error' do + before(:example) do + stub_request(:get, /https:\/\/maps.googleapis.com\/maps\/api\/geocode\/.*/) + .to_return(:status => 500, body: 'Internal server error.') + end + + it 'should raise GoogleMapsService::Error::ServerError' do + expect { client.geocode('Sydney') }.to raise_error GoogleMapsService::Error::ServerError + end + end + + context 'with unauthorized status code error' do + before(:example) do + stub_request(:get, /https:\/\/maps.googleapis.com\/maps\/api\/geocode\/.*/) + .to_return(:status => 401, body: 'Unauthorized.') + end + + it 'should raise GoogleMapsService::Error::ClientError' do + expect { client.geocode('Sydney') }.to raise_error GoogleMapsService::Error::ClientError + end + end + + context 'with client error' do + before(:example) do + stub_request(:get, /https:\/\/maps.googleapis.com\/maps\/api\/geocode\/.*/) + .to_return(:status => 400, body: 'Bad request.') + end + + it 'should raise GoogleMapsService::Error::ClientError' do + expect { client.geocode('Sydney') }.to raise_error GoogleMapsService::Error::ClientError + end + end + + context 'with redirect error' do + before(:example) do + stub_request(:get, /https:\/\/maps.googleapis.com\/maps\/api\/geocode\/.*/) + .to_return(:status => 301, headers: { 'location' => 'https://maps2.googleapis.com' } ) + end + + it 'should raise GoogleMapsService::Error::RedirectError' do + expect { client.geocode('Sydney') }.to raise_error GoogleMapsService::Error::RedirectError + end + end + context 'with connection failed' do before(:example) do stub_request(:get, /https:\/\/maps.googleapis.com\/maps\/api\/geocode\/.*/) From 569cf23c5ed4ba1dfc72bfd398067a2693d08853 Mon Sep 17 00:00:00 2001 From: Edward Samuel Pasaribu Date: Wed, 23 Sep 2015 23:29:33 +0800 Subject: [PATCH 5/5] Bump version to 0.4.1 --- CHANGELOG.md | 3 ++- lib/google_maps_service/version.rb | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index a7a692d..086cdb7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,8 +1,9 @@ # Changelog -## HEAD +## 0.4.1 * Support JRuby 9.0.0.0 +* Refactoring and more test coverage ## 0.4.0 diff --git a/lib/google_maps_service/version.rb b/lib/google_maps_service/version.rb index 2d64b5d..d7d91dd 100644 --- a/lib/google_maps_service/version.rb +++ b/lib/google_maps_service/version.rb @@ -1,6 +1,6 @@ module GoogleMapsService # GoogleMapsService gem version - VERSION = '0.4.0' + VERSION = '0.4.1' # Current operating system # @private