Reputation: 396
I am using mySQL v5.7.29 MySQL Community Server (GPL)
I have a table where I create a unique index to avoid inserting duplicate values, on the following columns (all columns except the timestamp Updated
) :
CREATE UNIQUE INDEX daily_unique ON daily(`Contract Date`, `Delivery`, `Product`, `Region`, `Price`)
I need to select the latest record by Updated ( timestamp ) .
I have tried the following:
SELECT * FROM daily
WHERE updated = ( SELECT max(Updated) FROM daily )
However, because there are multiple Delivery, Product, Region, the above does not work.
Here is an excerpt of the records:
Contract Date Delivery Product Region Price Updated
0 2020-04-06 2020-04-01 A B 1 2020-04-06 23:00:17
1 2020-04-06 2020-04-01 A B 2 2020-04-07 10:30:16
I need the query to return the latest record only ( each set of Delivery, Product and Region should only return a single Contract Date and Price ).
Contract Date Delivery Product Region Price Updated
1 2020-04-06 2020-04-01 A B 2 2020-04-07 10:30:16
Upvotes: 0
Views: 56
Reputation: 50173
You can also use correlated sub-query :
SELECT d.*
FROM daily d
WHERE d.updated = (SELECT MAX(d1.updated)
FROM daily d1
WHERE d.Delivery = d1.Delivery AND
d.Product = d1.Product AND
d.Region = d1.Region AND
);
Upvotes: 1
Reputation: 522712
If you are using MySQL 8+, then ROW_NUMBER
is the way to go here:
WITH cte AS (
SELECT *, ROW_NUMBER() OVER (PARTITION BY Delivery, Product, Region
ORDER BY Updated DESC) rn
FROM daily
)
SELECT `Contract Date`, Delivery, Product, Region, Price, Updated
FROM cte
WHERE rn = 1;
The row number above will count, starting at 1 with the most recently updated record, for each group of delivery/product/region records. Then, we query the CTE to retain only the latest record for each group.
Just in case you are using an earlier version of MySQL, here is another way to do it:
SELECT d1.`Contract Date`, d1.Delivery, d1.Product, d1.Region, d1.Price, d1.Updated
FROM daily d1
INNER JOIN
(
SELECT Delivery, Product, Region, MAX(Updated) AS MaxUpdated
FROM daily
GROUP BY Delivery, Product, Region
) d2
ON d1.Delivery = d2.Delivery AND
d1.Product = d2.Product AND
d1.Region = d2.Region AND
d1.Updated = d2.MaxUpdated;
Upvotes: 2