0
votes

I am following Magento development tutorial Magento for Developers: Part 5 - Magento Models and ORM Basics

when i try to echo the class name i get following error. PS: i am using Magento 1.7

Warning: get_class() expects parameter 1 to be object, boolean given  in C:\xampp\htdocs\magento\app\code\local\Microdatanet\Weblog\controllers\IndexController.php on line 19

#0 [internal function]: mageCoreErrorHandler(2, 'get_class() exp...', 'C:\xampp\htdocs...', 19, Array)
#1 C:\xampp\htdocs\magento\app\code\local\Microdatanet\Weblog\controllers\IndexController.php(19): get_class(false)
#2 C:\xampp\htdocs\magento\app\code\core\Mage\Core\Controller\Varien\Action.php(419): Microdatanet_Weblog_IndexController->testModelAction()
#3 C:\xampp\htdocs\magento\app\code\core\Mage\Core\Controller\Varien\Router\Standard.php(250): Mage_Core_Controller_Varien_Action->dispatch('testModel')
#4 C:\xampp\htdocs\magento\app\code\core\Mage\Core\Controller\Varien\Front.php(176): Mage_Core_Controller_Varien_Router_Standard->match(Object(Mage_Core_Controller_Request_Http))
#5 C:\xampp\htdocs\magento\app\code\core\Mage\Core\Model\App.php(354): Mage_Core_Controller_Varien_Front->dispatch()
#6 C:\xampp\htdocs\magento\app\Mage.php(683): Mage_Core_Model_App->run(Array)
#7 C:\xampp\htdocs\magento\index.php(87): Mage::run('', 'store')
#8 {main}

FILE: app\code\local\Microdatanet\Weblog\controllers\IndexController.php

<?php
class Microdatanet_Weblog_IndexController extends Mage_Core_Controller_Front_Action {
    public function testModelAction(){   
       $blogpost = Mage::getModel('weblog/blogpost');  
       echo get_class($blogpost); 
    }
}
?>

FILE: app\code\local\Microdatanet\Weblog\etc\config.xml

<?xml version="1.0" encoding="UTF-8"?>
<config>
    <modules>
        <Microdatanet_Weblog>
            <version>0.1.0</version>
        </Microdatanet_Weblog>
    </modules>

    <global>
        <models>
            <weblog>
                <class>Microdatanet_Weblog_Model</class>
                <resourceModel>weblog_mysql4</resourceModel>
            </weblog>
            <weblog_mysql4>
                <class>Microdatanet_Weblog_Model_Mysql4</class>
            </weblog_mysql4>
        </models>
    </global>

    <frontend>
        <routers>
            <weblog>
                <use>standard</use>
                <args>
                    <module>Microdatanet_Weblog</module>
                    <frontName>weblog</frontName>
                </args>
            </weblog>
        </routers>
    </frontend>
</config>

FILE: app\code\local\Microdatanet\Weblog\Model\Blogpost.php

<?php
class Mircodatanet_Weblog_Model_Blogpost extends Mage_Core_Model_Abstract 
{
    protected function _construct()
    {
        $this->_init('weblog/blogpost');
    }   
}
?>
1

1 Answers

3
votes

When a class cannot be instantiated via Magento factory methods, there are a number of ways to debug. Learning how to perform differential diagnosis in Magento is important given its heavy use of configurations and its particular conventions.

All class definitions in Magento are (should be) loaded via the autoloader (Varien_Autoload), which is invoked in and relies on the include path settings in app/Mage.php:

$paths[] = BP . DS . 'app' . DS . 'code' . DS . 'local';
$paths[] = BP . DS . 'app' . DS . 'code' . DS . 'community';
$paths[] = BP . DS . 'app' . DS . 'code' . DS . 'core';
$paths[] = BP . DS . 'lib';

$appPath = implode(PS, $paths);
set_include_path($appPath . PS . Mage::registry('original_include_path'));
include_once "Mage/Core/functions.php";
include_once "Varien/Autoload.php";

Varien_Autoload::register();

Once this happens, all that PHP needs to find class definitions is that the class name matches the path to the file relative to the include paths from above. This type of autoloading scheme is prevalent in PHP projects.

This presents the first test strategy: invoking the class directly. In a controller action or test file, do the following:

$obj = new Microdatanet_Weblog_Model_Blogpost;

If PHP cannot find the class definition then this will throw a fatal error. If the class definition can be found, that's good, two things are true: the file path is correct given the class name passed to new, and the class name is correct inside the Blogpost.php file.

Again, this is a typical autoloading scheme in PHP these days. What Magento does is to use some methods to build a class name based on some information in XML. FYI, there are only two useful purposes that this factory method approach provides: allowing for runtime classname rewrites, and registering single instances in the registry.

Assuming that the class can be invoked as above, if Mage::getModel('weblog/blogpost') doesn't return a class instance, the problem must be with configuration. There are usually three reasons that this occurs: module configuration is not being included, module configuration is malformed, or the config is parsed but the information inside is not usable.

So, how to differentially diagnose class group configuration problems? First, ensure that the module configuration is being included and parsed in the first place: break the XML by mismatching tags or other unparseable syntax. Refresh or disable the configuration cache and the system should throw a parse error. If not, one of three things has happened: the module is not properly activated in app/etc/modules/[declaration file].xml, the module's config.xml file is in the wrong place, or the system is suppressing the error! It's easy to troubleshoot all of these in a test script:

<?php
error_reporting(E_ALL | E_STRICT);
ini_set('display_errors',1);

include 'app/Mage.php';

Mage::setIsDeveloperMode(true);

Mage::app();

var_dump(`Mage::getModel('weblog/blogpost')`);

The important bit is the call to setIsDeveloperMode(), as this will cause Magento to output errors it would normally suppress.

If at this point there is no parse error thrown, then the problem must be incorrect xpath or values in the module config.xml.