2 Copyright (c) 2013, Los Alamos National Security, LLC
5 Redistribution and use in source and binary forms, with or without modification, are permitted provided that the
6 following conditions are met:
8 * Redistributions of source code must retain the above copyright notice, this list of conditions and the following
10 * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the
11 following disclaimer in the documentation and/or other materials provided with the distribution.
12 * Neither the name of Los Alamos National Security, LLC nor the names of its contributors may be used to endorse or
13 promote products derived from this software without specific prior written permission.
15 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
16 INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
18 SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
19 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
20 WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
21 THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 from requests_oauthlib import OAuth1Session
26 SEARCH_API_URL = 'http://api.yelp.com/v2/search'
27 BUSINESS_API_URL = 'http://api.yelp.com/v2/business/%s'
30 class YelpAPI(object):
33 This class implements the complete Yelp 2.0 API. It offers access to both the Search API and
34 Business API. It is simple and completely extensible since it dynamically takes arguments. This will
35 allow it to continue working even if Yelp changes the spec. The only thing that should cause this to break
36 is if Yelp changes the URL scheme.
39 class YelpError(Exception):
42 This class is used for all non-API errors. For example, this exception will be raised if a non-JSON-parseable
43 response from Yelp is received.
47 class YelpAPIError(Exception):
50 This class is used for all API errors. For a list of all possible Yelp API errors, see
51 http://www.yelp.com/developers/documentation/v2/errors.
55 def __init__(self, consumer_key, consumer_secret, token, token_secret):
56 self._yelp_session = OAuth1Session(consumer_key, consumer_secret, token, token_secret)
59 def _get_clean_parameters(kwargs):
61 Clean the parameters by filtering out any parameters that have a None value.
63 return dict((k, v) for k, v in kwargs.items() if v is not None)
65 def search_query(self, **kwargs):
67 This function implements the Yelp Search API (http://www.yelp.com/developers/documentation/v2/search_api).
68 Arbitrary keywords can be passed in, and a dynamically-generated dict of businesses will be returned.
70 parameters = YelpAPI._get_clean_parameters(kwargs)
71 response = self._yelp_session.get(SEARCH_API_URL, params=parameters)
73 # raise YelpError if Yelp returns invalid JSON or something other than JSON
75 response_json = response.json()
76 except ValueError as e:
77 raise self.YelpError(e)
79 # Yelp can return one of many different API errors, so check for one of them
80 # possible errors: http://www.yelp.com/developers/documentation/v2/errors
81 if 'error' in response_json:
82 if 'field' in response_json['error']:
83 raise self.YelpAPIError(response_json['error']['id'], '%s [field=%s]' % (response_json['error']['text'], response_json['error']['field']))
85 raise self.YelpAPIError(response_json['error']['id'], response_json['error']['text'])
87 # we got a good response, so return
90 def business_query(self, id, **kwargs):
92 Similar to search_query, this function implements the Yelp Business API (http://www.yelp.com/developers/documentation/v2/business).
93 A mandatory business ID must be passed in, as well as any arbitrary keywords allowed by Yelp. A single dict will be returned for the
97 raise ValueError('A valid business ID must be given.')
99 parameters = YelpAPI._get_clean_parameters(kwargs)
100 response = self._yelp_session.get(BUSINESS_API_URL % id, params=parameters)
102 # Yelp currently returns a 404 HTML page if an invalid business ID is provided, so check for that
104 response_json = response.json()
106 raise self.YelpError('Unable to parse JSON from Yelp response. This is likely caused by an invalid business ID [id=%s].' % id)
108 # we got a good response, so return