I'm building a website for my client with an e-commerce component. She wants to offer free delivery if the address of the buyer is within 30 driving miles of her home. I know if I go to the URL:
with A being the starting address and B being the ending address it will return the data in which that information is encoded (as some subset of xml I think). Is there a way to do something like this within the backend so the consumer never sees anything and just save the driving distance number to a JS or PHP variable?
I have no experience of this stuff but I would do something along the lines of:
- Submit A and B to your server
- Request the url in php
- Parse the XML on the server however you want
- Respond to client with distance or error message
If its as simple as it sounded there then it shouldn't take too long :-D
I dont know how you would do that but if I get a minute I might try it out myself :-P
You would do an AJAX call to that url with the addresses, parse the responseXML and get the pull the distance out. If you need a more specific example, let me know and I'll type something up quickly. In the meantime, have a look at
Thanks guys, conceptually Ajax is what i was thinking, and I have used it extensively but I'm having some issues with how that would work since when you visit the URL it prompts you to save the file; it's not actually a page rather a downloadable file. Scott, if you have time could you explain or give an example. I've also never parsed something out like this.
Remember that for security reasons (that is preventing cross-site scripting attacks) Ajax requests can only be made to URLs of the same protocol, host and port of the page containing the Ajax request. Some browsers might allow arbitrary URLs, but you shouldn't rely on support for this.
Wouldn't that pose a problem as well?
Obviously your website wont share the same host as google, or you would be google?
Yes, it would. You will need a proxy script, in php or whatever, that does the work of getting the data for you and returning it to you. I will try to write up an thorough example sometime later today.
Scott Prelewicz
Senior Web Developer
COMAND Solutions
I'm having a very boring day at work so I've done this just to see if it would work the way i first proposed...
Code:
$a = "manchester";
$b = "liverpool";
//Create the url
$myurl = "http://maps.google.com/maps?q=from+{$a}+to+{$b}&output=kml";
//Open the url
$f = fopen ($myurl, "r");
//Read the contents
$str = stream_get_contents($f);
//String match the distance
preg_match("/Distance: ([0-9.-]+)/", $str, $distance);
//Respond
echo "$a is ".($distance[1]<30?"less":"more")." than 30miles from $b by car";
If you set that up on your own server, you could use bog standard ajax that you are already familiar with to send the start place and destination, run it through that code i posted and reply again with bog standard ajax.
I used a preg_match rather than parse the xml because:
1) I didnt know how to parse the element containing the distance
2) It works
EDIT: I meant to quote this snippet from php.net
If PHP has decided that filename specifies a registered protocol, and that protocol is registered as a network URL, PHP will check to make sure that allow_url_fopen is enabled. If it is switched off, PHP will emit a warning and the fopen call will fail.
Parsing the XML would not have worked anyway, because it looks like Distance is only used as CDATA in the <description> tag. Not a separate XML tag itself.
This will work fine for cfgcjm -- until they change the description.
In this instance, much better to just use preg_match, but as slaughters said, you'll have to keep track of the xml to see if they change the return format. Being google, I'd feel somewhat safe they'll keep it consistant, but obviously there's no guarantee.
Anyway, here's some client side code (using Prototype):
Code:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<HTML>
<HEAD>
<TITLE> New Document </TITLE>
<META NAME="Generator" CONTENT="EditPlus">
<META NAME="Author" CONTENT="">
<META NAME="Keywords" CONTENT="">
<META NAME="Description" CONTENT="">
<script src="/js/prototype.js"></script>
<script>
function getDistance() {
new Ajax.Request('/distanceProxy.php', {
method:'get',
parameters: $('distanceForm').serialize(true),
onSuccess: function(transport){
var response = transport.responseText || "no response text";
alert(response);
},
onFailure: function(){ alert('Something went wrong...') }
});
return false;
}
</script>
</HEAD>
<BODY>
<form action="" method="post" id="distanceForm" onSubmit="getDistance(); return false;">
<input type="text" name="start" id="start">
<input type="text" name="end" id="end">
<input type="submit" name="submit" id="submit">
</form>
</BODY>
</HTML>
Last edited by ScottPrelewicz; 02-17-2009 at 10:01 AM.
Reason: Change code
Scott Prelewicz
Senior Web Developer
COMAND Solutions
Parsing the XML would not have worked anyway, because it looks like Distance is only used as CDATA in the <description> tag. Not a separate XML tag itself.
Thats why I didnt know how to parse the element :-D
Ok, houston, we have a problem. It works great with your inputs of manchester and liverpool but i went to change them (because i need to eventually input addresses) I changed them to New York NY and Philadelphia PA and it does not return a result. I altered the code slightly but it works for Manchester and liverpool:
Outputs:
manchester is 34.3 miles from liverpool by car
new york ny is miles from philadelphia pa by car
PHP Code:
<?PHP
$a = "new york ny";
$b = "philadelphia pa";
//Create the url
$myurl = "http://maps.google.com/maps?q=from+{$a}+to+{$b}&output=kml";
//Open the url
$f = fopen ($myurl, "r");
//Read the contents
$str = stream_get_contents($f);
//String match the distance
preg_match("/Distance: ([0-9.-]+)/", $str, $distance);
//Respond
echo "$a is ".$distance[1]." miles from $b by car";
?>
You probably need to format those addresses beter. Use commas before the state and put in zipcodes if you can. I didn't test this, just guessing from past experience.
Scott Prelewicz
Senior Web Developer
COMAND Solutions
Bookmarks