简体   繁体   中英

Which is a better way to search from multiple tables using PDO in PHP?

I have an HTML form where there is a search field to type for a product name, and below are checkboxes, each for one shop where the product name is to be searched. Users can search from multiple shops by checking the boxes. The form sends a GET request to server, where there is a database with separate tables for separate shops.

<form action="price.php" method="get">
    <input type="text" id="query" name="query" value="">
    <input type="checkbox" name="shop1" id="shop1">
    <input type="checkbox" name="shop2" id="shop2">
    <input type="submit" name="submit" value="submit">
</form>

So in server side I have written a PHP code that will search for the product name from those tables that correspond to the shops checked by the user. Since I will be adding more and more shops in the future, which of the following PHP codes are better suited?

VERSION 1

<?php
function search($pdo, $shop) {
if ( isset($_GET[$shop]) && ($_GET['query'] !== "") ) {
    switch ($shop) {
        case "shop1":
            $stmt = $pdo->prepare("SELECT * FROM `shop1` WHERE `name` LIKE :query");
            $stmt->execute(array(":query" => "%". $_GET['query'] . "%"));
            break;
        case "shop2":
            $stmt = $pdo->prepare("SELECT * FROM `shop2` WHERE `name` LIKE :query");
            $stmt->execute(array(":query" => "%". $_GET['query'] . "%"));
            break;
        ...
        ...
        ...
    }

    $rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
    if ( count($rows) === 0 ) {
        $_SESSION[$shop] = 'nothing found from '. $shop;
        return array();
    } else {
        return $rows;
    }
    } else {
        return array();
    }
}

if ( ! isset($_GET['query']) ) {
    $_SESSION['success'] = "search for an item";
} else {
    $rowsShop1 = search($pdo, "shop1");
    $rowsShop2 = search($pdo, "shop2");
    ...
    ...
    ...
}
?>

VERSION 2

<?php
function search1($pdo, $shop, $sql) {
    $stmt = $pdo->prepare($sql);
    $stmt->execute(array(":query" => "%". $_GET['query'] . "%"));
    $rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
    if ( count($rows) === 0 ) {
        $_SESSION[$shop] = 'nothing found from '. $shop;
        return array();
    } else {
        return $rows;
    }
}

if ( ! isset($_GET['query']) ) {
    $_SESSION['success'] = "search for an item";
} else {
    if ( isset($_GET['shop1']) && ($_GET['query'] !== "") ) {
        $rowsShop1 = search1($pdo, "shop1", "SELECT * FROM `shop1` WHERE `name` LIKE :query");
    }
    if ( isset($_GET['shop2']) && ($_GET['query'] !== "") ) {
        $rowsShop2 = search1($pdo, "shop2", "SELECT * FROM `shop2` WHERE `name` LIKE :query");
    }
    ...
    ...
    ...
}
?>

Or is there a better way to do this?

To go further than my comment, here is a fiddle so you can try the database model I described: https://www.db-fiddle.com/f/wPuc6P87MYuKKBYwztvK7X/0

This can allow you to easily manage your shops and products through their own CRUD without having to work in several tables.

Here below the SQL code if the fiddle somehow doesn't work anymore. (assuming MySQL / MariaDB)

create table product
(
    id int auto_increment,
    name varchar(255) not null,
    constraint product_pk
        primary key (id)
);

create table shop
(
    id int auto_increment,
    name varchar(255) not null,
    constraint shop_pk
        primary key (id)
);

create table product_shop
(
  id int auto_increment,
  product_id int,
  shop_id int,
  quantity int not null default 0,
  constraint product_shop_pk
      primary key (id)
);

alter table product_shop
    add constraint product_shop_product_fk
        foreign key (product_id) references product (id);
alter table product_shop
    add constraint product_shop_shop_fk
        foreign key (shop_id) references shop (id);

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