PHP: Be careful with global constants

Did you know that global constants, when undefined, evaluate to a string containing the constant name? Talk about a mouthful – here’s an example repurposed from the PHP docs:

<?php
define("CONSTANT", "Hello world.");
echo CONSTANT; // outputs "Hello world." 
echo Constant; // outputs "Constant" and issues a notice.
?>

Depending on your programming background, this probably isn’t what you had in mind. Not me at least – all the languages I’ve ever dealt with fail when attempting to evaluate undefined constants.

That means that if you’re not careful, an undefined constant can cause bugs like this:

if ($user_level < ADMIN_LVL) { // Typo! Should be ADMIN_LEVEL
   // always evaluated
}

I’ve also seen permutations of the following:

define('DEBUG_MODE', true);

if (DEBUG) { // Yes, another typo
  // always executed -- aside: should use if_defined
}

There’s a couple defensive measures you can take. One, use an error reporting level of E_STRICT or E_ALL during development, which will emit a warning in the case above—if it’s evaluated. Better yet, stick to class constants. Undefined class constants throw good old fashioned errors, just like Ruby, Python, et al.

class Consts {
  const ADMIN_LEVEL = 5;
}

// Later that day ...

if ($user_level < Consts::ADMIN_LVL) { // Here's that typo again
  // throws an error
}

Failing fast like this could be the difference between having a bug reported to you immediately by your users, or having a bug reported to you 3 months later when errors pop-up in your database. Don’t know you guys, but I’ll take the first one.

PHP 5.3: Now with less chafing

I’m not one for blogging about feature announcements, but there’s been a recent flurry of PHP 5.3 news I’d like to draw attention to.

Namespaces will finally make an appearance. No comment necessary, really – what with PHP’s 5500+ global functions and reserved words.

Late static binding, along with dynamic static calls (see: __callStatic), will hopefully give way to an ActiveRecord implementation that doesn’t depend on a generic finder class.

Okay, so that’s only two. Yes, there’s a healthy list of other changes, but these solve some major pain points for me and other moonlight Ruby programmers.

If you’d like to learn more, Gergely Hodicska goes in depth on his blog.

ActiveSupport for PHP - Ruby style

One of the things I miss most from Rails is ActiveSupport, the module that modifies Ruby’s core classes (numbers, strings, more) with handy utility methods. They tie so well into the language, most Rails developers don’t realize they aren’t core methods.

Here’s a few examples:

>> 'hello_world'.camelize
=> 'HelloWorld'

>> 7.days.ago
=> Sun Aug 05 20:53:12 -0400 2007

>> 'purple people eater'.ends_with?('eater')
=> true

Is it possible to port this left-to-right style of coding to PHP?

Three less-than-obvious reasons why Ruby is the bomb

Instead of putting out “yet another top 10 list” of superficial, syntactical reasons why I prefer coding in Ruby, I thought I’d touch upon a few lesser-mentioned features that I miss big-time since picking up PHP:

Gems – shiny package management

RubyGems is a simple, easy to use package manager that gives you instant access to over 1500 Ruby libraries (called ‘gems’) via Rubyforge. Compare that to PEAR, PHP’s “Extension and Application Repository”, whose official channel contains less than 200 endorsed packages. It works something like this:

gem install rails --include-dependencies

To be fair, PEAR works very similarly, but it lacks one critical feature I’ve come to love with Gems – the ability to manage multiple versions of the same package. You can pick and choose which gem version to load from inside your app (examples below). This makes life much easier if you’re managing a bunch of different apps on the same machine, all with their own dependencies.

gem ‘rmagick’, '>= 1.1.3' # Only use rmagick with versions >= 1.1.3
gem ‘freshbooks’, '= 0.2' # Version 0.2 only

Did you know: There’s a book dedicated entirely to RubyGems.

Otherworldly code style consistency

Rubyists are staunch defenders of coding standards. After a year of developing with the language, I’ve yet to come across a single library or code example that uses either camelCase naming convention, tabs instead of spaces, or non-standard bracket use. It’s not that I particularly care for one set of rules or the other; it’s just refreshing to see the same familiar coding style every time I step into a new piece of Ruby code.

With PHP, you’re never sure what you’ll get. For example, SimpleXML, PHP5’s standard XML library, uses camelCase function names, whereas most “old school” PHP functions side with underscores (i.e. array_push).

Side note: I just discovered Ruby-SDL provides both Ruby-style method names and their C-style CamelCase equivalents, keeping both Rubyists and old-school SDLers happy. Very cool.

Plugins for everyone

Since you can modify existing classes at runtime in Ruby, adding support for extensions or plugins to your applications is trivial. If you’re writing software in PHP, you need to write hooks ahead of time, or else your users will need to modify the source themselves. The worst example of this is phpbb, whose extension system is a series of insert/remove code statements – yikes!

# my_app.rb
class SomeClass
  def some_method
    do_something
  end

end

# my_plugin.rb
class SomeClass
  def some_method
    do_something_else
  end
end

Looking for more?

