Mysql: How to get values from other table base from an id - mysql

Assuming that I have 3 tables on my database
Table:Category
category_id
Table:container
container_id
category_id
Table:products
container_id
product_id
How do you get all product_id based on a category_id?
For example I have these data inside my tables from above:
Table: category
sour
sweet
Bitter
Table: container
bottled
sachet
Table: product
sugar
vinegar
cocoa
How do you get all Product(tb_product) where category(tb_category) is sweet

You can use INNER JOIN to solve your problem.
SELECT a.*
FROM products a
INNER JOIN container b
on a.container_id = b.container_ID
INNER JOIN Category c
ON b.category_ID = c.categoryID
WHERE c.categoryName = 'sweete'
As you can see, I assume that the Category table has columns category_ID and categoryName. So in my example above,I've use category name to search for all products that belong on certain category.

select p.*
from Category c
join container c2 on c2.category_id = c.category_id
join product p on p.container_id = c2.container_id
where c.name = 'sweet';
Note the order of the tables in the query (which should perform faster than the other answer!)

you can use inner join like this:
SELECT a.product_id FROM products AS a INNER JOIN container AS b on a.container_id = b.container_Id INNER JOIN Category AS c on b.category_Id = c.category_id where c.category_id = 'new'

Related

How do you sql query all in stock products by category ID in M2?

As the title stated, I'm looking to query all in-stock products by category ID in Magento 2. And if possible to get only the parent(config) IDs if simple has stock, not sure if I make sense?
SELECT p.entity_id as product_id, p.sku, c.is_in_stock
FROM catalog_product_entity as p
INNER JOIN cataloginventory_stock_item as c
ON p.entity_id = c.product_id
To get all products that are in stock for a category id:
SELECT product.entity_id as product_id, product.sku, stock_item.is_in_stock FROM catalog_product_entity as product
INNER JOIN cataloginventory_stock_item as stock_item ON product.entity_id = stock_item.product_id
INNER JOIN catalog_category_product as cat_prod on product.entity_id = cat_prod.product_id
WHERE cat_prod.category_id=XXX and stock_item.is_in_stock=1;
If you only want the configurables, just add the condition like so: and product.type_id='configurable'

SQL query which return counted results from many tables

I have two tables 'shops' and 'products'. Shop has many products and product belongs to one shop. Moreover product belongs to the only one category. I have id's of 3 categories (for example 1,2,3). How can I get all shops having products which belongs to all 3 categories?
I tried
SELECT distinct s.*
from shops s
left join products p on p.shop_id = s.id
where p.category_id in (1,2,3)
but this returns shops with products which belongs to the category 1 OR 2 OR 3 But I want the products which belongs to the all 3 categories like 1 AND 2 AND 3, so every shop have to have at least 3 products
You could check the s.id having count(distinct p.category_id) = 3
SELECT s.id
from shops s
inner join products p on p.shop_id = s.id
where p.category_id in (1,2,3)
group by s.id
having count(distinct p.category_id) = 3
SELECT s.*
from shops s
join products p
on p.shop_id = s.id
where p.category_id in (1,2,3)
Group
by s.id
Having count(distinct p.category_id) = 3
Or something like that
Try this?
SELECT DISTINCT A.ID FROM SHOPS A, PRODUCTS B
WHERE A.ID = B.SHOP_ID AND EXISTS (SELECT COUNT(1) FROM PRODUCTS C, PRODUCTS D, PRODUCTS E WHERE B.ID = C.ID AND C.ID = D.ID AND D.ID = E.ID AND C.CATEGORY_ID = 1 AND D.CATEGORY_ID = 2 AND E.CATEGORY_ID = 3)
My T-SQL is rusty and this assumes I got the relations correct such that Shops 1 - M Products and, I'm unsure if Category is an entity but Category 1 - M Product. Also, just for future work, I've found it helps when your entities are names singular nouns but that's just my preference. Good luck.
Use group by will return by each shop
SELECT distinct s.*
from shops s
left join products p on p.shop_id = s.id
where p.category_id in (1,2,3)
group by s.id
having count(distinct p.category_id) = 3

find records grouped by two columns in mysql

