# Using custom or alternate geocoders

TransparentMaps custom Geocoder creation guide

TransparentMaps supports both the Google Maps API Geocoder and the Yahoo! Geocoder API. Currently the Google Maps API Geocoder provides geocoding services for street addresses in over 60 countries. However, since geocoding accuracy will vary dramatically from location to location, or may not be available at all for your location, you may find the need to use a different geocoding service. This guide will provide some basic instructions for creating your own custom geocoder script.

The script must take the input from TransparentMaps and then connect to its specified geocoder API and obtain the results. The script then must return the results to TransparentMaps in a specific format so it can parse the data and use it properly.

Naming requirements for your custom geocoder:

Your custom geocoding script file MUST be named other_geocoder.inc.php and placed inside the /addons/transparentmaps/geocoders/ folder.

Within your custom geocoder script file you MUST have a function named other_geocoder which will obtain the coordinates from the external geocoding service and return that information back to TransparentMaps. You can have other functions within in your geocoder script file that the other_geocoder() function relies upon, however only other_geocoder() will manage the input and output to TransparentMAPS.

example function framework:

<?php
      function other_geocoder($address, $address2, $address3, $address4, $city, $state, $zip, $country, $key) {
           //setup your return array. Set the ['encoded'] key to 'yes' if geocoding is successful
           $data_arr = array();
           $data_arr['longitude']='';
           $data_arr['latitude']='';
           $data_arr['encoded'] = 'no';

           //your code goes here

           return $data_arr
      }
?>

The function's variables should be mostly self explanatory. $address through $country are automatically derived from your settings in OR's Site Config -> Listings tab-> Map Settings. A Country field, if not set in Site Config will be automatically obtained via the Default Country value set on the TMAPS API/Geocoder tab. The $key variable is the value for the Alternate Geocoder Key you have saved on the TMAPS API/Geocoder Configuration tab. If your geocoding service does not require a key, it can be left empty in TMAPs.

The data returned from the function: other_geocoder() must contain an array with the following keys:

$data_arr['longitude'] - The longitude coordinates for your listing.

$data_arr['latitude'] - The latitude coordinates for your listing.

$data_arr['encoded'] - yes or no, to inform TransparentMaps if the geocoding was successful or not.

Custom geocoding function example for http://geocod.io/ (opens new window) geocoding service.

other_geocoder.inc.php

