<?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>Tony Thomas &#187; PHP</title>
	<atom:link href="http://anthonygthomas.com/tag/php/feed/" rel="self" type="application/rss+xml" />
	<link>http://anthonygthomas.com</link>
	<description>Father to two, husband to one, web developer and musician.</description>
	<lastBuildDate>Fri, 11 Nov 2011 14:00:07 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3</generator>
		<item>
		<title>An Unexpected Problem with CakePHP and Email Elements</title>
		<link>http://anthonygthomas.com/2010/05/24/an-unexpected-problem-with-cakephp-and-email-elements/</link>
		<comments>http://anthonygthomas.com/2010/05/24/an-unexpected-problem-with-cakephp-and-email-elements/#comments</comments>
		<pubDate>Mon, 24 May 2010 21:27:51 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[CakePHP]]></category>
		<category><![CDATA[email elements]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://anthonygthomas.com/?p=434</guid>
		<description><![CDATA[For several months now I&#8217;ve been triggering functions in my CakePHP controllers using crontabs. It&#8217;s especially handy for summarizing data and sending out reports via email. I&#8217;m about to change jobs and I&#8217;m trying to set up as many systems as I can to help staff manage our data after I leave. Part of that [...]]]></description>
			<content:encoded><![CDATA[<p>For several months now I&#8217;ve been triggering functions in my <a title="CakePHP" href="http://cakephp.org" target="_blank" onclick="pageTracker._trackPageview('/outgoing/cakephp.org?referer=');">CakePHP</a> controllers <a href="http://www.lost-in-code.com/programming/php-code/cakephp-crontab/" onclick="pageTracker._trackPageview('/outgoing/www.lost-in-code.com/programming/php-code/cakephp-crontab/?referer=');">using crontabs</a>. It&#8217;s especially handy for summarizing data and sending out reports via email. I&#8217;m about to change jobs and I&#8217;m trying to set up as many systems as I can to help staff manage our data after I leave. Part of that means writing a few more crons to send out more emails. Today while trying to do just that, I ran into something unexpected that held me up for an hour or so until I had an epiphany on my way home. For the purposes of this post, I&#8217;m assuming you&#8217;ve already set up a cron dispatcher and know how to trigger cron jobs.</p>
<p>For one more week I&#8217;m working in a research clinic. One of the things we need to keep track of is who is late in getting us a sample. We need to check for blood and throat samples (which come from swishing some saline around in the mouth). This can be done by hand, but soon the study will grow and the number of participants will make that hard to manage. So I just want to check to see who is late and send out an email to staff to let them know.</p>
<p>This function exists in my Patient controller:<span id="more-434"></span></p>
<pre class="brush: php; highlight: [50,51,52,53]; title: ; notranslate">
function cron_delinquency() {

	if (!defined('CRON_DISPATCHER')) // make sure the request comes through the cron dispatcher
	{
		$this-&gt;redirect('/'); exit('Invalid Request');
	}
	/* this looks up active patients who do not have an patient_id ending in &quot;D&quot;. &quot;D&quot; indicates they are a donor and we only need one specimen from them. */
	$active = $this-&gt;Patient-&gt;find('list', array(
		'conditions' =&gt; array(
			'Patient.id LIKE \'T%\' AND Patient.id NOT LIKE \'%D\'',
			'Patient.withdrawn != \'y\'',
			'Patient.active=&quot;1&quot;'),
		));
	$in = '\''; /* the patient_id's start with a &quot;T&quot; meaning all the patient_id's need to be enclosed in quotes */

	$in .= implode('\', \'', $active); // implode the list of patient_id's

	$in = $in . '\''; // end it all with a quote

	$blds = $this-&gt;Patient-&gt;Specimen-&gt;find('list', array( // find the blood specimens for this group of patients
		'conditions' =&gt; array(
			'Specimen.patient_id IN (' . $in .')',
			'Specimen.type' =&gt; array('BLD')
			),
		'fields' =&gt; array('patient_id', 'draw_date'),
		'order' =&gt; array('patient_id' =&gt; 'ASC', 'draw_date' =&gt; 'ASC')

		));

	$thrs = $this-&gt;Patient-&gt;Specimen-&gt;find('list', array( // find the throat samples for this group of patients
		'conditions' =&gt; array(
			'Specimen.patient_id IN (' . $in .')',
			'Specimen.type' =&gt; array('THR')
			),
		'fields' =&gt; array('patient_id', 'draw_date'),
		'order' =&gt; array('patient_id' =&gt; 'ASC', 'draw_date' =&gt; 'ASC')

		));

/* My Patient model has a function to filter arrays and return only those that are older than the proved Unix timestamp. */
	$delinquentBlood = $this-&gt;Patient-&gt;find_delinquent($blds, 2419200); // 2419200 = 4 weeks; 3628800 = 6 weeks
	$delinquentThroat = $this-&gt;Patient-&gt;find_delinquent($thrs, 3628800);

	if(count($delinquentBlood) &gt; 0 || count($delinquentThroat) &gt; 0) // if we find any who are delinquent
	{

		asort($delinquentBlood); // sort them
		asort($delinquentThroat);

		$data['delinquentBlood'] = $delinquentBlood;
		$data['delinquentThroat'] = $delinquentThroat;
		$data['bloodCounter'] = count($delinquentBlood);
		$data['throatCounter'] = count($delinquentThroat);

		$this-&gt;set('data', $data);

		$this-&gt;Email-&gt;to 	  = $to;
		$this-&gt;Email-&gt;from		= 'LCIS &lt;xxxxxxx@umn.edu&gt;';
		$this-&gt;Email-&gt;subject	= 'PPG Delinquency Report: ' . $bloodCounter .&quot; Subjects With Blood Specimens Due; &quot; . $throatCounter . &quot; With Throat Specimens Due.&quot;;
		$this-&gt;Email-&gt;sendAs	= 'html';
		$this-&gt;Email-&gt;template	= 'viptm_delinquency';
		$this-&gt;Email-&gt;send();
	}
}
</pre>
<p>It&#8217;s that highlighted bit that was really giving me trouble. Previously I had been setting those variables like so:</p>
<pre class="brush: php; title: ; notranslate">$this-&gt;set(compact('delinquentBlood', 'delinquentThroat', 'bloodCounter', 'throatCounter'));</pre>
<p>Ordinarily this would work with any other view, but the email element I have set up for this function was acting as if they variables weren&#8217;t set at all. <em>It wasn&#8217;t until I put them in an array called <code>$data</code>, that I could use them in my email element</em>. It was puzzling and it took me about an hour to figure that out, but once I did my email reports came with beautiful data.<strong>Similar Posts:</strong>
<ul class="similar-posts">
<li><a href="http://anthonygthomas.com/2010/05/24/an-unexpected-problem-with-cakephp-and-email-elements/" rel="bookmark" title="May 24, 2010">An Unexpected Problem with CakePHP and Email Elements</a></li>
<li><a href="http://anthonygthomas.com/2010/02/18/cakephp-containable-behavior-is-your-friend/" rel="bookmark" title="February 18, 2010">CakePHP: Containable Behavior is Your Friend</a></li>
<li><a href="http://anthonygthomas.com/2011/03/12/simple-rss-parsing-and-caching-using-php/" rel="bookmark" title="March 12, 2011">Simple RSS Parsing and Caching Using PHP</a></li>
<li><a href="http://anthonygthomas.com/2009/05/22/roll-your-own-cakephp-components/" rel="bookmark" title="May 22, 2009">Roll Your Own CakePHP Components</a></li>
<li><a href="http://anthonygthomas.com/2008/12/10/use-functions-from-other-controllers-while-maintaining-mvc-architecture-in-cakephp/" rel="bookmark" title="December 10, 2008">Use Functions from Other Controllers While Maintaining MVC Architecture in CakePHP</a></li>
</ul>
<p><!-- Similar Posts took 35.779 ms --></p>
]]></content:encoded>
			<wfw:commentRss>http://anthonygthomas.com/2010/05/24/an-unexpected-problem-with-cakephp-and-email-elements/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>CakePHP: Containable Behavior is Your Friend</title>
		<link>http://anthonygthomas.com/2010/02/18/cakephp-containable-behavior-is-your-friend/</link>
		<comments>http://anthonygthomas.com/2010/02/18/cakephp-containable-behavior-is-your-friend/#comments</comments>
		<pubDate>Thu, 18 Feb 2010 16:21:04 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[CakePHP]]></category>
		<category><![CDATA[containable behavior]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[web development]]></category>
		<category><![CDATA[behaviors]]></category>
		<category><![CDATA[containable]]></category>
		<category><![CDATA[optimization]]></category>
		<category><![CDATA[SQL]]></category>

		<guid isPermaLink="false">http://anthonygthomas.com/?p=369</guid>
		<description><![CDATA[When it comes to optimizing your CakePHP queries, you need to abandon Recursive and adopt Containable. In the example below I have the following models: Patient Specimen Result ResultType The associations in the model are: Result belongsTo ResultType hasMany Result Patient hasMany Result Specimen Specimen belongsTo Patient hasMany Result $paginate in the Result Controller Original [...]]]></description>
			<content:encoded><![CDATA[<p>When it comes to optimizing your CakePHP queries, you need to abandon Recursive and adopt Containable.</p>
<p>In the example below I have the following models:</p>
<ul>
<li>Patient</li>
<li>Specimen</li>
<li>Result</li>
<li>ResultType</li>
</ul>
<p>The associations in the model are:</p>
<ul>
<li>Result
<ul>
<li>belongsTo
<ul>
<li>ResultType
<ul>
<li>hasMany
<ul>
<li>Result</li>
</ul>
</li>
</ul>
</li>
<li>Patient
<ul>
<li>hasMany
<ul>
<li>Result</li>
<li>Specimen</li>
</ul>
</li>
</ul>
</li>
<li>Specimen
<ul>
<li>belongsTo
<ul>
<li>Patient</li>
</ul>
</li>
<li>hasMany
<ul>
<li>Result</li>
</ul>
</li>
</ul>
</li>
</ul>
</li>
</ul>
</li>
</ul>
<p><span id="more-369"></span></p>
<h3>$paginate in the Result Controller</h3>
<h4>Original version</h4>
<pre class="brush: php; highlight: [12]; title: ; notranslate">var $paginate = array(
		'fields' =&gt; array(
			'ResultType.type',
			'Specimen.draw_date',
			'Result.id',
			'Result.patient_id',
			'Result.specimen_id',
			'Result.result',
			'Result.created',
			'Result.modified'
			),
		'recursive' =&gt; 0,
		'limit' =&gt; 50);</pre>
<h4>The Same Thing Using Containable</h4>
<pre class="brush: php; highlight: [11,12,13,14,15,16,17,18,19,20,21,22,23]; title: ; notranslate">var $paginate = array(
		'fields' =&gt; array(
			'id',
			'patient_id',
			'specimen_id',
			'result',
			'created',
			'modified'
			),
		'limit' =&gt; 50,
		'contain' =&gt; array(
			'ResultType' =&gt; array(
				'fields' =&gt; array(
					'ResultType.type',
					'ResultType.id'
					)
				),
			'Specimen' =&gt; array(
				'fields' =&gt; array(
					'Specimen.id',
					'Specimen.draw_date'
					)
				)
			)
		);</pre>
<h3>The SQL</h3>
<h4>SQL Generated from the Original $paginate var</h4>
<pre class="brush: sql; highlight: [7,8,19,20]; title: ; notranslate">SELECT COUNT(*) AS `count`
FROM `results` AS `Result`
LEFT JOIN `result_types` AS `ResultType`
ON (`Result`.`result_type_id` = `ResultType`.`id`)
LEFT JOIN `specimens` AS `Specimen`
ON (`Result`.`specimen_id` = `Specimen`.`id`)
LEFT JOIN `patients` AS `Patient`
ON (`Result`.`patient_id` = `Patient`.`id`)
WHERE 1 = 1

/* 1879 milliseconds */

SELECT `ResultType`.`type`, `Specimen`.`draw_date`, `Result`.`id`, `Result`.`patient_id`, `Result`.`specimen_id`, `Result`.`result`, `Result`.`created`, `Result`.`modified`
FROM `results` AS `Result`
LEFT JOIN `result_types` AS `ResultType`
ON (`Result`.`result_type_id` = `ResultType`.`id`)
LEFT JOIN `specimens` AS `Specimen`
ON (`Result`.`specimen_id` = `Specimen`.`id`)
LEFT JOIN `patients` AS `Patient`
ON (`Result`.`patient_id` = `Patient`.`id`)
WHERE 1 = 1
ORDER BY `Result`.`created` desc
LIMIT 50

/* 2106 milliseconds */</pre>
<h4>SQL Generated Using Containable Behavior</h4>
<pre class="brush: sql; title: ; notranslate">SELECT COUNT(*) AS `count`
FROM `results` AS `Result`
LEFT JOIN `result_types` AS `ResultType`
ON (`Result`.`result_type_id` = `ResultType`.`id`)
LEFT JOIN `specimens` AS `Specimen`
ON (`Result`.`specimen_id` = `Specimen`.`id`)
WHERE 1 = 1

/* 10 milliseconds */

SELECT `Result`.`id`, `Result`.`patient_id`, `Result`.`specimen_id`, `Result`.`result`, `Result`.`created`, `Result`.`modified`, `ResultType`.`type`, `ResultType`.`id`, `Specimen`.`id`, `Specimen`.`draw_date`
FROM `results` AS `Result`
LEFT JOIN `result_types` AS `ResultType`
ON (`Result`.`result_type_id` = `ResultType`.`id`)
LEFT JOIN `specimens` AS `Specimen`
ON (`Result`.`specimen_id` = `Specimen`.`id`)
WHERE 1 = 1
ORDER BY `Result`.`created` desc
LIMIT 50

/* 19 milliseconds */</pre>
<h3>The Difference</h3>
<p>The first set of queries took nearly 4 seconds. The second: 29 milliseconds. Containable just gives you so much more control over what&#8217;s selected in your query. Using <code>recursive =&gt; 0</code> still joined the patients table both times because it was associated in the model&#8211;even though in this case we didn&#8217;t need it. Using the Containable Behavior in the second example removed the patients table from the queries altogether.</p>
<p>This is one of the key pitfalls of using a framework like CakePHP; You can get things running quickly, but you have to go back and optimize. Otherwise you can build a heavy load on the server.</p>
<h3>Resources</h3>
<ul>
<li><a title="CakePHP Framework" href="http://cakephp.org" onclick="pageTracker._trackPageview('/outgoing/cakephp.org?referer=');">CakePHP</a></li>
<li><a href="http://book.cakephp.org/view/474/Containable" onclick="pageTracker._trackPageview('/outgoing/book.cakephp.org/view/474/Containable?referer=');">The Containable Behavior</a></li>
<li><a title="The Recursive Model Attribute" href="http://book.cakephp.org/view/439/recursive" onclick="pageTracker._trackPageview('/outgoing/book.cakephp.org/view/439/recursive?referer=');">The Recursive Model Attribute</a></li>
</ul>
<p><strong>Similar Posts:</strong>
<ul class="similar-posts">
<li><a href="http://anthonygthomas.com/2010/02/18/cakephp-containable-behavior-is-your-friend/" rel="bookmark" title="February 18, 2010">CakePHP: Containable Behavior is Your Friend</a></li>
<li><a href="http://anthonygthomas.com/2010/05/24/an-unexpected-problem-with-cakephp-and-email-elements/" rel="bookmark" title="May 24, 2010">An Unexpected Problem with CakePHP and Email Elements</a></li>
<li><a href="http://anthonygthomas.com/2008/12/10/use-functions-from-other-controllers-while-maintaining-mvc-architecture-in-cakephp/" rel="bookmark" title="December 10, 2008">Use Functions from Other Controllers While Maintaining MVC Architecture in CakePHP</a></li>
<li><a href="http://anthonygthomas.com/2008/11/26/getting-blueprint-css-javascript-libraries-into-your-cakephp-layout/" rel="bookmark" title="November 26, 2008">Getting Blueprint CSS &#038; JavaScript Libraries Into Your CakePHP Layout</a></li>
<li><a href="http://anthonygthomas.com/2009/05/22/roll-your-own-cakephp-components/" rel="bookmark" title="May 22, 2009">Roll Your Own CakePHP Components</a></li>
</ul>
<p><!-- Similar Posts took 37.589 ms --></p>
]]></content:encoded>
			<wfw:commentRss>http://anthonygthomas.com/2010/02/18/cakephp-containable-behavior-is-your-friend/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Use Functions from Other Controllers While Maintaining MVC Architecture in CakePHP</title>
		<link>http://anthonygthomas.com/2008/12/10/use-functions-from-other-controllers-while-maintaining-mvc-architecture-in-cakephp/</link>
		<comments>http://anthonygthomas.com/2008/12/10/use-functions-from-other-controllers-while-maintaining-mvc-architecture-in-cakephp/#comments</comments>
		<pubDate>Wed, 10 Dec 2008 23:52:01 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[About the Author]]></category>
		<category><![CDATA[CakePHP]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[This Site]]></category>
		<category><![CDATA[web development]]></category>
		<category><![CDATA[dry]]></category>
		<category><![CDATA[mvc]]></category>

		<guid isPermaLink="false">http://anthonygthomas.com/?p=66</guid>
		<description><![CDATA[UPDATE (7/22/2009) requestionAction may not be the best solution. Read this. At my day job, I&#8217;m working on an application to keep track of specimens for our lab. A specimen is sent to the lab, then divided into aliquots which are put into boxes and stored in freezers. The previous sentence ought to give you [...]]]></description>
			<content:encoded><![CDATA[<h3>UPDATE (7/22/2009)</h3>
<p>requestionAction may not be the best solution. <a href="http://teknoid.wordpress.com/2009/01/17/can-we-talk-enough-about-requestaction/" onclick="pageTracker._trackPageview('/outgoing/teknoid.wordpress.com/2009/01/17/can-we-talk-enough-about-requestaction/?referer=');">Read this</a>.</p>
<p>At my day job, I&#8217;m working on an application to keep track of specimens for our lab. A specimen is sent to the lab, then divided into aliquots which are put into boxes and stored in freezers. The previous sentence ought to give you some idea of the architecture of the database, which in turn drives the Model for my application.</p>
<p>To take a step back for a second, I&#8217;m developing the application using the <a title="CakePHP" href="http://cakephp.org" onclick="pageTracker._trackPageview('/outgoing/cakephp.org?referer=');">CakePHP framework</a> which uses <a href="http://en.wikipedia.org/wiki/Model-view-controller" onclick="pageTracker._trackPageview('/outgoing/en.wikipedia.org/wiki/Model-view-controller?referer=');">MVC architecture</a>.</p>
<p>As you may have guessed I have specimen, aliquot, boxes and freezers tables. In turn then, I have Specimen, Aliquot, Box and Freezer Models.</p>
<p>The trick here is that I want to alert users when there are aliquots in the system that have not yet been assigned to boxes. It&#8217;s a simple query:</p>

<div class="wp_syntax"><div class="code"><pre class="language" style="font-family:monospace;">SELECT COUNT(aliquot.id)
FROM aliquots
WHERE aliquots.box_id IS NULL</pre></div></div>

<p>The problem is that I want the number of unstored aliquots to be displayed on every page in the left column as a persistent reminder that there are are aliquots that need to be put away. I want to do that in a way that maintains the MVC architecture and doesn&#8217;t violate the <a href="http://en.wikipedia.org/wiki/Don%27t_repeat_yourself" onclick="pageTracker._trackPageview('/outgoing/en.wikipedia.org/wiki/Don_27t_repeat_yourself?referer=');">DRY philosophy</a>.</p>
<p>Since the query is run on the aliquots table and each view is generally specific to it&#8217;s own model, I either have to run a recursive query to access data across models&#8211;which adds overhead&#8211;or implement the solution below which lightens the load a bit and is a more elegant bit of code. (<a title="CakePHP Group" href="http://groups.google.com/group/cake-php/browse_thread/thread/b302d650fa9ec36e/82fd46c3d4e9eeec#82fd46c3d4e9eeec" onclick="pageTracker._trackPageview('/outgoing/groups.google.com/group/cake-php/browse_thread/thread/b302d650fa9ec36e/82fd46c3d4e9eeec_82fd46c3d4e9eeec?referer=');">Tip of the hat to Jon Bennet for offering the solution</a>.)</p>
<p><a href="http://api.cakephp.org/class_object.html#c40a38b60a3748b9cf75215b92ee3db1" onclick="pageTracker._trackPageview('/outgoing/api.cakephp.org/class_object.html_c40a38b60a3748b9cf75215b92ee3db1?referer=');">The solution involves CakePHP&#8217;s requestAction()</a>.</p>
<p>I can define the method in my aliquots controller and call it from anywhere. So if aliquots_controller.php has a method that retrieves the data from the model (in this case called &#8216;unstored&#8217;) I can simply put the following code into my layout:</p>

<div class="wp_syntax"><div class="code"><pre class="language" style="font-family:monospace;">$unstored = $this-&amp;gt;requestAction('aliquots/unstored');
if(!empty($unstored)) {
echo $html-&amp;gt;link('&lt;strong&gt;' . $unstored['unstored'] . ' aliquots have not been stored.&lt;/strong&gt;', '/aliquots/store');
}</pre></div></div>

<p>I only have to define the method once to use it throughout my application. Problem solved.<strong>Similar Posts:</strong>
<ul class="similar-posts">
<li><a href="http://anthonygthomas.com/2008/12/10/use-functions-from-other-controllers-while-maintaining-mvc-architecture-in-cakephp/" rel="bookmark" title="December 10, 2008">Use Functions from Other Controllers While Maintaining MVC Architecture in CakePHP</a></li>
<li><a href="http://anthonygthomas.com/2010/02/18/cakephp-containable-behavior-is-your-friend/" rel="bookmark" title="February 18, 2010">CakePHP: Containable Behavior is Your Friend</a></li>
<li><a href="http://anthonygthomas.com/2009/05/22/roll-your-own-cakephp-components/" rel="bookmark" title="May 22, 2009">Roll Your Own CakePHP Components</a></li>
<li><a href="http://anthonygthomas.com/2010/03/14/display-form-fields-based-on-selection-using-jquery/" rel="bookmark" title="March 14, 2010">Display Form Fields Based on Selection Using JQuery</a></li>
<li><a href="http://anthonygthomas.com/2010/05/24/an-unexpected-problem-with-cakephp-and-email-elements/" rel="bookmark" title="May 24, 2010">An Unexpected Problem with CakePHP and Email Elements</a></li>
</ul>
<p><!-- Similar Posts took 21.388 ms --></p>
]]></content:encoded>
			<wfw:commentRss>http://anthonygthomas.com/2008/12/10/use-functions-from-other-controllers-while-maintaining-mvc-architecture-in-cakephp/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Getting Blueprint CSS &amp; JavaScript Libraries Into Your CakePHP Layout</title>
		<link>http://anthonygthomas.com/2008/11/26/getting-blueprint-css-javascript-libraries-into-your-cakephp-layout/</link>
		<comments>http://anthonygthomas.com/2008/11/26/getting-blueprint-css-javascript-libraries-into-your-cakephp-layout/#comments</comments>
		<pubDate>Wed, 26 Nov 2008 19:55:58 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Blueprint Framework]]></category>
		<category><![CDATA[CakePHP]]></category>
		<category><![CDATA[css]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[web development]]></category>
		<category><![CDATA[jquery]]></category>
		<category><![CDATA[libraries]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://anthonygthomas.com/?p=59</guid>
		<description><![CDATA[Updated 12/3/2008 The other day I wrote about getting the Blueprint CSS framework into your WordPress theme. If you&#8217;re developing in CakePHP, it&#8217;s even easier to link multiple style sheets and JavaScript libraries to your layout file. &#60;?php $css = array('blueprint/screen', 'blueprint/ie', 'style'); $jslibraries = array('prototype', 'scriptaculous', 'jquery'); echo $html-&#62;css('blueprint/print', 'stylesheet', 'media="print"'); echo $html-&#62;css($css, 'stylesheet', [...]]]></description>
			<content:encoded><![CDATA[<p>Updated 12/3/2008</p>
<p>The other day I wrote about <a href="http://anthonygthomas.com/2008/11/23/incorporating-blueprint-css-into-your-new-wordpress-theme/">getting the Blueprint CSS framework into your WordPress theme</a>. If you&#8217;re developing in <a href="http://cakephp.org" onclick="pageTracker._trackPageview('/outgoing/cakephp.org?referer=');">CakePHP</a>, it&#8217;s even easier to link multiple style sheets and JavaScript libraries to your <a href="http://book.cakephp.org/view/96/Layouts" onclick="pageTracker._trackPageview('/outgoing/book.cakephp.org/view/96/Layouts?referer=');">layout file</a>.</p>
<p><code>&lt;?php</code></p>
<p><code>$css = array('blueprint/screen', 'blueprint/ie', 'style');<br />
$jslibraries = array('prototype', 'scriptaculous', 'jquery');</code><code><span style="text-decoration: line-through;"><br />
</span>echo $html-&gt;css('blueprint/print', 'stylesheet', 'media="print"');</code><code><br />
echo $html-&gt;css($css, 'stylesheet', 'media=”screen, projection”');<br />
echo $javascript-&gt;link($jslibraries);</code><br />
<code>?&gt;</code></p>
<p>Let&#8217;s take these one at a time.</p>
<p><code>$css = array('blueprint/screen', 'blueprint/ie', 'style');</code></p>
<p><a href="http://book.cakephp.org/view/205/HTML" onclick="pageTracker._trackPageview('/outgoing/book.cakephp.org/view/205/HTML?referer=');">CakePHP&#8217;s html helper</a> will load any css file you specify. First, make sure the css files are in <code>app/webroot/css</code>. Then put any css files you want to link to your layout in an array like I have above. You might have noticed that I didn&#8217;t include print in my array. That&#8217;s because we want to add an media=&#8221;print&#8221; as a separate attribute that the other style sheets won&#8217;t have.</p>
<p>Once they&#8217;re loaded into your array, simply put <code>echo $html-&gt;css($css);</code> in the head of your layout. The output will be:<br />
<code>&lt;link rel="stylesheet" type="text/css" href="/app/webroot/css/blueprint/screen.css" /&gt;<br />
&lt;link rel="stylesheet" type="text/css" href="/app/webroot/css/blueprint/ie.css" /&gt;<br />
&lt;link rel="stylesheet" type="text/css" href="/app/webroot/css/style.css" /&gt;</code></p>
<p>We still haven&#8217;t linked our print style sheet. Make sure you link the print style sheet above the others so they override it. We can add <code>media="print"</code> by putting this into our layout head:</p>
<p><code>echo $html-&gt;css('blueprint/print', 'stylesheet', 'media="print"');</code></p>
<p>So now:</p>
<p><code>$css = array('blueprint/screen', 'blueprint/ie', 'style');<br />
</code><code>echo $html-&gt;css('blueprint/print', 'stylesheet', 'media="print"');</code><code><br />
</code><code>echo $html-&gt;css($css, 'stylesheet', 'media=”screen, projection”');</code></p>
<p>Results in:</p>
<p><code>&lt;link rel="stylesheet" type="text/css" href="/cvp-msi/https/app/webroot/css/blueprint/print.css" media="print" /&gt;<br />
&lt;link rel="stylesheet" type="text/css" href="/cvp-msi/https/app/webroot/css/blueprint/screen.css" media="screen, projection" /&gt;<br />
&lt;link rel="stylesheet" type="text/css" href="/cvp-msi/https/app/webroot/css/blueprint/ie.css" media="screen, projection" /&gt;<br />
&lt;link rel="stylesheet" type="text/css" href="/cvp-msi/https/app/webroot/css/style.css" media="screen, projection" /&gt;</code></p>
<p>Two things to note. In <code>$html-&gt;css($path, $attributes)</code>, the first argument is the path from <code>app/webroot/css</code>. The second argument is html attributes.</p>
<p>Linking JavaScript libraries is very similar.</p>
<p><code>$jslibraries = array('prototype', 'scriptaculous', 'jquery');</code></p>
<p>This will link to <code>prototype.js</code>, <code>scriptaculous.js</code> and <code>jquery.js</code> respectively as long as there in <code>app/webroot/js</code>.</p>
<p>Put <code>echo $javascript-&gt;link($jslibraries);</code> into the head of your layout and you&#8217;re done. You have all three JavaScript libraries at your disposal.</p>
<p>Other good resources:</p>
<ul>
<li><a href="http://book.cakephp.org/view/181/Core-Helpers" onclick="pageTracker._trackPageview('/outgoing/book.cakephp.org/view/181/Core-Helpers?referer=');">CakePHP Core Helpers</a></li>
<li><a href="http://book.cakephp.org/view/27/Developing-with-CakePHP" onclick="pageTracker._trackPageview('/outgoing/book.cakephp.org/view/27/Developing-with-CakePHP?referer=');">Developing With CakePHP</a></li>
<li><a href="http://api.cakephp.org/class_javascript_helper.html#cab1eb59cacd608ec02e79cfd8710094" onclick="pageTracker._trackPageview('/outgoing/api.cakephp.org/class_javascript_helper.html_cab1eb59cacd608ec02e79cfd8710094?referer=');">CakePHP API JavaScript link Helper</a></li>
<li><a href="http://api.cakephp.org/class_html_helper.html#b8e7fe2bca7be4c25f9a660038131f00" onclick="pageTracker._trackPageview('/outgoing/api.cakephp.org/class_html_helper.html_b8e7fe2bca7be4c25f9a660038131f00?referer=');">CakePHP API CSS link Helper</a></li>
</ul>
<p><strong>Similar Posts:</strong>
<ul class="similar-posts">
<li><a href="http://anthonygthomas.com/2008/11/26/getting-blueprint-css-javascript-libraries-into-your-cakephp-layout/" rel="bookmark" title="November 26, 2008">Getting Blueprint CSS &#038; JavaScript Libraries Into Your CakePHP Layout</a></li>
<li><a href="http://anthonygthomas.com/2008/11/23/incorporating-blueprint-css-into-your-new-wordpress-theme/" rel="bookmark" title="November 23, 2008">Incorporating Blueprint CSS Into Your New WordPress Theme</a></li>
<li><a href="http://anthonygthomas.com/2010/02/08/introducing-the-baseline-development-wordpress-theme/" rel="bookmark" title="February 8, 2010">Introducing the Baseline Development WordPress Theme</a></li>
<li><a href="http://anthonygthomas.com/2008/11/22/blueprint-css-readme-file/" rel="bookmark" title="November 22, 2008">Blueprint CSS Readme File</a></li>
<li><a href="http://anthonygthomas.com/2010/02/16/baseline-theme-version-1-0-1/" rel="bookmark" title="February 16, 2010">Baseline Theme Version 1.0.1</a></li>
</ul>
<p><!-- Similar Posts took 29.367 ms --></p>
]]></content:encoded>
			<wfw:commentRss>http://anthonygthomas.com/2008/11/26/getting-blueprint-css-javascript-libraries-into-your-cakephp-layout/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>My Private Summer of Coding</title>
		<link>http://anthonygthomas.com/2008/05/13/my-private-summer-of-coding/</link>
		<comments>http://anthonygthomas.com/2008/05/13/my-private-summer-of-coding/#comments</comments>
		<pubDate>Tue, 13 May 2008 18:02:52 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[About the Author]]></category>
		<category><![CDATA[Amazon]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[wordpress]]></category>
		<category><![CDATA[CakePHP]]></category>
		<category><![CDATA[cullect]]></category>
		<category><![CDATA[PodPress]]></category>
		<category><![CDATA[Ruby On Rails]]></category>
		<category><![CDATA[Tony Thomas]]></category>

		<guid isPermaLink="false">http://anthonygthomas.com/?p=32</guid>
		<description><![CDATA[A couple of weeks ago I met with Garrick VanBuren to talk about cullect.com. I came away from the lunch excited about two things: Trying out some of the features in cullect that I hadn&#8217;t quite understood before and giving Ruby on Rails another shot. I went to lunch with Garrick to offer him some [...]]]></description>
			<content:encoded><![CDATA[<p>A couple of weeks ago I met with <a href="http://garrickvanburen.com/" onclick="pageTracker._trackPageview('/outgoing/garrickvanburen.com/?referer=');">Garrick VanBuren</a> to talk about <a href="http://cullect.com" onclick="pageTracker._trackPageview('/outgoing/cullect.com?referer=');">cullect.com</a>. I came away from the lunch excited about two things: Trying out some of the features in cullect that I hadn&#8217;t quite understood before and giving Ruby on Rails another shot.</p>
<p>I went to lunch with Garrick to offer him some feedback about why I hadn&#8217;t adopted cullect yet. (I&#8217;ve had an account for about 7 months.) A few colleagues were raving about it. I knew I had to be missing something. I was.</p>
<p>While I think cullect has a way to go before widespread adoption (it runs a little slow on my PowerBook), I see what everyone else likes about it and more importantly, I see lots of potential. So, nice work Garrick. I drank the Kool-Aid. <a href="http://cullect.com/206" onclick="pageTracker._trackPageview('/outgoing/cullect.com/206?referer=');">I now curate a small batch of feeds about music</a> and &#8220;recommend&#8221; posts so the best rise to the top in my &#8220;Important&#8221; list. <a href="http://minneapoliscast.com" onclick="pageTracker._trackPageview('/outgoing/minneapoliscast.com?referer=');">This way I can also repurpose those same articles to Minneapoliscast</a>. In other words, I can repurpose content so that relevant reading is included with what I publish. It&#8217;s fun and it&#8217;s cool.</p>
<p>I&#8217;m not even going to talk about how you can pay cullect so that part of your monthly subscription goes to publishers you read. I can&#8217;t even tell you how cool I think that is.</p>
<p>What I really wanted to write about is how I came away from our conversation inspired to try Ruby on Rails. I&#8217;ve been toying with RoR for about a year now. As I started working my way through <em>Agile Web Development on Rails</em> last year, the realization gradually dawned on me that I was going to have to sit down and learn Ruby. So I bought a pdf version of <em>Programming Ruby</em>, but I didn&#8217;t really get very far before other duties called. I just didn&#8217;t have time to learn a new language.</p>
<p>After talking with Garrick I was determined to give it another shot. Then I thought, there has to be a Rails-like set of tools for PHP&#8211;a language I&#8217;ve been working in for years. That thought and a quick Google search led me to <a href="http://cakephp.org" onclick="pageTracker._trackPageview('/outgoing/cakephp.org?referer=');">CakePHP</a>.</p>
<p>Two weeks later and I&#8217;m near completion of the first module to <a href="http://cvp.umn.edu" onclick="pageTracker._trackPageview('/outgoing/cvp.umn.edu?referer=');">manage clinic and lab data here at work</a>. Once I got my head wrapped around MVC and the built-in helpers in CakePHP, the development got faster and faster. (Disclosure: The database was already fully envisioned and built beforehand. An important first step.) I can&#8217;t tell you how gratifying it is to quickly code something in a few lines, test it and have it work. I have a whole summer of coding ahead of me. I&#8217;m very excited to deploy this application by fall.</p>
<p>On a final note, I was feeling a little cocky, so I coded my first <a href="http://wordpress.org" onclick="pageTracker._trackPageview('/outgoing/wordpress.org?referer=');">WordPress</a> plugin yesterday too. Again, easy. It&#8217;s not quite ready for public release yet but with a little tweaking, I might just release it. Basically it just pulls in <a href="http://www.mightyseek.com/podpress/" onclick="pageTracker._trackPageview('/outgoing/www.mightyseek.com/podpress/?referer=');">PodPress</a> data and lists the ten most popular podcasts on Minneapoliscast.</p>
<p>I was a little worried that with our research slowing down over the summer I was going to be bored. Now I&#8217;m really looking forward to the coming months. Fun stuff.<strong>Similar Posts:</strong>
<ul class="similar-posts">
<li><a href="http://anthonygthomas.com/2008/05/13/my-private-summer-of-coding/" rel="bookmark" title="May 13, 2008">My Private Summer of Coding</a></li>
<li><a href="http://anthonygthomas.com/2008/04/11/transparency/" rel="bookmark" title="April 11, 2008">Transparency</a></li>
<li><a href="http://anthonygthomas.com/2008/03/26/be-careful-with-your-betas/" rel="bookmark" title="March 26, 2008">Be Careful With Your Betas</a></li>
<li><a href="http://anthonygthomas.com/2008/03/31/will-apple-google-one-day-be-perceived-like-microsoft-is-now/" rel="bookmark" title="March 31, 2008">Will Apple &#038; Google One Day Be Perceived Like Microsoft Is Now?</a></li>
<li><a href="http://anthonygthomas.com/2010/01/08/using-mind-mapping-software-to-develop-data-models/" rel="bookmark" title="January 8, 2010">Using Mind Mapping Software to Develop Data Models</a></li>
</ul>
<p><!-- Similar Posts took 36.956 ms --></p>
]]></content:encoded>
			<wfw:commentRss>http://anthonygthomas.com/2008/05/13/my-private-summer-of-coding/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
	</channel>
</rss>

