简体   繁体   中英

Fetching Product Detail from Child Category via Parent Category in PHP

I have category table which stores all category info [ parent and child both] , category_child table which stores parent and child category relation , and product_category table which stores relation between child_category and product .

  1. category - All Category { cid , cname , isParent , status } column.

  2. category_child - Realtion { parent_id , child_id }.

  3. category_product - Relation { product_id , child_category_id }

  4. product - All product details { pid , pname , pimage , pprice , pstock }

I am displaying all Parent Category Link in Front page. Now, Whenever any person will click on parent category Link, I want to display 4 product information from each child category of parent category .

here is my code, which is horrible at the moment, and i am looking for some help in minimising it as much as possible.

$fetchChild = $mysqli->query("SELECT child_id from category_child where parent_id='".$mysqli->real_escape_string($pid)."'");
$listchild = array();
if($fetchChild->num_rows > 0) {
    $n = 1;
    while($storeChild = $fetchChild->fetch_assoc()) {
        $listchild['child_id'][$n] = $mysqli->query("SELECT product_id from category_product where child_category_id='".$mysqli->real_escape_string($storeChild[$n])."'");
        if($listchild['child_id'][$n]->num_rows > 0) {
            $i = 1;
            while($storeMore = $listchild['child_id'][$n]->fetch_assoc()) {
                $listchild['product_id'][$i] = $mysqli->query("SELECT pid, pname, pimage, pprice, pstock from product where pid='".$mysqli->real_escape_string($storeMore[$i])."'");
                if($listchild['child_id'][$n]['product_id'][$i]->num_rows > 0) {
                    $me = 1;
                    while($smeLast = $storeMore[$i]->fetch_assoc()) {
                        $listchild['child_id'][$n]['product_id'][$i]['pid'] = $smeLast['pid'];
                        $listchild['child_id'][$n]['product_id'][$i]['pid'] = $smeLast['pname'];
                        $listchild['child_id'][$n]['product_id'][$i]['pid'] = $smeLast['pimage'];
                        $listchild['child_id'][$n]['product_id'][$i]['pid'] = $smeLast['pprice'];
                        $listchild['child_id'][$n]['product_id'][$i]['pid'] = $smeLast['pstock'];
                        $me++;
                    }
                } else {
                    echo '<meta http-equiv="refresh" content="0; url=index.php?error=Something+Went+Wrong+We+are+Fixing+it" />';
                }
                $listchild['product_id'][$i]->free();
                $i++;
            }
        }
        $listchild['child_id'][$n]->free();
        $n++;
    }

} else {
    echo '<meta http-equiv="refresh" content="0; url=index.php" />';
}
$fetchChild->free();

Kindly help in minimizing nested while and query in my code.

Thanks

If you want, you can put everything into one SQL query using JOIN statement.

SELECT `category`.*, `product`.* FROM `product` 
LEFT JOIN `category_product` ON `category_product`.`product_id` = `product`.`pid`  
LEFT JOIN `category_child` ON `category_child`.`child_id` =  `category_product`.`child_id`
LEFT JOIN `category` ON `category`.`cid` = `category_child`.`child_id`
WHERE `category_child`.`parent_id`='".$mysqli->real_escape_string($pid)."'

But I don't think it's the best solution.

PS. By the way, there is no LIMIT of 4 products per child category in your code, so I haven't put it either.

You can reduce all your queries to one query with JOINS. Using joins will allow you to return results from one table (eg product) basing on the conditions provided in another table or tables (eg category_product, category_child).

Read more about joins somewhere at Stack Overflow or browse some other resources. For example http://www.codinghorror.com/blog/2007/10/a-visual-explanation-of-sql-joins.html .

You should never use SQL query in a loop! It is very slow, you can overload the sql server etc...

Your database structure is bad. If you want to store hiearchical tree there are better options:

Tree 1 level:

      1A2

Tree 2 level:

      1A6
   2B3   4C5

Tree 3 level:

          1A12
   2B7    8C9   10D11
3E4   5F6

You have a left and a right value by each node, and you can have the parent id too. You can check whether a node is leaf or branch if you check the difference of the right-left. By leaves it is one. You can check whether a leaf is under a branch if its left is bigger than the left of the branch and its right is smaller than the right of the branch. etc... This structure is described on several sites, for example here: nested set model

After you transformed your model to nested set, you can use a simple sql to ask for your products. Something like this:

SELECT
    p.*
FROM
    categories c, categories b, products p, product_categories pc
WHERE
    b.category_id = ?
AND
    c_category_id <> b.category_id
AND
    c.category_left BETWEEN b.category_left AND b.category_right
AND
    c.category_right - c.category_left = 1
AND
    c.category_id = pc.category_id
AND
    p.product_id = pc.product_id

This is good for beginning, your code will contain group by, limit, etc... because you want to ask only a single product per category... (or you can simply use order by rand() and limit 4 ...)

You should use prepared statements instead of manual escaping... http://php.net/manual/en/mysqli.prepare.php

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM