<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Eric Martin &#187; PHP</title>
	<atom:link href="http://www.ericmmartin.com/tag/php/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.ericmmartin.com</link>
	<description></description>
	<lastBuildDate>Thu, 22 Apr 2010 15:28:47 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0</generator>
		<item>
		<title>CakePHP 1.2 RC2 &#8211; Apache Crash on Vista</title>
		<link>http://www.ericmmartin.com/cakephp-12-rc2-apache-crash-on-vista/</link>
		<comments>http://www.ericmmartin.com/cakephp-12-rc2-apache-crash-on-vista/#comments</comments>
		<pubDate>Tue, 01 Jul 2008 04:45:54 +0000</pubDate>
		<dc:creator>Eric Martin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Bugs]]></category>
		<category><![CDATA[Frameworks]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://www.ericmmartin.com/?p=44</guid>
		<description><![CDATA[In my spare time (yeah, right), I've been busy developing a web application using CakePHP. I ran into a problem tonight that I wanted to share, in case anyone else happens to run into something similar. After making some changes to my app, I went to test it out, only to get an Vista notification [...]]]></description>
			<content:encoded><![CDATA[<p>In my spare time (yeah, right), I've been busy developing a web application using <a href="http://www.cakephp.org">CakePHP</a>. I ran into a problem tonight that I wanted to share, in case anyone else happens to run into something similar.</p>
<p>After making some changes to my app, I went to test it out, only to get an Vista notification stating that httpd.exe had shut down unexpectedly. I checked my Event Viewer Application logs and found an Error with the following details:</p>
<pre><code>Faulting application httpd.exe, version 2.2.6.0, time stamp 0x46deb625,
faulting module ntdll.dll, version 6.0.6001.18000, time stamp 0x4791a7a6,
exception code 0xc00000fd, fault offset 0x00065950, process id 0x998,
application start time 0x01c8db31c2d05070.</code></pre>
<p>After a bit of debugging and scratching my head, I remembered that I had deleted a "view helper" file that I had created, but forgot to remove the reference to it (<code>var $helpers = array()</code>) from my app_controller.php file...doh!</p>
<p>I am a bit surprised that CakePHP wasn't able to catch this problem since it seems to catch so many other "missing" situations. Perhaps there is a way that CakePHP can prevent the issue...</p>
<div class="note">Update: this issue was already a <a href="https://trac.cakephp.org/ticket/5010">reported bug</a> and looks like it is due to an infinate recursion when trying to load a helper that does not exist.</div>
]]></content:encoded>
			<wfw:commentRss>http://www.ericmmartin.com/cakephp-12-rc2-apache-crash-on-vista/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Traffic charts for my commute</title>
		<link>http://www.ericmmartin.com/traffic-charts-for-my-commute/</link>
		<comments>http://www.ericmmartin.com/traffic-charts-for-my-commute/#comments</comments>
		<pubDate>Sun, 09 Sep 2007 20:41:36 +0000</pubDate>
		<dc:creator>Eric Martin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://www.ericmmartin.com/traffic-charts-for-my-commute/</guid>
		<description><![CDATA[When I changed jobs, my commute changed from mostly surface streets to mostly highway. I-80 is notoriously congested and I wanted to strategically plan my commute to avoid as much traffic as possible. I started by watching traffic online and then found Traffic.com, where I could create custom drives and receive alerts, etc. Pretty cool...but [...]]]></description>
			<content:encoded><![CDATA[<p>When I changed jobs, my commute changed from mostly <a href="http://maps.google.com/maps?f=d&amp;hl=en&amp;geocode=&amp;saddr=Rocklin,+CA&amp;daddr=Data+Dr,+Rancho+Cordova,+CA+95670&amp;sll=37.0625,-95.677068&amp;sspn=60.551768,113.730469&amp;ie=UTF8&amp;z=11&amp;om=1" target="_blank">surface</a> streets to mostly <a href="http://maps.google.com/maps?f=d&amp;hl=en&amp;geocode=&amp;saddr=Rocklin,+CA&amp;daddr=Howe+Ave,+Sacramento,+CA+95825&amp;sll=38.687475,-121.256735&amp;sspn=0.236899,0.44426&amp;ie=UTF8&amp;ll=38.68819,-121.330261&amp;spn=0.236898,0.44426&amp;z=11&amp;om=1" target="_blank">highway</a>. I-80 is notoriously congested and I wanted to strategically plan my commute to avoid as much traffic as possible.</p>
<p>I started by watching traffic online and then found <a href="http://www.traffic.com" target="_blank">Traffic.com</a>, where I could create custom drives and receive alerts, etc. Pretty cool...but I wanted a way to SEE traffic trends, so I designed a way to get data from Traffic.com and to then display that data in a graph.</p>
<p>Traffic.com offers a <a href="http://en.wikipedia.org/wiki/RSS" target="_blank">RSS</a> feed, so my plan was to use data from that feed to generate the graphs. So, I signed up at Traffic.com and created two custom drives; "Home to Work" and "Work to Home". Next I created a database and tables to hold the data:</p>
<p><span id="more-5"></span></p>
<pre><code>CREATE DATABASE `traffic`;
CREATE TABLE `data` (
`time` int(11) NOT NULL,
`route_id` tinyint(3) NOT NULL,
`jam_factor` decimal(4,2) NOT NULL,
`num_incidents` tinyint(2) NOT NULL,
KEY `route_id` (`route_id`)
);
CREATE TABLE `route` (
`route_id` int(11) NOT NULL auto_increment,
`name` varchar(20) NOT NULL,
PRIMARY KEY  (`route_id`)
);
</code></pre>
<p>Next, I created a <a href="http://en.wikipedia.org/wiki/Crontab" target="_blank">cron</a> job that retrieved traffic data from the feed every 15 minutes:</p>
<pre><code>#!/usr/local/bin/php -q

&lt;?php

$db = 'traffic';
$user = 'username';
$pass = 'password';

// Connect and select database
mysql_connect('localhost', $user, $pass) or die('Could not connect: ' . mysql_error());
mysql_select_db($db) or die('Could not select database');

retrieveTrafficData();

function retrieveTrafficData() {
    $rssUrl = 'http://rss.traffic.com/rss.xml?c=XXX';
    $rssXml = file_get_contents($rssUrl);
    $xml = new SimpleXMLElement($rssXml);

    foreach ($xml-&gt;channel[0]-&gt;item as $item) {

        $time = strtotime($item-&gt;pubDate);
        $description = $item-&gt;description;

        $data = split('-', $description);

        $route = trim($data[0]);
        $jf = split(':', str_replace(' ', '', $data[2]));
        $inc = split(':', str_replace(' ', '', $data[3]));
        $inc = preg_replace('/(.*)/', '', $inc);

        $route_id = getRouteId($route);

        $insert = "INSERT INTO data (time, route_id, jam_factor, num_incidents) VALUES ('$time', $route_id, $jf[1], $inc[1]);";
        mysql_query($insert) or die('Route data insert failed: ' . mysql_error());
    }
}

function getRouteId($route_name) {
    // look for route_id
    $query = "SELECT route_id FROM route WHERE name = '$route_name';";
    $result = mysql_query($query) or die('RouteId query failed: ' . mysql_error());

    if (mysql_num_rows($result) &lt; 1) {
        // insert route_id
        $insert = "INSERT INTO route (name) VALUES ('$route_name');";
        mysql_query($insert) or die('Route name insert failed: ' . mysql_error());
        $id = mysql_insert_id();
    } else {
        $row = mysql_fetch_assoc($result);
        $id = $row['route_id'];
    }
    return $id;
}
?&gt;
</code></pre>
<p>Now that I had the data, I needed to find a way to display it in a graph. I looked at a few existing graph libraries and ended up writing my own...which was very basic. I put up a site and used AJAX to call a PHP script that retrieves the data from the database and returns it in JSON format. It worked, but it wasn't anything fancy...</p>
<p>About a month later, I stumbled upon <a href="http://simile.mit.edu/timeplot/" target="_blank">Timeplot</a>. The library is very impressive but the only problem was that it didn't support JSON as a data format. So, I added the ability to use JSON as a data source for the graphs:</p>
<pre><code>/*
 * Mimic the timeplot.loadText function
 * - Only needed to change eventSource.loadText to eventSource.loadJSON
 */
Timeplot._Impl.prototype.loadJSON=function(url,separator,eventSource,filter){
    if(this._active){
        var tp=this;

        var fError=function(statusText,status,xmlhttp){
            tp.hideLoadingMessage();
            $('#my-timeplot').empty().html("&lt;span class='error'&gt;Failed to load JSON data from " url ". Error: " statusText "&lt;/span");
        };

        var fDone=function(xmlhttp){
            try{
                if(xmlhttp.responseText.replace(/([|])/g,'').length&gt;0){ // added to check for empty result set
                    eventSource.loadJSON(xmlhttp.responseText,separator,url,filter);
                }
                else {
                    $('#my-timeplot').empty().html("&lt;span class='error'&gt;No data found&lt;/span&gt;");
                }
            }catch(e){
                SimileAjax.Debug.exception(e);
            }finally{
                tp.hideLoadingMessage();
            }
        };

        this.showLoadingMessage();
        window.setTimeout(function(){SimileAjax.XmlHttp.get(url,fError,fDone);},0);
    }
}

/*
 * Mimic the eventSource.loadText function
 * - Do not parse all data, only the JSON value when creating an evt
 * - Parse the JSON into an Object
 */
Timeplot.DefaultEventSource.prototype.loadJSON=function(jsonText,separator,url,filter){
    if(jsonText==null){
        return;
    }

    var data = jsonText.parseJSON(); // parse JSON into an Object

    this._events.maxValues=new Array();
    var base=this._getBaseURL(url);

    var dateTimeFormat='iso8601';
    var parseDateTimeFunction=this._events.getUnit().getParser(dateTimeFormat);

    var added=false;

    if(filter){
        data=filter(data);
    }

    if(data){
        for(var i=0;i&lt;data.length;i  ){
            var row=data[i];
            if(row.date){
                var evt=new Timeplot.DefaultEventSource.NumericEvent(
                    parseDateTimeFunction(row.date),
                    this._parseJSONValue(row.value,separator)
                );
                this._events.add(evt);
                added=true;
            }
        }
    }

    if(added){
        this._fire('onAddMany',[]);
    }
}

/*
 * Turn the JSON value into an array so that it can be correctly processed
 * by Timeplot
 */
Timeplot.DefaultEventSource.prototype._parseJSONValue=function(value,separator){
    value=value.replace(/rn?/g,'n');
    var pos=0;
    var len=value.length;
    var line=[];
    while(pos&lt;len){
        var nextseparator=value.indexOf(separator,pos);
        var nextnline=value.indexOf('n',pos);
        if(nextnline&lt;0)nextnline=len;
        if(nextseparator&gt;-1&amp;&amp;nextseparator&lt;nextnline){
            line[line.length]=value.substr(pos,nextseparator-pos);
            pos=nextseparator 1;
        }else{
            line[line.length]=value.substr(pos,nextnline-pos);
            pos=nextnline 1;
            break;
        }
    }
    if(line.length&lt;0)return;
    return line;
}
</code></pre>
<p>Throw it all together and <a href="http://www.ericmmartin.com/traffic/">here is the final result</a>!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.ericmmartin.com/traffic-charts-for-my-commute/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>PHP Bug &#8211; glob(), GLOB_BRACE, and Windows paths</title>
		<link>http://www.ericmmartin.com/php-bug-glob-glob_brace-and-windows-paths/</link>
		<comments>http://www.ericmmartin.com/php-bug-glob-glob_brace-and-windows-paths/#comments</comments>
		<pubDate>Sun, 02 Sep 2007 20:26:39 +0000</pubDate>
		<dc:creator>Eric Martin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Bugs]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://ericmmartin.com/general/php-bug-glob-glob_brace-and-windows-paths/</guid>
		<description><![CDATA[I stumbled upon a PHP framework called Kohana, which is based on CodeIgniter. I've used CI a bit in the past and thought I'd give Kohana a whirl. I downloaded the latest code and tried to run it on a Windows XP machine. Well, when I brought up the site, I got an error: Fatal [...]]]></description>
			<content:encoded><![CDATA[<p>I stumbled upon a PHP framework called <a href="http://kohanaphp.com/" target="_blank">Kohana</a>, which is based on <a href="http://codeigniter.com/" target="_blank">CodeIgniter</a>. I've used CI a bit in the past and thought I'd give Kohana a whirl. I downloaded the latest code and tried to run it on a Windows XP machine.</p>
<p>Well, when I brought up the site,  I got an error:</p>
<pre><code>Fatal error: Unable to locate the requested file, log.php in &lt;system_path&gt;/system/core/Kohana.php on line 408
</code></pre>
<p>After a lot of digging, I found that there was a glob() call that was not behaving correctly. I narrowed it down to what I believe to be a <a href="http://bugs.php.net/bug.php?id=42501" target="_blank">bug</a> in PHP with the <a href="http://us3.php.net/glob" target="_blank">glob() function</a>, using the GLOB_BRACE flag, and using a pattern that includes a colon (as in <code>{c:/firstFolderToCheck,c:/secondFolderToCheck}</code>).</p>
<p>Assuming it turns out to be valid, I'm surprised that it hasn't been found/reported before...</p>
]]></content:encoded>
			<wfw:commentRss>http://www.ericmmartin.com/php-bug-glob-glob_brace-and-windows-paths/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>
