qpowell / google_places Goto Github PK
View Code? Open in Web Editor NEWA Ruby wrapper around the Google Places API
License: MIT License
A Ruby wrapper around the Google Places API
License: MIT License
Google Places API now includes a "Reviews" endpoint as of the Google I/O 2012 conference.
I can submit a pull request if it helps but I'm kinda of a newbie programmer, but I can try!
Richard Ortega
I already commented on the comment of someone else earlier but thought it will be better to create an issue addressing this. How do I sanitize the output of say:
@client.spots(-33.8670522, 151.1957362, types: ['restaurant'])
Perhaps an array of objects each with its accessible properties, or grabbing single data with its property
Whenever I try to access any part of the address, all I get is a nilclass.
According to the documentation the id and reference keys are going to be removed. Spot.find method should use the place_id to fetch a Spot instead of the reference.
In addition to searching by type, it should be possible to filter spots by name.
The API documentation specifies that both the search and detail operations return a "price_level" attribute but it isn't being marshalled in to spot objects.
https://developers.google.com/places/documentation/search
Note: The id and reference fields are deprecated as of June 24, 2014. They are replaced by the new place ID, a unique identifier that can be used to compare places and to retrieve information about a place. The Places API currently returns a place_id in all responses, and accepts a placeid in the Place Details and Place Delete requests. Soon after June 24, 2015, the API will stop returning the id and reference fields in responses. Some time later, the API will no longer accept the reference in requests. We recommend that you update your code to use the new place ID instead of id and reference as soon as possible.
Can this be included in the response?
See: Title
The Places Search API docs (https://developers.google.com/places/webservice/search#PlaceSearchResponses) say:
types[]
contains an array of feature types describing the given result. See the list of supported types for more information. XML responses include multiple<type>
elements if more than one type is assigned to the result.
But, when doing the following:
client = GooglePlaces::Client.new(YOUR_GOOGLE_API_KEY)
spot = client.spot("CnRnAAAAafljZfT_KDUT-SkOQxOF9CGOIjBfRzerEKJxz9r-v4URPSq4-nSHFZf0sk_Uz3oq-EMsRp-3aUbs7PxBdSNDX_4IVd1uBbrQdP8ZHN0N-DXo4BhDjlcM1K7IH_x3mgzFmsTEBcfgY2Tza5r9UW_RLhIQ34VFi1yO_QhK-MefdF1C_hoU5Lxkhi_IS_6Oky9m6GUrbp5mWC0")
spot.types # => nil
So, it looks like it's possible for the Places API to not return any types for certain spots. This isn't necessarily something the gem needs to handle, but I'm curious if it would be helpful for others to have this return an empty array vs nil.
Assuming you're displaying these categories in a view or something, you may want to output them like so: @spot.types.join(", ")
. Having this return an empty string (in the case of an array) vs undefined method 'join' for nil:NilClass
would allow you to write code without having to handle special cases where this information may not be available.
Or, I could just be crazy and this issue isn't relevant to anyone else :) Thoughts?
According to https://developers.google.com/console/help/#activatingapis
It seems like if a project is already using OAuth2, then API Keys cannot be used (I do not see the option of generating an API key in google's console). Can we have an option to authenticate using OAuth2?
The APIs represented in the Google APIs Console require that requests include a unique project identifier. This enables the Console to tie a request to a specific project in order to monitor traffic, enforce quotas, and handle billing. Google supports two separate mechanisms to create a unique project identifier: OAuth 2.0 client IDs and API keys.
An OAuth 2.0 client ID can generate an access token for an application that uses the OAuth 2.0 protocol to call Google APIs. The token contains an identifier that uniquely identifies your application, and allows the Console to properly attribute corresponding API traffic, quotas, and billing data to the Console project that the API is enabled within.
An API key is a unique key that you generate using the Console. When your application needs to call an API that's enabled in this project, the application passes this key into all API requests as a key=API_key parameter. Use of this key does not require any user action or consent, does not grant access to any account information, and is not used for authorization.
If you are only calling APIs that do not require user data, such as the Google Custom Search API, then API keys may be simpler to implement. However, if your application already uses an OAuth 2.0 access token, then there is no need to generate an API key as well. In fact, Google ignores passed API keys if an OAuth 2.0 access token is already associated with the corresponding project.
hey,
is it possible to add next page token on textsearch?
thx
Thank you for creating this gem.
How can we search for spots/places by name and/or by type?
I tried the following:
@client.spots(lat, lng, {:name => 'italian', :type => 'restaurant', :radius => 10000})
Changing radius affects the results, but not name and type.
type — Restricts the results to places matching the specified type. Only one type may be specified (if more than one type is provided, all types following the first entry are ignored). See the list of supported types.
Hi,
first of all, thank you for the wrapper. Appreciate your work.
I have a question regarding the documentation:
This option should be used with care, as it adds an additional API call for EACH spot in the collection. E.g. a spots collection of 100 spots will use 101 API calls when the detail: true option is set.
Shouldn't that be 200 API calls then? List of 100 spots. EACH spot an extra call for the details, makes 200 calls, right?
I can't get #spots_by_bounds to actually query within a supplied bounding box. I don't think the Google API currently supports this feature.
I tried actually running the stubbed out example from the specs, and that doesn't work as expected, it just returns results from around the US, none in the supplied bounding box: https://gist.github.com/gbuesing/a28932ac8dcb64c5bcf6
Nor can I find any mention of a bounds parameter in the Google Places API documentation: https://developers.google.com/places/web-service/search#TextSearchRequests . It does appear to be a feature of the client-side JS library, but not the server-side API.
I notice that this feature was added in February: #74 . Did Google change the API since then?
Can anybody else get this to actually work? If not, I'd be happy to pull together a pull request that drops this no-longer supported feature.
Hi, I am calling client.spots_by_pagetoken(pagetoken) method to get next 20 results but I am getting the error as Invalid Request Error? @marceldegraaf Can you please guide?
Is there anyway to pull more than 20+ per request? I know there is a next page token, but does that work with this gem?
Hi,
sorry, I don't find any information.
all is working fine, but when ask for spot.website , url, city etc it is always nil.
I get one image, different types, address and the spot name.
Do I have to pay for this website, url .. info on Google places?
Thanks, Michael
/home/oleg/.rbenv/versions/2.1.4/lib/ruby/gems/2.1.0/gems/google_places-0.27.0/lib/google_places/request.rb:325:in `parsed_response': GooglePlaces::InvalidRequestError (GooglePlaces::InvalidRequestError)
for code
require 'google_places'
API_KEY = "AIzaSyDCjp3CMfuSvKftEnyY_zSIXNkjpNbPM2Y"
@client = GooglePlaces::Client.new(API_KEY)
spots = @client.spots_by_query('Gap, London')
puts spots
next_page_token = spots.last.nextpagetoken
puts next_page_token
next_spots = @client.spots_by_pagetoken(next_page_token)
We can load more with miltipage: true
require 'google_places'
API_KEY = "AIzaSyDCjp3CMfuSvKftEnyY_zSIXNkjpNbPM2Y"
@client = GooglePlaces::Client.new(API_KEY)
spots = @client.spots_by_query('Gap, London', multipage: true)
puts spots
next_page_token = spots.last.nextpagetoken
puts next_page_token
next_spots = @client.spots_by_pagetoken(next_page_token)
Hello,
Thanks for putting this gem together!
I have a small problem. How can I get the results from the query?
I use your examples and I get no venues back (I tried other coordinates too).
This is my code:
@client = GooglePlaces::Client.new(MY_KEY)
@client.spots(-33.8670522, 151.1957362, :types => 'restaurant')
render :json => @client, :status => :success
This is my result:
{
"api_key": "MY_KEY",
"options": {}
}
I think the location data needs to be cast to strings a little more explicitly. For example when I try and query the location "-0.00006560", the string representation is in scientific notation. I've fixed this in my own code by casting the floats before hand, but it would be nice if the gem did it automatically.
eg: @client.spots(("%.8f"%place.lat),("%.8f"%place.lon),:radius=>1000)
Thanks for the very useful gem!
Is there a convenient way to serialize the output? I can json-encode the result, but GooglePlaces::Photo
objects, for one, include their API key. This would make it much easier to cache the result. Unless it's obvious how to do this.
Iam trying to find by giving restaurant but i couldn't get restaurant image but i was getting only default image the link is https://maps.gstatic.com/mapfiles/place_api/icons/restaurant-71.png
is this an issue or do i need to pay for google to get images display?
v1.0.0
While making a request to the Google Places API, we received a response from Google with a status of 502, with the following body:
<html lang=en>
<meta charset=utf-8>
<meta name=viewport content="initial-scale=1, minimum-scale=1, width=device-width">
<title>Error 502 (Server Error)!!1</title>
<style>
*snip*
</style>
<a href=//www.google.com/><span id=logo aria-label=Google></span></a>
<p><b>502.</b> <ins>That’s an error.</ins>
<p>The server encountered a temporary error and could not complete your request.<p>Please try again in 30 seconds. <ins>That’s all we know.</ins>
...
This error is unhandled by the library, and a JSON::ParserError
is thrown by
google_places/lib/google_places/request.rb
Line 351 in cb33d8b
I do not see "profile_photo_url" in GooglePlaces::Review as it is in original response from Google places API. May you add it?
#<GooglePlaces::Review:0x007fb9462e2640 @rating=5, @type=nil, @author_name="Таня ЯЯ", @author_url="https://www.google.com/maps/contrib/102709091342507193601/reviews", @text="", @time=1474563857>
As stated by @railsondhi:
Is there a way we can improve the address_components attribute? Right now it just returns an array of components (eg street address, city, postal code, province). Right now we're leaving it to the end user to get their necessary data from the array, but wouldn't it be nice if this gem had attributes like street_address, city, postal code, and province so we make less work for the end user? Problem is not every Spot has their components organized in the same way. One Spot could have address_components[1] be "city," and another Spot could have it be "road." Silly design from Google.
Do I need to use a separate API to convert ZipCode to Lat/Long in order to send to Google Places API?
Hey Marcel,
What are your thoughts on caching results from the Places API?
Thanks to my thorough test suites, I'm quickly depleting my quota from Google. Should we build in caching into the Gem?
Perhaps we could use Redis? Here's a nice tutorial I found: http://jimneath.org/2011/03/24/using-redis-with-ruby-on-rails.html
@client = GooglePlaces::Client.new(API_KEY)
@client.predictions_by_input(
'San F',
lat: 0.0,
lng: 0.0,
radius: 20000000,
types: 'geocode',
language: I18n.locale,
)
undefined method `predictions_by_input' for #GooglePlaces::Client:0x0000000625bcb8
Hello, I noticed that spot.city, spot.rating, spot.opening_hours, etc. are always nil. Is this due to a change in the API?
The Google Places API is expensive when charged for every single autocomplete and places detail request. Luckily, they have added Session pricing to their rate model.
To do this, users provide a session token that is used for every "group" of autocomplete requests. A "group" is considered to be a series of Places Autocomplete requests that result in a Place Details request.
So instead of being charged for every single request, and then the Places Detail request, you only get charged for the single Places Detail request so long as the proceeding Autocomplete requests shared the same session token.
A session token can be any string, though Google recommends UUID 4.
I suggest allowing the user to specify the session token on each call to the client through the options hash as opposed to setting the token during the initialization phase
RubyGems.org doesn't report a license for your gem. This is because it is not specified in the gemspec of your last release.
via e.g.
spec.license = 'MIT'
# or
spec.licenses = ['MIT', 'GPL-2']
Including a license in your gemspec is an easy way for rubygems.org and other tools to check how your gem is licensed. As you can image, scanning your repository for a LICENSE file or parsing the README, and then attempting to identify the license or licenses is much more difficult and more error prone. So, even for projects that already specify a license, including a license in your gemspec is a good practice. See, for example, how rubygems.org uses the gemspec to display the rails gem license.
There is even a License Finder gem to help companies/individuals ensure all gems they use meet their licensing needs. This tool depends on license information being available in the gemspec. This is an important enough issue that even Bundler now generates gems with a default 'MIT' license.
I hope you'll consider specifying a license in your gemspec. If not, please just close the issue with a nice message. In either case, I'll follow up. Thanks for your time!
Appendix:
If you need help choosing a license (sorry, I haven't checked your readme or looked for a license file), GitHub has created a license picker tool. Code without a license specified defaults to 'All rights reserved'-- denying others all rights to use of the code.
Here's a list of the license names I've found and their frequencies
p.s. In case you're wondering how I found you and why I made this issue, it's because I'm collecting stats on gems (I was originally looking for download data) and decided to collect license metadata,too, and make issues for gemspecs not specifying a license as a public service :). See the previous link or my blog post about this project for more information.
Right now if something goes wrong google_places just returns an empty array. In my case the API Key was wrong, and had to add some debug code in the library to figure that out.
It would be nice if google_places would throw an error or something.
Hi!
I was wondering where to get this "spot identifier" from a location? Is this the "cid" within the google url?
if yes then this doesn't work for me since I get:
irb(main):024:0> @client.spot(12386347495841372973) GooglePlaces::InvalidRequestError: GooglePlaces::InvalidRequestError from /home/user/.rvm/gems/ruby-2.0.0-p0/gems/google_places-0.12.0/lib/google_places/request.rb:245:in `parsed_response' from /home/user/.rvm/gems/ruby-2.0.0-p0/gems/google_places-0.12.0/lib/google_places/request.rb:84:in `spot' from /home/user/.rvm/gems/ruby-2.0.0-p0/gems/google_places-0.12.0/lib/google_places/spot.rb:113:in `find' from /home/user/.rvm/gems/ruby-2.0.0-p0/gems/google_places-0.12.0/lib/google_places/client.rb:119:in `spot' from (irb):24 from /home/user/.rvm/rubies/ruby-2.0.0-p0/bin/irb:13:in `'
the "cid" was retrieved from this URL:
https://maps.google.de/maps?ie=UTF8&cid=12386347495841372973&q=Burj+al+Arab&iwloc=A&gl=DE&hl=de
best
p
The original API have facility for searching for cities in a specific country by passing the parameter "types=(cities)&components=country:in". I did not find such a facility in this gem.
Hi,
All my request generates spots with postalcodes nil.it is a bug?
Federico
When search for spots by Name, it would be helpful to exclude certain Types from the results.
For example, if you search for "italian" spots, you may want to exclude type "grocery_or_supermarket." Or if you search for "volkswagen" spots, you may want to exclude type "car_repair" if you're only looking for dealers.
I tried the following in spot.rb:
response['results'].map do |result|
self.new(result) unless result.types.include?('grocery_or_supermarket')
end
But I got the following error:
NoMethodError: undefined method `types' for #<Hash:0x000001011e6ed0>
The result review rating is incorrect:
#<GooglePlaces::Review:0x007fa831eddc18
@author_name="Patryk D.",
@author_url="https://plus.google.com/103575742885777451053",
@rating=0,
@text="A friend ...",
@time=1400145408,
@type="overall">
It seems to be using the rating of the aspect rather then the actual review rating:
{"aspects"=>[{"rating"=>0, "type"=>"overall"}],
"author_name"=>"Patryk D.",
"author_url"=>"https://plus.google.com/103575742885777451053",
"language"=>"en",
"rating"=>1,
"text"=>"A friend ...",
"time"=>1400145408}
is there a way to use zip code to find city and state?
Hi there,
I happened to realise that I cannot get the phone number for any results...
@formatted_phone_number=nil, @international_phone_number=nil
Is there a way to get them?
Direct api finds the spot for 'Kinetron Inc.' as searched below:
but the gem's spot method as below returns empty:
spots = @client.spots(40.2414420, -74.046970, :name=> "Kinetron Inc.")
However, it works with the first word:
@client.spots(40.2414420, -74.046970, :name=> "Kinetron")
How do we get it working with multiple words in name?
Google Places Detail provides a field called user_ratings_total
.
Is there a reason why this is not an attribute on the Spot
model?
Thank you!
The Prediction initialize method doesn't set all of the fields from the result—namely the structured_formatting
fields:
Can these be added to the initializer?
@client.spot(@place_id) throws a argument error for some of the place ids
When I view what the methods return, I see this. What is it?
@formatted_phone_number=nil, @international_phone_number=nil, @formatted_address="Man Mo Temple, 124-126 Hollywood Rd, Central, Hong Kong", @address_components=nil, @street_number=nil, @street=nil, @city=nil, @region=nil, @postal_code=nil, @Country=nil, @Rating=nil, @price_level=nil, @opening_hours=nil, @url=nil, @CID=0, @website=nil, @zagat_reviewed=nil, @zagat_selected=nil, @Aspects=[], @review_summary=nil, @photos=[], @reviews=[], @nextpagetoken=nil, @events=[], @utc_offset=nil>,
I tried to marshal a result set so that I could store it in a DB with Marshal.dump(GOOGLE_PLACES.spots_by_query(my_query))
- but that resulted in: ArgumentError (string contains null byte)
So, after poking around GooglePlaces::Spot.initialize
I see that json_result_object
isn't stored on the Spot anywhere, which I suppose, if it were available, could be used to reconstitute the object later on, along with the api key. e.g. GooglePlaces::Spot.new(result_json_object_from_database, my_api_key)
I could submit a PR to make the raw results a bit more accessible, but curious to get the maintainers thoughts first.
Thanks!
Thank you for making this gem.
With a GooglePlaces::Clinet#spot of 0.24.0, error occurs.
ex.
clinet = GooglePlaces::Client.new(API_KEY, true)
client.spot('Cp...69w')
=> GooglePlaces::InvalidRequestError: GooglePlaces::InvalidRequestError
from google_places-0.24.0/lib/google_places/request.rb:325:in `parsed_response'
Please a fix.
According to google docs When google.maps.places.RankBy.PROMINENCE is specified, the radius parameter is required.
rankby = options.delete(:rankby)
radius = options.delete(:radius) || 1000 if rankby.nil?
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.