Bonjour,
Je viens vers vous pour une optimisation de mon schéma de bdd parce que je pense pas que seule la requête soit la cause de la lenteur.
Voici le schéma actuel :
Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65 -- -- Structure de la table `produit` ~70.000 lignes -- CREATE TABLE IF NOT EXISTS `produit` ( `id_produit` int(11) NOT NULL AUTO_INCREMENT, `nom_fabricant` varchar(32) NOT NULL, `code_fabricant` varchar(20) NOT NULL, `sku` varchar(12) NOT NULL, `desc1` varchar(35) NOT NULL, `desc2` varchar(35) NOT NULL, `ref_fabricant` varchar(20) NOT NULL, `code_barre` varchar(13) NOT NULL, `cat_produit` varchar(4) NOT NULL, `ft_imported` tinyint(1) NOT NULL, PRIMARY KEY (`id_produit`), KEY `ft_produit` (`nom_fabricant`,`code_fabricant`,`desc1`,`desc2`,`ref_fabricant`,`code_barre`,`ft_imported`), FULLTEXT KEY `index_produit` (`nom_fabricant`,`code_fabricant`,`desc1`,`desc2`,`ref_fabricant`,`code_barre`) ) ENGINE=MyISAM DEFAULT CHARSET=latin1; -- -------------------------------------------------------- -- -- Structure de la table `stock_fr` ~78.000 lignes -- CREATE TABLE IF NOT EXISTS `stock_fr` ( `stock_sku` varchar(12) NOT NULL, `stock_ref_fabricant` varchar(20) NOT NULL, `stock_qte_dispo` smallint(6) NOT NULL, `stock_qte_cmd` smallint(6) NOT NULL, `etat` varchar(8) NOT NULL, PRIMARY KEY (`stock_sku`) ) ENGINE=MyISAM DEFAULT CHARSET=latin1; -- -------------------------------------------------------- -- -- Structure de la table `stock_eu` ~30.000 lignes -- CREATE TABLE IF NOT EXISTS `stock_eu` ( `stock_eu_sku` varchar(12) NOT NULL, `stock_eu_ref_fabricant` varchar(20) NOT NULL, `stock_eu_qte_dispo` varchar(8) NOT NULL, `stock_eu_qte_cmd` varchar(8) NOT NULL, `stock_eu_etat` varchar(8) NOT NULL, PRIMARY KEY (`stock_eu_sku`) ) ENGINE=MyISAM DEFAULT CHARSET=latin1; -- -------------------------------------------------------- -- -- Structure de la table `xml_valeur` ~390.000 lignes -- CREATE TABLE IF NOT EXISTS `xml_valeur` ( `sku` varchar(12) NOT NULL, `id_xml_propriete` varchar(20) NOT NULL, `libel_xml_valeur` varchar(255) NOT NULL, PRIMARY KEY (`sku`,`id_xml_propriete`), KEY `libel_xml_valeur` (`libel_xml_valeur`), FULLTEXT KEY `libel_xml_valeur_2` (`libel_xml_valeur`) ) ENGINE=MyISAM DEFAULT CHARSET=latin1;
Un produit possède une ou plusieurs valeurs de `priopriétés` (table non représentée car non utilisée et utile dans ce cas-ci).
Là où commence les problèmes c'est pour les recherches par mot-clés.
J'utilise cette requête. Elle retourne ~900 lignes en ~15-20 secondes (affichage compris) et c'est là que c'est gênant. C'est beaucoup trop long.
Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25 SELECT P.desc1, P.sku, P.desc2, P.cat_produit, nom_fabricant, stock_qte_dispo, stock_qte_cmd, etat, stock_eu_qte_dispo, stock_eu_qte_cmd, stock_eu_etat, id_produit, ref_fabricant, code_barre, code_fabricant, libel_xml_valeur FROM produit P LEFT OUTER JOIN stock_fr TF ON P.sku = TF.stock_sku LEFT OUTER JOIN stock_eu TR ON P.sku = TR.stock_eu_sku INNER JOIN xml_valeur XV ON XV.sku = P.sku WHERE ( desc1 LIKE '%windows%' OR desc2 LIKE '%windows%' OR nom_fabricant LIKE '%windows%' OR code_fabricant LIKE '%windows%' OR ref_fabricant LIKE '%windows%' OR code_barre LIKE '%windows%' OR libel_xml_valeur LIKE '%windows%' ) AND ( desc1 LIKE '%premium%' OR desc2 LIKE '%premium%' OR nom_fabricant LIKE '%premium%' OR code_fabricant LIKE '%premium%' OR ref_fabricant LIKE '%premium%' OR code_barre LIKE '%premium%' OR libel_xml_valeur LIKE '%premium%' ) GROUP BY P.id_produit
Je suis passé par une recherche de type FULLTEXT mais c'est aux alentours de 32 secondes cette fois, avec cette requête :
Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10 SELECT P.sku, P.desc1, P.desc2, P.cat_produit, prix_public, prix_revendeur, nom_fabricant, produit_en_stock, stock_qte_dispo, stock_qte_cmd, etat, stock_eu_qte_dispo, stock_eu_qte_cmd, stock_eu_etat, id_produit, content, ref_fabricant, code_barre, code_fabricant, libel_xml_valeur FROM price P LEFT OUTER JOIN totfrhrl TF ON P.sku = TF.stock_sku LEFT OUTER JOIN totrihrl TR ON P.sku = TR.stock_eu_sku INNER JOIN xml_valeur XV ON XV.sku = P.sku WHERE MATCH (`desc1`, `desc2`, `nom_fabricant`, `code_fabricant`, `ref_fabricant`, `code_barre`, `libel_xml_valeur`) AGAINST ('+windows +premium' IN BOOLEAN MODE) GROUP BY P.id_produit;
J'avoue ne plus avoir d'idée pour que les temps de recherche soit acceptables. A condition qu'ils puissent l'être mais j'en doute.
Auriez-vous une idée pour que j'optimise au mieux cette recherche, que ce soit au niveau conceptuel que SQL ?
Partager