· 6 years ago · Jul 08, 2019, 02:46 PM
1Если задача не требует нахождения заказов пользователя, в которых он сменил номер телефона, то я предложил бы такой вариант:
2
3DROP TABLE IF EXISTS `orders`;
4CREATE TABLE IF NOT EXISTS `orders` (
5 `order_id` int(11) unsigned NOT NULL,
6 `user_id` int(11) unsigned NOT NULL,
7 PRIMARY KEY (`order_id`),
8 KEY `user_id` (`user_id`)
9) ENGINE=InnoDB DEFAULT CHARSET=utf8;
10
11
12DROP TABLE IF EXISTS `phones_to_orders`;
13CREATE TABLE IF NOT EXISTS `phones_to_orders` (
14 `phones_to_orders_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
15 `order_id` int(10) unsigned NOT NULL,
16 `phone_number` varchar(50) NOT NULL,
17 PRIMARY KEY (`phones_to_orders_id`),
18 UNIQUE KEY `order_id_phone_number` (`order_id`,`phone_number`),
19 KEY `order_id` (`order_id`)
20) ENGINE=InnoDB DEFAULT CHARSET=utf8;
21
22
23
24При такой архитектуре мы можем достать все заказы, которые содержат заданный номер телефона с помощью запроса:
25SELECT o.order_id
26FROM phones_to_orders AS p2o
27INNER JOIN orders AS o ON o.order_id = p2o.order_id
28WHERE p2o.phone_number = '8KKKNNNNNNN';
29
30
31Однако, у заказов может быть несколько телефонных номеров и один пользователь может чередовать номера, а в каких то случаях указать сразу несколько:
321 заказ
33 8 999-999-99-99
34
352 заказ
36 8 111-111-11-11
37
383 заказ
39 8 999-999-99-99
40 8 111-111-11-11
41
42
43
44В таком случае мы можем связать первый и второй заказ через третий:
45SELECT DISTINCT o.order_id
46FROM asdasd_orders2 AS o
47INNER JOIN asdasd_phones_to_orders AS p2o ON o.order_id = p2o.order_id
48INNER JOIN (
49 SELECT DISTINCT p2o2.phone_number FROM asdasd_phones_to_orders AS p2o
50 INNER JOIN asdasd_phones_to_orders AS p2o2 ON p2o2.order_id = p2o.order_id
51 WHERE p2o.phone_number = '84951234567'
52) AS p ON p.phone_number = p2o.phone_number;
53
54
55Так же мы можем создать еще 2 таблицы: users и phones_to_users. В момент создания заказа искать номер в таблице phones_to_users и при успешном нахождении получать идентификатор пользователя и записывать его в таблицу orders.
56Если пользователь передал несколько телефонных номеров, тогда мы связываем с ним все новые.
57При такой архитектуре мы без проблем определим все заказы пользователя без вложенных запросов:
58
59DROP TABLE IF EXISTS `phones_to_users`;
60CREATE TABLE IF NOT EXISTS `phones_to_users` (
61 `phones_to_users_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
62 `user_id` int(10) unsigned NOT NULL,
63 `phone_number` varchar(50) NOT NULL,
64 PRIMARY KEY (`phones_to_users_id`),
65 UNIQUE KEY `phone_number_user_id` (`phone_number`,`user_id`)
66) ENGINE=InnoDB DEFAULT CHARSET=utf8;
67
68
69SELECT o.order_id
70FROM phones_to_users AS u
71INNER JOIN orders AS o ON o.user_id = u.user_id
72WHERE u.phone_number = '84951234567'
73
74
75Но, ничего не мешает пользователю сделать следующую схему:
761 заказ
77 8 999-999-99-99
78 8 888-888-88-88
79
802 заказ
81 8 111-111-11-11
82
833 заказ
84 8 888-888-88-88
85
864 заказ
87 8 999-999-99-99
88 8 111-111-11-11
89
90
91В данном случае первый заказ принадлежит пользователю №1, второй пользователю №2, третий пользователю №1.
92В этом случае, в момент оформления заказа №4, я бы связал заказ №2 с первым пользователем.