Tuesday, July 11, 2006

cx_oracle and mac os x

What a pain, if you get this error:
/usr/bin/ld: can't locate file for: -lclntsh

then you should try creating a symlink to libclntsh.dylib.10.1:
Use something like this: "ln -sf libclntsh.dylib.10.1 libclntsh.a"

Monday, May 29, 2006


Model view controller architecture has been a staple of desktop application development for a hell of a long time. I dont know when exactly it became a buzz word in web development but I feel pretty safe saying it is the new hotness. And why not, with the increasing complexity of these newfangled web applications and websites in general the encapsulation and flexibility of mvc design makes darn good sense (buzzwords bolded for the executives out there). But what happens when a good design idea meets a really really evil language...

Well ok, php isn't evil per se, it's just misunderstood. Grossly, horrifyling misunderstood on a level that only economists and libertarians can appreciate (and maybe perl programmers but they enjoy that kind of thing). It's simple, php allows people to write really bad code and still accomplish whatever it is they want to do and fast. However, it is possible to write readable, maintainable code in php and using mvc will help with that. So without further ado here's my interpretation of mvc in php.

The model is the interface to the database. All database specific code goes in here. If you are using flat files, tables, and/or smoke signals do all the loading and saving in the models. Here's the model for the example.

File: Car.mdl

class Car
public static function getCar($car_id)
$query = "SELECT * FROM cars WHERE car_id='$car_id'";
$result = mysql_query($query);
$row = mysql_fetch_object($result);

$car = array();
$car['car_id'] = $row->car_id;
$car['color'] = $row->color;

return car;

public static function updateCar($car_id, $car_color)
$query = "UPDATE cars SET color='$car_color' WHERE car_id='$car_id'";

These functions would be called to load a specific car and update a car's color. I'm trying to leave out extraneous code to make the principles more clear so don't jump all over me for a lack of error checking and whatnot. Anyway, you've got a car in the database you need the data. You load it up and stick it into an array. Not exactly rocket science. When you want to update a car's color you send the car_id and the color.

Now for the controller. The purpose of this part is to act as an intermediary, controlling logic flow and massaging data for the template and model. Your controller tells the template what parts of the page to display and how to display them. Here's the example:

File: Car.php


if ( isset($_REQUEST['car_submit']) )
Car::updateCar($_REQUEST['car_id'], $_REQUEST['car_color']);

$car = Car::getCar($_REQUEST['car_id']);

This isn't going to make a whole lot of sense until you see the template file so here it is:

File: Car.tmpl

<form action="Car.php" method="post">
<input name="car_id" value="<?php echo $car[car_id]; ?>" type="hidden">
<input name="car_color" value="<?php echo $car[color]; ?>" type="text">
<input name="car_submit" value="Update" type="submit">

The controller is the page you would link to from other parts of your site. In this case it would probably be called from a page with a list of cars, each being a link with a url like: Car.php?car_id=23

Before it includes the template, the controller calls on the model to load the data from the database.

The form calls the controller when the update button is pressed. Then the controller tells the model to update the databse. The important part here is that the template is only concerned with the interface to the user.

Splitting your code up this way will make your life so much easier it's ridiculous. With this design you can load up a controller and quickly get an idea of the logic flow of a page. You can swap out different data sources with a minimal amount of rewrites and you can pass off designing the templates to an artist with minimal php knowledge, or have them do mockups and you fill in the php. MVC is a Good Thing(tm), you should use it.