Hello guys I have 4 tables as an key-value store in mysql
t1 (article): t2:
| id | date | | id | key | value |
------------- ---------------------------
| 1 | 2016 | | 1 | title | title1 |
| 2 | 2017 | | 1 | user_id | 1 |
| 3 | 2018 | | 2 | title | title2 |
------------- | 2 | user_id | 2 |
| 3 | title | title3 |
| 3 | user_id | 1 |
---------------------------
t1 (user): t2:
| id | date | | id | key | value |
------------- -------------------------
| 1 | NULL | | 1 | name | user1 |
| 2 | NULL | | 2 | name | user2 |
------------- -------------------------
SELECT t1.id,
GROUP_CONCAT(IF(t2.key='title',t2.value,NULL)) AS title,
t1.date,
GROUP_CONCAT(IF(t2.key='user_id',t2.value,NULL)) AS user_id,
(
SELECT GROUP_CONCAT(IF(t4.key='user_name',t4.value,NULL))
FROM t4
GROUP BY t4.id
HAVING t4.id = user_id
) AS user_name
FROM t1
INNER JOIN t2
ON t1.id = t2.id
GROUP BY t1.id
i want to print out the name of the user that is stored as an id in t2 like:
| id | title | date | user_id | user_name |
------------------------------------------------
| 1 | title1 | 2016 | 1 | user1 |
| 2 | title2 | 2017 | 2 | user2 |
| 3 | title3 | 2018 | 1 | user1 |
------------------------------------------------
i have tested WHERE clause and HAVING clause, but nothing works for me.
I found your table references way too confusing, so I used an interpretation of the sample data. I only needed 3 of the 4 tables by the way. Demo
MySQL 5.6 Schema Setup:
CREATE TABLE articles
(`id` int, `date` date)
;
INSERT INTO articles
(`id`, `date`)
VALUES
(1, '2016-01-01'),
(2, '2017-01-01'),
(3, '2018-01-01')
;
CREATE TABLE users
(`id` int, `date` date)
;
INSERT INTO users
(`id`, `date`)
VALUES
(1, NULL),
(2, NULL)
;
CREATE TABLE t2_upper
(`id` int, `key` varchar(7), `value` varchar(6))
;
INSERT INTO t2_upper
(`id`, `key`, `value`)
VALUES
(1, 'title', 'title1'),
(1, 'user_id', '1'),
(2, 'title', 'title2'),
(2, 'user_id', '2'),
(3, 'title', 'title3'),
(3, 'user_id', '1')
;
CREATE TABLE t2_lower
(`id` int, `key` varchar(4), `value` varchar(5))
;
INSERT INTO t2_lower
(`id`, `key`, `value`)
VALUES
(1, 'name', 'user1'),
(2, 'name', 'user2')
;
Query 1:
select a.id, tn.value article_title, a.date, tu.id user_id, u.value user_name
from articles a
inner join (
select
*
from t2_upper
where `key` = 'title'
) tn on a.id = tn.id
inner join (
select
*
from t2_upper
where `key` = 'user_id'
) tu on a.id = tu.id
inner join (
select
*
from t2_lower
where `key` = 'name'
) u on tu.value = u.id
Results:
| id | article_title | date | user_id | user_name |
|----|---------------|------------|---------|-----------|
| 1 | title1 | 2016-01-01 | 1 | user1 |
| 2 | title2 | 2017-01-01 | 2 | user2 |
| 3 | title3 | 2018-01-01 | 3 | user1 |
Related
I have two tables like this
and I want latest data by date
tbl_fruit_info
+-----+--------+
| sId | sName |
+-----+--------+
| 1 | Apple |
| 2 | Banana |
| 3 | Orange |
+-----+--------+
tbl_fruit_data
+------------+----------+-------------+
| date | fruit_id | fruit_price |
+------------+----------+-------------+
| 2017-01-26 | 1 | 44.7 |
| 2017-01-27 | 1 | 51 |
| 2017-01-25 | 1 | 71.5 |
| 2017-01-21 | 2 | 44 |
| 2017-01-23 | 2 | 55 |
| 2017-01-24 | 2 | 71 |
+------------+----------+-------------+
I tried with this
SELECT tbl_fruit_info.*, tbl_fruit_data.*
FROM tbl_fruit_data
LEFT JOIN
tbl_fruit_info ON tbl_fruit_info.sId = tbl_fruit_data.fruit_id
GROUP BY
tbl_fruit_info.sId
ORDER BY
max(tbl_fruit_data.date) DESC;
The Output I am looking for is like this:
+-----+--------+----------------------------+
| sId | sName | date |fruit_price |
+-----+--------+----------------------------+
| 1 | Apple | 2017-01-27 | 51 |
| 2 | Banana | 2017-01-24 | 71 |
| 3 | Orange | 0000-00-00 | 0 |
+-----+--------+----------------------------+
But I get this:
+-----+--------+----------------------------+
| sId | sName | date |fruit_price |
+-----+--------+----------------------------+
| 1 | Apple | 2017-01-26 | 44.7 |
| 2 | Banana | 2017-01-21 | 44 |
+-----+--------+----------------------------+
Any assistance would be greatly appreciated.
select * from tbl_fruit_data f
left join tbl_fruit_info i ON i.sId = f.fruit_id
where f.Date =
(Select max(date) from tbl_fruit_data
where fruit_id = f.fruit_id)
SELECT fi.*, fd.*
FROM tbl_fruit_data fd
FULL OUTER JOIN tbl_fruit_info fi ON fi.sId = fd.fruit_id
WHERE fd.fruit_id IS NULL OR fd.date = (
SELECT max(fd_inner.date)
FROM tbl_fruit_data fd_inner
WHERE fd_inner.fruit_id = fd.fruit_id
)
ORDER BY fd.date DESC;
Update 2017-01-30: Incorporates rows in tbl_fruit_info that don't have a corresponding row in tbl_fruit_data, now.
Ok here goes.
**Get the latest prices on fruit, ADDED fruits not having a price
SELECT d1.date, d1.fruit_id, d1.fruit_price, i.sId, i.sName
FROM tbl_fruit_info i
LEFT JOIN tbl_fruit_data d1
ON d1.fruit_id = i.sId
WHERE d1.date = (SELECT MAX(d2.date)
FROM tbl_fruit_data d2
WHERE d2.fruit_id = d1.fruit_id
)
UNION
SELECT CAST('0001-01-01' AS datetime) date, i.sId fruit_id, 0 fruit_price, i.sId, i.sName
FROM tbl_fruit_info i
WHERE i.sId NOT IN (SELECT d2.fruit_id FROM tbl_fruit_data d2)
Sql fiddle for test on the same data provides in question:
http://sqlfiddle.com/#!9/872ed4/9
Used these definitions
CREATE TABLE tbl_fruit_info
(`sId` int, `sName` varchar(6))
;
INSERT INTO tbl_fruit_info
(`sId`, `sName`)
VALUES
(1, 'Apple'),
(2, 'Banana'),
(3, 'Orange')
;
CREATE TABLE tbl_fruit_data
(`date` datetime, `fruit_id` int, `fruit_price` int)
;
INSERT INTO tbl_fruit_data
(`date`, `fruit_id`, `fruit_price`)
VALUES
('2017-01-26 00:00:00', 1, 44.7),
('2017-01-27 00:00:00', 1, 51),
('2017-01-25 00:00:00', 1, 71.5),
('2017-01-21 00:00:00', 2, 44),
('2017-01-23 00:00:00', 2, 55),
('2017-01-24 00:00:00', 2, 71)
;
Using dadde's fiddle (with some tweaks) - and assuming that the MySQL tag is correct...
CREATE TABLE tbl_fruit_info
(`sId` int auto_increment PRIMARY KEY, `sName` varchar(6))
;
INSERT INTO tbl_fruit_info
(`sId`, `sName`)
VALUES
(1, 'Apple'),
(2, 'Banana'),
(3, 'Orange')
;
CREATE TABLE tbl_fruit_data
(`date` datetime, `fruit_id` int, `fruit_price` int, primary key (fruit_id,date))
;
INSERT INTO tbl_fruit_data
(`date`, `fruit_id`, `fruit_price`)
VALUES
('2017-01-26 00:00:00', 1, 44.7),
('2017-01-27 00:00:00', 1, 51),
('2017-01-25 00:00:00', 1, 71.5),
('2017-01-21 00:00:00', 2, 44),
('2017-01-23 00:00:00', 2, 55),
('2017-01-24 00:00:00', 2, 71)
;
SELECT a.sid
, a.sname
, COALESCE(b.date,'0000-00-00') date
, COALESCE(b.fruit_price,0) fruit_price
FROM tbl_fruit_info a
LEFT
JOIN
( SELECT x.*
FROM tbl_fruit_data x
JOIN
( SELECT fruit_id, MAX(date) date
FROM tbl_fruit_data
GROUP
BY fruit_id
) y
ON y.fruit_id = x.fruit_id
AND y.date = x.date) b
ON b.fruit_id = a.sid;
+-----+--------+---------------------+-------------+
| sid | sname | date | fruit_price |
+-----+--------+---------------------+-------------+
| 1 | Apple | 2017-01-27 00:00:00 | 51 |
| 2 | Banana | 2017-01-24 00:00:00 | 71 |
| 3 | Orange | 0000-00-00 | 0 |
+-----+--------+---------------------+-------------+
create table #t1
(id int,name varchar(100));
create table #t2(
[date] date,
id int,
price float)
insert into #t1
select 1,'Apple'
union
select 2,'Banana'
insert into #t2
select getdate()-3,1,33.2
union
select getdate()-2,1,30.5
union
select getdate()-4,1,23.4
union
select getdate()-3,2,21
union
select getdate()-2,2,35
Query
select q.name,t2.* from (
select t1.id,t1.name,MAX(t2.date) as date from #t1 t1
inner join #t2 t2 on t1.id=t2.id
group by t1.id,t1.name
) as q inner join #t2 t2
on q.id=t2.id and t2.date=q.date
Edit: Fixed, replaced CTE with subquery, thanks dadde for pointing out CTE isn't supported in MySQL. CTE or Subquery does the same job here
I am working on a project where users table has column Country,state and city. and another table named projects also contains the column country,state and city.
Now i want to get the most relevent results from project table where projects should have same city,state and country. means the row where city.state and country all match should be on top. and which only match country should be at bottom.
users
ID | username | country | state | city
1 | user1 | country1| state1 |city1
2 | user2 | country2| state2 |city2
3 | user3 | country3| state3 |city3
projects
title | country | state | city
p1 | country1| state1 |city1
p2 | country1| state1 |city2
p3 | country1| state2 |city2
Suppose user1 is login and i want to show most relevent results to this user according to user location.
e.g in project taqble in row p1 all country state and city mis matching with user country state and city. in p2 two only country and state is matching and in p3 only country is matching. what i want to do it to retrieve row in in this order p1,p2 and p3.
Try this, hope help for you;)
SQL Fiddle
MySQL 5.6 Schema:
CREATE TABLE users
(`ID` int, `username` varchar(5), `country` varchar(8), `state` varchar(6), `city` varchar(5))
;
INSERT INTO users
(`ID`, `username`, `country`, `state`, `city`)
VALUES
(1, 'user1', 'country1', 'state1', 'city1'),
(2, 'user2', 'country2', 'state2', 'city2'),
(3, 'user3', 'country3', 'state3', 'city3')
;
CREATE TABLE projects
(`title` varchar(2), `country` varchar(8), `state` varchar(6), `city` varchar(5))
;
INSERT INTO projects
(`title`, `country`, `state`, `city`)
VALUES
('p1', 'country1', 'state1', 'city1'),
('p2', 'country1', 'state1', 'city2'),
('p3', 'country1', 'state2', 'city2')
;
Query 1:
select t1.*, t2.*, (t1.country = t2.country) + (t1.state = t2.state) + (t1.city = t2.city) as cnt
from users t1
left join projects t2
on t1.country = t2.country or t1.state = t2.state or t1.city = t2.city
order by t1.id, cnt desc
Results:
| ID | username | country | state | city | title | country | state | city | cnt |
|----|----------|----------|--------|-------|--------|----------|--------|--------|--------|
| 1 | user1 | country1 | state1 | city1 | p1 | country1 | state1 | city1 | 3 |
| 1 | user1 | country1 | state1 | city1 | p2 | country1 | state1 | city2 | 2 |
| 1 | user1 | country1 | state1 | city1 | p3 | country1 | state2 | city2 | 1 |
| 2 | user2 | country2 | state2 | city2 | p3 | country1 | state2 | city2 | 2 |
| 2 | user2 | country2 | state2 | city2 | p2 | country1 | state1 | city2 | 1 |
| 3 | user3 | country3 | state3 | city3 | (null) | (null) | (null) | (null) | (null) |
I have a table like this:
// mytable
+----+---------+---------+
| id | related | color |
+----+---------+---------+
| 1 | 1 | red |
| 2 | 1 | blue |
| 3 | 3 | green |
| 4 | 1 | white |
| 5 | 3 | brown |
| 6 | 6 | gray |
| 7 | 3 | black |
| 8 | 1 | orange |
| 9 | 6 | pink |
+----+---------+---------+
I have an id number and I need to get the color of related id.
For example:
$id = 4; // I need to get `red`
$id = 5; // I need to get `green`
$id = 6; // I need to get `gray`
$id = 9; // I need to get `gray`
I can do that by using a JOIN. Something like this:
SELECT t2.color FROM mytable t1 JOIN mytable t2 ON t1.related = t2.id WHERE t1.id = :id
My query works as expected .. But I'm not sure using a JOIN for doing that is standard. Actually I'm trying to know is there any better approach? Or mine is a normal way?
What's wrong with SELECT t.related FROM mytable t WHERE t.id = :id? JOIN makes nothing more but checking if there is a actual id in 'related' column or not
I've done two different query and explain them, hope can give you some hints.
SQL Fiddle
MySQL 5.6 Schema:
CREATE TABLE mytable
(`id` int, `related` int, `color` varchar(6))
;
INSERT INTO mytable
(`id`, `related`, `color`)
VALUES
(1, 1, 'red'),
(2, 1, 'blue'),
(3, 3, 'green'),
(4, 1, 'white'),
(5, 3, 'brown'),
(6, 6, 'gray'),
(7, 3, 'black'),
(8, 1, 'orange'),
(9, 6, 'pink')
;
Query 1:
SELECT t2.color FROM mytable t1 JOIN mytable t2 ON t1.related = t2.id WHERE t1.id = '4'
Results:
| color |
|-------|
| red |
Query 2:
explain SELECT t2.color FROM mytable t1 JOIN mytable t2 ON t1.related = t2.id WHERE t1.id = '4'
Results:
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
|----|-------------|-------|------|---------------|--------|---------|--------|------|----------------------------------------------------|
| 1 | SIMPLE | t1 | ALL | (null) | (null) | (null) | (null) | 9 | Using where |
| 1 | SIMPLE | t2 | ALL | (null) | (null) | (null) | (null) | 9 | Using where; Using join buffer (Block Nested Loop) |
Query 3:
SELECT t1.color FROM mytable t1 WHERE exists (select 1 from mytable t2 where t1.id = t2.related and t2.id ='4')
Results:
| color |
|-------|
| red |
Query 4:
explain SELECT t1.color FROM mytable t1 WHERE exists (select 1 from mytable t2 where t1.id = t2.related and t2.id ='4')
Results:
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
|----|--------------------|-------|------|---------------|--------|---------|--------|------|-------------|
| 1 | PRIMARY | t1 | ALL | (null) | (null) | (null) | (null) | 9 | Using where |
| 2 | DEPENDENT SUBQUERY | t2 | ALL | (null) | (null) | (null) | (null) | 9 | Using where |
you can handle this in simple ways also
select t.color from mytable t where t.id = '$id' (for one value)
select t.color from mytable t where t.id in ('$id1','$id2','$id3','$id4' ) (for multi-values comma separated strings)
I have 2 Tables and I want to join a to b and for eace join get the unjoind results
table pixel
+----+------------+------------+-------------------+--------+------+------------+
| id | account_id | project_id | uuid | name | type | date |
+----+------------+------------+-------------------+--------+------+------------+
| 10 | 2 | 3 | E03AA~F86A1~7C661 | test 1 | 0 | 1420553362 |
| 11 | 2 | 3 | A3E3B~B4182~DA556 | test 2 | 1 | 1420553933 |
| 9 | 1 | 1 | 57EAE~E633C~B929F | test 3 | 1 | 1420041387 |
+----+------------+------------+-------------------+--------+------+------------+
table pixel_tags
+----+------------+-------------------+--------------+--------------+------------+
| id | project_id | pixel | tag | name | date |
+----+------------+-------------------+--------------+--------------+------------+
| 6 | 0 | 57EAE~E633C~B929F | facebook-cpc | facebook-cpc | 1420041606 |
| 7 | 0 | 57EAE~E633C~B929F | google-cpc | google-cpc | 1420041621 |
| 8 | 0 | A3E3B~B4182~DA556 | utm_google | test | 1420554059 |
+----+------------+-------------------+--------------+--------------+------------+
this is my query
SELECT
`pixel`.*,
(CASE WHEN `pixel_tags`.`name` <>'' THEN `pixel_tags`.`name` ELSE `pixel`.`name` END ) `p_name`,
`pixel_tags`.`tag`
FROM `pixel`
LEFT JOIN `pixel_tags` ON `pixel`.`uuid`=`pixel_tags`.`pixel`
WHERE `pixel`.`account_id`='1'
the result is
if there are tags for the pixel they will show up in the name,
but I need to return both, so for example if one pixel has 2 tags, I wanna get 3 rows, 1 with the name and 2 with the tags
Thank you.
dump
-- phpMyAdmin SQL Dump
-- version 4.0.10.7
-- http://www.phpmyadmin.net
--
-- Host: localhost
-- Generation Time: May 14, 2015 at 01:19 PM
-- Server version: 5.5.42-cll
-- PHP Version: 5.4.23
SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
SET time_zone = "+00:00";
--
-- Database: `mslm_db`
--
-- --------------------------------------------------------
--
-- Table structure for table `pixel`
--
CREATE TABLE IF NOT EXISTS `pixel` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`account_id` int(11) NOT NULL,
`project_id` int(11) NOT NULL,
`uuid` text NOT NULL,
`name` text NOT NULL,
`type` int(11) NOT NULL,
`date` bigint(20) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=22 ;
--
-- Dumping data for table `pixel`
--
INSERT INTO `pixel` (`id`, `account_id`, `project_id`, `uuid`, `name`, `type`, `date`) VALUES
(10, 2, 3, '75D79~535F8~96FA1~F1B5E~C21E7~E03AA~F86A1~7C661', '×—×ž×•×¦×™× ×–×” ××—', 0, 1420553362),
(11, 2, 3, '195A6~83005~4C660~62EF3~8C79A~A3E3B~B4182~DA556', '×—×ž×•×¦×™× ×–×” ×חות', 1, 1420553933),
(9, 1, 1, 'D0950~15D68~354C8~5FBAE~DAF05~57EAE~E633C~B929F', 'טורקיז', 1, 1420041387),
(12, 4, 5, 'E92E8~DEDA0~11571~86FEA~13AF9~B2266~F8EFD~FB9D3', 'חביתה', 0, 1420554873),
(13, 4, 5, '38FFD~3A1F4~A3CDE~7A90E~AF099~CD11D~28752~67D77', 'חלומי', 1, 1420555402),
(14, 4, 5, '9525D~A8682~1932E~85D96~B5830~03BF8~9C77D~7EBE2', 'סביח', 1, 1420555681),
(15, 5, 6, '3784E~151DA~7BFDE~C12F6~A6C01~435E3~36E4E~ED4AB', '×‘×™×§×™× ×™ בוטו×', 1, 1420556203),
(16, 1, 1, '1211B~9C86C~83024~9039C~43F8F~B639D~547EB~8CFAC', 'שולחן', 0, 1421322108),
(17, 1, 1, 'A8DF0~23617~904F6~94880~99192~4781E~D8712~221A7', 'כס×', 1, 1421322943),
(18, 1, 1, '0A492~EA76B~01948~061AB~A74A7~34F58~42DAC~366DE', 'חזותה', 0, 1421945914),
(19, 1, 20, '2E3FE~200C7~FC8E1~17323~A9A1D~6F278~CBECF~CDD6E', '×’× - מעיל', 0, 1422351583),
(20, 1, 20, '85CF8~71D5A~71C24~D9FC1~3A041~A1AC7~AB6CE~E1B1D', 'שפן של מורדי', 0, 1431527532),
(21, 1, 0, 'AF627~4E88E~13138~49BE4~49BB7~DAB92~DF35E~14C97', '', 0, 1431589094);
-- --------------------------------------------------------
--
-- Table structure for table `pixel_tags`
--
CREATE TABLE IF NOT EXISTS `pixel_tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`project_id` int(11) NOT NULL,
`pixel` text NOT NULL,
`tag` text NOT NULL,
`name` text NOT NULL,
`date` bigint(20) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=11 ;
--
-- Dumping data for table `pixel_tags`
--
INSERT INTO `pixel_tags` (`id`, `project_id`, `pixel`, `tag`, `name`, `date`) VALUES
(6, 0, 'D0950~15D68~354C8~5FBAE~DAF05~57EAE~E633C~B929F', 'facebook-cpc', 'facebook-cpc', 1420041606),
(7, 0, 'D0950~15D68~354C8~5FBAE~DAF05~57EAE~E633C~B929F', 'google-cpc', 'google-cpc', 1420041621),
(8, 0, '195A6~83005~4C660~62EF3~8C79A~A3E3B~B4182~DA556', 'utm_google', 'גוגל גוגל', 1420554059),
(9, 0, '9525D~A8682~1932E~85D96~B5830~03BF8~9C77D~7EBE2', 'utm-facebook', 'פייסבוק', 1420556056),
(10, 0, 'A8DF0~23617~904F6~94880~99192~4781E~D8712~221A7', 'h_test', '×—× ×” בדיקה', 1421323080);
The query may be-
SELECT `pixel`.*,
`pixel_tags`.`name`as p_name,
`pixel_tags`.`tag`
FROM `pixel`
JOIN `pixel_tags` ON `pixel`.`uuid`=`pixel_tags`.`pixel`
WHERE `pixel`.`account_id`='1'
UNION
SELECT `pixel`.*, NULL , NULL
FROM `pixel`
WHERE `pixel`.`account_id`='1' AND `uuid` not in (select distinct pixel from pixel_tags);
i am setting an example-
mysql> select * from pixel;
+----+------------+------------+------+--------+------+------------+
| id | account_id | project_id | uuid | name | type | date |
+----+------------+------------+------+--------+------+------------+
| 10 | 2 | 3 | a | test 1 | 0 | 1420553362 |
| 11 | 2 | 3 | b | test 2 | 1 | 1420553933 |
| 9 | 1 | 1 | c | test 3 | 1 | 1420041387 |
+----+------------+------------+------+--------+------+------------+
3 rows in set (0.00 sec)
mysql> select * from pixel_tags;
+----+------------+-------+-----------+----------+------------+
| id | project_id | pixel | tag | name | date |
+----+------------+-------+-----------+----------+------------+
| 6 | 0 | c | facebook | facebook | 1420553606 |
| 7 | 0 | c | google | google | 1420041621 |
| 8 | 0 | b | do_google | test | 1420554059 |
+----+------------+-------+-----------+----------+------------+
3 rows in set (0.00 sec)
mysql> SELECT `pixel`.*,
-> `pixel_tags`.`name`as p_name,
-> `pixel_tags`.`tag`
-> FROM `pixel`
-> JOIN `pixel_tags` ON `pixel`.`uuid`=`pixel_tags`.`pixel`
-> WHERE `pixel`.`account_id`='2'
-> UNION
-> SELECT `pixel`.*, NULL , NULL
-> FROM `pixel`
-> WHERE `pixel`.`account_id`='2' AND `uuid` not in (select distinct pixel from pixel_tags);
+----+------------+------------+------+--------+------+------------+--------+-----------+
| id | account_id | project_id | uuid | name | type | date | p_name | tag |
+----+------------+------------+------+--------+------+------------+--------+-----------+
| 11 | 2 | 3 | b | test 2 | 1 | 1420553933 | test | do_google |
| 10 | 2 | 3 | a | test 1 | 0 | 1420553362 | NULL | NULL |
+----+------------+------------+------+--------+------+------------+--------+-----------+
2 rows in set (0.00 sec)
if still you are not getting then it may help. I have removed account_id condition in where from both queries.
mysql> SELECT `pixel`.*,
-> `pixel_tags`.`name`as p_name,
-> `pixel_tags`.`tag`
-> FROM `pixel`
-> JOIN `pixel_tags` ON `pixel`.`uuid`=`pixel_tags`.`pixel`
-> UNION
-> SELECT `pixel`.*, NULL , NULL
-> FROM `pixel`
-> WHERE `uuid` not in (select distinct pixel from pixel_tags);
+----+------------+------------+------+--------+------+------------+----------+-----------+
| id | account_id | project_id | uuid | name | type | date | p_name | tag |
+----+------------+------------+------+--------+------+------------+----------+-----------+
| 9 | 1 | 1 | c | test 3 | 1 | 1420041387 | facebook | facebook |
| 9 | 1 | 1 | c | test 3 | 1 | 1420041387 | google | google |
| 11 | 2 | 3 | b | test 2 | 1 | 1420553933 | test | do_google |
| 10 | 2 | 3 | a | test 1 | 0 | 1420553362 | NULL | NULL |
+----+------------+------------+------+--------+------+------------+----------+-----------+
4 rows in set (0.02 sec)
I have table with data:
| id | status |
+-----+--------+
| 1 | 1 |
| 2 | 1 |
| 3 | 0 |
| 4 | 2 |
| 5 | 2 |
I have file, that I need to load into this table and replace:
| id | status |
+----+--------+
| 1 | 1 |
| 2 | 0 |
| 3 | 0 |
| 4 | 0 |
| 5 | 1 |
I have one condition: if status in table =2 and status in file =0, leave status in table =2, otherwise replace status in table from file.
After query I need to get new data:
| id | status |
+-----+--------+
| 1 | 1 |
| 2 | 0 |
| 3 | 0 |
| 4 | 2 |
| 5 | 1 |
I'm trying do it with query:
load data local
infile '".$file."'
replace
into table t1
fields terminated by ',' enclosed by '\"'
(#tid,
teacher_name,
email,
#pid,
tca_form_type,
prod_company,
prod_name,
#stts)
set status = if((select status from (select status from t1 where teacher_id=#tid and prod_id=#pid) as tmp)=2 and #stts=0,status,#stts),
teacher_id = #tid, prod_id = #pid
After that I get status fields NULL.
How to resolve this problem?
Edit:
I tried:
set status = if((select #var:=status from (select status from t1 where teacher_id=#tid and prod_id=#pid) as tmp)=2 and #stts=0,#var,#stts),
But result status 2 changed to 0.
Table schema:
CREATE TABLE `table` (
`id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
`teacher_id` VARCHAR(20) NOT NULL COLLATE 'utf8_unicode_ci',
`status` INT(11) NULL DEFAULT NULL,
`prod_id` VARCHAR(10) NOT NULL COLLATE 'utf8_unicode_ci',
PRIMARY KEY (`id`),
UNIQUE INDEX `teacher_id_UNIQUE` (`teacher_id`, `prod_id`)
)
COLLATE='utf8_unicode_ci'
ENGINE=InnoDB
ROW_FORMAT=COMPACT
AUTO_INCREMENT=2053;
Real data:
| id | teacher_id | status | prod_id |
+-----+------------+--------+---------+
| 1 | a1 | 1 | 15 |
| 2 | a1 | 1 | 16 |
| 3 | a1 | 0 | 17 |
| 4 | a2 | 2 | 16 |
| 5 | a2 | 2 | 18 |
| 6 | a3 | 0 | 15 |
| 7 | a3 | 1 | 20 |
File data:
| teacher_id | status | prod_id |
+------------+--------+---------+
| a1 | 0 | 15 |
| a1 | 1 | 16 |
| a1 | 0 | 17 |
| a2 | 1 | 16 |
| a2 | 0 | 18 |
| a3 | 1 | 15 |
| a3 | 1 | 20 |
My temporary solution:
load data local
infile '".$file."'
into table table_tmp
fields terminated by ',' enclosed by '\"'
(teacher_id,
teacher_name,
email,
prod_id,
tca_form_type,
prod_company,
prod_name,
status);
INSERT INTO table
(teacher_id, teacher_name, email, status, prod_id, tca_form_type, prod_company, prod_name)
SELECT teacher_id, teacher_name, email, `status`, prod_id, tca_form_type, prod_company, prod_name FROM table_tmp
ON DUPLICATE KEY UPDATE table.status = IF(table.status = 2 and VALUES(status) = 0, table.status, VALUES(status));
I think this should suffice:
load data local
infile '".$file."'
replace
into table t1
fields terminated by ',' enclosed by '\"'
(#tid,
teacher_name,
email,
#pid,
tca_form_type,
prod_company,
prod_name,
#stts)
set status = if(status = 2 and #stts = 0, status, #stts),
teacher_id = #tid, prod_id = #pid;
If this doesn't help, you can try with the values() function, although it says that it's for the INSERT ... ON DUPLICATE KEY UPDATE statement.
In an INSERT ... ON DUPLICATE KEY UPDATE statement, you can use the VALUES(col_name) function in the UPDATE clause to refer to column values from the INSERT portion of the statement. In other words, VALUES(col_name) in the UPDATE clause refers to the value of col_name that would be inserted, had no duplicate-key conflict occurred. This function is especially useful in multiple-row inserts. The VALUES() function is meaningful only in the ON DUPLICATE KEY UPDATE clause of INSERT statements and returns NULL otherwise. See Section 13.2.5.3, “INSERT ... ON DUPLICATE KEY UPDATE Syntax”.
If that doesn't help either, please provide the table schema and so on, so we can have a try ourselfs and don't have to guess.