Question

I'm with difficulties with controller and view.

Two tables N - 1 relation

Products: ID (PK), Name, Price, size, id_Category

(154,shirt,20,M,333)
(155,hat,20,L,325)

Categories: ID (PK), Name

(333,new)
(325,discount)

What I tought for the View:

<?php 
foreach($cats as $cat) { 
    foreach($prods as $prod) { 
        /* category info */
        if ($cat['id'] == $prod['id_Category']) {
        /* products info */
        }
     }
     /* a break between categories */
 }
?>

What I expecto to see:

  • Category X
    • Prod
    • Prod
    • Etc


  • Category Y
    • Prod
    • Prod
    • Etc

I dont have a clue about the controller, and im not sure about the view too.

Was it helpful?

Solution

Use Containable

Containable is a behavior which allows you to limit/expand query results to the scope you define.

For example, this will give you a list of Categories:

// Pseudo controller code
$categories = $this->Category->find('all');
array(
    array(
        'Category' => array(...)
    ),
    array(
        'Category' => array(...)
    )
)

Whereas this will give you a list of categories with all of their products:

// Pseudo controller code
$categories = $this->Category->find('all', array(
    'contain' => array('Product')
));
$this->set('categories', $categories); // used in the view
array(
    array(
        'Category' => array(...),
        'Product' => array(
            array(...),
        )
    ),
    array(
        'Category' => array(...)
        'Product' => array(
            array(...),
        )
    )
)

In this way, the only thing necessary to do in the controller is loop on the categories and then loop on the contained products:

// App/View/Categories/index.ctp example
<?php foreach($categories as $row): ?>
    In category: <?= $row['Category']['name'] ?> we have:
    <?php foreach($row['Product'] as $product): ?>
        * <?= $product['name'] ?>
    <?php endforeach; ?>
<?php endforeach; ?>

Conventions make life easier.

The conventional name for the foreign key to define the relation ship "belongsTo Category" is category_id

Named like so the product model can be defined like so:

<?php
// App/Model/Product.php
class Product extends AppModel {
    public $belongsTo = array('Category');
}

If you don't want to change the foreign key - it's not a problem you'll just need to tell CakePHP which fieldname to look for:

<?php
// App/Model/Product.php
class Product extends AppModel {
    public $belongsTo = array(
        'Category' => array(
            'foreignKey' => 'id_Category'
         )
    );
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top