DB Schema for Dynamic Categories

£可爱£侵袭症+ 提交于 2019-12-10 16:45:38

问题


Added Update #1. Please check at the end of the question. Thanks.

Friends,

I am designing a Product Listing with categories and filters tied to the categories. I currently have a database schema with static categories. I have to make them dynamic. I couldn't find out the right schema to make it dynamic, so I hard code the schema in the form. My detailed work is as follows.


MySQL Stuff

The main products table is the index of all the products and each category of products have separate fields. For eg., consider a bike and a TV. These two products share common fields that are in the product table:

  1. Product ID
  2. Name
  3. Price
  4. Photo
  5. Category

And when it comes to the category, it has some extra fields. So, bike comes in the automobiles category, where it has fields:

  1. Mileage
  2. Engine Type
  3. Seater
  4. Fuel

For the TV product, it comes in its own category, TV, where the fields are:

  1. Dimensions
  2. Video Type
  3. Response Time
  4. Input Options

Currently my database structure is as follows:

DESC `Products`;
+------------+--------------+------+-----+---------+----------------+
|      FIELD |         TYPE | NULL | KEY | DEFAULT |          EXTRA |
+------------+--------------+------+-----+---------+----------------+
| Product ID |      int(11) |   NO | PRI |  (null) | auto_increment |
|       Name | varchar(255) |  YES |     |  (null) |                |
|      Price |      int(11) |  YES |     |  (null) |                |
|      Photo | varchar(255) |  YES |     |  (null) |                |
|   Category |      int(11) |  YES |     |  (null) |                |
+------------+--------------+------+-----+---------+----------------+

And the category fields are as:

DESC `television`;
+---------------+--------------+------+-----+---------+-------+
|         FIELD |         TYPE | NULL | KEY | DEFAULT | EXTRA |
+---------------+--------------+------+-----+---------+-------+
|    Product ID |      int(11) |  YES |     |  (null) |       |
|    Dimensions |  varchar(25) |  YES |     |  (null) |       |
|    Video Type | varchar(255) |  YES |     |  (null) |       |
| Response Time |  varchar(25) |  YES |     |  (null) |       |
| Input Options |         text |  YES |     |  (null) |       |
+---------------+--------------+------+-----+---------+-------+

DESC `automobiles`;
+-------------+--------------+------+-----+---------+-------+
|       FIELD |         TYPE | NULL | KEY | DEFAULT | EXTRA |
+-------------+--------------+------+-----+---------+-------+
|  Product ID |      int(11) |  YES |     |  (null) |       |
|     Mileage |      int(11) |  YES |     |  (null) |       |
| Engine Type | varchar(255) |  YES |     |  (null) |       |
|      Seater |      int(11) |  YES |     |  (null) |       |
|        Fuel | varchar(255) |  YES |     |  (null) |       |
+-------------+--------------+------+-----+---------+-------+

And when I insert data to the database, I use this way:

INSERT INTO `television`
    (`Product ID`, `Dimensions`, `Video Type`, `Response Time`, `Input Options`)
VALUES
    (1, 100, 'hd', 2, 'hd');
INSERT INTO `automobiles`
    (`Product ID`, `Mileage`, `Engine Type`, `Seater`, `Fuel`)
VALUES
    (1, 100, 'hd', 2, 'hd');

HTML / PHP

Seems to be fine for a static set of categories, where I use a simple form like the following.

Television

<form action="new.php">
    <ul>
        <li>
            <label>Name</label>
            <input type="text" />
        </li>
        <li>
            <label>Price</label>
            <input type="text" />
        </li>
        <li>
            <label>Photo</label>
            <input type="text" />
        </li>
        <li>
            <label>Category</label>
            <input type="text" />
        </li>
        <li>
            <label>Dimensions</label>
            <input type="text" />
        </li>
        <li>
            <label>Video Type</label>
            <input type="text" />
        </li>
        <li>
            <label>Response Time</label>
            <input type="text" />
        </li>
        <li>
            <label>Input Options</label>
            <input type="text" />
        </li>
        <li>
            <input type="submit" />
        </li>
    </ul>
</form>

Automobile

<form action="new.php">
    <ul>
        <li>
            <label>Name</label>
            <input type="text" />
        </li>
        <li>
            <label>Price</label>
            <input type="text" />
        </li>
        <li>
            <label>Photo</label>
            <input type="text" />
        </li>
        <li>
            <label>Category</label>
            <input type="text" />
        </li>
        <li>
            <label>Mileage</label>
            <input type="text" />
        </li>
        <li>
            <label>Engine Type</label>
            <input type="text" />
        </li>
        <li>
            <label>Seater</label>
            <input type="text" />
        </li>
        <li>
            <label>Fuel</label>
            <input type="text" />
        </li>
        <li>
            <input type="submit" />
        </li>
    </ul>
</form>

My Problem

Now the form data is simple. I just use the structure of table to insert into the database. The problem now I face is, what if the categories are supposed to be dynamic? How am I supposed to change my database schema to make it dynamic?

Okay, let me define what's my view of dynamic. When the admin wants to add new categories, what I currently do is, create new forms for the categories, go to phpMyAdmin and add a new table and again the same insert queries and new files will be added. I want to do this via an admin panel using PHP alone. Is this feasible? What kind of schema changes should I make?


Update #1

First of all. Thanks! Now I have improvised my table this way. Now I have four tables.

  1. Products - Index of all the products.
  2. Categories - For name-sake? Includes the category name and its parent.
  3. Attributes - Includes the attribute names for the category.
  4. Association - The association of the Product ID, Attribute ID, and its value.

Now, well, I am working on. This looks promising. Will wait for answers, at the same time, update my work too! :) Thanks.


回答1:


I think you need to change your database schema. Here I can see that the categories are child to other parent categories with nth level. And also sub categories have different value field. For this you may required custom field management, to make those field also dynamic. So altogether my suggestive schema will be as follows.

Product

Product_ID, Name, Price, Photo, Category_ID (forignkey of category table)

Category

Category_ID, Name, Parent_ID

Category_Field

Category_Field_ID, Category_ID, Name, Type

Product_Category_Field_Value

ID, Product_ID, Category_ID, Category_Field_ID, Value

So here in Product table we mapped category by Category_ID. In Category table we maintain sub category by parent_ID. It means if the category is a root category use 0 in parent_ID else use Category_ID of its parent category. In Category_Field use custom field name which associate with category. Here type is the type of field or data, for example text, textarea, select, radio etc you can use in type. Product_Category_Field_Value is used for value of custom field for each product. Use this it will works. All the best.




回答2:


Instead of having a separate table for types of categories, you should have a table for filters. Filters will have names/values and be a subset of a category. For now, let's say that a product can only belong to a single category as this simplifies things.

Product (proID, fields, catID)
Categories (catID, catName)
Filters (filID, catID, filterName)
ProductFilters (proID, filID)

You can populate Categories with automobile and TV. Whatever category you choose, a product can only correspond to one of them, so you should be as general as possible. Then, you have filters for a category that you can set up ahead of time (mileage, fuel, etc.).

Having the correct filters for a category has to be enforced on the application side rather than the schema.

Finally, a link between Products and Filters allows you to set values for individual filter names (the mileage value, the fuel, value, etc.) You can check against catID to confirm that all corresponding Filter names are accounted for and any ProductFilters entries with the wrong catID are ignored.

You could also eliminate Categories entirely and have only filters, products, and their mappings, but then you don't get an additional check for possible filters for a product.



来源:https://stackoverflow.com/questions/17036376/db-schema-for-dynamic-categories

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!