fetching images from multiple tables - php

I am building a small online shop where I have a parent table called 'products' and a child table called 'images'.
I have followed best practice and set up a foreign key constraint with the field product_id establishing a link between both tables.
products
product_id (PK parent table)
product_title
product_category_id
product-price
product_quantity
product_description
long_description
product_image
images
image_id (PK for child table)
product_id (foreign key)
product_image_two
NB: Each product will have 2 images, thus I want to retrieve a product based on its product_id and get the associated images from each table.
ie. the query pulls product_image from 'products' and product_image_two from 'images'
I have trawled through a multitude of posts on here about JOIN and tried to refactor other folks code so far without success.
My Current Statement
<?php
$query = query("SELECT p.* , i.* FROM products p,images i WHERE p.product_id=i.product_id");
confirm($query);
while ($row = fetch_array($query)):
?>

It sounds like what you want is a LEFT JOIN. Using a LEFT JOIN, you can select everything in the product table but only rows from the images table if their corresponding key is present in the products table. So for example, your query could look like:
SELECT p.* , i.*
FROM products p,
LEFT JOIN images i ON
p.product_id = i.product_id
This will return every row in the products table, and a value of null for each column in the images table if no second image exists. Here is a simplified demo of what this does: SQL Fiddle

Try with inner join: according to your explanation it should work
SELECT p.product_id,p.product_image, i.product_image_two FROM products p
inner join images i on
p.product_id=i.product_id

Related

SQL Query to select a products brand and relating it to a third table

I have a task to get products info like top sales, date, and brands. However there is no field Brands in a product table. What I have is two separate tables for products and brands, in addition I have another product_sales table which is basically the main table for products sales but the main table doesn't know anything about brands.
I suppose I have to join somehow the two basic tables and then link them by product id to the main table.
For now, I believe I have to work with the two tables containing info about the brand.
Brands has {id, brandId, brandname, total }
BrandsProducts has {id, brandid, productId }
My query:
SELECT
b.brandid,
b.brandname,
p.productid
FROM pgcdonbrands b, pgcdonbrandsproducts p
WHERE b.brandid = p.brandid
This I believe returns the correct result, Brand name and Id, and which Product Id is related to that brand. My question is now, how do I go on about including this in my main query for Product Sales table. The end result should be Product Name and Brand Name.
Something like this. As per your data you'll decide JOIN TYPE (LEFT/INNER).
SELECT *
FROM productSales ps
INNER JOIN (SELECT b.brandid,
b.brandname,
p.productid
FROM pgcdonbrands b
INNER JOIN pgcdonbrandsproducts p
ON b.brandid = p.brandid) t
ON ps.productid = t.productid;
SELECT ...
FROM BrandsProducts
INNER JOIN Brands ON BrandsProducts.brandid = BrandsProducts.brandid
WHERE ...
By joining your tables like this, you can use them as one virtual table

How to build an admin with multi categories in PHP and MySQL?

