Changeset 391

Show
Ignore:
Timestamp:
10/09/06 12:03:02 (2 years ago)
Author:
sgillies
Message:

strip out dependence on the Yahoo geocoding web API. Replace with geopy (#68, #183).

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • PleiadesGeocoder/trunk/CHANGES.txt

    r356 r391  
    11Changes 
    22======= 
     3 
     4All ticket numbers are relative to http://icon.stoa.org/trac/pleiades/tickets. 
    35 
    460.6 - 2 October 2006 
     
    1416- New @@geo logical view replaces all previous Python skin helper scripts. 
    1517 
     180.6.1 - 9 Ocober 2006 
     19--------------------- 
     20- Switch to use of geopy for geocoding (ticket #68, #183). 
     21 
  • PleiadesGeocoder/trunk/DEPENDENCIES.txt

    r356 r391  
    22============ 
    33 
    4 - ElementTree or lxml 
     4- geopy: http://exogen.case.edu/projects/geopy/ 
    55 
  • PleiadesGeocoder/trunk/README.txt

    r356 r391  
    22================ 
    33 
    4 A geocoder for Plone locations based on the Yahoo API. A geocoder converts 
    5 text locations such as "Fort Collins, Colorado" to spatial coordinates. Other 
     4A geocoder for Plone locations based on geopy. A geocoder converts text 
     5locations such as "Fort Collins, Colorado" to spatial coordinates. Other 
    66geocoding backends could be supported in the future. 
    77 
     
    1515------------ 
    1616 
    17 PleiadesGeocoder is installed like any other Plone product. It depends on  
    18 ElementTree or lxml. Your choice. Until we have a release, we will describe 
    19 installing from SVN. 
     17PleiadesGeocoder is installed like any other Plone product. Until we have a 
     18release, we will describe installing from SVN. 
    2019 
    21201. Checkout PleiadesGeocoder 
     
    2827 
    29283. Give the portal_geocoder a trial run via portal_geocoder/geocodeForm. 
    30  
    31 4. Register for a Yahoo application id and enter it in 
    32    portal_geocoder/manage_propertiesForm. 
    3329 
    3430 
     
    5450Funding for the creation of this software was provided by a grant from the  
    5551U.S. National Endowment for the Humanities (http://www.neh.gov). 
     52 
  • PleiadesGeocoder/trunk/__init__.py

    r227 r391  
    3232 
    3333from config import product_name 
    34 from geocode import YahooGeocoder 
     34from geocode import Geocoder 
    3535 
    3636skin_globals=globals() 
    3737registerDirectory('skins', skin_globals) 
    3838 
    39 tools = (YahooGeocoder,) 
     39tools = (Geocoder,) 
    4040 
    4141def initialize(context): 
  • PleiadesGeocoder/trunk/geocode.py

    r227 r391  
    2828# =========================================================================== 
    2929 
    30 import urllib 
    31  
    32 # Import etree from elementtree or lxml 
    33 try: 
    34     from elementtree import ElementTree as etree 
    35 except: 
    36     from lxml import etree 
    37  
    3830from Globals import InitializeClass 
    3931from OFS.SimpleItem import SimpleItem 
     
    4739from Products.PageTemplates.PageTemplateFile import PageTemplateFile 
    4840 
    49 class YahooGeocoder(UniqueObject, PropertyManager, SimpleItem): 
     41from geopy.geocoders import Google 
     42 
     43 
     44class Geocoder(UniqueObject, PropertyManager, SimpleItem): 
    5045     
    51     """A proxy for the Yahoo geocoder
     46    """A proxy for geocoders using geopy
    5247    """ 
    5348    meta_type = product_name 
     
    5651    security = ClassSecurityInfo() 
    5752     
    58     def __init__(self, appid='YahooDemo'): 
     53    def __init__(self, **kwargs): 
    5954        """Create a new instance. 
    60  
    61         Parameters 
    62         ---------- 
    63         appid : string 
    64             Application id. See  
    65             http://developer.yahoo.com/faq/index.html#appid 
    6655        """ 
    67         self._serverurl = 'http://api.local.yahoo.com' 
    68         self._service = '/MapsService/V1' 
    69         self._url = self._serverurl + self._service 
    70         self.manage_addProperty('appid', 'YahooDemo', 'string') 
     56        self._g = Google(resource='maps') 
    7157 
    7258    security.declareProtected(view_permission, 'geocode') 
     
    8268 
    8369        """ 
    84         request = "%s/%s" % (self._url, 'geocode') 
    85         data = {'appid':    getattr(self, 'appid', 'YahooDemo'), 
    86                 'location': location } 
    87         u = urllib.urlopen(request, urllib.urlencode(data)) 
    88         response = u.read() 
    89         u.close() 
    90  
    91         infoset = etree.fromstring(response) 
    92          
    93         # Error? 
    94         error = infoset.find('{urn:yahoo:api}Error') 
    95         if error: 
    96             raise GeocoderError, error.find('{urn:yahoo:api}Message').text 
    9770             
    9871        # Get results 
    9972        records = [] 
    100         results = infoset.findall('{urn:yahoo:maps}Result') 
     73        results = [x for x in self._g.geocode(location, exactly_one=False)] 
    10174        for result in results: 
    10275            r = {} 
    103             r['precision'] = result.get('precision', None) 
    104             r['warning'] = result.get('warning', None) 
    105             r['lat'] = result.find('{urn:yahoo:maps}Latitude').text 
    106             r['lon'] = result.find('{urn:yahoo:maps}Longitude').text 
    107             r['city'] = result.find('{urn:yahoo:maps}City').text 
    108             r['state'] = result.find('{urn:yahoo:maps}State').text 
    109             r['country'] = result.find('{urn:yahoo:maps}Country').text 
     76            r['place'] = result[0] 
     77            r['lat'] = result[1][0] 
     78            r['lon'] = result[1][1] 
    11079            records.append(r) 
    11180        return records 
  • PleiadesGeocoder/trunk/tests/test_tool.py

    r176 r391  
    99 
    1010from Products.PleiadesGeocoder.interfaces.simple import IGeoItemSimple 
    11 from Products.PleiadesGeocoder import YahooGeocoder 
     11from Products.PleiadesGeocoder import Geocoder 
    1212 
    1313class ExistenceTest(PloneTestCase.PloneTestCase): 
    14  
    1514    def afterSetUp(self): 
    16         self.id = YahooGeocoder.id 
    17  
     15        self.id = Geocoder.id 
    1816    def testGeocoderToolExists(self): 
    1917        self.failUnless(self.id in self.portal.objectIds()) 
    2018        
    21         
     19class GoogleGeocodeTest(PloneTestCase.PloneTestCase): 
     20    def afterSetUp(self): 
     21        self.g = self.portal.portal_geocoder 
     22    def test_ftc(self): 
     23        results = self.g.geocode('Fort Collins, CO') 
     24        r = results[0] 
     25        self.assertEqual(r['place'], u'Fort Collins, CO', results) 
     26        self.assertAlmostEqual(r['lat'], 40.585278) 
     27        self.assertAlmostEqual(r['lon'], -105.083889) 
     28    def test_london(self): 
     29        results = self.g.geocode('London, England') 
     30        r = results[0] 
     31        self.assertEqual(r['place'], u'London, UK', results) 
     32        self.assertAlmostEqual(r['lat'], 51.500197) 
     33        self.assertAlmostEqual(r['lon'], -0.126197) 
     34    def test_goteborg(self): 
     35        results = self.g.geocode('Goteborg, Sweden') 
     36        r = results[0] 
     37        self.assertEqual(r['place'], u'Goteborg, Sweden', results) 
     38        self.assertAlmostEqual(r['lat'], 57.690996) 
     39        self.assertAlmostEqual(r['lon'], 11.971496) 
     40 
     41      
    2242def test_suite(): 
    2343    from unittest import TestSuite, makeSuite 
    2444    suite = TestSuite() 
    2545    suite.addTest(makeSuite(ExistenceTest)) 
     46    suite.addTest(makeSuite(GoogleGeocodeTest)) 
    2647    return suite 
    2748 
  • PleiadesGeocoder/trunk/version.txt

    r227 r391  
    1 0.6 
     10.6.1 
    22 
  • PleiadesGeocoder/trunk/www/geocode.pt

    r112 r391  
    8383  <tr class="search-results"> 
    8484    <td class="search-results" align="left" valign="top"> 
    85       <div class="form-label">Precision</div> 
    86     </td> 
    87     <td class="search-results" align="left" valign="top"> 
    8885      <div class="form-label">Location</div> 
    8986    </td> 
     
    9188      <div class="form-label">Lat/Long</div> 
    9289    </td> 
    93     <td class="search-results" align="left" valign="top"> 
    94       <div class="form-label">Warning</div> 
    95     </td> 
    9690  </tr> 
    9791 
    9892  <tbody class="search-results" tal:repeat="result results"> 
    9993      <tr tal:condition="repeat/result/odd" class="search-result-odd"> 
    100           <td class="search-results" tal:content="string:${result/precision}">Precision</td> 
    101           <td class="search-results" tal:content="string:${result/city}, ${result/state}, ${result/country}">Location</td> 
     94          <td class="search-results" tal:content="string:${result/place}">Location</td> 
    10295          <td class="search-results" tal:content="string:${result/lat} ${result/lon}">Lat/Long</td> 
    103           <td class="search-results" tal:content="string:${result/warning}">Warning</td> 
    10496      </tr> 
    10597      <tr tal:condition="repeat/result/even" class="search-result-even"> 
    106           <td class="search-results" tal:content="string:${result/precision}">Precision</td> 
    107           <td class="search-results" tal:content="string:${result/city}, ${result/state}, ${result/country}">Location</td> 
     98          <td class="search-results" tal:content="string:${result/place}">Location</td> 
    10899          <td class="search-results" tal:content="string:${result/lat} ${result/lon}">Lat/Long</td> 
    109           <td class="search-results" tal:content="string:${result/warning}">Warning</td> 
    110100      </tr> 
    111101  </tbody>