AJAX, JavaScript, PHP e Google maps: Georeferenziazione indirizzi

Questo post ha più di 1 anno. Il contenuto potrebbe essere obsoleto, non più completamente accessibile o mancante di alcune informazioni. In questo articolo ci sono informazioni simili, ma più recenti.

screenshot del programma georeferenziazione indirizziPer concludere il panorama dei possibili utilizzi della classe PHP per georeferenziare indirizzi multipli, vediamo l’impiego della tecnologia AJAX vera e propria.
Come avevo accennato nel precedente articolo, l’approccio non è così lineare per la necessità di invocare più volte l’oggetto XMLHttpRequest, e ancora peggio, per dover gestire le risposte multiple ed asincrone del server. Si rende infatti necessario, non solo creare tanti oggetti AJAX quante sono le richieste, ma anche altrettanti oggetti che gestiscano separatamente le risposte, mantenendo l’handle della chiamata.
Una buona soluzione mi è sembrata quella illustrata in questo articolo, ed è quella che ho adottato per questo esempio.

La pagina html iniziale comprende un form per l’immissione degli indirizzi e un semplice script javascript che, per ogni tag di tipo input, invoca una richiesta AJAX. Ecco il codice della funzione:

<script type="text/javascript" src="MultipleAjaxClassSimple.js"></script> 
<script type="text/javascript">
 
function getFormValues() 
{
  document.getElementById("divResults").innerHTML = '';
  var myForm = document.getElementById("myForm").getElementsByTagName('input');
  var len = myForm.length;
  var params = '';
  for (i = 0; i < len; i++) {
    if(myForm[i].type == 'text'){
      params = myForm[i].value; 
      ajaxSaveTag(params);         
    }        
  }
}    
</script>

Lo script AJAX è composto da quattro funzioni:

  • ajaxSaveTag()
  • httpRequest()
  • initRequest()
  • ReturnSaveTag()

La prima funzione prende come parametro l’indirizzo da georeferenziare, compone una url con la querystring da passare allo script server e infine chiama la seconda funzione httpRequest() che si occupa di instanziare l’oggetto XMLHttpRequest. La terza funzione, initRequest() ha il compito di gestire le risposte del server, invocando i metodi della funzione di callback (la quarta: ReturnSaveTag()), che in realtà è un oggetto. Questo permette di creare tante istanze di callback quante sono le chiamate AJAX.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
// JavaScript Document
function ajaxSaveTag(tag) {
  var url  = 'ajaxSaveTags.php';
  url += '?query='+encodeURIComponent(tag);
  httpRequest("GET",url,1,new ReturnSaveTag());
}
function httpRequest(type,url,asynch,respHandle) {
  var request;
  // mozilla
  if (window.XMLHttpRequest) {
    request = new XMLHttpRequest();
  }
  // internet explorer
  else if (window.ActiveXObject) {
    request = new ActiveXObject("Msxml2.XMLHTTP");
    if (!request) {
      request = new ActiveXObject("Microsoft.XMLHTTP");
    }
  }
  // send request | error
  if (request) {
    initRequest(request,type,url,asynch,respHandle);
  }
  else {
  // ERROR!
  }
}
function initRequest(request,type,url,asynch,respHandle) {
  try {
    respHandle.setReqObj(request);
    request.onreadystatechange = respHandle.goResponse;
    request.open(type,url,asynch);
    request.send(null);
  } catch (errv) {
    // ERROR!
  }
}
function ReturnSaveTag() {
  var reqObj = null;
  this.setReqObj = setReqObj;
  this.goResponse = goResponse;
  function setReqObj(myVal) { reqObj = myVal; }
  function goResponse() {
    var request = reqObj;
    if (request.readyState == 4) {
      if (request.status == 200) {
        // Success!
        var mytext = request.responseText;
        var myDiv = document.getElementById("divResults");
        // display the HTML output
        myDiv.innerHTML = myDiv.innerHTML + mytext;
      } else {
        // ERROR (couldn't find ajax file)
      }
    }
    return true;
  } // end method
}

Lo script lato server ajaxSaveTags.php crea un header che non consenta al browser di utilizzare la cache, raccoglie i dati dalla querystring, utilizza la classe PHP geocodeaddr
per georeferenziare l’indirizzo, ed infine stampa il risultato formattato.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<?php
// make sure the user's browser doesn't cache the result
header('Expires: Wed, 23 Dec 1980 00:30:00 GMT');
header('Last-Modified: ' . gmdate('D, d M Y H:i:s') . ' GMT');
header('Cache-Control: no-cache, must-revalidate');
header('Pragma: no-cache');
require("geocoder4.class.php");
$data = array();
if (!empty($_GET['query']))
 {
  $toGeocode = $_GET['query'];
  $data = array($toGeocode);
 }      
//localhost key:
$gmpKey = "ABQIAAAAzr2EBOXUKnm_...";// Inserire la Google key corretta!
$test = &amp; new geocodeaddr($data,$gmpKey);
$geocodeResults = $test->getAddress();
$res = $geocodeResults[0]['address'].' lat: '.
       $geocodeResults[0]['lat'].' long: '.
       $geocodeResults[0]['lng'].'<br />';
// output the result
echo $res;
?>

Questa è la demo

Conclusioni:

L’utilizzo della tecnologia AJAX ha richiesto un codice un po’ più sofisticato e meno facilmente intuibile rispetto alla soluzione pseudo-AJAX. Sarebbe interessante fare un confronto anche in altre situazioni in cui sia necessario effettuare richieste asincrone al server, e verificare efficienza e robustezza di entrambi con carichi gravosi. Un’ultima curiosità: poiché le risposte del server sono asincrone, può capitare che l’ordine dei risultati non sia lo stesso delle chiamate.

Riferimenti ed approfondimenti:

Questo articolo è stato pubblicato in Informatica e contrassegnato con , , , . Aggiungi ai segnalibri il permalink.