SpinOneSolutions | I waste my time so that you don’t have to…

Oct/09

2

Magento – Part II : Models

The Problem:

You need to work with Magento Models, how chic!

The Solution:

Well, let’s be honest… I don’t have THE solution, but I do have some useful snippets of information to pass along.

Models are the meat of an MVC application.  They contain the definitions for your application’s components.  Stop for a moment and think conceptually about your application.  Anything that is represented by a database table is most likely going to be a Model.  Anything that can be mentally packaged up and labeled could be a Model.  How are Models built, used, and made use of in Magento?  Let’s find out.

In the Previous post I showed you how to create a custom Module and one of the main pieces of that Module was the Model Helloworld.

<?php
class Spinonesolutions_Helloworld_Model_Helloworld extends Varien_Object {
  function __construct() {
    parent::__construct();
  }

  function helloworld($arg) {
    echo "<br>Hello World! My argument is : " . $arg;
  }
}

I’m going to examine it now, in more detail, to flush out some of the intricacies of Magento.

Notice the class definition:

Spinonesolutions_Helloworld_Model_Helloworld

It’s important to maintain this naming convention since Magento uses an autoloader to load class files when they’re called for.  If they’re not named correctly it will look at the wrong place in the file system for the file which SHOULD contain the class it’s looking for, but alas it will not be there, and thus; it will not find it and you will receive an error.

Deconstructing the above:

Spinonsolutions_Helloworld_Model_Helloworld
{Namespace}_{Module}_Model_{Model}.php

Let’s look at some permutations to get a deeper understanding:

Spinonesolutions_Helloworld_Model_Worldhello
\Spinonesolutions\Helloworld\Model\Worldhello.php

Spinonesolutions_Helloworld_Model_Foo_Bar
\Spinonesolutions\Helloworld\Model\Foo\Bar.php

Spinonesolutions_Helloworld_Model_Foo_Helloworld
\Spinonesolutions\Helloworld\Model\Foo\Helloworld.php

Picking up the pattern?  Good!

 The __consruct method is called when Magento builds an instance of this Model.  My constructors always contain, at least, a call to the parent constructor and sometimes more depending on the Model.

 To instantiate an instance of a Model use Mage::getModel($modelClass,$arguments) or Mage::getSingleton($modelClass,$arguments).  The parameter $modelClass is a string, the construction of which is partially determined by the config.xml and partly by the Model’s class definition.  Let’s look at IndexController from Part I, line 23.

<?php
//IndexController is the default controller
//EG: http://localhost/spinonesolutions/
//Notice there's no parameters being passed as a parameter (Nothing after trailing "/")
//IndexController will be called since it's the default.
//"spinonesolutions" is the frontname as defined in confg.xml
class Spinonesolutions_Helloworld_IndexController extends Mage_Core_Controller_Front_Action {

  //indexAction is the default Action for any controller
  function indexAction() {
    echo "indexAction";
    $helloworld = Mage::getModel("spinonesolutions_helloworld/helloworld");
    $helloworld->helloworld("helloworld");
  }
}

The piece of $modelClass that comes before the backslash (spinonesolutions_helloworld) is defined in the config.xml file included in the etc directory of your Module.

<?xml version="1.0" encoding="UTF-8" ?>
<config>
<modules>
<Spinonesolutions_Helloworld>
<version>0.1.0</version>
</Spinonesolutions_Helloworld>
</modules>
<frontend>
<routers>
<spinonesolutions> <!-- I make this match my front name but I'm not sure it matters -->
<use>standard</use> <!-- Use standard routing as opposed to admin. IE: frontend vs admin -->
<args>
<module>Spinonesolutions_Helloworld</module> <!-- The module to search for controllers -->
<frontName>spinonesolutions</frontName> <!-- The first descriminator in the path. "spinonesolutions" in http://localhost/spinonesolutions/ -->
</args>
</spinonesolutions>
</routers>
</frontend>
<global>
<models>
<spinonesolutions_helloworld> <!-- This is used when istanting your Model EG: Mage::getModel("spinonesolutions_helloworld/hellworld") -->
<class>Spinonesolutions_Helloworld_Model</class> <!-- That class to use when isntanting objects of type above. -->
</spinonesolutions_helloworld>
</models>
</global>
</config>

Notice the models element.  It’s defining a label for the class (and folder) Spinonesolutions_Helloworld_Model.  Said in another way; given spinonesolutions_helloworld, the models element tells Magento what class and, by naming convention, what folder to look in for the second piece; that which comes after the backslash.

The piece that comes after the backslash (helloworld) tells Magento what particular Model you’re looking for.  In my example, it’s simply helloworld, so the autoloader is going to be looking for a file named Helloworld.php that contains a class definition Spinonesolutions_Helloworld_Model_Helloworld.  Lets extend the permutations that we used earlier adding how to instantiate each.

Spinonesolutions_Helloworld_Model_Worldhello
\Spinonesolutions\Helloworld\Model\Worldhello.php
$objModel = Mage::getModel(‘spinonesolutions_helloworld/worldhello’);

Spinonesolutions_Helloworld_Model_Foo_Bar
\Spinonesolutions\Helloworld\Model\Foo\Bar.php
$objModel = Mage::getModel(‘spinonesolutions_helloworld/foo_bar’);

Spinonesolutions_Helloworld_Model_Foo_Helloworld
\Spinonesolutions\Helloworld\Model\Foo\Helloworld.php
$objModel = Mage::getModel(‘spinonesolutions_helloworld/foo_helloworld’);

A great way to get a handle on how the naming conventions work is to meander through the core and note of name of the file and the folder structure it’s been placed in; then compare that to the class definition contained within.

One more time; since it took me a while to figure this out!

\Spinonesolutions\Helloworld\Model\Helloworld.php

Spinonesolutions_Helloworld_Model_Helloworld

<spinonesolutions_helloworld>
    <class>Spinonesolutions_Helloworld_Model</class>
</spinonesolutions_helloworld>

$objModel = Mage::getModel(‘spinonesolutions_helloworld/helloworld);

Do you see it!  Do you!?

One awesome, and very useful, property of Models is that they can extend any other Model you want.  This is, in general, how you extend core Models with your own functionality.

This is absolutely essential when you want to add on to the Magento code base.  If you just fire up your text editor and make your changes to the core, the next time you upgrade Magento, there’s a relatively good chance you’ll lose all your work.

That’s all for Models! Not really though, I’ve just covered the basics here, read on for more as I cover extending!

Download the source – Helloworld

  1. Part I : Custom Module
  2. Part II : Models
  3. Part III : Controllers
  4. Part IV : Extending Models
  5. Part V : Data Layer
Share and Enjoy:
  • Print
  • Digg
  • del.icio.us
  • Facebook
  • Google Bookmarks
  • DZone
  • Kirtsy
  • Propeller
  • Reddit
  • Slashdot
  • StumbleUpon
  • Suggest to Techmeme via Twitter
  • Technorati

RSS Feed

3 Comments for Magento – Part II : Models

Polprav | October 16, 2009 at 3:47 pm

Hello from Russia!
Can I quote a post in your blog with the link to you?

Will Wright | October 19, 2009 at 1:05 pm

Yes, of course!

Deng | January 28, 2010 at 11:59 pm

A very good post helping understanding the naming convention of magento. Thanks

Leave a comment!

«

»

Find it!

Theme Design by devolux.org