1
votes

In my database I have Categories, and they can have child categories. Categories also have products. Ex:

Category
    Sub-Category 1
      Product 1
        Sub-Sub-Category 1
            Product 2
            Product 3

Category Model

public function childs()
{
    return $this->hasMany('App\Category', 'parent_id', 'id');
}

public function products()
{
    return $this->belongsToMany('App\Products');
}

My question is if I do $Category->products, I want it to give me all the products. If I do $Sub-Sub-Category-1, it gives me product 2 and product 3. Thanks for the help.

1
No relationship would accomplish that, you'd likely want some sort of recursive function.Devon

1 Answers

0
votes

just a sample recursive method according to what daven commented.

It is not tested but the idea behind it is to grab all subcategories and select all of their products recursively.

    public function allProducts()
    {
        //call recursive method to append all children categories
        return $this->getAll([$this])
            //select category products as each item
            ->pluck('products')
            //flatten products into one dimension array
            ->flatten()
            //remove repeated products
            ->unique();
    }

    public function getAll($categories)
    {
        //appending categories array
        $append = collect();
        //walk-through input categories
        foreach ($categories as $category)
        {
            //if category has children add them to $append
            if ($category->childs()->count())
            {
                $append->merge($category->childs);
            }
        }
        //if there were children categories, also add their children to $append
        if ($append->count())
        {
            $append = $this->getAll($append);
        }
        //merge children and categories
        return $categories->merge($append);
    }