OR operator applying to entire WHERE clause - mysql

SELECT DISTINCT
customers.customer_id,
services.name
FROM users
INNER JOIN customers ON users.user_id=customers.user_id
LEFT JOIN appointments ON customers.customer_id=appointments.customer_id
INNER JOIN pets ON customers.customer_id=pets.customer_id
INNER JOIN services on appointments.service_id=services.service_id
WHERE ((appointments.customer_id IS NULL)
OR NOT (appointments.date > (SELECT SUBDATE(CURDATE(), 365)))
OR ((appointments.date > (SELECT SUBDATE(CURDATE(), 365)))
AND services.name NOT LIKE '%General Health Checkup%'))
GROUP BY customers.customer_id
I am trying to find all customers who are due a yearly general health checkup
this requires them to have:
a) never have appointments
b) not had an appointment in the past year
c) had an appointment in the past year but it wasn't a general health checkup
I assumed the final OR im my WHERE clause would only apply to that that operation i.e.
OR ((appointments.date > (SELECT SUBDATE(CURDATE(), 365))) AND services.name NOT LIKE '%General Health Checkup%'))
however it is ruling out all options for services named General Health Checkup.
How can i only apply this to that area of the where clause so that general health check up appointments can get through but only if they are from over a year ago.
Thanks !
appointments table:
CREATE TABLE `appointments` (
`appointment_id` int(8) NOT NULL,
`customer_id` int(8) DEFAULT NULL,
`service_id` int(4) DEFAULT NULL,
`staff_id` int(6) DEFAULT NULL,
`pet_id` int(9) DEFAULT NULL,
`date` date NOT NULL,
`start_time` time NOT NULL,
`status` enum('Open','Cancelled','Completed','') NOT NULL,
`create_date` datetime NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
--
-- Dumping data for table `appointments`
--
INSERT INTO `appointments` (`appointment_id`, `customer_id`, `service_id`, `staff_id`, `pet_id`, `date`, `start_time`, `status`, `create_date`) VALUES
(1, 1, 2, 1, 1, '2017-03-22', '10:00:00', 'Completed', '2022-03-16 11:28:46'),
(2, 3, 2, 1, 6, '2021-06-18', '12:00:00', 'Completed', '2021-06-15 11:01:43'),
(3, 2, 2, 1, 2, '2020-07-17', '13:00:00', 'Completed', '2020-05-14 11:30:18'),
(4, 3, 2, 1, 5, '2020-07-10', '14:00:00', 'Completed', '2020-05-21 11:30:18'),
(5, 4, 3, 1, 7, '2020-09-17', '10:00:00', 'Completed', '2022-03-16 12:31:59'),
(6, 8, 2, 1, 11, '2022-03-17', '12:00:00', 'Cancelled', '2022-03-17 23:44:56'),
(7, 4, 2, 7, 7, '2022-03-17', '10:00:00', 'Cancelled', '2022-03-17 23:50:11'),
(8, 1, 1, 13, 1, '2022-03-17', '13:00:00', 'Completed', '2022-03-18 00:28:10'),
(9, 7, 2, 13, 9, '2022-03-18', '15:00:00', 'Cancelled', '2022-03-18 13:16:37'),
(10, 7, 1, 13, 10, '2022-03-18', '16:00:00', 'Cancelled', '2022-03-18 13:48:12'),
(11, 1, 1, 13, 1, '2022-03-22', '11:00:00', 'Completed', '2022-03-22 12:34:55'),
(12, 11, 1, 13, 11, '2022-03-23', '13:00:00', 'Completed', '2022-03-23 15:28:22'),
(13, 9, 3, 13, 12, '2022-03-26', '13:00:00', 'Completed', '2022-03-26 13:13:46'),
(14, 35, 2, 13, 16, '2022-03-27', '10:00:00', 'Completed', '2022-03-27 16:09:14'),
(15, 34, 2, 13, 20, '2022-03-28', '10:00:00', 'Completed', '2022-03-28 10:05:41'),
(16, 33, 1, 13, 20, '2022-03-28', '12:00:00', 'Completed', '2022-03-28 11:40:50'),
(17, 8, 2, 13, 20, '2022-03-16', '14:00:00', 'Completed', '2022-03-28 12:31:42'),
(18, 15, 2, 13, 20, '2022-03-28', '14:00:00', 'Completed', '2022-03-28 12:33:47'),
(19, 31, 4, 13, 20, '2022-03-29', '00:00:00', 'Completed', '2022-03-29 14:20:04'),
(20, 31, 4, 13, 20, '2022-03-29', '10:00:00', 'Completed', '2022-03-29 14:20:42'),
(21, 1, 1, 13, 1, '2022-03-30', '11:00:00', 'Completed', '2022-03-30 15:18:23'),
(22, 33, 4, 13, 22, '2022-03-30', '12:00:00', 'Completed', '2022-03-30 15:22:02'),
(23, 3, 1, 13, 5, '2022-03-30', '13:00:00', 'Open', '2022-03-30 15:22:02'),
(24, 4, 1, 13, 7, '2022-03-30', '13:30:00', 'Completed', '2022-03-30 15:24:52'),
(25, 7, 2, 13, 10, '2022-03-30', '14:30:00', 'Open', '2022-03-30 15:26:11'),
(26, 12, 1, 7, 8, '2022-04-21', '10:00:00', 'Open', '2022-04-21 12:54:10'),
(27, 2, 1, 1, 8, '2022-04-21', '10:00:00', 'Cancelled', '2022-04-21 13:16:23'),
(28, 17, 4, 1, 20, '2022-04-21', '10:00:00', 'Completed', '2022-04-21 13:18:41'),
(29, NULL, 6, 7, 21, '2022-04-21', '12:00:00', 'Completed', '2022-04-21 16:22:44'),
(30, 13, 2, 3, 5, '2022-04-21', '14:00:00', 'Open', '2022-04-21 17:42:10'),
(31, 5, 1, 9, 14, '2022-04-22', '11:00:00', 'Open', '2022-04-22 16:16:57');
services table:
CREATE TABLE `services` (
`service_id` int(4) NOT NULL,
`name` varchar(100) NOT NULL,
`description` text NOT NULL,
`average_time` int(3) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
--
-- Dumping data for table `services`
--
INSERT INTO `services` (`service_id`, `name`, `description`, `average_time`) VALUES
(1, 'Consultation', 'General consultation to help you find the best path to good health for your pet.', 30),
(2, 'General Health Checkup', 'Review of your pets health.', 30),
(3, 'Microchip Insertion', 'Keep your dog safe and trackable with microchip.', 90),
(4, 'Puppy Vaccination', 'Initial puppy vaccination', 30),
(6, 'Booster Vaccination', 'Regular booster vaccincation service.', 30);

I would just check if the customer had a service_id=2 in the last year:
SELECT
customers.customer_id,
GROUP_CONCAT(CONCAT(services.name,'(',appointments.date,')')) as services
FROM users
INNER JOIN customers ON users.user_id=customers.user_id
LEFT JOIN appointments ON customers.customer_id=appointments.customer_id
INNER JOIN pets ON customers.customer_id=pets.customer_id
INNER JOIN services on appointments.service_id=services.service_id
WHERE SUBDATE(CURDATE(), 365) > (SELECT MAX(date)
FROM appointments
WHERE customers.customer_id=appointments.customer_id
AND appointments.service_id=2)
GROUP BY customers.customer_id
output:
customer_id
services
1
General Health Checkup(2017-03-22),Consultation(2022-03-30),Consultation(2022-03-22),Consultation(2022-03-17)
2
General Health Checkup(2020-07-17),Consultation(2022-04-21)
see: DBFIDDLE

Related

Update one table column data to another table column along with unique,duplicate check and update with suffix on duplicate

Need to do it for lower Mysql version like 4.9 to 5.6
I need to copy one table column data to another table but need to apply unique check and in case found duplicate then needs to add suffix to data and continue the update.(Don't want to stop query execution because of duplicate data) .
Let me clarify things:
My first table is tbl_categories:
cat_id cat_parent_id cat_active cat_display_order cat_suggested_hourly_rate
1 0 1 1 10
2 1 1 2 10
And second table is tbl_categories_metadata:
cdata_cat_id cdata_lang_id cdata_name
1 1 A
1 2 B
1 3 C
2 1 A
2 2 B
3 1 D
3 2 E
3 3 F
So in my second table category name added based on language id.
Now I need to add a unique column in first table with name cat_identifier, so I did :
ALTER TABLE `tbl_categories` ADD `cat_identifier` VARCHAR(100) NOT NULL AFTER `cat_id`;
Which worked fine, Now I have to make it unique, but straight forward it can not be done due to similar value present while running above query, so I did:
UPDATE
`tbl_categories` a
INNER JOIN `tbl_categories` b ON `a`.cat_id = `b`.cat_id
SET
`a`.cat_identifier = `b`.cat_id;
It worked fine and cat_id added to cat_identifier column, now I am able to made this column unique via below query :
ALTER TABLE `tbl_categories`
ADD UNIQUE KEY `cat_identifier` (`cat_identifier`);
Worked fine,and my table now look like this now:
cat_id cat_identifier cat_parent_id cat_active cat_display_order cat_suggested_hourly_rate
1 1 0 1 1 10
2 2 1 1 2 10
Where I am stuck:
I need to update cat_identifier values taken from cdata_name column based on language id 1, but in-case language id 1 has same data for 2 categories, then i need to add -cat_id as suffix for that data and needs to update
So I tried below query :
UPDATE
`tbl_categories`
INNER JOIN `tbl_categories_metadata` ON `tbl_categories`.cat_id = `tbl_categories_metadata`.cdata_cat_id
SET
`tbl_categories`.cat_identifier = `tbl_categories_metadata`.cdata_name
WHERE
`tbl_categories_metadata`.cdata_lang_id = 1;
It's working , but at once duplicate found for language 1 it stops.
What I want is In case duplicate found then add -cat_id (category id of column) as suffix and do update. like clean-3,clean-4 etc...
Purpose to do so : Sometime admin/front-end seller not adding language specific names for categories and some time they add same name, so we added cat_identifier which will be unique,language independent as well as mandatory to add. This concept will work straightforward for new installation of our project,but in already working system(previous version of our projects) we have to do it in a way so that with minimal changes system work fine.
Note: Queries to create both table along with data
CREATE TABLE `tbl_categories` (
`cat_id` int(11) UNSIGNED NOT NULL,
`cat_identifier` varchar(100) NOT NULL,
`cat_parent_id` int(11) UNSIGNED NOT NULL COMMENT '0 defaults to parent category',
`cat_active` tinyint(4) UNSIGNED NOT NULL COMMENT '0 - Inactive, 1 - Active',
`cat_display_order` decimal(4,2) NOT NULL,
`cat_suggested_hourly_rate` decimal(10,2) NOT NULL COMMENT 'This will be used as suggestion hourly rate for this category.'
) ENGINE=MyISAM DEFAULT CHARSET=utf8mb4;
INSERT INTO `tbl_categories` (`cat_id`, `cat_identifier`, `cat_parent_id`, `cat_active`, `cat_display_order`, `cat_suggested_hourly_rate`) VALUES
(1, '', 0, 1, '1.00', '20.00'),
(2, '', 1, 1, '4.00', '15.00'),
(3, '', 1, 0, '3.00', '12.00'),
(4, '', 1, 1, '1.00', '18.00'),
(5, '', 1, 1, '2.00', '15.00'),
(6, '', 1, 1, '5.00', '10.00'),
(7, '', 0, 1, '2.00', '25.00'),
(8, '', 7, 1, '1.00', '20.00'),
(9, '', 7, 1, '2.00', '20.00'),
(10, '', 7, 1, '3.00', '20.00'),
(11, '', 0, 1, '3.00', '25.00'),
(12, '', 11, 1, '1.00', '20.00'),
(13, '', 11, 1, '2.00', '25.00'),
(14, '', 0, 1, '4.00', '20.00'),
(15, '', 14, 1, '1.00', '18.00'),
(16, '', 14, 1, '2.00', '25.00'),
(17, '', 0, 1, '5.00', '30.00'),
(18, '', 17, 1, '1.00', '0.00'),
(19, '', 17, 1, '2.00', '0.00'),
(20, '', 17, 1, '3.00', '0.00'),
(21, '', 0, 0, '2.00', '20.00'),
(22, '', 0, 0, '4.00', '25.00'),
(23, '', 0, 1, '5.00', '15.00'),
(24, '', 0, 0, '8.00', '22.00'),
(25, '', 0, 0, '9.00', '28.00'),
(26, '', 0, 1, '1.00', '20.00'),
(27, '', 26, 1, '1.00', '20.00'),
(28, '', 26, 1, '2.00', '45.00'),
(29, '', 26, 1, '3.00', '40.00'),
(30, '', 0, 0, '2.00', '15.00'),
(31, '', 0, 1, '3.00', '30.00'),
(32, '', 31, 1, '1.00', '22.00'),
(33, '', 31, 1, '2.00', '0.00'),
(34, '', 0, 0, '4.00', '15.00'),
(35, '', 0, 1, '5.00', '25.00'),
(36, '', 35, 1, '1.00', '25.00'),
(37, '', 35, 1, '2.00', '10.00'),
(38, '', 0, 0, '1.00', '40.00'),
(39, '', 0, 1, '3.00', '25.00'),
(40, '', 39, 1, '1.00', '22.00'),
(41, '', 39, 1, '2.00', '25.00'),
(42, '', 0, 0, '6.00', '35.00'),
(43, '', 0, 1, '7.00', '15.00'),
(44, '', 23, 1, '1.00', '22.00'),
(45, '', 23, 1, '2.00', '20.00'),
(46, '', 7, 1, '4.00', '25.00'),
(47, '', 43, 1, '1.00', '35.00'),
(48, '', 43, 1, '2.00', '18.00'),
(49, '', 43, 1, '3.00', '20.00'),
(50, '', 43, 1, '4.00', '40.00'),
(51, '', 7, 1, '5.00', '28.00'),
(52, '', 0, 1, '1.00', '10.00'),
(53, '', 0, 1, '1.00', '10.00');
ALTER TABLE `tbl_categories`
ADD PRIMARY KEY (`cat_id`);
ALTER TABLE `tbl_categories`
MODIFY `cat_id` int(11) UNSIGNED NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=54;
CREATE TABLE `tbl_categories_metadata` (
`cdata_cat_id` int(11) UNSIGNED NOT NULL COMMENT 'ID of table tbl_categories',
`cdata_lang_id` int(11) UNSIGNED NOT NULL,
`cdata_name` varchar(255) NOT NULL
) ENGINE=MyISAM DEFAULT CHARSET=utf8mb4;
INSERT INTO `tbl_categories_metadata` (`cdata_cat_id`, `cdata_lang_id`, `cdata_name`) VALUES
(1, 3, 'Limpieza'),
(1, 2, 'Nettoyage'),
(1, 1, 'Cleaning'),
(2, 1, 'Bathroom Deep Cleaning'),
(2, 2, 'Nettoyage en profondeur de la salle de bain'),
(2, 3, 'Limpieza profunda de ba?'),
(3, 3, 'Limpieza de alfombras'),
(3, 2, 'Nettoyage de tapis'),
(3, 1, 'Carpet Cleaning'),
(4, 3, 'Limpieza profunda en el hogar'),
(4, 2, 'Nettoyage en profondeur'),
(4, 1, 'Home Deep Cleaning'),
(5, 1, 'Kitchen Deep Cleaning'),
(5, 2, 'Nettoyage en profondeur de la cuisine'),
(5, 3, 'Limpieza profunda de cocina'),
(6, 1, 'Car Cleaning'),
(6, 2, 'Nettoyage de voiture'),
(6, 3, 'Limpieza de coches'),
(7, 3, 'Experto'),
(7, 2, 'Qualifié'),
(7, 1, 'Skilled'),
(8, 1, 'Electricians'),
(8, 2, '?'),
(8, 3, 'Electricistas'),
(9, 1, 'Plumbers'),
(9, 2, 'Plombiers'),
(9, 3, 'Fontaneros'),
(10, 1, 'Carpenters'),
(10, 2, 'Charpentiers'),
(10, 3, 'Carpinteros'),
(11, 1, 'Fitness & Yoga'),
(11, 2, 'Fitness et yoga'),
(11, 3, 'Fitness y yoga'),
(12, 1, 'Fitness Trainer at Home'),
(12, 2, 'Fitness Trainer ?'),
(12, 3, 'Entrenador de fitness en casa'),
(13, 1, 'Yoga Trainer at Home'),
(13, 2, 'Formateur de yoga ?'),
(13, 3, 'Entrenador de yoga en casa'),
(14, 1, 'Salon at Home'),
(14, 2, 'Salon ?'),
(14, 3, 'Salon en casa'),
(15, 3, 'Salon en casa'),
(15, 2, 'Salon à domicile'),
(15, 1, 'Salon at home'),
(16, 1, 'Makeup and Hairstyling'),
(16, 2, 'Maquillage et Coiffure'),
(16, 3, 'Maquillaje y Peluquer?'),
(17, 3, 'Servicios de fotografia'),
(17, 2, 'Services de photographie'),
(17, 1, 'Photography Services'),
(18, 1, 'Wedding Photography & Filming'),
(18, 2, 'Photographie et tournage de mariage'),
(18, 3, 'Fotografía y filmación de bodas'),
(19, 3, 'Fotografía y rodaje de cumpleaños'),
(19, 2, 'Photographie et tournage d\'anniversaire'),
(19, 1, 'Birthday Photography & Filming'),
(20, 1, 'Family Function Shoots'),
(20, 2, 'Prise de vue en famille'),
(20, 3, 'Disparos de funciones familiares'),
(21, 3, 'Pintura mural'),
(21, 2, 'Peinture murale'),
(22, 2, 'Charpenterie'),
(22, 1, 'Carpentry'),
(23, 3, 'Personal de mantenimiento'),
(23, 2, 'Bricoleur'),
(23, 1, 'Handyman'),
(24, 3, 'Actividades de jardinería'),
(24, 2, 'Activités de jardinage'),
(24, 1, 'Gardening Activities'),
(25, 2, 'Déménagement d\'une maison complète / déménagement d\'une maison'),
(25, 3, 'Remoción de casa completa / mudanza de casa'),
(25, 1, 'Full House Removal / House moving'),
(26, 1, 'Performing Arts'),
(26, 2, 'Arts performants'),
(26, 3, 'Las artes escénicas'),
(27, 1, 'Party Host'),
(27, 2, 'Hôte de fête'),
(27, 3, 'Anfitrión de la fiesta'),
(28, 1, 'DJ'),
(28, 2, 'DJ'),
(28, 3, 'DJ'),
(29, 1, 'Choreographer'),
(29, 2, 'Chorégraphe'),
(29, 3, 'Coreógrafo'),
(30, 3, 'Mesas de barman / espera'),
(30, 2, 'Tables de barman / d\'attente'),
(30, 1, 'Bartending / Waiting Tables'),
(31, 2, 'Connectivité réseau'),
(31, 1, 'Network Connectivity'),
(31, 3, 'Conectividad de red'),
(32, 1, 'Broadband Connection installation'),
(32, 2, 'Installation de connexion à large bande'),
(32, 3, 'Instalación de conexión de banda ancha'),
(33, 1, 'Leased Line Connection'),
(33, 2, 'Connexion de ligne louée'),
(33, 3, 'Conexión de línea arrendada'),
(34, 3, 'Vigilancia de los niños'),
(34, 2, 'Baby-sitting'),
(34, 1, 'Baby Sitting'),
(35, 1, 'Pet Services'),
(35, 2, 'Services pour animaux'),
(35, 3, 'Servicios para mascotas'),
(36, 1, 'Pet Bathing & Grooming'),
(36, 2, 'Bain et toilettage d\'animaux'),
(36, 3, 'Baño y aseo de mascotas'),
(37, 1, 'Walking the pet'),
(37, 2, 'Promener l\'animal'),
(37, 3, 'Paseando a la mascota'),
(38, 2, 'Antiparasitaire'),
(39, 1, 'Personal Training'),
(39, 2, 'Formation personnelle'),
(39, 3, 'Entrenamiento personal'),
(40, 1, 'Voice Modulation / Speech'),
(40, 2, 'Modulation vocale / discours'),
(40, 3, 'Modulación de voz / habla'),
(41, 1, 'Personality Trainer'),
(41, 2, 'Entraîneur de personnalité'),
(41, 3, 'Entrenador de personalidad'),
(42, 3, 'Carta de presentación / Redactor'),
(42, 2, 'Lettre d\'accompagnement / Rédacteur de CV'),
(42, 1, 'Cover Letter / Resume Writer'),
(43, 3, 'Otros'),
(43, 2, 'Autres'),
(43, 1, 'Others'),
(21, 1, 'Wall Painting'),
(44, 1, 'Gardening Activities'),
(44, 2, 'Activités de jardinage'),
(44, 3, 'Actividades de jardinería'),
(45, 1, 'House moving'),
(45, 2, 'déménagement'),
(45, 3, 'mudanza'),
(22, 3, 'Carpintería'),
(46, 1, 'Carpentry'),
(46, 2, 'Charpenterie'),
(46, 3, 'Carpintería'),
(47, 1, 'Cover letter/Resume Writer'),
(47, 2, 'Lettre de motivation / Rédacteur de CV'),
(47, 3, 'Carta de presentación / Redactor'),
(48, 1, 'Baby Sitting'),
(48, 2, 'Baby-sitting'),
(48, 3, 'Vigilancia de los niños'),
(49, 1, 'Bartending/ Waiting Tables'),
(49, 2, 'Tables de barman / d\'attente'),
(49, 3, 'Mesas de barman / espera'),
(50, 1, 'Pest Control'),
(50, 2, 'Antiparasitaire'),
(50, 3, 'Control de plagas'),
(38, 1, 'Pest Control'),
(38, 3, 'Control de plagas'),
(51, 1, 'Wall Painting'),
(51, 2, 'Peinture murale'),
(51, 3, 'Pintura mural'),
(52, 1, 'Cat1'),
(53, 1, 'Cleaning');
ALTER TABLE `tbl_categories_metadata`
ADD UNIQUE KEY `cat_id` (`cdata_cat_id`,`cdata_lang_id`);
This might work.
UPDATE tbl_categories a
INNER JOIN (
SELECT a.cat_id, MAX(b.cdata_name) cdata_name, ROW_NUMBER() OVER (PARTITION BY cdata_name ORDER BY cat_id) rn
FROM tbl_categories a
INNER JOIN tbl_categories_metadata b ON a.cat_id = b.cdata_cat_id
WHERE b.cdata_lang_id = 1
GROUP BY a.cat_id
) b ON a.cat_id = b.cat_id
SET a.cat_identifier = (CASE WHEN b.rn = 1 THEN b.cdata_name ELSE CONCAT(b.cdata_name, '-', a.cat_id) END)
https://dbfiddle.uk/?rdbms=mysql_8.0&fiddle=8f620a00e3d81012a3e1332f13914ed8
Revised version for MySQL 5.6
UPDATE tbl_categories a
INNER JOIN (
SELECT a.cat_id, MAX(b.cdata_name) cdata_name
FROM tbl_categories a
INNER JOIN tbl_categories_metadata b ON a.cat_id = b.cdata_cat_id
WHERE b.cdata_lang_id = 1
GROUP BY a.cat_id
) b ON a.cat_id = b.cat_id
LEFT JOIN (
SELECT MIN(a.cat_id) cat_id, b.cdata_name
FROM tbl_categories a
INNER JOIN tbl_categories_metadata b ON a.cat_id = b.cdata_cat_id
WHERE b.cdata_lang_id = 1
GROUP BY b.cdata_name
) c ON a.cat_id = c.cat_id AND b.cdata_name = c.cdata_name
SET a.cat_identifier = (CASE WHEN c.cat_id IS NOT NULL THEN b.cdata_name ELSE CONCAT(b.cdata_name, '-', a.cat_id) END)
;
https://dbfiddle.uk/?rdbms=mysql_5.6&fiddle=2c433ca4f20af22f7578dfe31e66db7b
Aside
cat_identifier and cat_id have the same meaning, which is confusing. A more appropriate name for the new column, given its use, would be default_name (or default_en_name). This answer will use the former.
Answer
First, set the column values to guaranteed unique values as planned, using both tbl_categories_metadata.cdata_name and tbl_categories.cat_id:
UPDATE `tbl_categories` AS tc
JOIN `tbl_categories_metadata` AS tcm
ON tc.cat_id = tcm.cdata_cat_id
SET `default_name` = CONCAT(tcm.cdata_name, '-', tc.cat_id)
WHERE
tcm.cdata_lang_id = 1;
The column could simply be left as-is. However, if you don't want the cat_id on some of the fields, remove it. What expression used to remove it depends on the version of MySQL server used (and what UDFs are loaded). If using MySQL 8.0, make use of REGEXP_REPLACE
UPDATE IGNORE `tbl_categories`
SET `default_name` = REGEXP_REPLACE(`default_name`,
CONCAT('-', cat_id, '$'),
'')
ORDER BY cat_id
Similarly, if you have a UDF that adds regex functionality, use that. If using a version before 8.0, a combination of SUBSTRING() and CHAR_LENGTH().
...
SET `default_name` = SUBSTRING(`default_name`, 1,
CHAR_LENGTH(`default_name`) - 1 - CHAR_LENGTH(cat_id)
)
...
A simpler (though more error-prone) solution would be to use REPLACE()
...
SET `default_name` = REPLACE(`default_name`,
CONCAT('-', cat_id), '')
...
Alternate Answer
More as an exercise, it can be done in a single query in a few ways; here's a systematic approach.
Whenever rows might depend on other rows (such as with unique indices, but not only then), a single-query solution can generally be done with an additional join on one of the tables, usually grouped and by the use of aggregate functions, though sometimes with non-equality join conditions (e.g. sometimes you can use something like tbl_alias_0.col < tbl_alias_1.col). To get the related rows, the join goes through tbl_categories_metadata. The table references clause would thus be:
...
`tbl_categories` AS tc
JOIN `tbl_categories_metadata` AS tcm
ON tc.cat_id = tcm.cdata_cat_id
JOIN `tbl_categories_metadata` AS tcm_groups
ON tcm.cdata_name = tcm_groups.cdata_name
AND tcm.cdata_lang_id = tcm_groups.cdata_lang_id
...
(Note that tcm is only used to join through in this example, though in some places some of the tcm_groups column references could be replaced with tcm column references.)
For this example, since each row (identified by cat_id or cdata_cat_id) will get assigned a cdata_name, these naturally form groups.
...
GROUP BY tc.cat_id, tcm_groups.cdata_name
...
The cdata_name in each group will potentially come from multiple rows in tbl_categories (via cdata_cat_id). As only one row from tbl_categories in the group won't have a suffix appended to the default name, this must be specified. One simple option is to pick the row with minimal cat_id, but other options (e.g. maximal cat_id, random) could be implemented instead. This is implemented with a CASE using a comparison with tcm_groups.cdata_cat_id to distinguish the cases.
...
CASE tc.cat_id
WHEN MIN(tcm_groups.cdata_cat_id) THEN tcm.cdata_name
ELSE CONCAT(tcm_groups.cdata_name, '-', tc.cat_id)
END
...
If this were a simple SELECT, the above components are all you'd need. (Starting with a SELECT is useful to check the work.) Combined, they are:
SELECT tc.cat_id,
CASE tc.cat_id
WHEN MIN(tcm_groups.cdata_cat_id) THEN tcm_groups.cdata_name
ELSE CONCAT(tcm_groups.cdata_name, '-', tc.cat_id)
END AS default_name
FROM `tbl_categories` AS tc
JOIN `tbl_categories_metadata` AS tcm
ON tc.cat_id = tcm.cdata_cat_id
JOIN `tbl_categories_metadata` AS tcm_groups
ON tcm.cdata_name = tcm_groups.cdata_name
AND tcm.cdata_lang_id = tcm_groups.cdata_lang_id
WHERE tcm_groups.cdata_lang_id = 1
GROUP BY tc.cat_id, tcm_groups.cdata_name
ORDER BY tc.cat_id
The one issue with this is that GROUP BY isn't allowed in UPDATE statements. To address this, the joined table, grouping and aggregate functions need to instead take place in a sub-SELECT. The groups therein should be the columns in JOIN conditions and any in the grouping clause. The aggregate functions get used in the result columns. This gives the sub-SELECT:
SELECT MIN(cdata_cat_id) AS cdata_cat_id, cdata_lang_id, cdata_name
FROM `tbl_categories_metadata`
GROUP BY cdata_name, cdata_lang_id
Rewriting the table references using that gives:
...
`tbl_categories` AS tc
JOIN `tbl_categories_metadata` AS tcm
ON tc.cat_id = tcm.cdata_cat_id
JOIN (
SELECT MIN(cdata_cat_id) AS cdata_cat_id, cdata_lang_id, cdata_name
FROM `tbl_categories_metadata`
GROUP BY cdata_name, cdata_lang_id
) AS tcm_groups
ON tcm.cdata_name = tcm_groups.cdata_name
AND tcm.cdata_lang_id = tcm_groups.cdata_lang_id
...
Aggregate functions are replaced with references to the sub-SELECT columns:
...
CASE tc.cat_id
WHEN tcm_groups.cdata_cat_id THEN tcm_groups.cdata_name
ELSE CONCAT(tcm_groups.cdata_name, '-', tc.cat_id)
END
...
These parts can be combined into an UPDATE:
UPDATE `tbl_categories` AS tc
JOIN `tbl_categories_metadata` AS tcm
ON tc.cat_id = tcm.cdata_cat_id
JOIN (
SELECT MIN(cdata_cat_id) AS cdata_cat_id, cdata_lang_id, cdata_name
FROM `tbl_categories_metadata`
GROUP BY cdata_name, cdata_lang_id
) AS tcm_groups
ON tcm.cdata_name = tcm_groups.cdata_name AND tcm.cdata_lang_id = tcm_groups.cdata_lang_id
SET default_name = CASE tc.cat_id
WHEN tcm_groups.cdata_cat_id THEN tcm.cdata_name
ELSE CONCAT(tcm.cdata_name, '-', tc.cat_id)
END
WHERE tcm.cdata_lang_id = 1
Performance
The sub-SELECT is less performant than the flat join, but can't be avoided in the UPDATE.
A WHERE tcm.cdata_lang_id = 1 could be added to the sub-SELECT. This won't affect correctness, but could result in a more efficient query if there's an index on cdata_lang_id. The most efficient query will result from an index on (cdata_lang_id, cdata_name).

mysql consult in same table

i have this table
INSERT INTO `relationships` (`id`, `term_id`, `order`) VALUES
(1, 1, 0),
(4, 2, 0),
(4, 3, 0),
(4, 4, 0),
(4, 5, 0),
(4, 7, 0),
(4, 8, 0),
(6, 3, 0),
(6, 8, 0),
(6, 9, 0),
(8, 6, 0),
(8, 7, 0),
(8, 8, 0),
(8, 10, 0),
(15, 3, 0),
(15, 4, 0),
(15, 10, 0);
I need to select all term_id containing the number 8 and 5 (relationship between this numbers)
expected result = id 4 and id 8
I try this
SELECT `id` FROM `relationships` WHERE `term_id`=8 or `term_id`=5
but selects all term_id belong to 8 and 5
result = id 4 id 8 AND id --> 6 <-- This is not the result I want.
This does the job:
SELECT
id
FROM relationships a
WHERE
a.term_id = 5 AND
EXISTS (SELECT * FROM relationships b WHERE b.term_id = 8 AND b.id = a.id) > 0
demo: http://www.sqlfiddle.com/#!9/e78cc/4/0

SELECT query for TableA and TableB IF TableB.col value (0 OR 1) I create new columns for 0 and 1

I have a Table pictures
create table pictures (
picture_id int(10) unsigned NOT NULL AUTO_INCREMENT,
mall_id float NOT NULL,
shop_id float NOT NULL,
picture_islogo int(11) NOT NULL ,
picture_path varchar(255) NOT NULL,
PRIMARY KEY (picture_id)
) ;
Sample Data for pictures
INSERT INTO pictures VALUES
(1, -1, 1, 1, 'photo.jpg'),
(2, -1, 2, 1, 'photo.jpg'),
(3, -1, 3, 1, 'photo.jpg'),
(4, -1, 4, 1, 'photo.jpg'),
(5, -1, 5, 1, 'photo.jpg'),
(6, -1, 6, 1, 'photo.jpg'),
(7, -1, 7, 1, 'photo.jpg'),
(8, -1, 8, 1, 'photo.jpg'),
(9, -1, 9, 1, 'photo.jpg'),
(10, -1, 10, 1, 'photo.jpg'),
(11, -1, 11, 1, 'photo.jpg'),
(12, -1, 12, 1, 'photo.jpg'),
(13, -1, 13, 1, 'photo.jpg'),
(14, -1, 13, 0, 'photo.jpg');
and other table malls
create table malls (
mall_id float NOT NULL AUTO_INCREMENT,
user_id float NOT NULL,
mall_displaysname varchar(255) NOT NULL,
mall_description text NOT NULL,
mall_contact varchar(14) NOT NULL,
mall_logo_picture_id int(11) NOT NULL,
mall_background_picture_id int(11) NOT NULL,
PRIMARY KEY (mall_id)
);
Sample Data for malls
INSERT INTO malls VALUES
(1, 2, 'mall', 'description', '+60 12 3456789', 14, 36),
(2, 5, 'mall 2', 'description', '+60 12 3456789', 15, 37),
(3, 6, 'mall 3', 'description ', '+60 12 3456789', 16, 38),
(4, 13, 'Multimedia University', 'description ', '+60 12 3456789', 17, 39),
(5, 18, 'Setia Walk', 'description ', '+60 12 3456789', 18, 40),
(6, 20, 'Ampang Point', 'description ', '+60 12 3456789', 19, 41),
(7, 21, 'Alamanda Plaza', 'description ', '+60 12 3456789', 20, 42),
(8, 22, 'Subang Parade', 'description ', '+60 12 3456789', 21, 43),
(9, 26, 'مجمع العرب - جدة', 'description ', '+60 12 3456789', 22, 44);
Where mall_background_picture_id and mall_background_picture_id reference to pictures.picture_id and Depend on the value of pictures.picture_islogo (0: Logo, 1:background or others)
i want a query to that returns the pictures.picture_path depends on the value of pictures.picture_islogo (0: Logo, 1:background or others)
the data that I need to get
mall_id , mall_displaysname, mall_logo, mall_background , mall_description, and mall_contact
Where mall_logo is the photo_path of the condition
pictures.picture_islogo = 1
and same thing with **mall_background** but
picture_islogo = 0
AND
mall_logo_picture_id = picture_id
Put the extra condition into the join condition:
select * -- you can chose what columns you want
from malls m
left join pictures pl on m.mall_logo_picture_id = pl.picture_id
and pl.picture_isLogo = 1
left join pictures pb on m.mall_background_picture_id = pb.picture_id
and pb.picture_isLogo = 0
To have left joins, the extra conditions must be in the join condition, which is evaluated as the join is being made.
If you put them in the where clause, which is evaluated after the join is made, you force the outer join to be an inner join, because the join must be successful fur the extra condition to be true.

mysql inner join with 3 tables issue with order count

I have the following sample tables.
CREATE TABLE IF NOT EXISTS `my_customer` (
`customer_id` int(11) NOT NULL AUTO_INCREMENT,
`customer_email` text NOT NULL,
PRIMARY KEY (`customer_id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=64 ;
INSERT INTO `my_customer` (`customer_id`, `customer_email`) VALUES
(4, 'muthu.d#test.in'),
(5, 'nsrirengan#test.in'),
(6, 'vinothini.k#test.in'),
(8, 'vinothini.k111#test.in'),
(63, 'sri.n321#test.in'),
(56, 'vesri.n#test.in'),
(57, 'veesri.n#test.in'),
(58, 'veeisri.n#test.in'),
(59, 'ren#test.in'),
(60, 'ren1#test.in'),
(61, 'nsrirengan123#test.in'),
(62, 'nsrirengan321#test.in'),
(53, 'sri.n#test.in'),
(54, 'royalrenga#test.in'),
(55, 'vesri#test.in');
CREATE TABLE IF NOT EXISTS `my_order` (
`orderid` int(11) NOT NULL AUTO_INCREMENT,
`ordergenerateid` varchar(20) NOT NULL,
`restaurant_id` int(11) NOT NULL,
`customer_id` int(11) NOT NULL,
`usertype` varchar(10) NOT NULL,
`customeremail` varchar(200) NOT NULL,
PRIMARY KEY (`orderid`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=152 ;
INSERT INTO `my_order` (`orderid`, `ordergenerateid`, `restaurant_id`, `customer_id`, `usertype`, `customeremail`) VALUES
(1, 'ORD0001', 3, 6, 'C', 'vinothini.k#test.in'),
(2, 'ORD0002', 1, 6, 'C', 'vinothini.k#test.in'),
(3, 'ORD0003', 3, 6, 'C', 'vinothini.k#test.in'),
(4, 'ORD0004', 3, 6, 'C', 'vinothini.k#test.in'),
(5, 'ORD0005', 3, 0, 'G', 'vinothini.k5555555#test.in'),
(6, 'ORD0006', 3, 6, 'C', 'vinothini.k#test.in'),
(7, 'ORD0007', 3, 6, 'C', 'vinothini.k#test.in'),
(8, 'ORD0008', 3, 6, 'C', 'vinothini.k#test.in'),
(9, 'ORD0009', 3, 6, 'C', 'vinothini.k#test.in'),
(10, 'ORD0010', 3, 6, 'C', 'vinothini.k#test.in'),
(11, 'ORD0011', 3, 6, 'C', 'vinothini.k#test.in'),
(12, 'ORD0012', 3, 6, 'C', 'vinothini.k#test.in'),
(13, 'ORD0013', 3, 6, 'C', 'vinothini.k#test.in'),
(14, 'ORD0014', 3, 6, 'C', 'vinothini.k#test.in'),
(15, 'ORD0015', 2, 3, 'C', 'sri.n#test.in'),
(16, 'ORD0016', 2, 3, 'C', 'sri.n#test.in'),
(17, 'ORD0017', 2, 3, 'C', 'sri.n#test.in'),
(18, 'ORD0018', 2, 3, 'C', 'sri.n#test.in'),
(19, 'ORD0019', 2, 3, 'C', 'sri.n#test.in'),
(20, 'ORD0020', 8, 3, 'C', 'sri.n#test.in'),
(21, 'ORD0021', 5, 3, 'C', 'sri.n#test.in'),
(22, 'ORD0022', 13, 3, 'C', 'sri.n#test.in'),
(23, 'ORD0023', 13, 3, 'C', 'sri.n#test.in'),
(24, 'ORD0024', 13, 3, 'C', 'sri.n#test.in'),
(25, 'ORD0025', 13, 3, 'C', 'sri.n#test.in'),
(26, 'ORD0026', 13, 3, 'C', 'sri.n#test.in'),
(27, 'ORD0027', 13, 3, 'C', 'sri.n#test.in'),
(28, 'ORD0028', 13, 3, 'C', 'sri.n#test.in'),
(29, 'ORD0029', 13, 3, 'C', 'sri.n#test.in'),
(30, 'ORD0030', 13, 3, 'C', 'sri.n#test.in'),
(31, 'ORD0031', 13, 3, 'C', 'sri.n#test.in'),
(32, 'ORD0032', 13, 3, 'C', 'sri.n#test.in'),
(33, 'ORD0033', 13, 3, 'C', 'sri.n#test.in'),
(34, 'ORD0034', 13, 3, 'C', 'sri.n#test.in'),
(35, 'ORD0035', 13, 3, 'C', 'sri.n#test.in'),
(36, 'ORD0036', 13, 3, 'C', 'sri.n#test.in'),
(37, 'ORD0037', 13, 3, 'C', 'sri.n#test.in'),
(38, 'ORD0038', 13, 3, 'C', 'sri.n#test.in'),
(39, 'ORD0039', 19, 3, 'C', 'sri.n#test.in'),
(40, 'ORD0040', 13, 3, 'C', 'sri.n#test.in'),
(41, 'ORD0041', 13, 3, 'C', 'sri.n#test.in'),
(42, 'ORD0042', 13, 3, 'C', 'sri.n#test.in'),
(43, 'ORD0043', 13, 3, 'C', 'sri.n#test.in'),
(44, 'ORD0044', 13, 3, 'C', 'sri.n#test.in'),
(45, 'ORD0045', 13, 3, 'C', 'sri.n#test.in'),
(46, 'ORD0046', 13, 3, 'C', 'sri.n#test.in'),
(47, 'ORD0047', 13, 3, 'C', 'sri.n#test.in'),
(48, 'ORD0048', 13, 3, 'C', 'sri.n#test.in'),
(49, 'ORD0049', 19, 3, 'C', 'sri.n#test.in'),
(51, 'ORD0051', 13, 3, 'C', 'sri.n#test.in'),
(52, 'ORD0052', 13, 3, 'C', 'sri.n#test.in'),
(53, 'ORD0053', 13, 3, 'C', 'sri.n#test.in'),
(54, 'ORD0054', 13, 10, 'G', 'sri.nas#test.in'),
(55, 'ORD0055', 13, 11, 'G', 'sri.nasqw#test.in'),
(56, 'ORD0056', 13, 12, 'G', 'sri.nqw#test.in'),
(57, 'ORD0057', 13, 13, 'G', 'sri.nas1123#test.in'),
(58, 'ORD0058', 13, 14, 'G', 'sri.nqw13#test.in'),
(59, 'ORD0059', 13, 15, 'G', 'sri.nas123#test.in'),
(60, 'ORD0060', 13, 16, 'G', 'sri.nas12345#test.in'),
(61, 'ORD0061', 13, 17, 'G', 'sri.nqw123#test.in'),
(62, 'ORD0062', 13, 18, 'G', 'sri.nas123111#test.in'),
(63, 'ORD0063', 13, 19, 'G', 'sri#test.in'),
(64, 'ORD0064', 13, 20, 'G', 'sri.nas111#test.in'),
(65, 'ORD0065', 13, 21, 'G', 'sri.nas12354klk#test.in'),
(66, 'ORD0066', 13, 22, 'G', 'sri.nas123879#test.in'),
(67, 'ORD0067', 13, 23, 'G', 'sri.nasasd#test.in'),
(68, 'ORD0068', 13, 24, 'G', 'sri.nasqwe#test.in'),
(69, 'ORD0069', 13, 25, 'G', 'sri.nas121212#test.in'),
(70, 'ORD0070', 13, 26, 'G', 'sri.nasqwqw#test.in'),
(71, 'ORD0071', 13, 27, 'G', 'sri.nqw321#test.in'),
(72, 'ORD0072', 13, 28, 'G', 'sri.nas123123#test.in'),
(73, 'ORD0073', 13, 3, 'C', 'sri.n#test.in'),
(74, 'ORD0074', 13, 3, 'C', 'sri.n#test.in'),
(75, 'ORD0075', 13, 3, 'C', 'sri.n#test.in'),
(76, 'ORD0076', 13, 3, 'C', 'sri.n#test.in'),
(77, 'ORD0077', 13, 3, 'C', 'sri.n#test.in'),
(78, 'ORD0078', 13, 3, 'C', 'sri.n#test.in'),
(79, 'ORD0079', 13, 3, 'C', 'sri.n#test.in'),
(121, 'ORD0121', 13, 52, 'G', 'sssri.n123123#test.in'),
(122, 'ORD0122', 13, 3, 'C', 'sri.n#test.in'),
(123, 'ORD0123', 13, 3, 'C', 'sri.n#test.in'),
(84, 'ORD0084', 13, 3, 'C', 'sri.n#test.in'),
(86, 'ORD0086', 13, 3, 'C', 'sri.n#test.in'),
(87, 'ORD0087', 13, 3, 'C', 'sri.n#test.in'),
(89, 'ORD0089', 13, 31, 'G', 'royalrenga#test.in'),
(90, 'ORD0090', 13, 32, 'G', 'nsri.n#test.in'),
(91, 'ORD0091', 13, 33, 'G', 'nnsri.n#test.in'),
(92, 'ORD0092', 13, 3, 'C', 'sri.n#test.in'),
(93, 'ORD0093', 13, 34, 'G', 'sssri.n#test.in'),
(94, 'ORD0094', 13, 35, 'G', 'qwsri.n#test.in'),
(95, 'ORD0095', 13, 36, 'G', 'snsri.n#test.in'),
(96, 'ORD0096', 13, 37, 'G', 'ncnsri.n#test.in'),
(97, 'ORD0097', 13, 38, 'G', 'nwnsri.n#test.in'),
(98, 'ORD0098', 13, 39, 'G', 'ncnasri.n#test.in'),
(99, 'ORD0099', 13, 40, 'G', 'ncnsasri.n#test.in'),
(100, 'ORD0100', 13, 41, 'G', 'ncqqnasri.n#test.in'),
(101, 'ORD0101', 13, 42, 'G', 'asdqazsri.nas123#test.in'),
(102, 'ORD0102', 13, 43, 'G', 'nacqqnasri.n#test.in'),
(103, 'ORD0103', 13, 3, 'C', 'sri.n#test.in'),
(104, 'ORD0104', 13, 3, 'C', 'sri.n#test.in'),
(105, 'ORD0105', 13, 3, 'C', 'sri.n#test.in'),
(106, 'ORD0106', 13, 3, 'C', 'sri.n#test.in'),
(107, 'ORD0107', 13, 3, 'C', 'sri.n#test.in'),
(108, 'ORD0108', 13, 0, 'G', 'sri.n#test.in'),
(109, 'ORD0109', 13, 3, 'C', 'sri.n#test.in'),
(110, 'ORD0110', 13, 3, 'C', 'sri.n#test.in'),
(111, 'ORD0111', 13, 44, 'G', 'qsw#test.in'),
(112, 'ORD0112', 13, 45, 'G', 'asdasd#test.in'),
(113, 'ORD0113', 13, 46, 'G', 'qweee#test.in'),
(114, 'ORD0114', 13, 47, 'G', 'qweqwe#test.in'),
(115, 'ORD0115', 13, 48, 'G', 'nsv123sri.n#test.in'),
(116, 'ORD0116', 13, 49, 'G', 'asdasdasd#test.in'),
(117, 'ORD0117', 13, 50, 'G', 'asdasdasdasd#test.in'),
(118, 'ORD0118', 13, 51, 'G', 'qwerew#test.in'),
(119, 'ORD0119', 13, 7, 'C', 'kvinocse86#test.in'),
(120, 'ORD0120', 13, 3, 'C', 'sri.n#test.in'),
(124, 'ORD0124', 13, 53, 'C', 'sri.n#test.in'),
(125, 'ORD0125', 13, 0, 'G', 'sri.n#test.in'),
(126, 'ORD0126', 13, 53, 'C', 'sri.n#test.in'),
(127, 'ORD0127', 13, 53, 'C', 'sri.n#test.in'),
(128, 'ORD0128', 13, 53, 'C', 'sri.n#test.in'),
(129, 'ORD0129', 13, 53, 'C', 'sri.n#test.in'),
(130, 'ORD0130', 13, 53, 'C', 'sri.n#test.in'),
(131, 'ORD0131', 13, 53, 'C', 'sri.n#test.in'),
(132, 'ORD0132', 13, 53, 'C', 'sri.n#test.in'),
(133, 'ORD0133', 13, 53, 'C', 'sri.n#test.in'),
(134, 'ORD0134', 13, 53, 'C', 'sri.n#test.in'),
(135, 'ORD0135', 13, 53, 'C', 'sri.n#test.in'),
(136, 'ORD0136', 13, 53, 'C', 'sri.n#test.in'),
(137, 'ORD0137', 13, 53, 'C', 'sri.n#test.in'),
(138, 'ORD0138', 13, 53, 'C', 'sri.n#test.in'),
(139, 'ORD0139', 13, 0, 'G', 'sri.n321#test.in'),
(140, 'ORD0140', 13, 53, 'C', 'sri.n123#test.in'),
(141, 'ORD0141', 13, 53, 'C', 'sri.n#test.in'),
(142, 'ORD0142', 13, 53, 'C', 'sri.n#test.in'),
(143, 'ORD0143', 13, 55, 'G', 'vesri#test.in'),
(144, 'ORD0144', 13, 56, 'G', 'vesri.n#test.in'),
(145, 'ORD0145', 13, 57, 'G', 'veesri.n#test.in'),
(146, 'ORD0146', 13, 58, 'G', 'veeisri.n#test.in'),
(147, 'ORD0147', 13, 59, 'G', 'ren#test.in'),
(148, 'ORD0148', 13, 60, 'G', 'ren1#test.in'),
(149, 'ORD0149', 13, 53, 'C', 'sri.n#test.in'),
(150, 'ORD0150', 13, 53, 'C', 'sri.n#test.in'),
(151, 'ORD0151', 13, 53, 'C', 'sri.n#test.in');
CREATE TABLE IF NOT EXISTS `my_restaurant` (
`restaurant_id` int(11) NOT NULL AUTO_INCREMENT,
`restaurant_name` varchar(100) NOT NULL,
PRIMARY KEY (`restaurant_id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=23 ;
INSERT INTO `my_restaurant` (`restaurant_id`, `restaurant_name`) VALUES
(1, 'Fuji Sushi'),
(2, 'Big Pete''s Pizza'),
(3, 'Vinos Pizza'),
(4, 'Wafaa and Mikes Cafe'),
(5, 'Fuji Sushi (San Marco Blvd)'),
(6, 'Midtown Deli + Cafe'),
(7, 'De Real Ting Cafe'),
(8, 'Alex Delicatessen'),
(9, 'Two Doors Down Restaurant'),
(10, 'Ginas Deli'),
(11, 'The Mudville Grille (Beach Blvd)'),
(12, 'Casbah Cafe'),
(13, 'Alexander Grill'),
(14, 'The Southern Grill'),
(15, 'Cool Moose Cafe'),
(16, 'Basil: Thai and Sushi'),
(17, 'Hot Wok'),
(18, 'China Joy'),
(19, 'Blu Diner'),
(21, 'New Test restaurant'),
(22, 'testing res');
I have written the following SQL for Most Order done by customer with restauant.
SELECT o.customeremail AS custemail, o.restaurant_id, rest.restaurant_name, COUNT( o.customeremail ) AS totalordercount
FROM my_order AS o
INNER JOIN my_customer AS cust ON cust.customer_email = o.customeremail
INNER JOIN my_restaurant AS rest ON rest.restaurant_id = o.restaurant_id
WHERE o.orderid IS NOT NULL
GROUP BY o.restaurant_id
ORDER BY totalordercount DESC
I'm getting the result like this.
custemail restaurant_id restaurant_name totalordercount
sri.n#test.in 13 Alexander Grill 79
vinothini.k#test.in 3 Vinos Pizza 12
sri.n#test.in 2 Big Pete's Pizza 5
sri.n#test.in 19 Blu Diner 2
vinothini.k#test.in 1 Fuji Sushi 1
sri.n#test.in 8 Alex Delicatessen 1
sri.n#test.in 5 Fuji Sushi (San Marco Blvd) 1
SELECT *
FROM `my_order`
WHERE `restaurant_id` =13
AND `customeremail` = 'sri.n#test.in'
LIMIT 0 , 30
I'm getting from above query with 71 rows only. But my query is showing the rows 79
sri.n#test.in 13 Alexander Grill 79
But I need the output like this.
custemail restaurant_id restaurant_name totalordercount
sri.n#test.in 13 Alexander Grill 71
vinothini.k#test.in 3 Vinos Pizza 12
sri.n#test.in 2 Big Pete's Pizza 5
sri.n#test.in 19 Blu Diner 2
vinothini.k#test.in 1 Fuji Sushi 1
sri.n#test.in 8 Alex Delicatessen 1
sri.n#test.in 5 Fuji Sushi (San Marco Blvd) 1
Thanks in advance
First, you're misusing the pernicious nonstandard MySQL extension to GROUP BY by trying to display a customer email in your result set aggregated by restaurant. Your misuse of this causes your result set to contain arbitrary values of custemail.
Second, this simple query reveals that there are 121 orders for the Alexander Grill. Your claim that there are only 71 seems to be incorrect.
SELECT COUNT(*), o.restaurant_id, r.restaurant_name
FROM my_order AS o
LEFT JOIN my_restaurant AS r ON o.restaurant_id = r.restaurant_id
GROUP BY o.restaurant_id, r.restaurant_name
Third, there are quite a few orders with a customer_id that isn't found in your customer table. You're using INNER JOIN so your query is dropping and not counting those orders. LEFT JOIN will restore those dropped records. But still, you are not using the results of that JOIN.
Fourth, your WHERE o.orderid IS NOT NULL clause is pointless: that column is a primary key.
Try this query leaving out the my_customer table JOIN:
SELECT o.restaurant_id,
rest.restaurant_name,
COUNT( DISTINCT o.customer_id ) AS distinctcustomercount,
COUNT( * ) AS totalordercount
FROM my_order AS o
LEFT JOIN my_restaurant AS rest ON rest.restaurant_id = o.restaurant_id
GROUP BY o.restaurant_id, rest.restaurant_name /* fix GROUP BY misuse */
ORDER BY COUNT( * ) DESC, rest.restaurant_name
I think this does the trick for you. It fully specifies the GROUP BY, and it does some kind of ordering among the restaurant rows that only have one order.
I think you are looking for visit count for restaurants for a customer email that has presence in the customer table. The other numbers just turn out to be right because the others from the 71'er have only visited one restaraunt.
You need to add the customer email to the group by if you want customers for each restaurant.
SELECT o.customeremail AS custemail,
o.restaurant_id, rest.restaurant_name, COUNT(o.customeremail ) AS totalordercount
FROM my_order AS o
INNER JOIN my_customer AS cust ON cust.customer_email = o.customeremail
INNER JOIN my_restaurant AS rest ON rest.restaurant_id = o.restaurant_id
GROUP BY o.restaurant_id, o.customeremail
ORDER BY totalordercount DESC
My answer is the same as Ollie's except I leave the customer join in, I think that presence is required to get the results expected.

mysql query inner join result set issues [closed]

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 9 years ago.
CREATE TABLE IF NOT EXISTS `maf_game_questions` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`gid` int(11) NOT NULL,
`qid` int(11) NOT NULL,
`qtext` text NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB ;
INSERT INTO `maf_game_questions` (`id`, `gid`, `qid`, `qtext`) VALUES
(1, 1, 6, 'Click on a state that has part of the Rocky Mountain Range to reveal a fact about agriculture.'),
(2, 1, 1, 'Click on a state that borders another country to see a fact about agriculture.'),
(3, 1, 15, 'Find a state where part of the border is created by a river to show a fact about agriculture.'),
(4, 1, 14, 'Choose a state that has part of the Missouri River to see a fact about agriculture.'),
(5, 1, 5, 'Click on a state that borders the Mississippi river to see a fact about agriculture.'),
(6, 1, 16, 'Click on a state with a panhandle to see a fact about agriculture.'),
(7, 1, 8, 'Find a state that is part of the Great Plains to check out a fact about agriculture.'),
(8, 1, 3, 'Select a state that has a bay to show a fact about agriculture.'),
(9, 1, 13, 'Select a state that has part of the Ohio River to view a fact about agriculture.'),
(10, 1, 9, 'Choose a state that is on the Atlantic Ocean to reveal a fact about agriculture.'),
(11, 1, 10, 'Select a state on the Pacific Ocean to see a fact about agriculture.'),
(12, 1, 4, 'Choose a state on the Gulf of Mexico to show a fact about agriculture.'),
(13, 1, 7, 'Find a state that has part of the Appalachian Mountain Range to see a fact about agriculture.'),
(14, 1, 2, 'Find a state that has a peninsula to check out a fact about agriculture.'),
(15, 1, 11, 'Click on a state with a desert to show a fact about agriculture.'),
(16, 1, 12, 'Find a state that borders one of the Great Lakes to see a fact about agriculture.');
CREATE TABLE IF NOT EXISTS `maf_game_stats` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`userid` varchar(100) NOT NULL,
`sessionid` varchar(100) NOT NULL,
`gid` int(11) NOT NULL,
`qid` int(11) NOT NULL,
`result` varchar(50) NOT NULL,
`accesstime` datetime NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB;
INSERT INTO `maf_game_stats` (`id`, `userid`, `sessionid`, `gid`, `qid`, `result`, `accesstime`) VALUES
(1, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 6, '0', '2013-04-02 16:26:22'),
(2, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 1, '1', '2013-04-02 16:26:27'),
(3, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 15, '0', '2013-04-02 16:26:35'),
(4, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 14, '1', '2013-04-02 16:26:42'),
(5, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 5, '1', '2013-04-02 16:26:51'),
(6, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 6, '1', '2013-04-04 16:27:24'),
(7, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 16, '1', '2013-04-04 16:27:32'),
(8, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 15, '0', '2013-04-04 16:27:38'),
(9, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 8, '1', '2013-04-04 16:27:48'),
(10, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 3, '1', '2013-04-02 16:31:22'),
(11, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 16, '1', '2013-04-02 16:31:28'),
(12, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 13, '0', '2013-04-02 16:31:44'),
(13, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 9, '0', '2013-04-02 16:31:53'),
(14, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 8, '1', '2013-04-02 16:32:00'),
(15, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 16, '1', '2013-04-02 16:35:02'),
(16, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 10, '0', '2013-04-02 16:35:11'),
(17, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 4, '0', '2013-04-02 16:35:17'),
(18, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 9, '1', '2013-04-02 16:35:23'),
(19, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 4, '0', '2013-04-02 16:35:29'),
(20, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 7, '0', '2013-04-03 19:06:12'),
(21, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 2, '1', '2013-04-03 19:06:17'),
(22, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 11, '0', '2013-04-03 19:06:29'),
(23, 'KIHYAKQTZLSB975', 'ccb4vm744cttrc8is1uuosf8e0', 1, 12, '0', '2013-04-03 19:06:33'),
(24, 'KIHYAKQTZLSB975', 'r0ci652ln8j1oqhvjd88s0is34', 1, 5, '0', '2013-04-05 09:47:22'),
(25, 'KIHYAKQTZLSB975', 'r0ci652ln8j1oqhvjd88s0is34', 1, 2, '1', '2013-04-05 09:47:28'),
(26, 'KIHYAKQTZLSB975', 'r0ci652ln8j1oqhvjd88s0is34', 1, 14, '0', '2013-04-05 09:47:37'),
(27, 'KIHYAKQTZLSB975', 'r0ci652ln8j1oqhvjd88s0is34', 1, 9, '1', '2013-04-05 09:47:43'),
(28, 'KIHYAKQTZLSB975', 'r0ci652ln8j1oqhvjd88s0is34', 1, 12, '0', '2013-04-05 09:47:50');
SELECT a.gid, a.qid, q.qtext, SUM(a.result = 1) first_attempt_correct, SUM(a.result = 0) first_attempt_incorrect, c.all_attempt_correct, c.all_attempt_incorrect
FROM maf_game_stats a
INNER JOIN
(
SELECT USERID, gid, QID, MIN(ACCESSTIME) AS min_date
FROM maf_game_stats
GROUP BY USERID, gid, qid
) b ON a.USERID = b.USERID AND
a.gid = b.gid AND
a.qid = b.qid AND
a.ACCESSTIME = b.min_date
INNER JOIN
(
SELECT gid, QID, SUM(result = 1) AS all_attempt_correct, SUM(result = 0) AS all_attempt_incorrect
FROM maf_game_stats
GROUP BY gid, qid
) c ON a.gid = c.gid AND
a.qid = c.qid
INNER JOIN maf_game_questions q ON a.qid = q.qid AND a.gid = q.gid
WHERE a.gid ='1'
AND a.ACCESSTIME >= '2013-04-05' AND a.ACCESSTIME < '2013-04-05' + INTERVAL 1 DAY
GROUP BY a.gid, a.qid
Q: ineed result below given result set useing 2013-04-02 to 2013-04-05 works fine but the same day 2013-04-05 to 2013-04-05 not getting result ? any idea please
here is sqlfidler :
http://sqlfiddle.com/#!2/181a2/1
------------------------
qtext 1st attempt correct 1st attempt incorrect all attempt correct all attempt incorrect
---------- --------------------- ---------------------- -------------------- ---------------------------
question 0 0 0 1
question 0 0 0 1
question 0 0 0 0
question 0 0 0 0
question 0 0 1 0
Is this what you're looking for -- move the WHERE criteria to your JOIN. The problem with your above query is your're joining on the MIN(AccessTime) and no records come back for 2013-04-05 within the MIN results.
SELECT *
FROM maf_game_stats a
INNER JOIN
(
SELECT USERID, gid, QID, MIN(ACCESSTIME) AS min_date
FROM maf_game_stats
WHERE ACCESSTIME >= '2013-04-05' AND ACCESSTIME < '2013-04-06'
GROUP BY USERID, gid, qid
) b ON a.USERID = b.USERID AND
a.gid = b.gid AND
a.qid = b.qid AND
a.ACCESSTIME = b.min_date
INNER JOIN
(
SELECT gid, QID, SUM(result = 1) AS all_attempt_correct, SUM(result = 0) AS all_attempt_incorrect
FROM maf_game_stats
GROUP BY gid, qid
) c ON a.gid = c.gid AND
a.qid = c.qid
INNER JOIN maf_game_questions q ON a.qid = q.qid AND a.gid = q.gid
WHERE a.gid ='1'
GROUP BY a.gid, a.qid
Updated SQL Fiddle