I'd like to build an administration page for my website, where I could use multiple checkboxes to store / updates many categories for a single post.
So I've created three tables:
POST Table (id (index, auto-increment, not null), subject, content)
CATEGORIES Table (id (index, auto-increment, not null), name)
POST_CATEGORIES Table (id (index, auto-increment, not null), id_cat (foreign key to CATEGORIES.id), id_post (foreign key to POST.id))
(This last table is building relations between the posts and its categories.)
So I'm trying to list the categories with multiple checkboxes. I'm doing this query, but it doesn't work as expected:
$select = $db->query('SELECT categories.id, categories.name, post_categories.id_cat AS fk_cat, post_categories.id_post AS fk_post, post.id AS post_id
FROM `categories`
LEFT JOIN post_categories
ON categories.id = id_cat
LEFT JOIN posts
ON post.id = id_post');
Result is i have a list of categories, but each category name is repeated depending on the number of posts having this category (e.g : if post 1 and post 2 have both category 1, category 1 will appear 2 times in my list).
EDIT :
Thanks for the replies, here is a sqlfiddle to see what's happening...
http://sqlfiddle.com/#!9/4c304/1
(I'm trying to display a list of categories. I won't select * from categories table because in a next step, i'd like the right categories to be checked when i edit a post.)
SELECT DISTINCT c.id
, c.name
, p.id post_id
FROM categories c
LEFT
JOIN post_categories pc
ON c.id = pc.id_cat
LEFT
JOIN posts p
ON p.id = pc.id_post
If i use GROUP BY categories.id, i don't have doubles anymore...
But it only keeps the first post which is "tagged" with the current category. I need to keep all those informations.
Maybe i should filter by a php query? Something like if count(category.id > 1) then only display the one where post_id = current post edit? (sorry if it's not clear, i feel a bit confuses :( )

Joins and Many to Many Relationship in mySQL

So I have a database consisting of posts and categories using the following tables
posts (PostID, PostName, PostCategory)
categories (CategoryID, CategoryName)
then I have another table which is there to join the two together as follows
posts_categories (Posts_Category_ID, PostID, CategoryID)
I would like to know how to create an SQL Query for the following commands:
a. Create an SQL Query to populate a single POST with MULTIPLE CATEGORIES
b. Search for all POSTS that CONTAINS MULTIPLE CATEGORIES
ex a. Create Post Named "Post1" with Categories "Digital","Analog","Linear"
ex b. Search for all Posts containing Categories "Digital" and "Linear"
Thanks a lot for your help.
If you are talking about fetching the data then do a join between the tables using the chaining table. Something like below
select p.PostName, c.CategoryName
from posts p inner join post_categories pc on p.PostID = pc.PostID
inner join categories c on c.CategoryID = pc.CategoryID
where c.CategoryName in ('Digitl','Linear')
I don't know if I totally get your question, but the query below should return those entries in the many-to-many table that have more than one categoryId for a single postId. Let me know if this helps:
select *
from posts_categories pc
join (
select postId
from posts_categories
group by postId
having count(categoryId) >1
) x on x.postId = pc.postId
Also, you should have a unique constraint on this table for the postId and categoryId columns or make that your primary key.

PHP how to display rows from two tables

I have two tables namely 'categories' & 'products' as follows:
categories
id | name
products
id | cat_id | name
cat_id in products references the categories table.
Now, I want to display the list of all products on a page, which will have to also display the name of the category the product belongs to(not the cat_id).
I am very new in PHP, so am doing the following way:
foreach($products as $product):
echo $product->id . $product->name;
echo getCategoryName($product->cat_id);
endforeach;
Its obvious that the database call to retrieve the corresponding category name is equal to the number of products to be displayed, and something tells me this is not good at all.
So, is there a better way to do the above? maybe by using SQL JOIN?
You should use SQL join, which is by far the best and easiest way to select data from two tables.
SELECT
p.id AS id, c.name AS category, p.name AS name
FROM
products AS p LEFT JOIN categories AS c ON p.cat_id = c.id
You can also use the statement by Trevor, but that's a different type of join. Both will work in this case, as long as the product ID always exist.
Update: A little update on LEFT JOIN and RIGHT JOIN. When you select from 2 tables, you have a left and right table (products is left here, categories is right). The query I gave you will match all products even if the category does not exist. A RIGHT JOIN would match all categories even if there are no products in that category.
Yeah, you'll need a sql join. Something like this:
categories id | name
products id | cat_id | name
select categories.name, products.id, products.name
from categories, products
where categories.id = products.cat_id

Querying 2 Tables in a single query

I have a table for posts and a table for categories, what i want is to select posts that are in a specific category. The problem is that the category is stored in another table and not in the posts table, here is the example:
posts
id title body
---------------------------
125 Some title Blah blah
categories
postid category
----------------
125 politic
I want in single query to fetch posts in the politic category by example, what to do?
Use:
SELECT p.id,
p.title,
p.body
FROM POSTS p
JOIN CATEGORIES c ON c.postid = p.id
WHERE c.category = 'politic'
The issue I have with your CATEGORIES table is that storing the category value as a string means the data isn't normalized - you should instead have a CATEGORY table:
CATEGORY
category_id (primary key, auto_increment)
category_description
...and use the category_id value in the CATEGORIES table:
CATEGORIES
category_id (primary key, foreign key to CATEGORY.category_id)
post_id (primary key, foreign key to POSTS.postid)
select p.*
from posts p
inner join categories c
on p.id = c.postid
where
c.category = 'politic'
You need to join the two tables in your query
SELECT *
FROM posts P
INNER JOIN categories C on C.post_id = P.id
WHERE C.category = 'politic'
You can intuitively (this is NOT exactly a technically correct explanation) think of this join as appending the category field to a row in posts with the shared id (this is the 'on C.post_id = P.id'). The WHERE clause indicates that you want only those rows where category is 'politic'.
Inner join is one of several join types. Left join in particularly is another common one, and its difference in this situation is that rows of post without a match in categories would still be listed, but with nulls for the fields from categories. (With inner join such rows would not remain)
http://en.wikipedia.org/wiki/Join_%28SQL%29

Categories