|
1 |
| -import {parseTitle} from './parseTitle'; |
| 1 | +import {parseTitle, parseTitleWithPrice} from './parseTitle'; |
2 | 2 |
|
3 | 3 | describe('weight', () => {
|
4 |
| - test('Extract weight', () => { |
| 4 | + test('Extract weight/volume', () => { |
5 | 5 | expect(parseTitle('Garnier, 1,5кг')).toStrictEqual({
|
6 |
| - weight: 1.5, |
7 | 6 | quantity: 1,
|
8 |
| - item_weight: 1.5, |
9 |
| - weight_unit: 'кг', |
| 7 | + units: [{ |
| 8 | + total: 1.5, |
| 9 | + value: 1.5, |
| 10 | + unit: 'кг', |
| 11 | + }], |
10 | 12 | });
|
11 | 13 |
|
12 | 14 | expect(parseTitle('Сметана Пискаревская, 15%, 200 г')).toStrictEqual({
|
13 |
| - weight: 0.2, |
14 | 15 | quantity: 1,
|
15 |
| - item_weight: 0.2, |
16 |
| - weight_unit: 'кг', |
17 |
| - }); |
18 |
| - expect( |
19 |
| - parseTitle('Творог фруктовый Агуша Черника 3.9% 100г для дет.пит. с 6 месяцев'), |
20 |
| - ).toStrictEqual({ |
21 |
| - weight: 0.1, |
22 |
| - quantity: 1, |
23 |
| - item_weight: 0.1, |
24 |
| - weight_unit: 'кг', |
| 16 | + units: [{ |
| 17 | + total: .2, |
| 18 | + value: .2, |
| 19 | + unit: 'кг', |
| 20 | + }], |
25 | 21 | });
|
26 | 22 |
|
27 | 23 | expect(parseTitle('Garnier Банан для очень сухих волос, 390 мл')).toStrictEqual({
|
28 |
| - weight: 0.39, |
29 | 24 | quantity: 1,
|
30 |
| - item_weight: 0.39, |
31 |
| - weight_unit: 'л', |
| 25 | + units: [{ |
| 26 | + total: .39, |
| 27 | + value: .39, |
| 28 | + unit: 'л', |
| 29 | + }], |
32 | 30 | });
|
33 | 31 | expect(parseTitle('Garnier, 390 грамм')).toStrictEqual({
|
34 |
| - weight: 0.39, |
35 | 32 | quantity: 1,
|
36 |
| - item_weight: 0.39, |
37 |
| - weight_unit: 'кг', |
| 33 | + units: [{ |
| 34 | + total: .39, |
| 35 | + value: .39, |
| 36 | + unit: 'кг', |
| 37 | + }], |
38 | 38 | });
|
39 | 39 | });
|
| 40 | + |
40 | 41 | test('extract length', () => {
|
41 |
| - expect(parseTitle('Силовой кабель МБ Провод ВВГмб-П нг(А)-LS 3 x 1,5 мм², 10 м')).toStrictEqual( |
42 |
| - { |
43 |
| - weight: 10, |
44 |
| - quantity: 1, |
45 |
| - item_weight: 10, |
46 |
| - weight_unit: 'м', |
47 |
| - }, |
48 |
| - ); |
| 42 | + expect(parseTitle('Силовой кабель МБ Провод ВВГмб-П нг(А)-LS 3 x 1,5 мм², 10 м')) |
| 43 | + .toStrictEqual({ |
| 44 | + quantity: 1, |
| 45 | + units: [{ |
| 46 | + total: 10, |
| 47 | + value: 10, |
| 48 | + unit: 'м', |
| 49 | + }], |
| 50 | + }, |
| 51 | + ); |
| 52 | + }); |
| 53 | + test('without unit', () => { |
| 54 | + expect(parseTitle('Aroy-d 70% 17-19%')).toStrictEqual({quantity: 1, units: []}); |
49 | 55 | });
|
50 | 56 | });
|
51 | 57 | test('Extract quantity', () => {
|
52 |
| - expect(parseTitle('Aroy-d Кокосовое молоко 70% жирность 17-19%, 2 шт')).toStrictEqual({ |
53 |
| - weight: null, |
| 58 | + expect(parseTitle('Aroy-d 70% жирность 17-19%, 2 шт')).toStrictEqual({ |
54 | 59 | quantity: 2,
|
55 |
| - item_weight: null, |
56 |
| - weight_unit: null, |
| 60 | + units: [], |
57 | 61 | });
|
58 | 62 | });
|
59 | 63 |
|
60 |
| -test('Extract quantity and weight', () => { |
61 |
| - expect(parseTitle('Щедрые хлебцы с чесноком 100г/8шт')).toStrictEqual({ |
62 |
| - weight: 0.1 * 8, |
63 |
| - quantity: 8, |
64 |
| - item_weight: 0.1, |
65 |
| - weight_unit: 'кг', |
66 |
| - }); |
67 |
| - expect(parseTitle('Рис Увелка пропаренный, 5×80 г')).toStrictEqual({ |
68 |
| - weight: 0.08 * 5, |
69 |
| - quantity: 5, |
70 |
| - item_weight: 0.08, |
71 |
| - weight_unit: 'кг', |
72 |
| - }); |
73 |
| - expect(parseTitle("Кофе молотый 500 г, Peppo's набор 2 упаковки по 250 гр")).toStrictEqual({ |
74 |
| - weight: 0.5, |
75 |
| - quantity: 2, |
76 |
| - item_weight: 0.25, |
77 |
| - weight_unit: 'кг', |
| 64 | +describe('Extract quantity and weight', () => { |
| 65 | + test('Common cases', () => { |
| 66 | + expect(parseTitle('Щедрые хлебцы с чесноком 100г/8шт')).toStrictEqual({ |
| 67 | + quantity: 8, |
| 68 | + units: [{ |
| 69 | + total: .1 * 8, |
| 70 | + value: .1, |
| 71 | + unit: 'кг', |
| 72 | + }], |
| 73 | + }); |
78 | 74 | });
|
79 |
| - expect(parseTitle('Кофе молотый, 1 кг, натуральный (2 упаковки по 500г)')).toStrictEqual({ |
80 |
| - weight: 1, |
81 |
| - quantity: 2, |
82 |
| - item_weight: 0.5, |
83 |
| - weight_unit: 'кг', |
| 75 | + test('cases', () => { |
| 76 | + const cases = [ |
| 77 | + '80г×5шт', |
| 78 | + '80 г. по 5', |
| 79 | + '5×80 г', |
| 80 | + '5х80 г', |
| 81 | + '80 г x 5 шт', |
| 82 | + '5 шт. по 80 грамм', |
| 83 | + '80 г x 5', |
| 84 | + ]; |
| 85 | + for (const title of cases) { |
| 86 | + expect(parseTitle('Рис, ' + title), title).toStrictEqual({ |
| 87 | + quantity: 5, |
| 88 | + units: [{total: .08 * 5, value: .08, unit: 'кг'}], |
| 89 | + }); |
| 90 | + } |
84 | 91 | });
|
85 | 92 |
|
86 |
| - expect( |
87 |
| - parseTitle('Пряность Куркума молотая для мяса, риса, овощей Global Spice - набор 3х20 г'), |
88 |
| - ).toStrictEqual({ |
89 |
| - weight: 0.02 * 3, |
90 |
| - quantity: 3, |
91 |
| - item_weight: 0.02, |
92 |
| - weight_unit: 'кг', |
93 |
| - }); |
| 93 | + test('Fuzzy check combinations', () => { |
| 94 | + const quantity = 5; |
| 95 | + const quantity_units = ['шт']; |
| 96 | + const weight = 100; |
| 97 | + const weight_units = { |
| 98 | + 'кг': ['г', 'грамм', 'гр'], |
| 99 | + 'л': ['мл'], |
| 100 | + }; |
| 101 | + const delimiter = ['по', '×', 'х', '*']; |
| 102 | + for (const q_u of quantity_units) { |
| 103 | + for (const [unit, unit_displays] of Object.entries(weight_units)) { |
| 104 | + for (const u_d of unit_displays) { |
| 105 | + for (const d of delimiter) { |
94 | 106 |
|
95 |
| - expect(parseTitle('Aroy-d Кокосовое молоко 70% жирность 17-19%, 500 мл x 2 шт')).toStrictEqual({ |
96 |
| - weight: 1.0, |
97 |
| - quantity: 2, |
98 |
| - item_weight: 0.5, |
99 |
| - weight_unit: 'л', |
100 |
| - }); |
| 107 | + const weight_variations = [`${weight}${u_d}`, `${weight} ${u_d}`, `${weight} ${u_d}.`]; |
| 108 | + const quantity_variations = [`${quantity}${q_u}`, `${quantity} ${q_u}`, |
| 109 | + `${quantity} ${q_u}.`, `${quantity}`]; |
| 110 | + let delim_variations = [d, ` ${d}`, `${d} `, ` ${d} `, ` ${d} `]; |
| 111 | + if (['по'].includes(d)) { |
| 112 | + // Word delim must be around spaces |
| 113 | + delim_variations = [` ${d} `] |
| 114 | + } |
101 | 115 |
|
102 |
| - expect(parseTitle('100% Кокосовое молоко АЗБУКА ПРОДУКТОВ кулинарное 6шт*1л')).toStrictEqual({ |
103 |
| - weight: 6.0, |
104 |
| - quantity: 6, |
105 |
| - item_weight: 1.0, |
106 |
| - weight_unit: 'л', |
| 116 | + for (const w of weight_variations) { |
| 117 | + for (const q of quantity_variations) { |
| 118 | + for (const dv of delim_variations) { |
| 119 | + const titles = [`${w}${dv}${q}`, `${q}${dv}${w}`]; |
| 120 | + for (const t of titles) { |
| 121 | + expect(parseTitle('Рис, ' + t), t).toStrictEqual({ |
| 122 | + quantity: quantity, |
| 123 | + units: [{total: (weight * quantity) / 1000, value: weight / 1000, unit: unit}], |
| 124 | + }); |
| 125 | + } |
| 126 | + } |
| 127 | + } |
| 128 | + } |
| 129 | + } |
| 130 | + } |
| 131 | + } |
| 132 | + } |
107 | 133 | });
|
108 |
| - |
109 |
| - expect( |
110 |
| - parseTitle('Тофу классический, соевый продукт, комплект 2 шт. по 300 грамм, Green East'), |
111 |
| - ).toStrictEqual({ |
112 |
| - weight: 0.6, |
| 134 | +}); |
| 135 | +test('Priority parse weight with quantity', () => { |
| 136 | + expect(parseTitle('Кофе молотый 500 г, Peppo\'s набор 2 упаковки по 250 гр')).toStrictEqual({ |
113 | 137 | quantity: 2,
|
114 |
| - item_weight: 0.3, |
115 |
| - weight_unit: 'кг', |
| 138 | + units: [{ |
| 139 | + total: .25 * 2, |
| 140 | + value: .25, |
| 141 | + unit: 'кг', |
| 142 | + }], |
116 | 143 | });
|
117 |
| - |
118 |
| - expect(parseTitle('Влажный корм для кошек Whiskas, 75 г x 28')).toStrictEqual({ |
119 |
| - weight: 0.075 * 28, |
120 |
| - quantity: 28, |
121 |
| - item_weight: 0.075, |
122 |
| - weight_unit: 'кг', |
| 144 | + expect(parseTitle('Кофе молотый, 1 кг, натуральный (2 упаковки по 500г)')).toStrictEqual({ |
| 145 | + quantity: 2, |
| 146 | + units: [{ |
| 147 | + total: .5 * 2, |
| 148 | + value: .5, |
| 149 | + unit: 'кг', |
| 150 | + }], |
123 | 151 | });
|
124 |
| -}); |
125 |
| - |
126 |
| -test('Extract quantity and weight with priority', () => { |
127 | 152 | expect(parseTitle('Порционный сахар в стиках 1 кг (200шт. х 5 гр.) белый')).toStrictEqual({
|
128 |
| - weight: 0.005 * 200, |
129 | 153 | quantity: 200,
|
130 |
| - item_weight: 0.005, |
131 |
| - weight_unit: 'кг', |
| 154 | + units: [{ |
| 155 | + total: .005 * 200, |
| 156 | + value: .005, |
| 157 | + unit: 'кг', |
| 158 | + }], |
132 | 159 | });
|
133 | 160 | });
|
134 |
| - |
135 | 161 | test('Extract combined quantity', () => {
|
136 | 162 | expect(parseTitle('60шт х 10уп')).toStrictEqual({
|
137 |
| - weight: null, |
138 | 163 | quantity: 600,
|
139 |
| - item_weight: null, |
140 |
| - weight_unit: null, |
| 164 | + units: [], |
141 | 165 | });
|
142 | 166 | expect(parseTitle('SYNERGETIC 110 шт, набор 2х55 шт, бесфосфатные')).toStrictEqual({
|
143 |
| - weight: null, |
144 | 167 | quantity: 110,
|
145 |
| - item_weight: null, |
146 |
| - weight_unit: null, |
| 168 | + units: [], |
| 169 | + }); |
| 170 | +}); |
| 171 | + |
| 172 | + |
| 173 | +describe('Parse with price', () => { |
| 174 | + test('with quantity', () => { |
| 175 | + expect(parseTitleWithPrice('Aroy-d 70% жирность 17-19%, 2 шт', 200)) |
| 176 | + .toStrictEqual({ |
| 177 | + quantity: 2, |
| 178 | + quantity_price: 100, |
| 179 | + quantity_price_display: '100 ₽/шт', |
| 180 | + units: [], |
| 181 | + }); |
| 182 | + }); |
| 183 | + test('with unit', () => { |
| 184 | + expect(parseTitleWithPrice('Aroy-d 70% жирность 17-19%, 200г', 200)) |
| 185 | + .toStrictEqual({ |
| 186 | + quantity: 1, |
| 187 | + quantity_price: null, |
| 188 | + quantity_price_display: null, |
| 189 | + units: [{ |
| 190 | + total: .2, |
| 191 | + value: .2, |
| 192 | + price: 200 / .2, |
| 193 | + price_display: '1000 ₽/кг', |
| 194 | + unit: 'кг', |
| 195 | + }], |
| 196 | + }); |
| 197 | + }); |
| 198 | + test('without unit', () => { |
| 199 | + expect(parseTitleWithPrice('Aroy-d 70% 17-19%', 200)) |
| 200 | + .toStrictEqual(null); |
| 201 | + }); |
| 202 | + |
| 203 | + test('With quantity and unit', () => { |
| 204 | + expect(parseTitleWithPrice('Aroy-d 70% 17-19% 500 мл x 2 шт', 200)) |
| 205 | + .toStrictEqual({ |
| 206 | + 'quantity': 2, |
| 207 | + 'quantity_price': 100, |
| 208 | + 'quantity_price_display': '100 ₽/шт', |
| 209 | + 'units': [ |
| 210 | + { |
| 211 | + 'price': 200, |
| 212 | + 'price_display': '200 ₽/л', |
| 213 | + 'total': 1, |
| 214 | + 'unit': 'л', |
| 215 | + 'value': 0.5, |
| 216 | + }, |
| 217 | + ], |
| 218 | + }); |
| 219 | + }); |
| 220 | +}); |
| 221 | + |
| 222 | + |
| 223 | +describe('Multi-units', () => { |
| 224 | + test('Parse led lamps, we need compare lm/w and lm/rub', () => { |
| 225 | + expect(parseTitle('Лампа светодиодная E27 220-240 В 10 Вт ' + |
| 226 | + 'груша матовая 1000 лм нейтральный белый свет')).toStrictEqual( |
| 227 | + { |
| 228 | + quantity: 1, |
| 229 | + units: [ |
| 230 | + { |
| 231 | + value: 1000, |
| 232 | + unit: 'лм', |
| 233 | + total: 1000, |
| 234 | + }, |
| 235 | + { |
| 236 | + value: 10, |
| 237 | + unit: 'Вт', |
| 238 | + total: 10, |
| 239 | + }, |
| 240 | + ], |
| 241 | + }, |
| 242 | + ); |
147 | 243 | });
|
148 | 244 | });
|
0 commit comments