<?php
// (C)2015 Transparent Technologies, Inc.
// this custom geocoder function for geocode.io requires TransparentMaps v3.1.1 or newer
// you must obtain a free or paid geocode.io API key to use this
function other_geocoder($address, $address2, $address3, $address4, $city, $state, $zip, $country, $key) {
    global $api;
    if ($key =='') {
        die('Fatal error: API Key required for geocod.io');
    }

    //setup the return array
    $data_arr['longitude']='';
    $data_arr['latitude']='';
    $data_arr['encoded'] = 'no';

    //build up the street address
    $gaddress = $address;
    if ($address2 != '') {
        $gaddress .= ' ' . $address2;
    }
    if ($address3 != '') {
        $gaddress .= ' ' . $address3;
    }
    if ($address4 != '') {
        $gaddress .= ' ' . $address4;
    }
    $gaddress= urlencode($gaddress);

    if ($city != '') {
        $gcity = '&city='.urlencode($city);
    }
    if ($state != '') {
        $gstate = '&state='.urlencode($state);
    }
    if ($zip != '') {
        $gzip ='&postal_code='.urlencode($zip);
    }

    $geocoder_url = 'https://api.geocod.io/v1/geocode?street=' . $gaddress.$gcity.$gstate.$gzip.'&api_key='.$key;

    //initialize curl
    $link = curl_init ();
    curl_setopt ($link, CURLOPT_URL, $geocoder_url);
    curl_setopt ($link, CURLOPT_VERBOSE, 1);
    curl_setopt ($link, CURLOPT_SSL_VERIFYPEER, 0);
    curl_setopt ($link, CURLOPT_SSL_VERIFYHOST, 0);
    curl_setopt ($link, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt ($link, CURLOPT_MAXREDIRS, 6);
    curl_setopt ($link, CURLOPT_CONNECTTIMEOUT, 30);
    curl_setopt ($link, CURLOPT_TIMEOUT, 60);

    $results = curl_exec ($link);

    //get the HTTP return response
    $info = curl_getinfo($link);

    if (empty($info['http_code'])) {
            curl_close ($link);
            die("No connection could be established to geocod.io geocoder");
    }
    else {
        $result_array = json_decode($results,true);
         switch($info['http_code']){
            case '200':
                //success! assign the coordinates to our return array, and set the encoded flag
                $data_arr['longitude']=$result_array['results'][0]['location']['lng'];
                $data_arr['latitude']=$result_array['results'][0]['location']['lat'];
                $data_arr['encoded'] = 'yes';
            break;
            case '403':
                die($info['http_code'] .' Invalid geocod.io API key or access denied');
            break;
            case '422':
                $api->load_local_api('log__log_create_entry',array('log_api_command'=>'GEOCOD.IO', 'log_message'=> $info['http_code'] .' '.$result_array['error'] .' '. $gaddress.$gcity.$gstate.$gzip));
            break;
            case '500':
                die($info['http_code'] .' geocod.io server error. It\'s not you.');
            break;
            default:
                die('Undocumented Error Code');
         }
    }
    curl_close ($link);
    return $data_arr;
}
?>

Custom geocoding function example for Mapquest https://developer.mapquest.com/ (opens new window) geocoding service.

other_geocoder.inc.php

<?php
// (C)2015 Transparent Technologies, Inc.
// this custom geocoder function for mapquest requires TransparentMaps v3.1.1 or newer
// you must obtain a free or paid Mapquest API key to use this
function other_geocoder($address, $address2, $address3, $address4, $city, $state, $zip, $country, $key) {
    global $api;
    if ($key =='') {
        die('Fatal error: API Key required for Mapquest geocoder');
    }

    //setup the return array
    $data_arr['longitude']='';
    $data_arr['latitude']='';
    $data_arr['encoded'] = 'no';

    //build up the street address
    $gaddress = $address;
    if ($address2 != '') {
        $gaddress .= ' ' . $address2;
    }
    if ($address3 != '') {
        $gaddress .= ' ' . $address3;
    }
    if ($address4 != '') {
        $gaddress .= ' ' . $address4;
    }
    $gaddress= urlencode($gaddress);

    if ($city != '') {
        $gcity = '&city='.urlencode($city);
    }
    if ($state != '') {
        $gstate = '&state='.urlencode($state);
    }
    if ($zip != '') {
        $gzip ='&postalCode='.urlencode($zip);
    }
    if ($country != '') {
        $gcountry ='&country='.urlencode($country);
    }

    $geocoder_url = 'http://www.mapquestapi.com/geocoding/v1/address?street=' . $gaddress.$gcity.$gstate.$gzip.$gcountry.'&key='.$key.'&maxResults=1';
    //initialize curl
    $link = curl_init ();
    curl_setopt ($link, CURLOPT_URL, $geocoder_url);
    curl_setopt ($link, CURLOPT_VERBOSE, 1);
    curl_setopt ($link, CURLOPT_SSL_VERIFYPEER, 0);
    curl_setopt ($link, CURLOPT_SSL_VERIFYHOST, 0);
    curl_setopt ($link, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt ($link, CURLOPT_MAXREDIRS, 6);
    curl_setopt ($link, CURLOPT_CONNECTTIMEOUT, 30);
    curl_setopt ($link, CURLOPT_TIMEOUT, 60);

    $results = curl_exec ($link);

    //get the HTTP return response
    $info = curl_getinfo($link);

    if (empty($info['http_code'])) {
            curl_close ($link);
            die("No connection could be established to Mapquest geocoder");
    }
    else {
        $result_array = json_decode($results,true);
         switch($result_array['info']['statuscode']){
            case '0':
                //success! assign the coordinates to our return array, and set the encoded flag
                $data_arr['longitude']=$result_array['results'][0]['locations'][0]['latLng']['lng'];
                $data_arr['latitude']=$result_array['results'][0]['locations'][0]['latLng']['lat'];
                $data_arr['encoded'] = 'yes';
            break;
            case '400':
                $api->load_local_api('log__log_create_entry',array('log_api_command'=>'MAPQUEST ERROR ', 'log_message'=> $result_array['info']['statuscode'] .' '.$result_array['info']['messages'][0] .'<br /> '. $gaddress.$gcity.$gstate.$gzip));
            break;
            case '403':
                die($result_array['info']['statuscode'] .' Invalid Mapquest API key or access denied');
            break;
            case '500':
                die($result_array['info']['statuscode'] .' Mapquest server error. It\'s not you.');
            break;
            default:
                die('Undocumented Error Code, or bad API key');
         }
    }
    curl_close ($link);
    return $data_arr;
}
?>