I want to find out all seller who have uploaded products in categories (electronics,clothing,furniture), so for 3 categories there can be 3 row against each seller . tables I have are
1.category{category_id,name},
2.seller {seller_id,username},
3.products{product_id,seller_id,category_id,title}
Note:There can be maximum 3 result (coz I'm searching in 3 categories) against one seller even if he added more than one product in single category
expected result:
**product_id** **category** **sellerUsername**
101 electronics kuldeep
211 furniture kuldeep
322 clothing kuldeep
167 electronics roman
245 furniture roman
247 clothing dangi
246 furniture dangi
..
..
if you need only the matching relation use inner join
select a.product_id, b.username, c.name
from products as a
inner join seller as b on b.seller_id = a.seller_id
inner join category as c on c.category_id = a.category_id
else use left join
select a.product_id, b.username, c.name
from products as a
left join seller as b on b.seller_id = a.seller_id
left join category as c on c.category_id = a.category_id
The general solution to your problem is to join the three tables together and then aggregate by seller and category. In my solution, I have arbitraily chosen the max product ID, in the absence of any logic for doing otherwise. The query is slightly tricky, in that we need to additionally join this result again to the category and seller tables to get the human readable category and seller names. The reason for this is the GROUP BY query should ideally be done by ID and not name, since conceivably two categories (or sellers) could have the same name but have different IDs.
SELECT t3.product_id,
COALESCE(t1.name, 'NA'),
COALESCE(t2.username, 'NA')
FROM
(
SELECT MAX(p.product_id) AS product_id,
c.category_id,
s.seller_id
FROM products p
LEFT JOIN category c
ON p.category_id = c.category_id
LEFT JOIN seller s
ON p.seller_id = s.seller_id
WHERE c.name IN ('electronics', 'clothing', 'furniture')
GROUP BY s.seller_id,
c.category_id
) t1
LEFT JOIN category t2
ON t1.category_id = t2.category_id
LEFT JOIN seller t3
ON t1.seller_id = t3.seller_id
Check Below Code.
SET #row_number:=0;
SET #db_names:= '';
SET #db_names2:= '';
select product_id,name as category ,username as sellerUsername
from (
select a.product_id, c.name ,b.username,
#row_number:=CASE WHEN #db_names=username and #db_names2=name THEN #row_number+1
ELSE 1 END AS row_number,#db_names:=username AS username2,#db_names2:=name AS name2
from products as a
left join seller as b on b.seller_id = a.seller_id
left join category as c on c.category_id = a.category_id
where name IN ('electronics', 'clothing', 'furniture')
)a where row_number < 2
order by sellerUsername,name;
Output :

Find missing combination of columns from two mysql tables

I have one product table like this:
productid categoryid
and another category table like this:
categoryid parentid
would like to find rows missing from product table
select distinct c.parentid, pc.productid, from products_categories pc
join categories c on pc.categoryid = c.categoryid
where concat(pc.productid,'-',c.parentid) not in (
select distinct concat(productid,'-',categoryid) from products_categories
)
however this is extremely slow. is there a way to do this with joins instead of the not in concat line? the concat is used to account for all possible combos.
Everytime you are adding a prefix productID & - to either parentID or categoryID.
You can try this:
SELECT DISTINCT c.parentid, pc.productid
FROM products_categories pc
JOIN categories c on pc.categoryid = c.categoryid
WHERE c.parentid NOT IN (
SELECT DISTINCT categoryid FROM products_categories
)
Edit 1: doesnt account for all combos
SELECT DISTINCT c1.parentid, pc.productid
FROM products_categories pc
INNER JOIN categories c1 ON pc.categoryid = c1.categoryid
LEFT JOIN categories c2 ON c1.parentid = c2.categoryid
WHERE c2.categoryid IS NULL
To find what is in tbl_x but not in tbl_y, do this
SELECT ...
FROM tbl_x
LEFT JOIN tbl_y USING(...)
WHERE tbl_y.id IS NULL;
The construct IN ( SELECT ... ) is very poorly optimized. LEFT JOIN is well optimized (assuming suitable index).

MySQL join with a "bounce" off a third table

I have 3 MySQL tables.
companies with company_id and company_name
products with product_id and company_id
names with product_id, product_name and other info about the product
I'm trying to output the product_name and the company_name in one query for a given product_id.
Basically I need information from the names and companies tables and the link between them is the products table.
How do I do a join that needs to "bounce" off a third table?
Something like this but this obviously doesn't work:
SELECT product_name, company_name
FROM names
LEFT OUTER JOIN companies ON
(names.product_id = products.product_id and products.company_id = companies.company_id)
WHERE product_id = '12345'
select n.product_name, c.company_name
from names n
left outer join products p on n.product_id = p.product_id
left outer join companies c on p.company_id = c.company_id
where n.product_id = '12345'
You nearly have it, you just need to include the third table as another join in your query:
SELECT product_name, company_name
FROM names
LEFT JOIN products ON names.product_id = products.product_id
LEFT JOIN companies ON products.company_id = companies.company_id
WHERE product_id = '12345'
Also you should note that if you are using LEFT JOIN then the company name could be NULL if the company that made the product is unknown. So you need to test for that in your code to avoid an exception. If you know that it should never be NULL, or if you want to explicilty exclude products for which you don't know the company then use an INNER JOIN instead of a LEFT JOIN in both cases.