If this list seems a little short, feel free to peruse the following fanboy articles:

PHP certification: proceed to checkout

What is it with the PHP community and their obsession with certification? The Zend company has one, along with a whole submarket of training materials and courses. Cake PHP, the Rails-like PHP framework, also offers their own certification. There’s even the possibility of Drupal certification.

Me? I’m happy with my MUDCRAP diploma.

Recap: DrupalCampToronto 2007

This past Friday and Saturday I attended DrupalCampToronto, a BarCamp-style gathering of Drupal enthusiasts here in Toronto. Now, I’m not really a Drupal guy, but now that I’m developing professionally in PHP, I thought it’d be a great opportunity to learn about and discuss one of the more popular open source PHP projects and CMS frameworks.

I’d estimate roughly 100 people attended the ad-hoc conference, spanning 4 rooms at the University of Toronto’s Bahen centre. I attended mostly introductory sessions: a general Drupal overview, an event-site building tutorial, an introduction to module development, and so forth. The event’s highlight, for me at least, was James Walker’s technology-agnostic talk on OpenID – an in-depth continuation of a shorter demonstration he gave at DemoCamp13 last month.

As a beginner I found the Drupal material a little tough to digest, and by Saturday’s end (and a week of fooling around with a local Drupal installation) I couldn’t consider myself among the converts. I did however meet some interesting folk, had two fantastic meals, and picked up a killer event t-shirt – a recipe for success if there ever was one. Thanks to the organizers for a great job.

See also: DrupalCampToronto on Technorati.

From Ruby to PHP: not a cakewalk

I’ve read a few opinionated pieces that mention how learning to program in PHP can make it difficult to pick up advanced object-oriented techniques down the road.

Is the reverse also true? Behaviour I’ve come to expect from other high level languages doesn’t always seem to translate to PHP.

Consider this simple (but meaningless) program written in Ruby:

class MyParent
  @classname = 'Parent' # static member variable

  def self.classname # static method
    return @classname
  end
end

class MyChild < MyParent
  @classname = 'Child' # override the static member variable
end

puts MyParent::classname # gives me 'Parent'
puts MyChild::classname # gives me 'Child'

Makes sense, right? Consider the same program, this time written in PHP:

class MyParent {
  static public $classname = 'Parent';

  static function classname() {
    return self::$classname;
  }
}

class MyChild extends MyParent {
  static public $classname = 'Child';
}

echo MyParent::classname(); # gives me 'Parent'
echo MyChild::classname(); # gives me 'Parent'

Which behaviour is “right”? Or is that even a fair evaluation?

As a side note, some folks in #php on freenode came up with this workaround, which seems to defeat the whole purpose of subclassing anyways.

PHP tools and libraries for Rails loyalists

I find myself in the thick of learning PHP, and I’ve got to admit, I’m having difficulty weaning off Ruby. If you’re in a similar position, you might find the following libraries and tools helpful – with a little less work, you can still build apps the Ruby way.

YAML loading with Spyc

YAML may just be a textual data format, but using it feels like a very Ruby thing to do, probably because most of us were introduced to it through Rails, where it’s used to describe database connections and test fixtures. Plus it doesn’t hurt that the yaml4r core library makes it dead easy to convert Ruby objects to yaml output.

It’s still good on the PHP side of things. Spyc is a YAML loader/dumper for PHP written by pre-eminent Rubyist Chris Wanstrath. (Coincidence?) Taking a cue from Rails, I’ve used it to configure database connections for a toy PHP app I’m putting together, and it works like a charm.

Update: Looks like we’ll see a Zend-friendly YAML parser soon.

Prototype and Scriptaculous

Okay, obviously Prototype and Scriptaculous are popular Javascript libraries that can be used outside of Rails, but what you might not be familiar with is Prototype’s Ruby-like syntax for Enumerable objects, complete with iterators and code blocks. If you’ve grown a fondness for Ruby methods like Enumerable#collect or #detect, then you might want to go with Prototype over other offerings. AJAX helpers are great, but these little language tweaks help make Javascript programming fun. Justin Palmer has a great tutorial on Prototype enumerables, if you’d like to read more.

Build Management with Rake

Rake is a build tool whose syntax is pure Ruby. You get all the mechanisms for describing build dependencies ala Make, combined with the flexibility of a fully featured programming language. Most people are introduced to Rake through Rails, but it can be used for anything – even building C programs. The popular Rails deployment tool Capistrano is actually a set of Rakefiles, which can also be used to deploy your PHP application.

PHP Reflection

Last, but not least, PHP 5 introduced reflection capabilities some time ago. Given the dearth of information available, I don’t think they’re used very much, but if you’ve grown accustomed to polling Ruby objects for their public interfaces, you might want to take a look. Matthew O’Phinney has a good overview of uses for reflection in PHP.

That’s what I’ve come up with so far. Any suggestions? I’ll add them to the list.

Side note: There’s always Symfony and Cake, but I figure if you’re moving from Rails to PHP, you’re probably working inside somebody else’s custom framework anyways.