CodeIgniter Forums
DataMapper ORM v1.8.0 - Printable Version

+- CodeIgniter Forums (https://forum.codeigniter.com)
+-- Forum: Archived Discussions (https://forum.codeigniter.com/forumdisplay.php?fid=20)
+--- Forum: Archived Libraries & Helpers (https://forum.codeigniter.com/forumdisplay.php?fid=22)
+--- Thread: DataMapper ORM v1.8.0 (/showthread.php?tid=37531)



DataMapper ORM v1.8.0 - El Forum - 06-02-2011

[eluser]WanWizard[/eluser]
Either use an include_related() on the get_iterated() statement, so you'll run only one query, or query inside the loop (at the expense of multiple queries).


DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]mrtopher[/eluser]
Have been struggling with advanced relationship for a couple days and am not getting anywhere.

I have two tables with a simple one-to-many relationship between them.

Code:
CREATE TABLE IF NOT EXISTS `brands` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `company_id` int(10) unsigned DEFAULT NULL,
  `brand_category_id` int(10) unsigned DEFAULT NULL,
  `name` varchar(200) NOT NULL,
  `website` varchar(255) DEFAULT NULL,
  `logo_image` varchar(100) NOT NULL,
  `sef_url` varchar(200) NOT NULL,
  `date_added` datetime NOT NULL,
  `date_updated` datetime DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;

-- --------------------------------------------------------

--
-- Table structure for table `brand_categories`
--

CREATE TABLE IF NOT EXISTS `brand_categories` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `name` varchar(100) NOT NULL,
  `sef_url` varchar(100) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;

Brand has one category and a brand category has many brands. To my understanding this doesn't need a join table because it isn't a many-to-many relationship, although I know that's an option.

I setup my two models as follows:

Code:
class brand_category extends DataMapper
{
    
    var $has_many = array('brands' => array(
            'class'         => 'brand',
            'other_field'     => 'category',
            'join_other_as' => 'brand',
            'join_self_as'     => 'brand_category'
            )
        );

}



class brand extends DataMapper
{

    var $has_one = array(
        'category' => array(
            'class'         => 'brand_category',
            'other_field'     => 'brands',
            'join_other_as' => 'brand_category',
            'join_self_as'     => 'brand'
            ),
        'company'
        );
        
    //var $has_many = array('event', 'promotion', 'user');

}

Everything looks fine until I try to save the relationship (a brand with a related category).

Code:
$cat = new Brand_category();
$cat->get_by_id(1);
        
$brand->name            = 'Test';
$brand->website         = 'http://google.com';
$brand->logo_image   = 'http://dummyimage.com/150x100/000/fff.png&text;="Test+logo"';
$brand->sef_url           = 'test';
$brand->save($cat, 'category');

I get an error "Unable to relate brand with brand_category." I have tried using just save() (as shown above) and also save_category() which I believe should work according to the documentation. Nothing has worked.

While trying to troubleshoot the issue it's looking like the $related_field is not getting passed to save() for whatever reason. When I placed breakpoints in the save() function of datamapper.php (line 1568) it wasn't seeing that I was passing category as a second argument (which solves the issue when I hardcode it into datamapper.php).

Am I doing something wrong? Any help would be greatly appreciated.


DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]bEz[/eluser]
Try doing just this...
[quote author="mrtopher" date="1307132092"]

Code:
class brand_category extends DataMapper
{  
    // added these just in case inflector has an issue.
    $table = 'brand_categories';
    $model = 'brand_category';

    // and this should suffice
    var $has_many = array('brand');
}


class brand extends DataMapper
{
    // and so should this
    var $has_one = array('brand_category', 'company');
      
    //var $has_many = array('event', 'promotion', 'user');
}
[/quote]

Notice how "brand" is singular and not needed to be ("brands").


Then, just save the brand object as so:
Code:
$cat = new Brand_category();
$cat->get_by_id(1);
        
$brand->name            = 'Test';
$brand->website         = 'http://google.com';
$brand->logo_image   = 'http://dummyimage.com/150x100/000/fff.png&text;="Test+logo"';
$brand->sef_url           = 'test';
$brand->save($cat);



DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]mrtopher[/eluser]
Thanks for the response bEz.

As a simple relationship everything works just as it should. However, I'm using an advanced relationship because I would like to be able to reference the relationship between the two objects using the more programmer friendly "brands" and "category" keys. That and I'm using this as a test case for more complicated relationships I will need to create between other objects in the future.

But if I can't even get this relatively easy example to work then I'm not sure Datamapper will work for me. Would really like it too though because it looks like a great library. The only other alternative out there appears to be Doctrine and the learning curve for that one is a bit intense.


DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]bEz[/eluser]
Ok, lemme setup a test case and get back to you...
Unless you want to supply your scheme for Companies, I'll just make one up and be back as fast as possible


DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]mrtopher[/eluser]
Company isn't important for this example, you can just remove that for now.

Thanks for the help!


DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]bEz[/eluser]
Ok, I've run the code against the DB Schema and the Model you defined using the following controller code and no errors!
Code:
<?php

class Store extends CI_Controller {

    function __construct()
    {
        parent::__construct();
        //$this->load->library('login_manager');
    }
    
    function index()
    {
        $brand = new Brand();
        $this->output->enable_profiler(TRUE);
        $cat = new Brand_category();
        $cat->get_by_id(1);
                        
        $brand->name            = 'Test';
        $brand->website         = 'http://google.com';
        $brand->logo_image   = 'http://dummyimage.com/150x100/000/fff.png&text;="Test+logo"';
        $brand->sef_url           = 'test';
        $brand->save($cat, 'category');  
    }
}

/* End of file store.php */

The following is the DB info from the profiler.
Quote:DATABASE: store QUERIES: 5 (removed SESSION query)
0.0003 SELECT * FROM `brands` LIMIT 1
0.0002 SELECT * FROM `brand_categories` LIMIT 1
0.0002 SELECT *
FROM (`brand_categories`)
WHERE `brand_categories`.`id` = 1
0.0004 INSERT INTO `brands` (`brand_category_id`, `name`, `website`, `logo_image`, `sef_url`) VALUES (1, 'Test', 'http://google.com', 'http://dummyimage.com/150x100/000/fff.png&text;=\"Test+logo\"', 'test')



DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]mrtopher[/eluser]
Well ain't that a kick in the head.

I just did a test on a different hosting account I have and it works there too. Never occurred to me it could be the server, guess I just assumed I was doing something wrong.

Ok so I guess I'm looking for differences between the two servers PHP configurations to see why they're compiling this code differently. Ugh.

Thanks for the help, I appreciate it!


DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]mrtopher[/eluser]
Well at least I know what the problem is. On my primary server the related_field parameter "category" is not getting to the library. It's coming through on my development server but not getting there on my primary server. Only difference is my dev server is running PHP 5.2.14 and my production server is running 5.3.5.

Anyone have any ideas what could be causing PHP 5.3.5 to mess (or strip completely) with parameters I'm passing to class methods?


DataMapper ORM v1.8.0 - El Forum - 06-03-2011

[eluser]bEz[/eluser]
My Development server is 5.3.4, but I cannot determine off the top of my head why 5.3.5 environment would cause this error, nor why 5.2.14 is not for that matter.