diff --git a/.vscode/ftp-kr.sync.cache.json b/.vscode/ftp-kr.sync.cache.json
index c6bc13d7..036aa49c 100644
--- a/.vscode/ftp-kr.sync.cache.json
+++ b/.vscode/ftp-kr.sync.cache.json
@@ -203,11 +203,7 @@
"category-description.php": {
"type": "-",
"size": 876,
-<<<<<<< HEAD
"lmtime": 1759440882784,
-=======
- "lmtime": 1760004579948,
->>>>>>> 75ca8fd840028fc69c3efb91a742413960c4defc
"modified": false
},
"classes": {
@@ -275,9 +271,9 @@
},
"CartRule.php": {
"type": "-",
- "size": 90626,
- "lmtime": 0,
- "modified": true
+ "size": 92516,
+ "lmtime": 1758059612896,
+ "modified": false
},
"Category.php": {
"type": "-",
@@ -984,7 +980,7 @@
"defines.inc.php": {
"type": "-",
"size": 8347,
- "lmtime": 1760004579950,
+ "lmtime": 1758059594454,
"modified": false
},
"defines_uri.inc.php": {
@@ -1039,7 +1035,203 @@
"themes": {},
"xml": {}
},
- "controllers": {},
+ "controllers": {
+ "front": {
+ "AddressController.php": {
+ "type": "-",
+ "size": 6415,
+ "lmtime": 0,
+ "modified": false
+ },
+ "AddressesController.php": {
+ "type": "-",
+ "size": 2633,
+ "lmtime": 0,
+ "modified": false
+ },
+ "AttachmentController.php": {
+ "type": "-",
+ "size": 2804,
+ "lmtime": 0,
+ "modified": false
+ },
+ "AuthController.php": {
+ "type": "-",
+ "size": 4577,
+ "lmtime": 0,
+ "modified": false
+ },
+ "CartController.php": {
+ "type": "-",
+ "size": 25476,
+ "lmtime": 1758056508693,
+ "modified": false
+ },
+ "ChangeCurrencyController.php": {
+ "type": "-",
+ "size": 1621,
+ "lmtime": 0,
+ "modified": false
+ },
+ "CmsController.php": {
+ "type": "-",
+ "size": 8218,
+ "lmtime": 0,
+ "modified": false
+ },
+ "ContactController.php": {
+ "type": "-",
+ "size": 1776,
+ "lmtime": 0,
+ "modified": false
+ },
+ "DiscountController.php": {
+ "type": "-",
+ "size": 6431,
+ "lmtime": 0,
+ "modified": false
+ },
+ "GetFileController.php": {
+ "type": "-",
+ "size": 14831,
+ "lmtime": 0,
+ "modified": false
+ },
+ "GuestTrackingController.php": {
+ "type": "-",
+ "size": 5428,
+ "lmtime": 0,
+ "modified": false
+ },
+ "HistoryController.php": {
+ "type": "-",
+ "size": 4105,
+ "lmtime": 0,
+ "modified": false
+ },
+ "IdentityController.php": {
+ "type": "-",
+ "size": 3252,
+ "lmtime": 0,
+ "modified": false
+ },
+ "IndexController.php": {
+ "type": "-",
+ "size": 1504,
+ "lmtime": 0,
+ "modified": false
+ },
+ "index.php": {
+ "type": "-",
+ "size": 1372,
+ "lmtime": 0,
+ "modified": false
+ },
+ "listing": {},
+ "MyAccountController.php": {
+ "type": "-",
+ "size": 1923,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderConfirmationController.php": {
+ "type": "-",
+ "size": 5807,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderController.php": {
+ "type": "-",
+ "size": 13231,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderDetailController.php": {
+ "type": "-",
+ "size": 9996,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderFollowController.php": {
+ "type": "-",
+ "size": 5845,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderReturnController.php": {
+ "type": "-",
+ "size": 7493,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderSlipController.php": {
+ "type": "-",
+ "size": 3698,
+ "lmtime": 0,
+ "modified": false
+ },
+ "PageNotFoundController.php": {
+ "type": "-",
+ "size": 2283,
+ "lmtime": 0,
+ "modified": false
+ },
+ "PasswordController.php": {
+ "type": "-",
+ "size": 12605,
+ "lmtime": 0,
+ "modified": false
+ },
+ "PdfInvoiceController.php": {
+ "type": "-",
+ "size": 2923,
+ "lmtime": 0,
+ "modified": false
+ },
+ "PdfOrderReturnController.php": {
+ "type": "-",
+ "size": 2551,
+ "lmtime": 0,
+ "modified": false
+ },
+ "PdfOrderSlipController.php": {
+ "type": "-",
+ "size": 2182,
+ "lmtime": 0,
+ "modified": false
+ },
+ "ProductController.php": {
+ "type": "-",
+ "size": 68697,
+ "lmtime": 0,
+ "modified": false
+ },
+ "SitemapController.php": {
+ "type": "-",
+ "size": 6693,
+ "lmtime": 0,
+ "modified": false
+ },
+ "StatisticsController.php": {
+ "type": "-",
+ "size": 3359,
+ "lmtime": 0,
+ "modified": false
+ },
+ "StoresController.php": {
+ "type": "-",
+ "size": 9328,
+ "lmtime": 0,
+ "modified": false
+ },
+ "UploadController.php": {
+ "type": "-",
+ "size": 2891,
+ "lmtime": 0,
+ "modified": false
+ }
+ }
+ },
"cron-estella.php": {
"type": "-",
"size": 2399,
@@ -1123,8 +1315,8 @@
".htaccess": {
"type": "-",
"size": 58836,
- "lmtime": 1760004579939,
- "modified": false
+ "lmtime": 1758142950157,
+ "modified": true
},
".htaccess.2025-01-27-1738009656": {
"type": "-",
@@ -6657,7 +6849,25 @@
"CartController.php": {
"type": "-",
"size": 2824,
- "lmtime": 1760004579951,
+ "lmtime": 1758055348995,
+ "modified": false
+ },
+ "index.php": {
+ "type": "-",
+ "size": 1031,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderController.php": {
+ "type": "-",
+ "size": 1306,
+ "lmtime": 0,
+ "modified": false
+ },
+ "OrderController.sync-conflict-20231027-195743-EDGUH2C.php": {
+ "type": "-",
+ "size": 1306,
+ "lmtime": 0,
"modified": false
}
}
@@ -12279,7 +12489,7 @@
"CartController.php": {
"type": "-",
"size": 3022,
- "lmtime": 1760004579953,
+ "lmtime": 1758055404883,
"modified": false
},
"CmsController.php": {
@@ -12315,7 +12525,7 @@
"Cart.php": {
"type": "-",
"size": 2169,
- "lmtime": 1760004579952,
+ "lmtime": 1758059610069,
"modified": false
},
"CartRule.php": {
@@ -12826,10 +13036,45 @@
"modified": false
},
"listing": {
+ "best-sales.tpl": {
+ "type": "-",
+ "size": 471,
+ "lmtime": 0,
+ "modified": false
+ },
+ "category.tpl": {
+ "type": "-",
+ "size": 2424,
+ "lmtime": 0,
+ "modified": false
+ },
+ "index.php": {
+ "type": "-",
+ "size": 1279,
+ "lmtime": 0,
+ "modified": false
+ },
+ "manufacturer.tpl": {
+ "type": "-",
+ "size": 1296,
+ "lmtime": 0,
+ "modified": false
+ },
+ "new-products.tpl": {
+ "type": "-",
+ "size": 472,
+ "lmtime": 0,
+ "modified": false
+ },
+ "prices-drop.tpl": {
+ "type": "-",
+ "size": 476,
+ "lmtime": 0,
+ "modified": false
+ },
"product-list.tpl": {
"type": "-",
"size": 7439,
-<<<<<<< HEAD
"lmtime": 1759441359817,
"modified": false
},
@@ -12843,9 +13088,6 @@
"type": "-",
"size": 1247,
"lmtime": 0,
-=======
- "lmtime": 1760004579996,
->>>>>>> 75ca8fd840028fc69c3efb91a742413960c4defc
"modified": false
}
},
@@ -12859,7 +13101,7 @@
"product.tpl": {
"type": "-",
"size": 8390,
- "lmtime": 1760004579997,
+ "lmtime": 1759177283842,
"modified": false
},
"suppliers.tpl": {
@@ -12882,19 +13124,19 @@
"dr_materac.css": {
"type": "-",
"size": 86720,
- "lmtime": 1760004661020,
+ "lmtime": 1760649826851,
"modified": false
},
"dr_materac.css.map": {
"type": "-",
"size": 243497,
- "lmtime": 1760004661020,
+ "lmtime": 1760649826854,
"modified": false
},
"dr_materac.scss": {
"type": "-",
"size": 111350,
- "lmtime": 1760004660504,
+ "lmtime": 1760649826856,
"modified": false
},
"index.php": {
@@ -12919,8 +13161,8 @@
"js": {
"custom.js": {
"type": "-",
- "size": 31821,
- "lmtime": 1760004579992,
+ "size": 33644,
+ "lmtime": 1760649826859,
"modified": false
},
"index.php": {
@@ -12951,6 +13193,60 @@
"lmtime": 0,
"modified": false
},
+ "1170x600 Bytom Po Centrum Handlowe.png": {
+ "type": "-",
+ "size": 520831,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600 Bytom Przed.png": {
+ "type": "-",
+ "size": 533235,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600 Dąbrowa Górnicza Przed 18pazdziernik 2025r.png": {
+ "type": "-",
+ "size": 585298,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600.jpg": {
+ "type": "-",
+ "size": 478153,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600 Opole po.png": {
+ "type": "-",
+ "size": 542706,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600 Opole Przed.png": {
+ "type": "-",
+ "size": 565827,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600 Ostrów Częstochowa PO 2.png": {
+ "type": "-",
+ "size": 585954,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600 Ostrów Częstochowa PRZED 2.png": {
+ "type": "-",
+ "size": 634579,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1170x600 Przeworsk Przed.png": {
+ "type": "-",
+ "size": 542523,
+ "lmtime": 0,
+ "modified": false
+ },
"1170x600 sleepmed.png": {
"type": "-",
"size": 624079,
@@ -12975,6 +13271,30 @@
"lmtime": 0,
"modified": false
},
+ "1170x628 allure drm.jpg": {
+ "type": "-",
+ "size": 465534,
+ "lmtime": 0,
+ "modified": false
+ },
+ "11 pazdziernik 1170x600.jpg": {
+ "type": "-",
+ "size": 435609,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1200x628 bez dat 1.jpg": {
+ "type": "-",
+ "size": 736958,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1200x628 Bytom Po.png": {
+ "type": "-",
+ "size": 600437,
+ "lmtime": 0,
+ "modified": false
+ },
"1200x628 hilding przedwiosnie 24.png": {
"type": "-",
"size": 1095660,
@@ -12987,6 +13307,18 @@
"lmtime": 0,
"modified": false
},
+ "1200x628 Kraśnik Po.png": {
+ "type": "-",
+ "size": 557390,
+ "lmtime": 0,
+ "modified": false
+ },
+ "1200x628 Kraśnik Przed.png": {
+ "type": "-",
+ "size": 570002,
+ "lmtime": 0,
+ "modified": false
+ },
"1200x628 - Opole grudzien 7 .png": {
"type": "-",
"size": 645702,
@@ -12999,6 +13331,12 @@
"lmtime": 0,
"modified": false
},
+ "1200x628 Przeworsk Po.png": {
+ "type": "-",
+ "size": 570961,
+ "lmtime": 0,
+ "modified": false
+ },
"1200x628 Puławy Po.png": {
"type": "-",
"size": 586201,
@@ -13101,6 +13439,12 @@
"lmtime": 0,
"modified": false
},
+ "18 pazdziernik 1170x600.jpg": {
+ "type": "-",
+ "size": 427963,
+ "lmtime": 0,
+ "modified": false
+ },
"1SLIDER 1920x798 (002) new design taniej o vat wakacje 24r.jpg": {
"type": "-",
"size": 555174,
@@ -13251,12 +13595,24 @@
"lmtime": 0,
"modified": false
},
+ "4 pazdziernik weekend fizjo.jpg": {
+ "type": "-",
+ "size": 423830,
+ "lmtime": 0,
+ "modified": false
+ },
"722365909-2025_03_21_scb_banner-drmaterac_1170x628_sk_v03.jpg": {
"type": "-",
"size": 235939,
"lmtime": 0,
"modified": false
},
+ "738616328-2025_05_08_scb_dr-materac_1170x628_dt.jpg": {
+ "type": "-",
+ "size": 212216,
+ "lmtime": 0,
+ "modified": false
+ },
"8061271.png": {
"type": "-",
"size": 1052276,
@@ -13269,6 +13625,18 @@
"lmtime": 0,
"modified": false
},
+ "8 urodziny dr materac.jpg": {
+ "type": "-",
+ "size": 176535,
+ "lmtime": 0,
+ "modified": false
+ },
+ "8-urodziny-dr-materac-promocje.jpg": {
+ "type": "-",
+ "size": 205704,
+ "lmtime": 0,
+ "modified": false
+ },
"alleluja.png": {
"type": "-",
"size": 479522,
@@ -13281,6 +13649,12 @@
"lmtime": 0,
"modified": false
},
+ "allure gratisy.jpeg": {
+ "type": "-",
+ "size": 108184,
+ "lmtime": 0,
+ "modified": false
+ },
"Back to School - Slider (1).png": {
"type": "-",
"size": 630122,
@@ -13491,6 +13865,12 @@
"lmtime": 0,
"modified": false
},
+ "baner-dr-materac-2025.png": {
+ "type": "-",
+ "size": 1024778,
+ "lmtime": 0,
+ "modified": false
+ },
"baner eco i natura kwiecien 24.png": {
"type": "-",
"size": 716874,
@@ -13725,6 +14105,18 @@
"lmtime": 0,
"modified": false
},
+ "baner na slider 1170x600 janpol przedluzona promocja.jpg": {
+ "type": "-",
+ "size": 122239,
+ "lmtime": 0,
+ "modified": false
+ },
+ "baner na slider 1170x600 promocja na materace Janpol w Dr Materac.png": {
+ "type": "-",
+ "size": 486270,
+ "lmtime": 0,
+ "modified": false
+ },
"Baner new design taniej o VAT wakacje 24r.png": {
"type": "-",
"size": 714068,
@@ -14481,6 +14873,12 @@
"lmtime": 0,
"modified": false
},
+ "Drm x Mollyflex 1200x628(1).jpg": {
+ "type": "-",
+ "size": 377846,
+ "lmtime": 0,
+ "modified": false
+ },
"drozszy materac w cenie tanszego magniflex.png": {
"type": "-",
"size": 960033,
@@ -14493,6 +14891,12 @@
"lmtime": 0,
"modified": false
},
+ ".DS_Store": {
+ "type": "-",
+ "size": 6148,
+ "lmtime": 0,
+ "modified": false
+ },
"Eko i natura dr materac slider a.png": {
"type": "-",
"size": 711972,
@@ -14859,6 +15263,12 @@
"lmtime": 0,
"modified": false
},
+ "jesienne promocje w dr materac 2025.png": {
+ "type": "-",
+ "size": 574673,
+ "lmtime": 0,
+ "modified": false
+ },
"Karibian Descanso.png": {
"type": "-",
"size": 908782,
@@ -14883,6 +15293,12 @@
"lmtime": 0,
"modified": false
},
+ "Karibian x DrMaterac poduszki gratis.png": {
+ "type": "-",
+ "size": 838466,
+ "lmtime": 0,
+ "modified": false
+ },
"karibuan descanso.png": {
"type": "-",
"size": 743047,
@@ -14919,6 +15335,24 @@
"lmtime": 0,
"modified": false
},
+ "Kraśnik Przed wersja A otwarcie salonu sprzedaży Dr Materac w Kraśniku A.png": {
+ "type": "-",
+ "size": 570350,
+ "lmtime": 0,
+ "modified": false
+ },
+ "letnie rabaty od polowy maja w dr materac.png": {
+ "type": "-",
+ "size": 796547,
+ "lmtime": 0,
+ "modified": false
+ },
+ "letni-reset-dr-materac-2025-4.jpg": {
+ "type": "-",
+ "size": 195012,
+ "lmtime": 0,
+ "modified": false
+ },
"llSLIDER 1920x798 mollyflex.jpg": {
"type": "-",
"size": 691421,
@@ -14943,6 +15377,12 @@
"lmtime": 0,
"modified": false
},
+ "lozko za 1 zl tempur sealy promocja w dr materac.jpg": {
+ "type": "-",
+ "size": 193415,
+ "lmtime": 0,
+ "modified": false
+ },
"LULANDIA BANER.png": {
"type": "-",
"size": 606919,
@@ -15729,6 +16169,12 @@
"lmtime": 0,
"modified": false
},
+ "promocja na materace hilding w dr materac do 25 procent taniej.png": {
+ "type": "-",
+ "size": 597656,
+ "lmtime": 0,
+ "modified": false
+ },
"promocja_na_materace_hilding.webp": {
"type": "-",
"size": 46134,
@@ -15999,6 +16445,12 @@
"lmtime": 0,
"modified": false
},
+ "serta materace promocja w salonach dr materac.jpg": {
+ "type": "-",
+ "size": 590450,
+ "lmtime": 0,
+ "modified": false
+ },
"Sertasealy.png": {
"type": "-",
"size": 275408,
@@ -16971,6 +17423,12 @@
"lmtime": 0,
"modified": false
},
+ "WEEKEND Z FIZJO.jpg": {
+ "type": "-",
+ "size": 423830,
+ "lmtime": 0,
+ "modified": false
+ },
"We Love Candles banner reklamujący sojowe świece zapachowe (002).jpg": {
"type": "-",
"size": 636193,
@@ -17057,8 +17515,8 @@
},
"Wietrzenie Magazynów - Slider.webp": {
"type": "-",
- "size": 72754,
- "lmtime": 1744921788347,
+ "size": 81476,
+ "lmtime": 1760649826858,
"modified": false
},
"Wiosenne promocje w dr materac.png": {
@@ -17091,6 +17549,12 @@
"lmtime": 0,
"modified": false
},
+ "Zdjęcie WhatsApp 2025-04-22 o 11.57.57_587048b9.jpg": {
+ "type": "-",
+ "size": 128804,
+ "lmtime": 0,
+ "modified": false
+ },
"ZG otwarcie sklepu z materacami w Zielonej Gorze.png": {
"type": "-",
"size": 458581,
@@ -17308,7 +17772,7 @@
"detail1526395446.tpl": {
"type": "-",
"size": 30680,
- "lmtime": 1760004579994,
+ "lmtime": 1759177283821,
"modified": false
},
"detail1526396195.tpl": {
@@ -17395,7 +17859,7 @@
"ps_categoryproducts.tpl": {
"type": "-",
"size": 9894,
- "lmtime": 1760004579995,
+ "lmtime": 1759177283831,
"modified": false
}
}
@@ -17651,7 +18115,7 @@
"product-variants.tpl": {
"type": "-",
"size": 3541,
- "lmtime": 1760004579998,
+ "lmtime": 1759177283852,
"modified": false
},
"quickview.tpl": {
@@ -19405,79 +19869,25 @@
"20250914_exception.log": {
"type": "-",
"size": 119,
- "lmtime": 1760004579999,
+ "lmtime": 1758058497237,
"modified": false
},
"20250915_exception.log": {
"type": "-",
"size": 202,
- "lmtime": 1760004579999,
- "modified": false
- },
- "20250918_exception.log": {
- "type": "-",
- "size": 119,
- "lmtime": 0,
- "modified": false
- },
- "20250924_exception.log": {
- "type": "-",
- "size": 220,
- "lmtime": 0,
- "modified": false
- },
- "20250925_exception.log": {
- "type": "-",
- "size": 1494,
- "lmtime": 0,
- "modified": false
- },
- "20250927_exception.log": {
- "type": "-",
- "size": 7140,
- "lmtime": 0,
- "modified": false
- },
- "20250928_exception.log": {
- "type": "-",
- "size": 11620,
- "lmtime": 0,
- "modified": false
- },
- "20250929_exception.log": {
- "type": "-",
- "size": 119,
- "lmtime": 0,
- "modified": false
- },
- "20251001_exception.log": {
- "type": "-",
- "size": 220,
- "lmtime": 0,
- "modified": false
- },
- "20251005_exception.log": {
- "type": "-",
- "size": 119,
- "lmtime": 0,
- "modified": false
- },
- "20251006_exception.log": {
- "type": "-",
- "size": 119,
- "lmtime": 0,
+ "lmtime": 1758058497307,
"modified": false
},
"dev.log": {
"type": "-",
- "size": 6225969,
- "lmtime": 1757272260216,
- "modified": true
+ "size": 6162684,
+ "lmtime": 1758058992965,
+ "modified": false
},
"idn.log": {
"type": "-",
"size": 51120,
- "lmtime": 1757272260347,
+ "lmtime": 1758058987835,
"modified": false
},
"prod": {
@@ -19490,1322 +19900,1238 @@
},
"prod.log": {
"type": "-",
- "size": 346968,
- "lmtime": 1760004580002,
+ "size": 346040,
+ "lmtime": 1758058981080,
+ "modified": false
+ },
+ "ps_accounts-2025-09-07": {
+ "type": "-",
+ "size": 1088428,
+ "lmtime": 1758058497601,
"modified": false
},
"ps_accounts-2025-09-08": {
"type": "-",
- "size": 1593248,
- "lmtime": 1760004580018,
+ "size": 1585790,
+ "lmtime": 1758058497761,
"modified": false
},
"ps_accounts-2025-09-09": {
"type": "-",
- "size": 1431994,
- "lmtime": 1760004580024,
+ "size": 1425292,
+ "lmtime": 1758058497941,
"modified": false
},
"ps_accounts-2025-09-10": {
"type": "-",
- "size": 1637755,
- "lmtime": 1760004580031,
+ "size": 1630090,
+ "lmtime": 1758058498104,
"modified": false
},
"ps_accounts-2025-09-11": {
"type": "-",
- "size": 1353151,
- "lmtime": 1760004580037,
+ "size": 1346818,
+ "lmtime": 1758058498277,
"modified": false
},
"ps_accounts-2025-09-12": {
"type": "-",
- "size": 1658267,
- "lmtime": 1760004580044,
+ "size": 1650506,
+ "lmtime": 1758058498444,
"modified": false
},
"ps_accounts-2025-09-13": {
"type": "-",
- "size": 1012139,
- "lmtime": 1760004580048,
+ "size": 1007402,
+ "lmtime": 1758058498594,
"modified": false
},
"ps_accounts-2025-09-14": {
"type": "-",
- "size": 1187132,
- "lmtime": 1760004580053,
+ "size": 1181576,
+ "lmtime": 1758058498747,
"modified": false
},
"ps_accounts-2025-09-15": {
"type": "-",
- "size": 1310845,
- "lmtime": 1760004580058,
+ "size": 1304710,
+ "lmtime": 1758058498909,
"modified": false
},
"ps_accounts-2025-09-16": {
"type": "-",
- "size": 1170829,
- "lmtime": 1760004580064,
- "modified": false
- },
- "ps_accounts-2025-09-25": {
- "type": "-",
- "size": 1433586,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-09-26": {
- "type": "-",
- "size": 1240910,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-09-27": {
- "type": "-",
- "size": 738804,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-09-28": {
- "type": "-",
- "size": 215006,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-09-29": {
- "type": "-",
- "size": 1435378,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-09-30": {
- "type": "-",
- "size": 1627538,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-01": {
- "type": "-",
- "size": 1815748,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-02": {
- "type": "-",
- "size": 1570756,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-03": {
- "type": "-",
- "size": 1251756,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-04": {
- "type": "-",
- "size": 775808,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-05": {
- "type": "-",
- "size": 808346,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-06": {
- "type": "-",
- "size": 1501574,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-07": {
- "type": "-",
- "size": 1557996,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-08": {
- "type": "-",
- "size": 1492282,
- "lmtime": 0,
- "modified": false
- },
- "ps_accounts-2025-10-09": {
- "type": "-",
- "size": 1231340,
- "lmtime": 0,
+ "size": 1165348,
+ "lmtime": 1758058977343,
"modified": false
},
"pshowsso_fallback_20250915230411.log": {
"type": "-",
"size": 299,
- "lmtime": 0,
+ "lmtime": 1758058714699,
"modified": false
},
"pshowsso_fallback_20250915230412.log": {
"type": "-",
"size": 398,
- "lmtime": 0,
+ "lmtime": 1758058714770,
"modified": false
},
"pshowsso_fallback_20250915230415.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058714840,
"modified": false
},
"pshowsso_fallback_20250915230425.log": {
"type": "-",
"size": 288,
- "lmtime": 0,
+ "lmtime": 1758058714909,
"modified": false
},
"pshowsso_fallback_20250915230427.log": {
"type": "-",
"size": 290,
- "lmtime": 0,
+ "lmtime": 1758058714980,
"modified": false
},
"pshowsso_fallback_20250915230437.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058715049,
"modified": false
},
"pshowsso_fallback_20250915230440.log": {
"type": "-",
"size": 275,
- "lmtime": 0,
+ "lmtime": 1758058715126,
"modified": false
},
"pshowsso_fallback_20250915230442.log": {
"type": "-",
"size": 279,
- "lmtime": 0,
+ "lmtime": 1758058715196,
"modified": false
},
"pshowsso_fallback_20250915230443.log": {
"type": "-",
"size": 323,
- "lmtime": 0,
+ "lmtime": 1758058715266,
"modified": false
},
"pshowsso_fallback_20250915230445.log": {
"type": "-",
"size": 242,
- "lmtime": 0,
+ "lmtime": 1758058715337,
"modified": false
},
"pshowsso_fallback_20250915230500.log": {
"type": "-",
"size": 529,
- "lmtime": 0,
+ "lmtime": 1758058715409,
"modified": false
},
"pshowsso_fallback_20250915230502.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058715477,
"modified": false
},
"pshowsso_fallback_20250915230503.log": {
"type": "-",
"size": 529,
- "lmtime": 0,
+ "lmtime": 1758058715547,
"modified": false
},
"pshowsso_fallback_20250915230509.log": {
"type": "-",
"size": 538,
- "lmtime": 0,
+ "lmtime": 1758058715621,
"modified": false
},
"pshowsso_fallback_20250915230525.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058715701,
"modified": false
},
"pshowsso_fallback_20250915230527.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058715770,
"modified": false
},
"pshowsso_fallback_20250915230534.log": {
"type": "-",
"size": 213,
- "lmtime": 0,
+ "lmtime": 1758058715839,
"modified": false
},
"pshowsso_fallback_20250915230536.log": {
"type": "-",
"size": 302,
- "lmtime": 0,
+ "lmtime": 1758058715914,
"modified": false
},
"pshowsso_fallback_20250915230537.log": {
"type": "-",
"size": 515,
- "lmtime": 0,
+ "lmtime": 1758058715982,
"modified": false
},
"pshowsso_fallback_20250915230538.log": {
"type": "-",
"size": 279,
- "lmtime": 0,
+ "lmtime": 1758058716057,
"modified": false
},
"pshowsso_fallback_20250915230539.log": {
"type": "-",
"size": 289,
- "lmtime": 0,
+ "lmtime": 1758058716125,
"modified": false
},
"pshowsso_fallback_20250915230540.log": {
"type": "-",
"size": 515,
- "lmtime": 0,
+ "lmtime": 1758058716199,
"modified": false
},
"pshowsso_fallback_20250915230541.log": {
"type": "-",
"size": 323,
- "lmtime": 0,
+ "lmtime": 1758058716269,
"modified": false
},
"pshowsso_fallback_20250915230544.log": {
"type": "-",
"size": 305,
- "lmtime": 0,
+ "lmtime": 1758058716340,
"modified": false
},
"pshowsso_fallback_20250915230547.log": {
"type": "-",
"size": 259,
- "lmtime": 0,
+ "lmtime": 1758058716412,
"modified": false
},
"pshowsso_fallback_20250915230548.log": {
"type": "-",
"size": 321,
- "lmtime": 0,
+ "lmtime": 1758058716485,
"modified": false
},
"pshowsso_fallback_20250915230550.log": {
"type": "-",
"size": 523,
- "lmtime": 0,
+ "lmtime": 1758058716555,
"modified": false
},
"pshowsso_fallback_20250915230551.log": {
"type": "-",
"size": 336,
- "lmtime": 0,
+ "lmtime": 1758058716625,
"modified": false
},
"pshowsso_fallback_20250915230552.log": {
"type": "-",
"size": 279,
- "lmtime": 0,
+ "lmtime": 1758058716703,
"modified": false
},
"pshowsso_fallback_20250915230554.log": {
"type": "-",
"size": 523,
- "lmtime": 0,
+ "lmtime": 1758058716777,
"modified": false
},
"pshowsso_fallback_20250915230555.log": {
"type": "-",
"size": 296,
- "lmtime": 0,
+ "lmtime": 1758058716849,
"modified": false
},
"pshowsso_fallback_20250915230559.log": {
"type": "-",
"size": 286,
- "lmtime": 0,
+ "lmtime": 1758058716921,
"modified": false
},
"pshowsso_fallback_20250915230602.log": {
"type": "-",
"size": 320,
- "lmtime": 0,
+ "lmtime": 1758058716993,
"modified": false
},
"pshowsso_fallback_20250915230605.log": {
"type": "-",
"size": 288,
- "lmtime": 0,
+ "lmtime": 1758058717063,
"modified": false
},
"pshowsso_fallback_20250915230606.log": {
"type": "-",
"size": 286,
- "lmtime": 0,
+ "lmtime": 1758058717135,
"modified": false
},
"pshowsso_fallback_20250915230608.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058717210,
"modified": false
},
"pshowsso_fallback_20250915230610.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058717280,
"modified": false
},
"pshowsso_fallback_20250915230611.log": {
"type": "-",
"size": 285,
- "lmtime": 0,
+ "lmtime": 1758058717350,
"modified": false
},
"pshowsso_fallback_20250915230612.log": {
"type": "-",
"size": 266,
- "lmtime": 0,
+ "lmtime": 1758058717424,
"modified": false
},
"pshowsso_fallback_20250915230615.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058717500,
"modified": false
},
"pshowsso_fallback_20250915230622.log": {
"type": "-",
"size": 279,
- "lmtime": 0,
+ "lmtime": 1758058717571,
"modified": false
},
"pshowsso_fallback_20250915230628.log": {
"type": "-",
"size": 484,
- "lmtime": 0,
+ "lmtime": 1758058717641,
"modified": false
},
"pshowsso_fallback_20250915230630.log": {
"type": "-",
"size": 252,
- "lmtime": 0,
+ "lmtime": 1758058717721,
"modified": false
},
"pshowsso_fallback_20250915230631.log": {
"type": "-",
"size": 248,
- "lmtime": 0,
+ "lmtime": 1758058717795,
"modified": false
},
"pshowsso_fallback_20250915230632.log": {
"type": "-",
"size": 277,
- "lmtime": 0,
+ "lmtime": 1758058717865,
"modified": false
},
"pshowsso_fallback_20250915230634.log": {
"type": "-",
"size": 258,
- "lmtime": 0,
+ "lmtime": 1758058717937,
"modified": false
},
"pshowsso_fallback_20250915230638.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058718010,
"modified": false
},
"pshowsso_fallback_20250915230641.log": {
"type": "-",
"size": 244,
- "lmtime": 0,
+ "lmtime": 1758058718083,
"modified": false
},
"pshowsso_fallback_20250915230645.log": {
"type": "-",
"size": 383,
- "lmtime": 0,
+ "lmtime": 1758058718152,
"modified": false
},
"pshowsso_fallback_20250915230648.log": {
"type": "-",
"size": 466,
- "lmtime": 0,
+ "lmtime": 1758058718222,
"modified": false
},
"pshowsso_fallback_20250915230650.log": {
"type": "-",
"size": 284,
- "lmtime": 0,
+ "lmtime": 1758058718294,
"modified": false
},
"pshowsso_fallback_20250915230651.log": {
"type": "-",
"size": 420,
- "lmtime": 0,
+ "lmtime": 1758058718367,
"modified": false
},
"pshowsso_fallback_20250915230653.log": {
"type": "-",
"size": 298,
- "lmtime": 0,
+ "lmtime": 1758058718442,
"modified": false
},
"pshowsso_fallback_20250915230654.log": {
"type": "-",
"size": 386,
- "lmtime": 0,
+ "lmtime": 1758058718527,
"modified": false
},
"pshowsso_fallback_20250915230655.log": {
"type": "-",
"size": 285,
- "lmtime": 0,
+ "lmtime": 1758058718601,
"modified": false
},
"pshowsso_fallback_20250915230657.log": {
"type": "-",
"size": 220,
- "lmtime": 0,
+ "lmtime": 1758058718672,
"modified": false
},
"pshowsso_fallback_20250915230658.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058718748,
"modified": false
},
"pshowsso_fallback_20250915230701.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058718818,
"modified": false
},
"pshowsso_fallback_20250915230705.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058718885,
"modified": false
},
"pshowsso_fallback_20250915230707.log": {
"type": "-",
"size": 552,
- "lmtime": 0,
+ "lmtime": 1758058718955,
"modified": false
},
"pshowsso_fallback_20250915230708.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058719029,
"modified": false
},
"pshowsso_fallback_20250915230710.log": {
"type": "-",
"size": 233,
- "lmtime": 0,
+ "lmtime": 1758058719101,
"modified": false
},
"pshowsso_fallback_20250915230711.log": {
"type": "-",
"size": 268,
- "lmtime": 0,
+ "lmtime": 1758058719171,
"modified": false
},
"pshowsso_fallback_20250915230712.log": {
"type": "-",
"size": 552,
- "lmtime": 0,
+ "lmtime": 1758058719245,
"modified": false
},
"pshowsso_fallback_20250915230715.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058719313,
"modified": false
},
"pshowsso_fallback_20250915230716.log": {
"type": "-",
"size": 262,
- "lmtime": 0,
+ "lmtime": 1758058719387,
"modified": false
},
"pshowsso_fallback_20250915230718.log": {
"type": "-",
"size": 416,
- "lmtime": 0,
+ "lmtime": 1758058719454,
"modified": false
},
"pshowsso_fallback_20250915230719.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058719528,
"modified": false
},
"pshowsso_fallback_20250915230722.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058719594,
"modified": false
},
"pshowsso_fallback_20250915230723.log": {
"type": "-",
"size": 220,
- "lmtime": 0,
+ "lmtime": 1758058719663,
"modified": false
},
"pshowsso_fallback_20250915230724.log": {
"type": "-",
"size": 317,
- "lmtime": 0,
+ "lmtime": 1758058719732,
"modified": false
},
"pshowsso_fallback_20250915230726.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058719803,
"modified": false
},
"pshowsso_fallback_20250915230729.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058719871,
"modified": false
},
"pshowsso_fallback_20250915230730.log": {
"type": "-",
"size": 251,
- "lmtime": 0,
+ "lmtime": 1758058719942,
"modified": false
},
"pshowsso_fallback_20250915230733.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058720012,
"modified": false
},
"pshowsso_fallback_20250915230735.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058720082,
"modified": false
},
"pshowsso_fallback_20250915230737.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058720154,
"modified": false
},
"pshowsso_fallback_20250915230740.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058720228,
"modified": false
},
"pshowsso_fallback_20250915230741.log": {
"type": "-",
"size": 329,
- "lmtime": 0,
+ "lmtime": 1758058720297,
"modified": false
},
"pshowsso_fallback_20250915230743.log": {
"type": "-",
"size": 265,
- "lmtime": 0,
+ "lmtime": 1758058720372,
"modified": false
},
"pshowsso_fallback_20250915230744.log": {
"type": "-",
"size": 255,
- "lmtime": 0,
+ "lmtime": 1758058720447,
"modified": false
},
"pshowsso_fallback_20250915230745.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058720520,
"modified": false
},
"pshowsso_fallback_20250915230746.log": {
"type": "-",
"size": 320,
- "lmtime": 0,
+ "lmtime": 1758058720593,
"modified": false
},
"pshowsso_fallback_20250915230749.log": {
"type": "-",
"size": 251,
- "lmtime": 0,
+ "lmtime": 1758058720667,
"modified": false
},
"pshowsso_fallback_20250915230750.log": {
"type": "-",
"size": 323,
- "lmtime": 0,
+ "lmtime": 1758058720739,
"modified": false
},
"pshowsso_fallback_20250915230751.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058720811,
"modified": false
},
"pshowsso_fallback_20250915230752.log": {
"type": "-",
"size": 268,
- "lmtime": 0,
+ "lmtime": 1758058720884,
"modified": false
},
"pshowsso_fallback_20250915230753.log": {
"type": "-",
"size": 305,
- "lmtime": 0,
+ "lmtime": 1758058720957,
"modified": false
},
"pshowsso_fallback_20250915230755.log": {
"type": "-",
"size": 290,
- "lmtime": 0,
+ "lmtime": 1758058721029,
"modified": false
},
"pshowsso_fallback_20250915230757.log": {
"type": "-",
"size": 220,
- "lmtime": 0,
+ "lmtime": 1758058721104,
"modified": false
},
"pshowsso_fallback_20250915230800.log": {
"type": "-",
"size": 336,
- "lmtime": 0,
+ "lmtime": 1758058721174,
"modified": false
},
"pshowsso_fallback_20250915230803.log": {
"type": "-",
"size": 296,
- "lmtime": 0,
+ "lmtime": 1758058721247,
"modified": false
},
"pshowsso_fallback_20250915230806.log": {
"type": "-",
"size": 286,
- "lmtime": 0,
+ "lmtime": 1758058721320,
"modified": false
},
"pshowsso_fallback_20250915230810.log": {
"type": "-",
"size": 283,
- "lmtime": 0,
+ "lmtime": 1758058721401,
"modified": false
},
"pshowsso_fallback_20250915230811.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058721472,
"modified": false
},
"pshowsso_fallback_20250915230813.log": {
"type": "-",
"size": 288,
- "lmtime": 0,
+ "lmtime": 1758058721545,
"modified": false
},
"pshowsso_fallback_20250915230814.log": {
"type": "-",
"size": 260,
- "lmtime": 0,
+ "lmtime": 1758058721617,
"modified": false
},
"pshowsso_fallback_20250915230816.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058721687,
"modified": false
},
"pshowsso_fallback_20250915230818.log": {
"type": "-",
"size": 307,
- "lmtime": 0,
+ "lmtime": 1758058721763,
"modified": false
},
"pshowsso_fallback_20250915230819.log": {
"type": "-",
"size": 299,
- "lmtime": 0,
+ "lmtime": 1758058721835,
"modified": false
},
"pshowsso_fallback_20250915230822.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058721905,
"modified": false
},
"pshowsso_fallback_20250915230823.log": {
"type": "-",
"size": 259,
- "lmtime": 0,
+ "lmtime": 1758058721974,
"modified": false
},
"pshowsso_fallback_20250915230825.log": {
"type": "-",
"size": 220,
- "lmtime": 0,
+ "lmtime": 1758058722047,
"modified": false
},
"pshowsso_fallback_20250915230826.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058722117,
"modified": false
},
"pshowsso_fallback_20250915230828.log": {
"type": "-",
"size": 424,
- "lmtime": 0,
+ "lmtime": 1758058722188,
"modified": false
},
"pshowsso_fallback_20250915230829.log": {
"type": "-",
"size": 296,
- "lmtime": 0,
+ "lmtime": 1758058722261,
"modified": false
},
"pshowsso_fallback_20250915230830.log": {
"type": "-",
"size": 296,
- "lmtime": 0,
+ "lmtime": 1758058722331,
"modified": false
},
"pshowsso_fallback_20250915230831.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058722409,
"modified": false
},
"pshowsso_fallback_20250915230832.log": {
"type": "-",
"size": 341,
- "lmtime": 0,
+ "lmtime": 1758058722483,
"modified": false
},
"pshowsso_fallback_20250915230833.log": {
"type": "-",
"size": 341,
- "lmtime": 0,
+ "lmtime": 1758058722553,
"modified": false
},
"pshowsso_fallback_20250915230834.log": {
"type": "-",
"size": 217,
- "lmtime": 0,
+ "lmtime": 1758058722622,
"modified": false
},
"pshowsso_fallback_20250915230835.log": {
"type": "-",
"size": 424,
- "lmtime": 0,
+ "lmtime": 1758058722695,
"modified": false
},
"pshowsso_fallback_20250915230840.log": {
"type": "-",
"size": 264,
- "lmtime": 0,
+ "lmtime": 1758058722764,
"modified": false
},
"pshowsso_fallback_20250915230842.log": {
"type": "-",
"size": 261,
- "lmtime": 0,
+ "lmtime": 1758058722836,
"modified": false
},
"pshowsso_fallback_20250915230846.log": {
"type": "-",
"size": 270,
- "lmtime": 0,
+ "lmtime": 1758058722906,
"modified": false
},
"pshowsso_fallback_20250915230850.log": {
"type": "-",
"size": 296,
- "lmtime": 0,
+ "lmtime": 1758058722976,
"modified": false
},
"pshowsso_fallback_20250915230855.log": {
"type": "-",
"size": 514,
- "lmtime": 0,
+ "lmtime": 1758058723050,
"modified": false
},
"pshowsso_fallback_20250915230857.log": {
"type": "-",
"size": 514,
- "lmtime": 0,
+ "lmtime": 1758058723122,
"modified": false
},
"pshowsso_fallback_20250915230859.log": {
"type": "-",
"size": 275,
- "lmtime": 0,
+ "lmtime": 1758058723196,
"modified": false
},
"pshowsso_fallback_20250915230901.log": {
"type": "-",
"size": 280,
- "lmtime": 0,
+ "lmtime": 1758058723267,
"modified": false
},
"pshowsso_fallback_20250915230902.log": {
"type": "-",
"size": 295,
- "lmtime": 0,
+ "lmtime": 1758058723340,
"modified": false
},
"pshowsso_fallback_20250915230903.log": {
"type": "-",
"size": 274,
- "lmtime": 0,
+ "lmtime": 1758058723409,
"modified": false
},
"pshowsso_fallback_20250915230912.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058723476,
"modified": false
},
"pshowsso_fallback_20250915230919.log": {
"type": "-",
"size": 267,
- "lmtime": 0,
+ "lmtime": 1758058723547,
"modified": false
},
"pshowsso_fallback_20250915230921.log": {
"type": "-",
"size": 217,
- "lmtime": 0,
+ "lmtime": 1758058723617,
"modified": false
},
"pshowsso_fallback_20250915230929.log": {
"type": "-",
"size": 259,
- "lmtime": 0,
+ "lmtime": 1758058723692,
"modified": false
},
"pshowsso_fallback_20250915230932.log": {
"type": "-",
"size": 213,
- "lmtime": 0,
+ "lmtime": 1758058723763,
"modified": false
},
"pshowsso_fallback_20250915230935.log": {
"type": "-",
"size": 320,
- "lmtime": 0,
+ "lmtime": 1758058723833,
"modified": false
},
"pshowsso_fallback_20250915230939.log": {
"type": "-",
"size": 515,
- "lmtime": 0,
+ "lmtime": 1758058723900,
"modified": false
},
"pshowsso_fallback_20250915230943.log": {
"type": "-",
"size": 515,
- "lmtime": 0,
+ "lmtime": 1758058723964,
"modified": false
},
"pshowsso_fallback_20250915230945.log": {
"type": "-",
"size": 515,
- "lmtime": 0,
+ "lmtime": 1758058724030,
"modified": false
},
"pshowsso_fallback_20250915230946.log": {
"type": "-",
"size": 321,
- "lmtime": 0,
+ "lmtime": 1758058724098,
"modified": false
},
"pshowsso_fallback_20250915230947.log": {
"type": "-",
"size": 273,
- "lmtime": 0,
+ "lmtime": 1758058724172,
"modified": false
},
"pshowsso_fallback_20250915230949.log": {
"type": "-",
"size": 336,
- "lmtime": 0,
+ "lmtime": 1758058724242,
"modified": false
},
"pshowsso_fallback_20250915230952.log": {
"type": "-",
"size": 306,
- "lmtime": 0,
+ "lmtime": 1758058724314,
"modified": false
},
"pshowsso_fallback_20250915230953.log": {
"type": "-",
"size": 251,
- "lmtime": 0,
+ "lmtime": 1758058724392,
"modified": false
},
"pshowsso_fallback_20250915230956.log": {
"type": "-",
"size": 477,
- "lmtime": 0,
+ "lmtime": 1758058724469,
"modified": false
},
"pshowsso_fallback_20250915230957.log": {
"type": "-",
"size": 477,
- "lmtime": 0,
+ "lmtime": 1758058724541,
"modified": false
},
"pshowsso_fallback_20250915230959.log": {
"type": "-",
"size": 320,
- "lmtime": 0,
+ "lmtime": 1758058724610,
"modified": false
},
"pshowsso_fallback_20250915231001.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058724682,
"modified": false
},
"pshowsso_fallback_20250915231002.log": {
"type": "-",
"size": 288,
- "lmtime": 0,
+ "lmtime": 1758058724752,
"modified": false
},
"pshowsso_fallback_20250915231005.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058724818,
"modified": false
},
"pshowsso_fallback_20250915231008.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058724889,
"modified": false
},
"pshowsso_fallback_20250915231009.log": {
"type": "-",
"size": 299,
- "lmtime": 0,
+ "lmtime": 1758058724956,
"modified": false
},
"pshowsso_fallback_20250915231012.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058725025,
"modified": false
},
"pshowsso_fallback_20250915231013.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058725097,
"modified": false
},
"pshowsso_fallback_20250915231023.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058725171,
"modified": false
},
"pshowsso_fallback_20250915231024.log": {
"type": "-",
"size": 310,
- "lmtime": 0,
+ "lmtime": 1758058725244,
"modified": false
},
"pshowsso_fallback_20250915231025.log": {
"type": "-",
"size": 229,
- "lmtime": 0,
+ "lmtime": 1758058725334,
"modified": false
},
"pshowsso_fallback_20250915231028.log": {
"type": "-",
"size": 220,
- "lmtime": 0,
+ "lmtime": 1758058725404,
"modified": false
},
"pshowsso_fallback_20250915231039.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058725475,
"modified": false
},
"pshowsso_fallback_20250915231043.log": {
"type": "-",
"size": 260,
- "lmtime": 0,
+ "lmtime": 1758058725543,
"modified": false
},
"pshowsso_fallback_20250915231044.log": {
"type": "-",
"size": 292,
- "lmtime": 0,
+ "lmtime": 1758058725615,
"modified": false
},
"pshowsso_fallback_20250915231046.log": {
"type": "-",
"size": 253,
- "lmtime": 0,
+ "lmtime": 1758058725685,
"modified": false
},
"pshowsso_fallback_20250915231047.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058725755,
"modified": false
},
"pshowsso_fallback_20250915231048.log": {
"type": "-",
"size": 277,
- "lmtime": 0,
+ "lmtime": 1758058725825,
"modified": false
},
"pshowsso_fallback_20250915231050.log": {
"type": "-",
"size": 253,
- "lmtime": 0,
+ "lmtime": 1758058725897,
"modified": false
},
"pshowsso_fallback_20250915231052.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058725967,
"modified": false
},
"pshowsso_fallback_20250915231055.log": {
"type": "-",
"size": 289,
- "lmtime": 0,
+ "lmtime": 1758058726035,
"modified": false
},
"pshowsso_fallback_20250915231057.log": {
"type": "-",
"size": 262,
- "lmtime": 0,
+ "lmtime": 1758058726105,
"modified": false
},
"pshowsso_fallback_20250915231059.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058726176,
"modified": false
},
"pshowsso_fallback_20250915231103.log": {
"type": "-",
"size": 289,
- "lmtime": 0,
+ "lmtime": 1758058726242,
"modified": false
},
"pshowsso_fallback_20250915231111.log": {
"type": "-",
"size": 284,
- "lmtime": 0,
+ "lmtime": 1758058726317,
"modified": false
},
"pshowsso_fallback_20250915231113.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058726387,
"modified": false
},
"pshowsso_fallback_20250915231116.log": {
"type": "-",
"size": 282,
- "lmtime": 0,
+ "lmtime": 1758058726458,
"modified": false
},
"pshowsso_fallback_20250915231117.log": {
"type": "-",
"size": 282,
- "lmtime": 0,
+ "lmtime": 1758058726530,
"modified": false
},
"pshowsso_fallback_20250915231119.log": {
"type": "-",
"size": 282,
- "lmtime": 0,
+ "lmtime": 1758058726601,
"modified": false
},
"pshowsso_fallback_20250915231120.log": {
"type": "-",
"size": 282,
- "lmtime": 0,
+ "lmtime": 1758058726672,
"modified": false
},
"pshowsso_fallback_20250915231127.log": {
"type": "-",
"size": 291,
- "lmtime": 0,
+ "lmtime": 1758058726743,
"modified": false
},
"pshowsso_fallback_20250915231133.log": {
"type": "-",
"size": 213,
- "lmtime": 0,
+ "lmtime": 1758058726814,
"modified": false
},
"pshowsso_fallback_20250915231136.log": {
"type": "-",
"size": 320,
- "lmtime": 0,
+ "lmtime": 1758058726886,
"modified": false
},
"pshowsso_fallback_20250915231140.log": {
"type": "-",
"size": 291,
- "lmtime": 0,
+ "lmtime": 1758058726960,
"modified": false
},
"pshowsso_fallback_20250915231142.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058727031,
"modified": false
},
"pshowsso_fallback_20250915231143.log": {
"type": "-",
"size": 305,
- "lmtime": 0,
+ "lmtime": 1758058727103,
"modified": false
},
"pshowsso_fallback_20250915231144.log": {
"type": "-",
"size": 230,
- "lmtime": 0,
+ "lmtime": 1758058727175,
"modified": false
},
"pshowsso_fallback_20250915231146.log": {
"type": "-",
"size": 284,
- "lmtime": 0,
+ "lmtime": 1758058727244,
"modified": false
},
"pshowsso_fallback_20250915231147.log": {
"type": "-",
"size": 321,
- "lmtime": 0,
+ "lmtime": 1758058727315,
"modified": false
},
"pshowsso_fallback_20250915231148.log": {
"type": "-",
"size": 287,
- "lmtime": 0,
+ "lmtime": 1758058727384,
"modified": false
},
"pshowsso_fallback_20250915231150.log": {
"type": "-",
"size": 336,
- "lmtime": 0,
+ "lmtime": 1758058727458,
"modified": false
},
"pshowsso_fallback_20250915231153.log": {
"type": "-",
"size": 296,
- "lmtime": 0,
+ "lmtime": 1758058727530,
"modified": false
},
"pshowsso_fallback_20250915231154.log": {
"type": "-",
"size": 283,
- "lmtime": 0,
+ "lmtime": 1758058727600,
"modified": false
},
"pshowsso_fallback_20250915231156.log": {
"type": "-",
"size": 286,
- "lmtime": 0,
+ "lmtime": 1758058727672,
"modified": false
},
"pshowsso_fallback_20250915231200.log": {
"type": "-",
"size": 320,
- "lmtime": 0,
+ "lmtime": 1758058727743,
"modified": false
},
"pshowsso_fallback_20250915231203.log": {
"type": "-",
"size": 288,
- "lmtime": 0,
+ "lmtime": 1758058727812,
"modified": false
},
"pshowsso_fallback_20250915231206.log": {
"type": "-",
"size": 281,
- "lmtime": 0,
+ "lmtime": 1758058727885,
"modified": false
},
"pshowsso_fallback_20250915231209.log": {
"type": "-",
"size": 283,
- "lmtime": 0,
+ "lmtime": 1758058727954,
"modified": false
},
"pshowsso_fallback_20250915231213.log": {
"type": "-",
"size": 209,
- "lmtime": 0,
+ "lmtime": 1758058728025,
"modified": false
},
"pshowsso_fallback_20250915231216.log": {
"type": "-",
"size": 276,
- "lmtime": 0,
+ "lmtime": 1758058728099,
"modified": false
},
"pshowsso_fallback_20250915231217.log": {
"type": "-",
"size": 251,
- "lmtime": 0,
+ "lmtime": 1758058728171,
"modified": false
},
"pshowsso_fallback_20250915231220.log": {
"type": "-",
"size": 268,
- "lmtime": 0,
+ "lmtime": 1758058728239,
"modified": false
},
"pshowsso_fallback_20250915231223.log": {
"type": "-",
"size": 230,
- "lmtime": 0,
+ "lmtime": 1758058728313,
"modified": false
},
"pshowsso_fallback_20250915231233.log": {
"type": "-",
"size": 267,
- "lmtime": 0,
+ "lmtime": 1758058728387,
"modified": false
},
"pshowsso_fallback_20250915231240.log": {
"type": "-",
"size": 282,
- "lmtime": 0,
+ "lmtime": 1758058728460,
"modified": false
},
"pshowsso_fallback_20250915231242.log": {
"type": "-",
"size": 282,
- "lmtime": 0,
+ "lmtime": 1758058728530,
"modified": false
},
"pshowsso_fallback_20250915231243.log": {
"type": "-",
"size": 229,
- "lmtime": 0,
+ "lmtime": 1758058728607,
"modified": false
},
"pshowsso_fallback_20250915231245.log": {
@@ -20813,12 +21139,6 @@
"size": 0,
"lmtime": 0,
"modified": false
- },
- "ps_accounts-2025-09-07": {
- "type": "-",
- "size": 1093546,
- "lmtime": 1760004580009,
- "modified": false
}
},
"modules": {},
diff --git a/modules/gm_omniprice/CHANGELOG b/modules/gm_omniprice/CHANGELOG
index 9fceff53..9463992b 100644
--- a/modules/gm_omniprice/CHANGELOG
+++ b/modules/gm_omniprice/CHANGELOG
@@ -1,7 +1,27 @@
+## [1.3.1] - 2025-08-26
+### Changed
+
+- cache use optimization for SQL queries
+
+## [1.3.0] - 2025-06-23
+### Changed
+
+- scripts changed to controllers for PrestaShop 9 compatibility
+
+## [1.2.13] - 2025-04-07
+### Changed
+
+- database performance optimization
+
+## [1.2.12] - 2025-01-13
+### Changed
+
+- groupinc module support in cron.php script
+
## [1.2.11] - 2024-12-19
### Changed
-- More conservative approach to cleaning prices
+- More conservative approach to cleaning old prices
## [1.2.10] - 2024-12-09
### Changed
diff --git a/modules/gm_omniprice/controllers/front/cron.php b/modules/gm_omniprice/controllers/front/cron.php
new file mode 100644
index 00000000..2d4d820b
--- /dev/null
+++ b/modules/gm_omniprice/controllers/front/cron.php
@@ -0,0 +1,126 @@
+displayTemplate();
+ $token = Tools::getValue('token');
+ $omni = $this->module;
+ $comparedToken = $omni->getTokenForScripts();
+ if ($token != $comparedToken) {
+ die('invalid token');
+ }
+ $action = Tools::getValue('action');
+ $verbose = !Tools::isSubmit('silent');
+ switch ($action) {
+ case 'index' :
+ $start = microtime(true);
+ echo 'PS '._PS_VERSION_.' ';
+ echo 'OmniPrice '.$omni->version.' ';
+ if (Tools::isSubmit('reset')) {
+ $omni->resetIndex();
+ echo 'RESET';
+ }
+ $productId = null;
+ if (Tools::isSubmit('pid')) {
+ $productId = (int) Tools::getValue('pid');
+ $omni->removeProductFromTodaysIndex($productId);
+ $omni->removeProductFromTodaysHistory($productId);
+ }
+ $omni->savePrices(true, $productId);
+ echo 'FINISH ';
+ if (Tools::isSubmit('debug')) {
+ echo 'DEBUG: ';
+ $debug = Db::getInstance()->executeS('SELECT * FROM `'._DB_PREFIX_.'gm_omniprice_history` WHERE `id_product` = '.$productId);
+ if ($debug) {
+ echo $omni->displayTable($debug, array_keys($debug[0]));
+ }
+ $debug = Db::getInstance()->executeS('SELECT * FROM `'._DB_PREFIX_.'gm_omniprice_cache` WHERE `id_product` = '.$productId);
+ if ($debug) {
+ echo $omni->displayTable($debug, array_keys($debug[0]));
+ }
+ }
+ $timeElapsedSeconds = microtime(true) - $start;
+ echo round($timeElapsedSeconds, 4).' s ';
+ break;
+ case 'cleanup' :
+ $omni->cleanUp($verbose);
+ echo 'FINISH ';
+ break;
+ case 'fill' :
+ $omni->fillMissingCache($verbose);
+ echo 'FINISH ';
+ break;
+ default:
+ echo $omni->l('Unknown action').' ';
+ }
+ exit();
+ }
+
+ protected function displayTemplate()
+ {
+ echo '
+
+
+
+
+ ';
+ }
+}
diff --git a/modules/gm_omniprice/controllers/front/index.php b/modules/gm_omniprice/controllers/front/index.php
new file mode 100644
index 00000000..a41987df
--- /dev/null
+++ b/modules/gm_omniprice/controllers/front/index.php
@@ -0,0 +1,35 @@
+
+* @copyright 2007-2014 PrestaShop SA
+* @license http://opensource.org/licenses/afl-3.0.php Academic Free License (AFL 3.0)
+* International Registered Trademark & Property of PrestaShop SA
+*/
+
+header("Expires: Mon, 26 Jul 1997 05:00:00 GMT");
+header("Last-Modified: ".gmdate("D, d M Y H:i:s")." GMT");
+
+header("Cache-Control: no-store, no-cache, must-revalidate");
+header("Cache-Control: post-check=0, pre-check=0", false);
+header("Pragma: no-cache");
+
+header("Location: ../");
+exit;
\ No newline at end of file
diff --git a/modules/gm_omniprice/cron.php b/modules/gm_omniprice/cron.php
index 4d7c0db9..80b39411 100644
--- a/modules/gm_omniprice/cron.php
+++ b/modules/gm_omniprice/cron.php
@@ -3,7 +3,9 @@
$start = microtime(true);
require('template.php');
require_once(dirname(__FILE__) . '/../../config/config.inc.php');
-
+if (Module::isEnabled('groupinc')) {
+ require_once(dirname(__FILE__) . '/../../init.php');
+}
$omni = Module::getInstanceByName('gm_omniprice');
$token = Tools::getValue('token');
$comparedToken = Tools::getAdminToken('gm_omniprice');
diff --git a/modules/gm_omniprice/gm_omniprice.php b/modules/gm_omniprice/gm_omniprice.php
index cac7e2bb..7d4257b0 100644
--- a/modules/gm_omniprice/gm_omniprice.php
+++ b/modules/gm_omniprice/gm_omniprice.php
@@ -1,172 +1,165 @@
name = 'gm_omniprice';
- $this->prefix = strtoupper($this->name);
- $this->tab = 'front_office_features';
- $this->version = '1.2.11';
- $this->author = 'GreenMouseStudio.com';
- $this->need_instance = 0;
- $this->bootstrap = true;
-
- parent::__construct();
-
- $this->displayName = $this->l('OmniPrice - Omnibus Directive price compliancy');
- $this->description = $this->l('Displays lowest price before current promotion for discounted products');
-
- $this->ps_versions_compliancy = array('min' => '1.6', 'max' => _PS_VERSION_);
- $this->getConfiguration();
- }
-
- public function getConfiguration()
- {
- $this->ignoredGroups = explode(',', Configuration::get($this->prefix . '_GROUPS'));
- $this->daysBack = Configuration::get($this->prefix . '_DAYS');
- $this->batchSize = Configuration::get($this->prefix . '_BATCH');
- $this->ignoreCountries = Configuration::get($this->prefix . '_IGNORE_COUNTRIES');
- $this->ignoreNonEuCountries = Configuration::get($this->prefix . '_IGNORE_NON_EU');
- $this->ignoreCombinations = Configuration::get($this->prefix . '_IGNORE_COMBINATIONS');
- $this->reindexOnSave = Configuration::get($this->prefix . '_REINDEX');
- $this->textColor = Configuration::get($this->prefix . '_TEXT_COLOR');
- $this->priceColor = Configuration::get($this->prefix . '_PRICE_COLOR');
- $this->backgroundColor = Configuration::get($this->prefix . '_BG_COLOR');
- $this->showIfNotEnoughHistoricalData = Configuration::get($this->prefix . '_SHOW_IF_NO_HISTORY');
- $this->showRealDiscount = Configuration::get($this->prefix . '_SHOW_REAL_DISCOUNT');
- $this->indexInactive = Configuration::get($this->prefix . '_INDEX_INACTIVE');
- $this->skipBelowCost = Configuration::get($this->prefix . '_SKIP_BELOW_COST');
-
- $this->defaultShopId = (int) Configuration::get('PS_SHOP_DEFAULT');
- $this->defaultCountryId = (int) Configuration::get('PS_COUNTRY_DEFAULT');
- $this->defaultGroupId = (int) Configuration::get('PS_CUSTOMER_GROUP');
- $this->defaultCurrencyId = (int) Configuration::get('PS_CURRENCY_DEFAULT');
- $this->today = date('Y-m-d');
- $this->yesterday = date('Y-m-d', strtotime("-1 days"));
- }
-
- public function install()
- {
- if (
- parent::install() && $this->installDb() &&
- $this->registerHook('displayProductPriceBlock') &&
- $this->registerHook('displayAdminProductsExtra') &&
- $this->registerHook('actionProductUpdate') &&
- $this->registerHook('actionObjectSpecificPriceAddAfter') &&
- $this->registerHook('actionObjectSpecificPriceUpdateAfter') &&
- $this->registerHook('actionObjectSpecificPriceDeleteAfter')
- )
+ public function __construct()
{
- Configuration::updateValue($this->prefix . '_DAYS', 30);
- Configuration::updateValue($this->prefix . '_BATCH', 100);
- Configuration::updateValue($this->prefix . '_IGNORE_COUNTRIES', true);
- Configuration::updateValue($this->prefix . '_IGNORE_NON_EU', true);
- Configuration::updateValue($this->prefix . '_REINDEX', true);
- Configuration::updateValue($this->prefix . '_SHOW_IF_NO_HISTORY', false);
- Configuration::updateValue($this->prefix . '_SHOW_REAL_DISCOUNT', false);
- Configuration::updateValue($this->prefix . '_INDEX_INACTIVE', false);
- Configuration::updateValue($this->prefix . '_SKIP_BELOW_COST', false);
- Configuration::updateValue($this->prefix . '_TEXT_COLOR', '#666666');
- Configuration::updateValue($this->prefix . '_PRICE_COLOR', '#666666');
- Configuration::updateValue($this->prefix . '_BG_COLOR', '#FFFFFF');
- if (Tools::version_compare(_PS_VERSION_, '1.7.0.0', '<'))
- {
- $this->registerHook('displayHeader');
- }
- else
- {
- $this->registerHook('actionFrontControllerSetMedia');
- }
- $this->autoConfig();
- return true;
- }
- return false;
- }
+ $this->name = 'gm_omniprice';
+ $this->prefix = strtoupper($this->name);
+ $this->tab = 'front_office_features';
+ $this->version = '1.3.1';
+ $this->author = 'GreenMouseStudio.com';
+ $this->need_instance = 0;
+ $this->bootstrap = true;
- public function autoConfig()
- {
- $combinationsHaveDiscountsOrImpacts = $this->getCombinationsDiscountsInfo() || $this->getCombinationsPriceImpactsInfo();
- Configuration::updateValue($this->prefix . '_IGNORE_COMBINATIONS', !$combinationsHaveDiscountsOrImpacts);
- if (!defined('_TB_VERSION_'))
- { //TB has a nasty bug here
- $groupsToSafelyIgnore = $this->findGroupsToSafelyIgnore();
- Configuration::updateValue($this->prefix . '_GROUPS', implode(',', $groupsToSafelyIgnore));
- }
- }
+ parent::__construct();
- public function installDb()
- {
- return Db::getInstance()->execute('
- CREATE TABLE IF NOT EXISTS `' . _DB_PREFIX_ . 'gm_omniprice_history` (
- `date` DATE NOT NULL,
+ $this->displayName = $this->l('OmniPrice - Omnibus Directive price compliancy');
+ $this->description = $this->l('Displays lowest price before current promotion for discounted products');
+
+ $this->ps_versions_compliancy = array('min' => '1.6', 'max' => _PS_VERSION_);
+ $this->getConfiguration();
+ }
+
+ public function getConfiguration()
+ {
+ $this->ignoredGroups = explode(',', Configuration::get($this->prefix.'_GROUPS'));
+ $this->daysBack = Configuration::get($this->prefix.'_DAYS');
+ $this->batchSize = Configuration::get($this->prefix.'_BATCH');
+ $this->ignoreCountries = Configuration::get($this->prefix.'_IGNORE_COUNTRIES');
+ $this->ignoreNonEuCountries = Configuration::get($this->prefix.'_IGNORE_NON_EU');
+ $this->ignoreCombinations = Configuration::get($this->prefix.'_IGNORE_COMBINATIONS');
+ $this->reindexOnSave = Configuration::get($this->prefix.'_REINDEX');
+ $this->textColor = Configuration::get($this->prefix.'_TEXT_COLOR');
+ $this->priceColor = Configuration::get($this->prefix.'_PRICE_COLOR');
+ $this->backgroundColor = Configuration::get($this->prefix.'_BG_COLOR');
+ $this->showIfNotEnoughHistoricalData = Configuration::get($this->prefix.'_SHOW_IF_NO_HISTORY');
+ $this->showRealDiscount = Configuration::get($this->prefix.'_SHOW_REAL_DISCOUNT');
+ $this->indexInactive = Configuration::get($this->prefix.'_INDEX_INACTIVE');
+ $this->skipBelowCost = Configuration::get($this->prefix.'_SKIP_BELOW_COST');
+
+ $this->defaultShopId = (int) Configuration::get('PS_SHOP_DEFAULT');
+ $this->defaultCountryId = (int) Configuration::get('PS_COUNTRY_DEFAULT');
+ $this->defaultGroupId = (int) Configuration::get('PS_CUSTOMER_GROUP');
+ $this->defaultCurrencyId = (int) Configuration::get('PS_CURRENCY_DEFAULT');
+ $this->today = date('Y-m-d');
+ $this->yesterday = date('Y-m-d', strtotime("-1 days"));
+ $this->token = $this->getTokenForScripts();
+ }
+
+ public function install()
+ {
+ if (parent::install() && $this->installDb() &&
+ $this->registerHook('displayProductPriceBlock') &&
+ $this->registerHook('displayAdminProductsExtra') &&
+ $this->registerHook('actionProductUpdate') &&
+ $this->registerHook('actionObjectSpecificPriceAddAfter') &&
+ $this->registerHook('actionObjectSpecificPriceUpdateAfter') &&
+ $this->registerHook('actionObjectSpecificPriceDeleteAfter')
+ ) {
+ Configuration::updateValue($this->prefix.'_DAYS', 30);
+ Configuration::updateValue($this->prefix.'_BATCH', 100);
+ Configuration::updateValue($this->prefix.'_IGNORE_COUNTRIES', true);
+ Configuration::updateValue($this->prefix.'_IGNORE_NON_EU', true);
+ Configuration::updateValue($this->prefix.'_REINDEX', true);
+ Configuration::updateValue($this->prefix.'_SHOW_IF_NO_HISTORY', false);
+ Configuration::updateValue($this->prefix.'_SHOW_REAL_DISCOUNT', false);
+ Configuration::updateValue($this->prefix.'_INDEX_INACTIVE', false);
+ Configuration::updateValue($this->prefix.'_SKIP_BELOW_COST', false);
+ Configuration::updateValue($this->prefix.'_TEXT_COLOR', '#666666');
+ Configuration::updateValue($this->prefix.'_PRICE_COLOR', '#666666');
+ Configuration::updateValue($this->prefix.'_BG_COLOR', '#FFFFFF');
+ if (Tools::version_compare(_PS_VERSION_, '1.7.0.0', '<')) {
+ $this->registerHook('displayHeader');
+ } else {
+ $this->registerHook('actionFrontControllerSetMedia');
+ }
+ $this->autoConfig();
+ return true;
+ }
+ return false;
+ }
+
+ public function autoConfig()
+ {
+ $combinationsHaveDiscountsOrImpacts = $this->getCombinationsDiscountsInfo() || $this->getCombinationsPriceImpactsInfo();
+ Configuration::updateValue($this->prefix.'_IGNORE_COMBINATIONS', !$combinationsHaveDiscountsOrImpacts);
+ if (!defined('_TB_VERSION_')) { //TB has a nasty bug here
+ $groupsToSafelyIgnore = $this->findGroupsToSafelyIgnore();
+ Configuration::updateValue($this->prefix.'_GROUPS', implode(',', $groupsToSafelyIgnore));
+ }
+ }
+
+ public function installDb()
+ {
+ return Db::getInstance()->execute('
+ CREATE TABLE IF NOT EXISTS `'._DB_PREFIX_.'gm_omniprice_history` (
+ `date` DATE NOT NULL,
`id_shop` INT(10) UNSIGNED NOT NULL,
`id_product` INT(10) UNSIGNED NOT NULL,
`id_product_attribute` INT(10) UNSIGNED NOT NULL,
@@ -177,10 +170,11 @@ class Gm_OmniPrice extends Module
`price_tin` DECIMAL(20,6),
`is_specific_price` TINYINT(1),
INDEX (`date`, `id_shop`, `id_product`),
- INDEX (`date`, `id_product`)
- ) ENGINE = ' . _MYSQL_ENGINE_ . ' DEFAULT CHARSET=UTF8;') &&
- Db::getInstance()->execute('
- CREATE TABLE IF NOT EXISTS `' . _DB_PREFIX_ . 'gm_omniprice_cache` (
+ INDEX (`date`, `id_product`),
+ INDEX (`id_shop`, `id_product`, `id_currency`, `id_country`, `id_group`, `id_product_attribute`, `date`)
+ ) ENGINE = '._MYSQL_ENGINE_.' DEFAULT CHARSET=UTF8;') &&
+ Db::getInstance()->execute('
+ CREATE TABLE IF NOT EXISTS `'._DB_PREFIX_.'gm_omniprice_cache` (
`id_shop` INT(10) UNSIGNED NOT NULL,
`id_product` INT(10) UNSIGNED NOT NULL,
`id_product_attribute` INT(10) UNSIGNED NOT NULL,
@@ -189,2350 +183,1920 @@ class Gm_OmniPrice extends Module
`id_group` INT(10) UNSIGNED NOT NULL,
`price_tex` DECIMAL(20,6),
`price_tin` DECIMAL(20,6),
- `date` DATE NOT NULL,
+ `date` DATE NOT NULL,
INDEX (`id_shop`, `id_product`, `id_product_attribute`, `id_currency`, `id_country`, `id_group`, `date`)
- ) ENGINE = ' . _MYSQL_ENGINE_ . ' DEFAULT CHARSET=UTF8;') &&
- Db::getInstance()->execute('
- CREATE TABLE IF NOT EXISTS `' . _DB_PREFIX_ . 'gm_omniprice_index` (
- `date` DATE NOT NULL,
+ ) ENGINE = '._MYSQL_ENGINE_.' DEFAULT CHARSET=UTF8;') &&
+ Db::getInstance()->execute('
+ CREATE TABLE IF NOT EXISTS `'._DB_PREFIX_.'gm_omniprice_index` (
+ `date` DATE NOT NULL,
`id_shop` INT(10) UNSIGNED NOT NULL,
`id_product` INT(10) UNSIGNED NOT NULL,
INDEX (`date`, `id_shop`)
- ) ENGINE = ' . _MYSQL_ENGINE_ . ' DEFAULT CHARSET=UTF8;');
- }
-
- public function uninstall()
- {
- if (!parent::uninstall())
- {
- return false;
+ ) ENGINE = '._MYSQL_ENGINE_.' DEFAULT CHARSET=UTF8;');
}
- if (
- !$this->uninstallDB() ||
- !Configuration::deleteByName($this->prefix . '_GROUPS') ||
- !Configuration::deleteByName($this->prefix . '_DAYS') ||
- !Configuration::deleteByName($this->prefix . '_BATCH') ||
- !Configuration::deleteByName($this->prefix . '_BG_COLOR') ||
- !Configuration::deleteByName($this->prefix . '_TEXT_COLOR') ||
- !Configuration::deleteByName($this->prefix . '_PRICE_COLOR') ||
- !Configuration::deleteByName($this->prefix . '_IGNORE_COUNTRIES') ||
- !Configuration::deleteByName($this->prefix . '_IGNORE_NON_EU') ||
- !Configuration::deleteByName($this->prefix . '_IGNORE_COMBINATIONS') ||
- !Configuration::deleteByName($this->prefix . '_TEXT_COLOR') ||
- !Configuration::deleteByName($this->prefix . '_PRICE_COLOR') ||
- !Configuration::deleteByName($this->prefix . '_BG_COLOR') ||
- !Configuration::deleteByName($this->prefix . '_SHOW_IF_NO_HISTORY') ||
- !Configuration::deleteByName($this->prefix . '_SHOW_REAL_DISCOUNT') ||
- !Configuration::deleteByName($this->prefix . '_INDEX_INACTIVE') ||
- !Configuration::deleteByName($this->prefix . '_REINDEX')
- )
+ public function uninstall()
{
- return false;
- }
- return true;
- }
-
- protected function uninstallDb()
- {
- $res = Db::getInstance()->execute('DROP TABLE IF EXISTS `' . _DB_PREFIX_ . 'gm_omniprice_history`');
- $res &= Db::getInstance()->execute('DROP TABLE IF EXISTS `' . _DB_PREFIX_ . 'gm_omniprice_cache`');
- $res &= Db::getInstance()->execute('DROP TABLE IF EXISTS `' . _DB_PREFIX_ . 'gm_omniprice_index`');
- return $res;
- }
-
- public function getContent()
- {
- $content = '';
- $content .= $this->postProcess();
- $content .= $this->displayGreenMouseModulesPanel();
- $content .= $this->displayForm();
- $content .= $this->displayInfo();
- $content .= $this->displayInformationPanel();
- return $content;
- }
-
- protected function postProcess()
- {
- $output = '';
- if (Tools::isSubmit('submit' . $this->name))
- {
- $this->ignoredGroups = Tools::getValue('groupBox');
- if (!is_array($this->ignoredGroups))
- {
- $this->ignoredGroups = [];
- }
- $groupsString = implode(',', $this->ignoredGroups);
- Configuration::updateValue($this->prefix . '_GROUPS', $groupsString);
-
- $this->daysBack = Tools::getValue($this->prefix . '_DAYS');
- Configuration::updateValue($this->prefix . '_DAYS', $this->daysBack);
-
- $this->batchSize = Tools::getValue($this->prefix . '_BATCH');
- Configuration::updateValue($this->prefix . '_BATCH', $this->batchSize);
-
- $this->ignoreCountries = Tools::getValue($this->prefix . '_IGNORE_COUNTRIES');
- Configuration::updateValue($this->prefix . '_IGNORE_COUNTRIES', $this->ignoreCountries);
-
- $this->ignoreNonEuCountries = Tools::getValue($this->prefix . '_IGNORE_NON_EU');
- Configuration::updateValue($this->prefix . '_IGNORE_NON_EU', $this->ignoreNonEuCountries);
-
- $this->ignoreCombinations = Tools::getValue($this->prefix . '_IGNORE_COMBINATIONS');
- Configuration::updateValue($this->prefix . '_IGNORE_COMBINATIONS', $this->ignoreCombinations);
-
- $this->reindexOnSave = Tools::getValue($this->prefix . '_REINDEX');
- Configuration::updateValue($this->prefix . '_REINDEX', $this->reindexOnSave);
-
- $this->textColor = Tools::getValue($this->prefix . '_TEXT_COLOR');
- Configuration::updateValue($this->prefix . '_TEXT_COLOR', $this->textColor);
-
- $this->priceColor = Tools::getValue($this->prefix . '_PRICE_COLOR');
- Configuration::updateValue($this->prefix . '_PRICE_COLOR', $this->priceColor);
-
- $this->backgroundColor = Tools::getValue($this->prefix . '_BG_COLOR');
- Configuration::updateValue($this->prefix . '_BG_COLOR', $this->backgroundColor);
-
- $this->showIfNotEnoughHistoricalData = Tools::getValue($this->prefix . '_SHOW_IF_NO_HISTORY');
- Configuration::updateValue($this->prefix . '_SHOW_IF_NO_HISTORY', $this->showIfNotEnoughHistoricalData);
-
- $this->showRealDiscount = Tools::getValue($this->prefix . '_SHOW_REAL_DISCOUNT');
- Configuration::updateValue($this->prefix . '_SHOW_REAL_DISCOUNT', $this->showRealDiscount);
-
- $this->indexInactive = Tools::getValue($this->prefix . '_INDEX_INACTIVE');
- Configuration::updateValue($this->prefix . '_INDEX_INACTIVE', $this->indexInactive);
-
- $this->skipBelowCost = Tools::getValue($this->prefix . '_SKIP_BELOW_COST');
- Configuration::updateValue($this->prefix . '_SKIP_BELOW_COST', $this->skipBelowCost);
-
- $output .= $this->displayConfirmation($this->l('Settings updated'));
- }
- return $output;
- }
-
- public function displayForm()
- {
- $helper = new HelperForm();
- $groups = Group::getGroups($this->context->language->id);
- $inputs = array(
- array(
- 'type' => 'text',
- 'label' => $this->l('Period'),
- 'desc' => $this->l('Number of days before promotion start to analyze'),
- 'name' => $this->prefix . '_DAYS',
- 'class' => 'fixed-width-md',
- ),
- array(
- 'type' => 'switch',
- 'label' => $this->l('Ignore countries'),
- 'name' => $this->prefix . '_IGNORE_COUNTRIES',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- 'hint' => $this->l('Analyze prices only for the default country, customers from other countries will see prices of the default country'),
- 'desc' => $this->l('Analyze prices only for the default country, customers from other countries will see prices of the default country')
- ),
- array(
- 'type' => 'switch',
- 'label' => $this->l('Ignore non EU countries'),
- 'name' => $this->prefix . '_IGNORE_NON_EU',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- 'hint' => $this->l('Skip non EU countries totally, customers from non EU countries will not see any message about previous price'),
- 'desc' => $this->l('Skip non EU countries totally, customers from non EU countries will not see any message about previous price')
- ),
- array(
- 'type' => 'switch',
- 'label' => $this->l('Ignore combinations'),
- 'name' => $this->prefix . '_IGNORE_COMBINATIONS',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- 'hint' => $this->l('Analyze prices only for the default combination, recommended if combinations don\'t have price impacts'),
- 'desc' => $this->l('Analyze prices only for the default combination, recommended if combinations don\'t have price impacts')
- ),
- array(
- 'type' => 'group',
- 'label' => $this->l('Ignored groups'),
- 'name' => 'groupBox',
- 'values' => $groups,
- 'hint' => $this->l('Ignore selected groups, customers from ignored groups will see prices for the default group (Customer), recommended if no group discounts in use'),
- 'desc' => $this->l('Ignore selected groups, customers from ignored groups will see prices for the default group (Customer), recommended if no group discounts in use')
- ),
- array(
- 'type' => 'text',
- 'label' => $this->l('Batch size'),
- 'desc' => $this->l('Number of products to process in a single CRON task run'),
- 'name' => $this->prefix . '_BATCH',
- 'class' => 'fixed-width-md',
- ),
- array(
- 'type' => 'switch',
- 'label' => $this->l('Reindex on product save'),
- 'name' => $this->prefix . '_REINDEX',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- 'hint' => $this->l('Reindex product on save'),
- 'desc' => $this->l('Reindex product on save')
- ),
- array(
- 'type' => 'color',
- 'label' => $this->l('Background color'),
- 'name' => $this->prefix . '_BG_COLOR',
- ),
- array(
- 'type' => 'color',
- 'label' => $this->l('Text color'),
- 'name' => $this->prefix . '_TEXT_COLOR',
- ),
- array(
- 'type' => 'color',
- 'label' => $this->l('Price color'),
- 'name' => $this->prefix . '_PRICE_COLOR',
- ),
- array(
- 'type' => 'switch',
- 'label' => $this->l('Show label even if not enough history'),
- 'name' => $this->prefix . '_SHOW_IF_NO_HISTORY',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- 'hint' => $this->l('For discounted products, if previous price is unknown, shows the current discounted price as the lowest one'),
- 'desc' => $this->l('For discounted products, if previous price is unknown, shows the current discounted price as the lowest one')
- ),
- array(
- 'type' => 'switch',
- 'label' => $this->l('Index inactive products'),
- 'name' => $this->prefix . '_INDEX_INACTIVE',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- 'hint' => $this->l('Store price history even if the product is not active'),
- 'desc' => $this->l('Store price history even if the product is not active'),
- ),
- );
- if (Tools::version_compare(_PS_VERSION_, '1.7.0.0', '>='))
- {
- $inputs[] = array(
- 'type' => 'switch',
- 'label' => $this->l('Show real discount from the previous price'),
- 'name' => $this->prefix . '_SHOW_REAL_DISCOUNT',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- 'hint' => $this->l('Display price change percentage after the lowest previous price'),
- 'desc' => $this->l('Display price change percentage after the lowest previous price')
- );
- }
- $inputs[] = array(
- 'type' => 'switch',
- 'label' => $this->l('Skip products sold below cost price'),
- 'name' => $this->prefix . '_SKIP_BELOW_COST',
- 'values' => array(
- array(
- 'id' => 'active_on',
- 'value' => 1,
- 'label' => $this->l('Yes')
- ),
- array(
- 'id' => 'active_off',
- 'value' => 0,
- 'label' => $this->l('No')
- )
- ),
- );
- $fieldsForm = array(
- 'form' => array(
- 'legend' => array(
- 'title' => $this->l('Settings'),
- 'icon' => 'icon-cogs'
- ),
- 'input' => $inputs,
- 'submit' => array(
- 'title' => $this->l('Save')
- )
- ),
- );
-
- $helper->show_toolbar = true;
- $helper->toolbar_scroll = true;
- $helper->table = $this->table;
- $helper->default_form_language = (int) Configuration::get('PS_LANG_DEFAULT');
- $helper->module = $this;
- $helper->allow_employee_form_lang = Configuration::get('PS_BO_ALLOW_EMPLOYEE_FORM_LANG') ? Configuration::get('PS_BO_ALLOW_EMPLOYEE_FORM_LANG') : 0;
- $helper->identifier = $this->identifier;
- $helper->submit_action = 'submit' . $this->name;
- $helper->currentIndex = $this->context->link->getAdminLink('AdminModules', false) . '&configure=' . $this->name . '&tab_module=' . $this->tab . '&module_name=' . $this->name;
- $helper->token = Tools::getAdminTokenLite('AdminModules');
- foreach ($groups as $group)
- {
- $helper->fields_value['groupBox_' . $group['id_group']] = in_array($group['id_group'], $this->ignoredGroups);
- }
- $helper->fields_value[$this->prefix . '_DAYS'] = $this->daysBack;
- $helper->fields_value[$this->prefix . '_BATCH'] = $this->batchSize;
- $helper->fields_value[$this->prefix . '_IGNORE_COUNTRIES'] = $this->ignoreCountries;
- $helper->fields_value[$this->prefix . '_IGNORE_NON_EU'] = $this->ignoreNonEuCountries;
- $helper->fields_value[$this->prefix . '_IGNORE_COMBINATIONS'] = $this->ignoreCombinations;
- $helper->fields_value[$this->prefix . '_REINDEX'] = $this->reindexOnSave;
- $helper->fields_value[$this->prefix . '_TEXT_COLOR'] = $this->textColor;
- $helper->fields_value[$this->prefix . '_PRICE_COLOR'] = $this->priceColor;
- $helper->fields_value[$this->prefix . '_BG_COLOR'] = $this->backgroundColor;
- $helper->fields_value[$this->prefix . '_SHOW_REAL_DISCOUNT'] = $this->showRealDiscount;
- $helper->fields_value[$this->prefix . '_INDEX_INACTIVE'] = $this->indexInactive;
- $helper->fields_value[$this->prefix . '_SKIP_BELOW_COST'] = $this->skipBelowCost;
- $helper->fields_value[$this->prefix . '_SHOW_IF_NO_HISTORY'] = $this->showIfNotEnoughHistoricalData;
-
- return $helper->generateForm(array($fieldsForm));
- }
-
- public function savePrices($verbose = false, $productId = null)
- {
- $this->clearIndex($this->yesterday);
- $output = '';
- $usetax = true;
- if (Tax::excludeTaxeOption())
- {
- $usetax = false;
- }
- $basicPrices = [];
- $stateId = 0;
- $zipcode = '';
-
- $output .= $this->today . '
';
- $output .= $this->l('Batch size') . ': ' . $this->batchSize . '
';
- $output .= $this->l('Default country ID:') . ' ' . $this->defaultCountryId . '
';
- $output .= $this->l('Default group ID:') . ' ' . $this->defaultGroupId . '
';
-
- $shopIds = $this->getShopsIds();
- $useReduction = true;
- if (Tools::isSubmit('init'))
- {
- $useReduction = false;
- }
- if ($this->skipBelowCost)
- {
- $rates = $this->getConversionRates();
- $costPriceMap = $this->getCostPriceMap();
- }
- $specificPriceOutput = null;
- foreach ($shopIds as $shopId)
- {
- $currencyIds = $this->getCurrencyIds($shopId);
- $countryIds = $this->getCountryIds($shopId);
- $groupIds = $this->getGroupIds($shopId);
- $lastCurrencyId = end($currencyIds);
- $lastCountryId = end($countryIds);
- $lastGroupId = end($groupIds);
- $attributesMap = $this->getProductAttributeMap($shopId);
- if (!$productId)
- {
- $productIds = $this->getProductIds($shopId);
- }
- else
- {
- if (!$this->indexInactive && !$this->productIsActive($productId, $shopId))
- {
- continue;
- }
- $productIds = [$productId];
- }
- $output .= '
' . $this->l('Shop ID:') . ' ' . $shopId . ' ';
- if (count($productIds) < 1)
- {
- $output .= '
' . $this->l('All products indexed') . '
';
- continue;
- }
- else
- {
- $output .= '
' . $this->l('Not finished yet, please run me again') . '
';
- }
- $output .= '
'
- . ' '
- . '' . $this->l('Product ID') . ' '
- . '' . $this->l('Attribute ID') . ' '
- . '' . $this->l('Country ID') . ' '
- . '' . $this->l('Currency ID') . ' '
- . '' . $this->l('Group ID') . ' '
- . '' . $this->l('Price') . ' '
- . '' . $this->l('Previous price') . ' '
- . '' . $this->l('Is discounted') . ' '
- . '' . $this->l('Action') . ' '
- . '' . $this->l('Lowest price') . ' '
- . ' ';
- $counter = 0;
- foreach ($currencyIds as $currencyId)
- {
- foreach ($countryIds as $countryId)
- {
- foreach ($groupIds as $groupId)
- {
- $discountedIds = $this->getDiscountedProductIds($shopId, $currencyId, $countryId, $groupId);
- foreach ($productIds as $productId)
- {
- $attributeId = 0;
- $basicKey = $shopId . '-' . $productId . '-' . $attributeId . '-' . $currencyId . '-' . $countryId . '-' . $groupId;
- $priceTin = Product::priceCalculation(
- $shopId,
- $productId,
- $attributeId,
- $countryId,
- $stateId,
- $zipcode,
- $currencyId,
- $groupId,
- 1, //quantity
- $usetax,
- 6, //decimals
- false, //only_reduc
- $useReduction, //use_reduc
- true, //with_ecotax
- $specificPriceOutput,
- true //use_group_reduction
- );
- $priceTin = sprintf("%.6f", $priceTin);
- $basicPrices[$basicKey] = $priceTin;
- $priceTex = $priceTin;
- if ($usetax)
- {
- $priceTex = Product::priceCalculation(
- $shopId,
- $productId,
- $attributeId,
- $countryId,
- $stateId,
- $zipcode,
- $currencyId,
- $groupId,
- 1, //quantity
- false, //no tax
- 6, //decimals
- false, //only_reduc
- $useReduction, //use_reduc
- true, //with_ecotax
- $specificPriceOutput,
- true //use_group_reduction
- );
- }
- $previously = $this->getPreviousPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- if ($previously)
- {
- $previousPrice = (float) $previously['price_tin'];
- $previousDiscount = (bool) $previously['is_specific_price'];
- }
- else
- {
- $previousPrice = 0;
- $previousDiscount = false;
- }
- if (Tools::isSubmit('init'))
- {
- $onDiscount = false;
- }
- else
- {
- if (Module::isEnabled('groupinc'))
- {
- $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId) || (is_array($specificPriceOutput) && (count($specificPriceOutput) > 1)); //groupinc module support
- }
- else
- {
- $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId);
- }
- }
- $onDiscountText = ($onDiscount ? $this->l('Yes') : $this->l('No'));
- //check if product is sold below cost price
- if ($this->skipBelowCost)
- {
- if ($this->checkIfProductIsSoldBelowCost(
- $priceTex,
- $costPriceMap,
- $rates,
- $shopId,
- $productId,
- $attributeId,
- $currencyId
- ))
- {
- $onDiscount = false;
- $onDiscountText = $this->l('Below cost');
- }
- }
- $output .= ''
- . '' . ++$counter . ' '
- . '' . $productId . ' '
- . '' . $attributeId . ' '
- . '' . $countryId . ' '
- . '' . $currencyId . ' '
- . '' . $groupId . ' '
- . '' . $priceTin . ' (' . $priceTex . ') '
- . '' . $previousPrice . ' '
- . '' . $onDiscountText . ' ';
- $priceIsCorrect = ($priceTin > 0);
- $priceChanged = (abs($previousPrice - $priceTin) > 0.01);
- $discountChanged = ($previousDiscount != $onDiscount);
- if (Tools::isSubmit('cache'))
- {
- $discountChanged = true;
- }
- if ($priceIsCorrect && ($priceChanged || $discountChanged))
- {
- $output .= '' . $this->l('Save') . ' ';
- $this->savePrice(
- $this->today,
- $shopId,
- $productId,
- $currencyId,
- $countryId,
- $groupId,
- $attributeId,
- $priceTex,
- $priceTin,
- $onDiscount
- );
- //calculate lowest price and add it to the cache
- if ($onDiscount)
- {
- $lowestPrices = $this->getLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- if ($lowestPrices)
- {
- $output .= '' . $lowestPrices['price_tin'] . ' (' . $lowestPrices['price_tex'] . ') ';
- $this->saveLowestPrice(
- $shopId,
- $productId,
- $currencyId,
- $countryId,
- $groupId,
- $attributeId,
- $lowestPrices['price_tex'],
- $lowestPrices['price_tin'],
- $lowestPrices['date']
- );
- }
- else
- {
- $output .= '' . $this->l('Unknown') . ' ';
- }
- }
- else
- {
- $output .= '' . $this->l('Not applicable') . ' ';
- }
- }
- else
- {
- $output .= '' . $this->l('No change') . ' ';
- $output .= '' . $this->l('No change') . ' ';
- }
- if (!$onDiscount)
- {
- $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- }
- $output .= ' ';
- //attributes
- if (array_key_exists($productId, $attributesMap))
- {
- foreach ($attributesMap[$productId] as $attributeId)
- {
- $priceTin = Product::priceCalculation(
- $shopId,
- $productId,
- $attributeId,
- $countryId,
- $stateId,
- $zipcode,
- $currencyId,
- $groupId,
- 1, //quantity
- $usetax,
- 6, //decimals
- false, //only_reduc
- $useReduction, //use_reduc
- true, //with_ecotax
- $specificPriceOutput,
- true //use_group_reduction
- );
- $priceTin = sprintf("%.6f", $priceTin);
- $priceTex = $priceTin;
- if ($usetax)
- {
- $priceTex = Product::priceCalculation(
- $shopId,
- $productId,
- $attributeId,
- $countryId,
- $stateId,
- $zipcode,
- $currencyId,
- $groupId,
- 1, //quantity
- false, //no tax
- 6, //decimals
- false, //only_reduc
- $useReduction, //use_reduc
- true, //with_ecotax
- $specificPriceOutput,
- true //use_group_reduction
- );
- }
- if (abs($priceTin - $basicPrices[$basicKey]) > 0.01)
- {
- $previously = $this->getPreviousPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- if ($previously)
- {
- $previousPrice = (float) $previously['price_tin'];
- $previousDiscount = (bool) $previously['is_specific_price'];
- }
- else
- {
- $previousPrice = 0;
- $previousDiscount = false;
- }
- if (Tools::isSubmit('init'))
- {
- $onDiscount = false;
- }
- else
- {
- if (Module::isEnabled('groupinc'))
- {
- $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId) || (is_array($specificPriceOutput) && (count($specificPriceOutput) > 1)); //groupinc module support
- }
- else
- {
- $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId);
- }
- }
- $onDiscountText = ($onDiscount ? $this->l('Yes') : $this->l('No'));
- if ($this->skipBelowCost)
- {
- if ($this->checkIfProductIsSoldBelowCost(
- $priceTex,
- $costPriceMap,
- $rates,
- $shopId,
- $productId,
- $attributeId,
- $currencyId
- ))
- {
- $onDiscount = false;
- $onDiscountText = $this->l('Below cost');
- }
- }
- $output .= ''
- . '' . ++$counter . ' '
- . '' . $productId . ' '
- . '' . $attributeId . ' '
- . '' . $countryId . ' '
- . '' . $currencyId . ' '
- . '' . $groupId . ' '
- . '' . $priceTin . ' (' . $priceTex . ') '
- . '' . $previousPrice . ' '
- . '' . $onDiscountText . ' ';
- $priceIsCorrect = ($priceTin > 0);
- $priceChanged = (abs($previousPrice - $priceTin) > 0.01);
- $discountChanged = ($previousDiscount != $onDiscount);
- if (Tools::isSubmit('cache'))
- {
- $discountChanged = true;
- }
- if ($priceIsCorrect && ($priceChanged || $discountChanged))
- {
- $output .= '' . $this->l('Save') . ' ';
- $this->savePrice(
- $this->today,
- $shopId,
- $productId,
- $currencyId,
- $countryId,
- $groupId,
- $attributeId,
- $priceTex,
- $priceTin,
- $onDiscount
- );
- if ($onDiscount)
- {
- $lowestPrices = $this->getLowestPrice(
- $shopId,
- $productId,
- $currencyId,
- $countryId,
- $groupId,
- $attributeId
- );
- if ($lowestPrices)
- {
- $output .= '' . $lowestPrices['price_tin'] . ' (' . $lowestPrices['price_tex'] . ') ';
- $this->saveLowestPrice(
- $shopId,
- $productId,
- $currencyId,
- $countryId,
- $groupId,
- $attributeId,
- $lowestPrices['price_tex'],
- $lowestPrices['price_tin'],
- $lowestPrices['date']
- );
- }
- else
- {
- $output .= '' . $this->l('Unknown') . ' ';
- }
- }
- else
- {
- $output .= '' . $this->l('Not applicable') . ' ';
- }
- }
- else
- {
- $output .= '' . $this->l('No change') . ' ';
- $output .= '' . $this->l('No change') . ' ';
- }
- if (!$onDiscount)
- {
- $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- }
- }
- else
- {
- //skip analyzing attribute if price is the same as basic
- //delete if the attribute is not on discount
- $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId);
- if (!$onDiscount)
- {
- $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- }
- }
- }
- }
- if ($currencyId == $lastCurrencyId && $groupId == $lastGroupId && $countryId == $lastCountryId)
- {
- $this->addProductToIndex($shopId, $productId, $this->today);
- }
- }
- }
- }
- }
- $output .= '
';
- }
- if ($verbose)
- {
- echo $output;
- }
- return true;
- }
-
- public function getLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $daysOffset = 0)
- {
- $lowestPriceTin = INF;
- $lowestPriceTex = INF;
- $lowestDate = '0000-00-00';
- for ($d = 1; $d <= $this->daysBack; $d++)
- {
- $days = $d + $daysOffset;
- $date = date('Y-m-d', strtotime("-$days days"));
- $row = Db::getInstance()->getRow(
- 'SELECT `price_tin`, `price_tex` '
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_history` '
- . ' WHERE `id_shop` = ' . $shopId
- . ' AND `id_product` = ' . $productId
- . ' AND `id_product_attribute` = ' . $attributeId
- . ' AND `id_currency` = ' . $currencyId
- . ' AND `id_group` = ' . $groupId
- . ' AND `id_country` = ' . $countryId
- . ' AND `date` <= \'' . $date . '\''
- . ' ORDER BY `date` DESC'
- );
- if ($attributeId != 0 && $row == false)
- {
- $attributeId = 0;
- $row = Db::getInstance()->getRow(
- 'SELECT `price_tin`, `price_tex` '
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_history` '
- . ' WHERE `id_shop` = ' . $shopId
- . ' AND `id_product` = ' . $productId
- . ' AND `id_product_attribute` = ' . $attributeId
- . ' AND `id_currency` = ' . $currencyId
- . ' AND `id_group` = ' . $groupId
- . ' AND `id_country` = ' . $countryId
- . ' AND `date` <= \'' . $date . '\''
- . ' ORDER BY `date` DESC'
- );
- }
- if ($row)
- {
- $priceTin = $row['price_tin'];
- if ($priceTin < $lowestPriceTin)
- {
- $lowestPriceTin = $priceTin;
- }
- $priceTex = $row['price_tex'];
- if ($priceTex < $lowestPriceTex)
- {
- $lowestPriceTex = $priceTex;
- $lowestDate = $date;
- }
- }
- else
- {
- break;
- }
- }
- if ($lowestPriceTex < INF)
- {
- return [
- 'price_tin' => $lowestPriceTin,
- 'price_tex' => $lowestPriceTex,
- 'date' => $lowestDate
- ];
- }
- else
- {
- return false;
- }
- }
-
- public function checkIfProductIsDiscounted($discountedIds, $productId, $attributeId)
- {
- if (Tools::isSubmit('init'))
- {
- return false;
- }
- foreach ($discountedIds as $item)
- {
- if (($item['id_product'] == $productId) && ($item['id_product_attribute'] == $attributeId))
- {
- return true;
- }
- if (($item['id_product'] == $productId) && ($item['id_product_attribute'] == 0))
- {
- return true;
- }
- }
- return false;
- }
-
- public function clearIndex($date)
- {
- return Db::getInstance()->delete('gm_omniprice_index', '`date` <= \'' . $date . '\'');
- }
-
- public function addProductToIndex($shopId, $productId, $date)
- {
- Db::getInstance()->insert(
- 'gm_omniprice_index',
- [
- 'date' => $date,
- 'id_shop' => $shopId,
- 'id_product' => $productId
- ]
- );
- }
-
- public function getPreviousPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId)
- {
- return Db::getInstance()->getRow('SELECT `price_tin`, `is_specific_price` FROM `' . _DB_PREFIX_ . 'gm_omniprice_history`'
- . ' WHERE `id_shop` = ' . $shopId . ' AND `id_product` = ' . $productId
- . ' AND `id_currency` = ' . $currencyId . ' AND `id_country` = ' . $countryId
- . ' AND `id_group` = ' . $groupId . ' AND `id_product_attribute` = ' . $attributeId
- . ' AND `date` < \'' . $this->today . '\''
- . ' ORDER BY `date` DESC');
- }
-
- public function saveLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $priceTex, $priceTin, $date)
- {
- $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- return Db::getInstance()->insert(
- 'gm_omniprice_cache',
- [
- 'id_shop' => $shopId,
- 'id_product' => $productId,
- 'id_currency' => $currencyId,
- 'id_country' => $countryId,
- 'id_group' => $groupId,
- 'id_product_attribute' => $attributeId,
- 'price_tex' => $priceTex,
- 'price_tin' => $priceTin,
- 'date' => $date
- ]
- );
- }
-
- public function deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId)
- {
- return Db::getInstance()->delete(
- 'gm_omniprice_cache',
- '`id_shop` = ' . $shopId
- . ' AND `id_product` = ' . $productId
- . ' AND `id_currency` = ' . $currencyId
- . ' AND `id_country` = ' . $countryId
- . ' AND `id_group` = ' . $groupId
- . ' AND `id_product_attribute` = ' . $attributeId
- );
- }
-
- public function savePrice($date, $shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $priceTex, $priceTin, $onDiscount = false)
- {
- if (Tools::isSubmit('cache'))
- {
- $this->deleteTodaysPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
- }
- Db::getInstance()->insert(
- 'gm_omniprice_history',
- [
- 'date' => $date,
- 'id_shop' => $shopId,
- 'id_product' => $productId,
- 'id_currency' => $currencyId,
- 'id_country' => $countryId,
- 'id_group' => $groupId,
- 'id_product_attribute' => $attributeId,
- 'price_tex' => $priceTex,
- 'price_tin' => $priceTin,
- 'is_specific_price' => $onDiscount
- ]
- );
- }
-
- public function deleteTodaysPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId)
- {
- return Db::getInstance()->delete(
- 'gm_omniprice_history',
- '`id_shop` = ' . $shopId
- . ' AND `id_product` = ' . $productId
- . ' AND `id_currency` = ' . $currencyId
- . ' AND `id_country` = ' . $countryId
- . ' AND `id_group` = ' . $groupId
- . ' AND `id_product_attribute` = ' . $attributeId
- . ' AND `date` = \'' . $this->today . '\''
- );
- }
-
- public function getGroupIds($shopId)
- {
- $ids = [$this->defaultGroupId];
- if (!Group::isFeatureActive())
- {
- return $ids;
- }
- $query = 'SELECT `gs`.`id_group`
- FROM `' . _DB_PREFIX_ . 'group_shop` `gs`
- WHERE `gs`.`id_shop` = ' . $shopId;
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- if (($row['id_group'] != $this->defaultGroupId) && !in_array($row['id_group'], $this->ignoredGroups))
- {
- $ids[] = (int) $row['id_group'];
- }
- }
- }
- return $ids;
- }
-
- public function getCountryIds($shopId)
- {
- $ids = [$this->defaultCountryId];
- if (Shop::isFeatureActive())
- {
- $ids = [Configuration::get('PS_COUNTRY_DEFAULT', null, null, $shopId)];
- }
- if (!$this->ignoreCountries)
- {
- $query = 'SELECT `cs`.`id_country`
- FROM `' . _DB_PREFIX_ . 'country_shop` `cs`
- LEFT JOIN `' . _DB_PREFIX_ . 'country` `c` ON (`cs`.`id_country` = `c`.`id_country`)
- WHERE `cs`.`id_shop` = ' . $shopId
- . ' AND `c`.`active` = 1';
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- if (!in_array($row['id_country'], $ids))
- {
- if ($this->ignoreNonEuCountries)
- {
- $country = new Country($row['id_country']);
- if (in_array($country->iso_code, $this->euCountries))
- {
- $ids[] = (int) $row['id_country'];
- }
- }
- else
- {
- $ids[] = (int) $row['id_country'];
- }
- }
- }
- }
- }
- return $ids;
- }
-
- public function getCurrencyIds($shopId)
- {
- $ids = [];
- $query = 'SELECT `cs`.`id_currency`
- FROM `' . _DB_PREFIX_ . 'currency` c
- LEFT JOIN `' . _DB_PREFIX_ . 'currency_shop` cs ON (cs.`id_currency` = c.`id_currency`)
- WHERE cs.`id_shop` = ' . (int) $shopId
- . ' AND c.`active` = 1';
- $currencies = Db::getInstance()->executeS($query);
- foreach ($currencies as $currency)
- {
- $ids[] = (int) $currency['id_currency'];
- }
- return $ids;
- }
-
- public function getProductIds($shopId)
- {
- $productIds = [];
- $query = 'SELECT `ps`.`id_product` '
- . ' FROM `' . _DB_PREFIX_ . 'product_shop` `ps`'
- . ' WHERE `ps`.`id_product` NOT IN '
- . ' (SELECT `id_product` FROM `' . _DB_PREFIX_ . 'gm_omniprice_index`'
- . ' WHERE `id_shop` = ' . $shopId . ' AND `date` = \'' . $this->today . '\')'
- . ($this->indexInactive ? ' ' : ' AND `ps`.`active` = 1 ')
- . ' AND `ps`.`id_shop` = ' . $shopId . ' '
- . ' ORDER BY `ps`.`id_product` ASC LIMIT ' . $this->batchSize;
-
- $res = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $productIds[] = (int) $row['id_product'];
- }
- }
- return $productIds;
- }
-
- public function getProductAttributeMap($shopId)
- {
- $map = [];
- if (!$this->ignoreCombinations)
- {
- $query = 'SELECT `id_product`, `id_product_attribute` '
- . ' FROM `' . _DB_PREFIX_ . 'product_attribute_shop` '
- . ' WHERE `id_shop` = ' . $shopId;
- $res = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $map[(int) $row['id_product']][] = (int) $row['id_product_attribute'];
- }
- }
- }
- return $map;
- }
-
- public function getShopsIds()
- {
- $list = [];
- $sql = 'SELECT `id_shop` FROM `' . _DB_PREFIX_ . 'shop`
- WHERE `active` = 1 AND `deleted` = 0';
- $res = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($sql);
- if ($res)
- {
- foreach ($res as $row)
- {
- $list[] = (int) $row['id_shop'];
- }
- }
- return $list;
- }
-
- public function hookDisplayProductPriceBlock($hookParams)
- {
- if (($hookParams['type'] == 'after_price') &&
- ((isset($hookParams['product']->id)) || (isset($hookParams['product']['id_product'])) || Tools::isSubmit('id_product'))
- )
- {
- if (isset($hookParams['product']->id))
- {
- $productId = (int) $hookParams['product']->id;
- }
- else if (isset($hookParams['product']['id_product']))
- {
- $productId = (int) $hookParams['product']['id_product'];
- }
- else
- {
- $productId = (int) Tools::getValue('id_product');
- }
- $showRealDiscount = $this->showRealDiscount;
- if (Tools::isSubmit('omnipricetest'))
- {
- $lowestCachedPrice = [
- 'formatted' => Tools::getValue('omnipricetest'),
- 'raw' => 1
- ];
- $showRealDiscount = false;
- }
- else
- {
- $params = $this->getCurrentParams($productId);
- if (Tools::isSubmit('omnidebug'))
- {
- var_export($params);
- echo $this->context->country->iso_code;
- }
- if ($this->ignoreNonEuCountries)
- {
- if (!in_array($this->context->country->iso_code, $this->euCountries))
- {
+ if (!parent::uninstall()) {
return false;
- }
}
- $lowestCachedPrice = $this->getLowestCachedPrice($params);
- }
- $realDiscount = '';
- if ($showRealDiscount && $lowestCachedPrice && isset($hookParams['product']['price_amount']))
- {
- $currentPrice = $hookParams['product']['price_amount'];
- $previousPrice = $lowestCachedPrice['raw'];
- $realDiscount = $this->calculateRealDisount($currentPrice, $previousPrice);
- }
-
- if (!$lowestCachedPrice)
- {
- //may have a promotion for an individual combination
- if (Tools::version_compare(_PS_VERSION_, '1.7.0.0', '<') && $this->hasAttributePrices($productId))
- {
- $lowestCachedPrice = [
- 'formatted' => '---',
- 'raw' => '0'
- ];
+ if (!$this->uninstallDB() ||
+ !Configuration::deleteByName($this->prefix.'_GROUPS') ||
+ !Configuration::deleteByName($this->prefix.'_DAYS') ||
+ !Configuration::deleteByName($this->prefix.'_BATCH') ||
+ !Configuration::deleteByName($this->prefix.'_BG_COLOR') ||
+ !Configuration::deleteByName($this->prefix.'_TEXT_COLOR') ||
+ !Configuration::deleteByName($this->prefix.'_PRICE_COLOR') ||
+ !Configuration::deleteByName($this->prefix.'_IGNORE_COUNTRIES') ||
+ !Configuration::deleteByName($this->prefix.'_IGNORE_NON_EU') ||
+ !Configuration::deleteByName($this->prefix.'_IGNORE_COMBINATIONS') ||
+ !Configuration::deleteByName($this->prefix.'_TEXT_COLOR') ||
+ !Configuration::deleteByName($this->prefix.'_PRICE_COLOR') ||
+ !Configuration::deleteByName($this->prefix.'_BG_COLOR') ||
+ !Configuration::deleteByName($this->prefix.'_SHOW_IF_NO_HISTORY') ||
+ !Configuration::deleteByName($this->prefix.'_SHOW_REAL_DISCOUNT') ||
+ !Configuration::deleteByName($this->prefix.'_INDEX_INACTIVE') ||
+ !Configuration::deleteByName($this->prefix.'_REINDEX')
+ ) {
+ return false;
}
- }
-
- $checkIfProductIsDiscounted = self::checkIfProductIsDiscounted( $this->getDiscountedProductIds( $params['id_shop'], $params['id_currency'], $params['id_country'], $params['id_group'] ), $productId, $params['id_product_attribute'] );
-
- if ( $lowestCachedPrice and $checkIfProductIsDiscounted )
- {
- $this->context->smarty->assign(
- [
- 'gm_omniprice_lowest' => $lowestCachedPrice['formatted'],
- 'gm_omniprice_lowest_raw' => $lowestCachedPrice['raw'],
- 'gm_omniprice_days' => $this->daysBack,
- 'gm_omniprice_color' => $this->textColor,
- 'gm_omniprice_price_color' => $this->priceColor,
- 'gm_omniprice_background' => $this->backgroundColor,
- 'gm_omniprice_show_real_discount' => $showRealDiscount,
- 'gm_omniprice_real_discount' => $realDiscount
- ]
- );
- return $this->display(__FILE__, 'price.tpl');
- }
- }
- }
-
- public function calculateRealDisount($currentPrice, $previousPrice)
- {
- if (!$currentPrice || !$previousPrice)
- {
- return false;
- }
- $realDiscount = '0%';
- if ($currentPrice < $previousPrice)
- {
- $discount = round((1 - $currentPrice / $previousPrice) * 100);
- $realDiscount = '-' . $discount . '%';
- }
- if ($currentPrice > $previousPrice)
- {
- $discount = round(($currentPrice / $previousPrice - 1) * 100);
- $realDiscount = '+' . $discount . '%';
- }
- return $realDiscount;
- }
-
- public function getLowestCachedPrice($params)
- {
- $displayMethod = Group::getPriceDisplayMethod($params['id_group']);
- if ($displayMethod)
- {
- $field = '`price_tex`';
- }
- else
- {
- $field = '`price_tin`';
- }
- $price = Db::getInstance()->getValue(
- 'SELECT ' . $field
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_cache`'
- . ' WHERE `id_shop` = ' . $params['id_shop']
- . ' AND `id_product` = ' . $params['id_product']
- . ' AND `id_currency` = ' . $params['id_currency']
- . ' AND `id_country` = ' . $params['id_country']
- . ' AND `id_group` = ' . $params['id_group']
- . ' AND `id_product_attribute` = ' . $params['id_product_attribute']
- );
-
- if ($price)
- {
- return [
- 'formatted' => $this->getFormattedPrice(round($price)),
- 'raw' => $price
- ];
- }
- // else if ($params['id_product_attribute'] != 0)
- // {
- // $price = Db::getInstance()->getValue(
- // 'SELECT ' . $field
- // . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_cache`'
- // . ' WHERE `id_shop` = ' . $params['id_shop']
- // . ' AND `id_product` = ' . $params['id_product']
- // . ' AND `id_currency` = ' . $params['id_currency']
- // . ' AND `id_country` = ' . $params['id_country']
- // . ' AND `id_group` = ' . $params['id_group']
- // . ' AND `id_product_attribute` = 0'
- // );
-
- // if ($price)
- // {
- // return [
- // 'formatted' => $this->getFormattedPrice(round($price)),
- // 'raw' => $price
- // ];
- // }
- // }
-
- if (!$price)
- {
- if ($this->showIfNotEnoughHistoricalData)
- {
- return $this->getLatestHistoricalPrice($params);
- }
- }
- return false;
- }
-
- protected function getLatestHistoricalPrice($params)
- {
- $price_1 = Product::getPriceStatic( $params['id_product'], true, $params['id_product_attribute'], 2, null, false, false );
- $price_2 = Product::getPriceStatic( $params['id_product'], true, $params['id_product_attribute'], 2, null, false, true );
-
- $displayMethod = Group::getPriceDisplayMethod($params['id_group']);
- if ($displayMethod)
- {
- $field = '`price_tex`';
- $arrayField = 'price_tex';
- }
- else
- {
- $field = '`price_tin`';
- $arrayField = 'price_tin';
- }
-
- $date_history = date( 'Y-m-d', strtotime( '-30 days', time() ) );
-
- $prices = Db::getInstance()->executeS(
- 'SELECT ' . $field . ', `is_specific_price`'
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_history`'
- . ' WHERE `id_shop` = ' . $params['id_shop']
- . ' AND `id_product` = ' . $params['id_product']
- . ' AND `id_currency` = ' . $params['id_currency']
- . ' AND `id_country` = ' . $params['id_country']
- . ' AND `id_group` = ' . $params['id_group']
- . ' AND `id_product_attribute` = ' . $params['id_product_attribute']
- . ' AND date >= \'' . $date_history . '\''
- );
-
- $price_find = null;
-
- if ( is_array( $prices ) and count( $prices ) )
- {
- foreach ( $prices as $price_tmp )
- {
- if ( $price_tmp['is_specific_price'] )
- {
- if ( round( $price_2 ) != round( $price_tmp['price_tin'] ) )
- {
- if ( $price_find == null or $price_find > round( $price_tmp['price_tin'] ) )
- $price_find = round( $price_tmp['price_tin'] );
- }
- }
- }
- }
-
- if ( $price_find )
- {
- return [
- 'formatted' => $this->getFormattedPrice( $price_find ),
- 'raw' => $price_find
- ];
- }
-
-// echo 'SELECT ' . $field . ', `is_specific_price`'
-// . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_history`'
-// . ' WHERE `id_shop` = ' . $params['id_shop']
-// . ' AND `id_product` = ' . $params['id_product']
-// . ' AND `id_currency` = ' . $params['id_currency']
-// . ' AND `id_country` = ' . $params['id_country']
-// . ' AND `id_group` = ' . $params['id_group']
-// . ' AND `id_product_attribute` = ' . $params['id_product_attribute']
-// . ' AND date >= \'' . $date_history . '\'';
-// echo '
'; print_r($prices); echo ' ';
- // if ((count($prices) == 1) && ($prices[0]['is_specific_price']))
- // {
- // return
- // [
- // 'formatted' => $this->getFormattedPrice(round($prices[0][$arrayField])),
- // 'raw' => $prices[0][$arrayField]
- // ];
- // }
- // else if ($params['id_product_attribute'] != 0)
- // {
- // $prices = Db::getInstance()->executeS(
- // 'SELECT ' . $field . ', `is_specific_price`'
- // . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_history`'
- // . ' WHERE `id_shop` = ' . $params['id_shop']
- // . ' AND `id_product` = ' . $params['id_product']
- // . ' AND `id_currency` = ' . $params['id_currency']
- // . ' AND `id_country` = ' . $params['id_country']
- // . ' AND `id_group` = ' . $params['id_group']
- // . ' AND `id_product_attribute` = 0'
- // . ' AND date >= \'' . $date_history . '\''
- // );
-
- // if ((count($prices) == 1) && ($prices[0]['is_specific_price']))
- // {
- // return
- // [
- // 'formatted' => $this->getFormattedPrice(round($prices[0][$arrayField])),
- // 'raw' => $prices[0][$arrayField]
- // ];
- // }
- // }
-
- $price_1 = Product::getPriceStatic( $params['id_product'], true, $params['id_product_attribute'], 2, null, false, false );
- $price_2 = Product::getPriceStatic( $params['id_product'], true, $params['id_product_attribute'], 2, null, false, true );
- if ( $price_1 != $price_2 )
- return
- [
- 'formatted' => $this->getFormattedPrice( round( $price_1 ) )
- ];
- return false;
- }
-
- public function getLowestCachedPricesForCombinations($params)
- {
- $prices = [];
- $displayMethod = Group::getPriceDisplayMethod($params['id_group']);
- if ($displayMethod)
- {
- $field = '`price_tex`';
- }
- else
- {
- $field = '`price_tin`';
- }
- $result = Db::getInstance()->executeS(
- 'SELECT ' . $field . ' AS `price`, `id_product_attribute` '
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_cache`'
- . ' WHERE `id_shop` = ' . $params['id_shop']
- . ' AND `id_product` = ' . $params['id_product']
- . ' AND `id_currency` = ' . $params['id_currency']
- . ' AND `id_country` = ' . $params['id_country']
- . ' AND `id_group` = ' . $params['id_group']
- );
- if ($result)
- {
- foreach ($result as $row)
- {
- $prices[$row['id_product_attribute']] = $this->getFormattedPrice(round($row['price']));
- }
- }
- else
- {
- if ($this->showIfNotEnoughHistoricalData)
- {
- $result = Db::getInstance()->executeS(
- 'SELECT ' . $field . ' AS `price`, `id_product_attribute` '
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_history`'
- . ' WHERE `id_shop` = ' . $params['id_shop']
- . ' AND `id_product` = ' . $params['id_product']
- . ' AND `id_currency` = ' . $params['id_currency']
- . ' AND `id_country` = ' . $params['id_country']
- . ' AND `id_group` = ' . $params['id_group']
- . ' AND `is_specific_price` = 1 '
- );
- if ($result)
- {
- foreach ($result as $row)
- {
- $prices[$row['id_product_attribute']] = $this->getFormattedPrice(round($row['price']));
- }
- }
- }
- }
- return $prices;
- }
-
- public function getFormattedPrice($price)
- {
- $context = Context::getContext();
- if (isset($context->currentLocale))
- {
- return $context->currentLocale->formatPrice($price, $context->currency->iso_code);
- }
- else
- {
- return Tools::displayPrice($price);
- }
- }
-
- public function hasAttributePrices($productId)
- {
- $res = Db::getInstance()->getValue('SELECT `id_product` FROM `' . _DB_PREFIX_ . 'gm_omniprice_cache` '
- . ' WHERE `id_product` = ' . $productId . ' AND `id_product_attribute` > 0');
- if ($res == $productId)
- {
- return true;
- }
- if ($this->showIfNotEnoughHistoricalData)
- {
- $res = Db::getInstance()->getValue('SELECT `id_product` FROM `' . _DB_PREFIX_ . 'gm_omniprice_history` '
- . ' WHERE `id_product` = ' . $productId . ' AND `id_product_attribute` > 0 AND `is_specific_price` = 1');
- if ($res == $productId)
- {
return true;
- }
}
- return false;
- }
- public function getCurrentParams($productId)
- {
- $params = [];
- $params['id_shop'] = (int) $this->context->shop->id;
- $params['id_currency'] = (int) $this->context->currency->id;
- $params['id_product'] = (int) $productId;
- if ($this->ignoreCombinations)
+ protected function uninstallDb()
{
- $params['id_product_attribute'] = 0;
+ $res = Db::getInstance()->execute('DROP TABLE IF EXISTS `'._DB_PREFIX_.'gm_omniprice_history`');
+ $res &= Db::getInstance()->execute('DROP TABLE IF EXISTS `'._DB_PREFIX_.'gm_omniprice_cache`');
+ $res &= Db::getInstance()->execute('DROP TABLE IF EXISTS `'._DB_PREFIX_.'gm_omniprice_index`');
+ return $res;
}
- else
- {
- $params['id_product_attribute'] = $this->getIdProductAttribute($params['id_product']);
- }
- if ($this->ignoreCountries)
- {
- $params['id_country'] = $this->defaultCountryId;
- if (Shop::isFeatureActive())
- {
- $params['id_country'] = Configuration::get('PS_COUNTRY_DEFAULT', null, null, $params['id_shop']);
- }
- }
- else
- {
- $params['id_country'] = $this->context->country->id;
- }
- $currentGroup = $this->context->customer->id_default_group;
- if (in_array($currentGroup, $this->ignoredGroups))
- {
- $params['id_group'] = $this->defaultGroupId;
- }
- else
- {
- $params['id_group'] = $currentGroup;
- }
- return $params;
- }
- public function getDiscountedProductIds($shopId, $currencyId, $countryId, $groupId)
- {
- if ($this->globalRuleExists($shopId, $currencyId, $countryId, $groupId))
+ public function getContent()
{
- return $this->getAllProductIdsFromShop($shopId);
+ $content = '';
+ $content .= $this->postProcess();
+ $content .= $this->displayGreenMouseModulesPanel();
+ $content .= $this->displayForm();
+ $content .= $this->displayInfo();
+ $content .= $this->displayInformationPanel();
+ return $content;
}
- $beginning = null;
- $ending = null;
- if (Tools::version_compare(_PS_VERSION_, '1.6.1.10', '<='))
+
+ protected function postProcess()
{
- $now = date('Y-m-d H:i:00');
- $beginning = $now;
- $ending = $now;
- }
- $ids = SpecificPrice::getProductIdByDate($shopId, $currencyId, $countryId, $groupId, $beginning, $ending, 0, true);
- return $ids;
- }
-
- protected function getAllProductIdsFromShop($shopId)
- {
- $ids = [];
- $query = 'SELECT `id_product` FROM `' . _DB_PREFIX_ . 'product_shop` WHERE `id_shop` = ' . $shopId;
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $ids[] = [
- 'id_product' => (int) $row['id_product'],
- 'id_product_attribute' => 0
- ];
- }
- }
- return $ids;
- }
-
- public function globalRuleExists($shopId, $currencyId, $countryId, $groupId)
- {
- $query = 'SELECT `id_specific_price` FROM `' . _DB_PREFIX_ . 'specific_price` '
- . ' WHERE (`id_shop` = 0 OR `id_shop` = ' . $shopId . ') '
- . ' AND (`id_currency` = 0 OR `id_currency` = ' . $currencyId . ') '
- . ' AND (`id_country` = 0 OR `id_country` = ' . $countryId . ') '
- . ' AND (`id_group` = 0 OR `id_group` = ' . $groupId . ') '
- . ' AND (`from` <= NOW() OR `from` = \'0000-00-00 00:00:00\') '
- . ' AND (`to` >= NOW() OR `to` = \'0000-00-00 00:00:00\' ) '
- . ' AND `id_product` = 0 '
- . ' AND `id_product_attribute` = 0 '
- . ' AND `from_quantity` > 0 ';
- $result = (int) Db::getInstance()->getValue($query);
- return ($result > 0);
- }
-
- public function getIdProductAttribute($productId)
- {
- $idProductAttribute = $this->getIdProductAttributeByGroup($productId);
- if (null === $idProductAttribute)
- {
- $idProductAttribute = (int) Tools::getValue('id_product_attribute');
- }
- if (!$idProductAttribute)
- {
- $idProductAttribute = $this->getDefaultAttributeIdForProduct($productId);
- }
- return $idProductAttribute;
- }
-
- protected function getDefaultAttributeIdForProduct($productId)
- {
- $shopId = $this->context->shop->id;
- return (int) Db::getInstance()->getValue('SELECT `id_product_attribute` FROM `' . _DB_PREFIX_ . 'product_attribute_shop` '
- . ' WHERE `default_on` = 1 AND `id_shop` = ' . $shopId . ' AND `id_product` = ' . $productId);
- }
-
- protected function getIdProductAttributeByGroup($productId)
- {
- $groups = Tools::getValue('group');
- if (empty($groups))
- {
- return null;
- }
- return (int) Product::getIdProductAttributeByIdAttributes(
- $productId,
- $groups,
- true
- );
- }
-
- public function hookActionFrontControllerSetMedia($params)
- {
- $this->context->controller->registerStylesheet(
- 'module-gm_omniprice-style',
- 'modules/' . $this->name . '/views/css/gm_omniprice.css',
- [
- 'media' => 'all',
- 'priority' => 200,
- ]
- );
- }
-
- protected function displayInfo()
- {
- $token = Tools::getAdminToken($this->name);
- $output = '
'
- . '
'
- . $this->l('Gathering price history')
- . '
';
- $output .= '
';
- $output .= '
';
- $output .= '
'
- . '
'
- . $this->l('Cleaning old price history')
- . '
';
- $output .= '
';
- $output .= '
';
- return $output;
- }
-
- protected function displayInformationPanel()
- {
- $output = '
'
- . '
'
- . $this->l('Information')
- . '
';
- if (!defined('_TB_VERSION_'))
- { //TB has a nasty bug here
- $output .= '
' . $this->l('Groups with no customers:') . ' ' . implode(', ', $this->findEmptyGroups()) . '
';
- }
- $output .= '
' . $this->l('Groups with group reductions:') . ' ' . implode(', ', $this->findGroupsWithGroupReduction()) . '
';
- $output .= '
' . $this->l('Groups with specific prices:') . ' ' . implode(', ', $this->findGroupsWithSpecificPrices()) . '
';
- $output .= '
' . $this->l('Groups with specific price rules:') . ' ' . implode(', ', $this->findGroupsWithSpecifiPriceRules()) . '
';
- $output .= '
' . $this->l('Products have combinations with price impacts:') . ' ' . ($this->getCombinationsPriceImpactsInfo() ? $this->l('Yes') : $this->l('No')) . '
';
- $output .= '
' . $this->l('Individual combinations have discounts:') . ' ' . ($this->getCombinationsDiscountsInfo() ? $this->l('Yes') : $this->l('No')) . '
';
- $output .= '
' . $this->l('Number of active countries:') . ' ' . $this->countActiveCountries() . '
';
- $output .= '
' . $this->l('Number of active currencies:') . ' ' . $this->countActiveCurrencies() . '
';
- $output .= '
' . $this->l('Number of prices stored in history:') . ' ' . $this->countStoredPrices() . '
';
- $output .= '
';
- return $output;
- }
-
- protected function countActiveCurrencies()
- {
- return (int) Db::getInstance()->getValue('SELECT COUNT(`id_currency`) FROM `' . _DB_PREFIX_ . 'currency` WHERE `active` = 1');
- }
-
- protected function countActiveCountries()
- {
- return (int) Db::getInstance()->getValue('SELECT COUNT(`id_country`) FROM `' . _DB_PREFIX_ . 'country` WHERE `active` = 1');
- }
-
- protected function countStoredPrices()
- {
- return (int) Db::getInstance()->getValue('SELECT COUNT(`id_product`) FROM `' . _DB_PREFIX_ . 'gm_omniprice_history`');
- }
-
- protected function getCombinationsPriceImpactsInfo()
- {
- $query = 'SELECT `id_product` FROM `' . _DB_PREFIX_ . 'product_attribute` WHERE `price` != 0';
- $res = Db::getInstance()->getValue($query);
- if ($res)
- {
- return true;
- }
- else
- {
- return false;
- }
- }
-
- protected function getCombinationsDiscountsInfo()
- {
- $query = 'SELECT `id_product` FROM `' . _DB_PREFIX_ . 'specific_price` WHERE `id_product_attribute` > 0';
- $res = Db::getInstance()->getValue($query);
- if ($res)
- {
- return true;
- }
- else
- {
- return false;
- }
- }
-
- protected function getGroupNames()
- {
- $langId = $this->context->language->id;
- $query = 'SELECT `id_group`, `name` FROM `' . _DB_PREFIX_ . 'group_lang` WHERE `id_lang` = ' . $langId;
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $this->groupNames[(int) $row['id_group']] = $row['name'];
- }
- }
- }
-
- protected function findGroupsToSafelyIgnore()
- {
- $groups = $this->findEmptyGroups(true);
- $guestGroupId = Configuration::get('PS_GUEST_GROUP');
- $unidentifiedGroupId = Configuration::get('PS_UNIDENTIFIED_GROUP');
- $groups[] = $guestGroupId;
- $groups[] = $unidentifiedGroupId;
- $groups = array_unique($groups);
- sort($groups);
- $ignoredGroups = [];
- foreach ($groups as $groupId)
- {
- if ($groupId != $this->defaultGroupId)
- {
- $ignoredGroups[] = $groupId;
- }
- }
- return $ignoredGroups;
- }
-
- protected function findEmptyGroups($returnIds = false)
- {
- $emptyGroups = [];
- $emptyIds = [];
- $res = Group::getGroups($this->context->language->id);
- foreach ($res as $row)
- {
- $group = new Group((int) $row['id_group']);
- $customerCount = $group->getCustomers(true);
- if ($customerCount < 1)
- {
- $emptyGroups[] = $row['name'];
- $emptyIds[] = $row['id_group'];
- }
- }
- if ($returnIds)
- {
- return $emptyIds;
- }
- if (!count($emptyGroups))
- {
- return [$this->l('None')];
- }
- return $emptyGroups;
- }
-
- protected function findGroupsWithSpecifiPriceRules()
- {
- $groupIds = [];
- $query = 'SELECT `id_group` FROM `' . _DB_PREFIX_ . 'specific_price_rule` WHERE `id_group` > 0';
- $res = Db::getInstance()->executes($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $groupIds[] = (int) $row['id_group'];
- }
- }
- $groupIds = array_unique($groupIds);
- sort($groupIds);
- return $this->getGroupNamesForIds($groupIds);
- }
-
- protected function findGroupsWithSpecificPrices()
- {
- $groupIds = [];
- $query = 'SELECT `id_group` FROM `' . _DB_PREFIX_ . 'specific_price` WHERE `id_group` > 0';
- $res = Db::getInstance()->executes($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $groupIds[] = (int) $row['id_group'];
- }
- }
- $groupIds = array_unique($groupIds);
- sort($groupIds);
- return $this->getGroupNamesForIds($groupIds);
- }
-
- protected function findGroupsWithGroupReduction()
- {
- $groupIds = [];
- $query = 'SELECT `id_group` FROM `' . _DB_PREFIX_ . 'group` WHERE `reduction` > 0';
- $res = Db::getInstance()->executes($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $groupIds[] = (int) $row['id_group'];
- }
- }
- $query = 'SELECT `id_group` FROM `' . _DB_PREFIX_ . 'group_reduction` WHERE `reduction` > 0';
- $res = Db::getInstance()->executes($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $groupIds[] = (int) $row['id_group'];
- }
- }
- $groupIds = array_unique($groupIds);
- sort($groupIds);
- return $this->getGroupNamesForIds($groupIds);
- }
-
- protected function getGroupNamesForIds($groupIds)
- {
- if (!count($groupIds))
- {
- return [$this->l('None')];
- }
- $names = [];
- $this->getGroupNames();
- foreach ($groupIds as $groupId)
- {
- $names[] = $this->groupNames[$groupId];
- }
- return $names;
- }
-
- public function hookActionProductUpdate($params)
- {
- $productId = $params['id_product'];
- $this->reindexProduct($productId);
- }
-
- public function hookActionObjectSpecificPriceAddAfter($params)
- {
- $sp = $params['object'];
- if ($sp->id_product)
- {
- $this->reindexProduct($sp->id_product);
- }
- }
-
- public function hookActionObjectSpecificPriceUpdateAfter($params)
- {
- $sp = $params['object'];
- if ($sp->id_product)
- {
- $this->reindexProduct($sp->id_product);
- }
- }
-
- public function hookActionObjectSpecificPriceDeleteAfter($params)
- {
- $sp = $params['object'];
- if ($sp->id_product)
- {
- $this->reindexProduct($sp->id_product);
- }
- }
-
- public function reindexProduct($productId)
- {
- $this->removeProductFromTodaysIndex($productId);
- $this->removeProductFromTodaysHistory($productId);
- if ($this->reindexOnSave)
- {
- $this->savePrices(false, $productId);
- }
- }
-
- public function resetIndex()
- {
- Db::getInstance()->delete('gm_omniprice_index');
- Db::getInstance()->delete('gm_omniprice_history', '`date` = \'' . $this->today . '\'');
- }
-
- public function removeProductFromTodaysIndex($productId)
- {
- Db::getInstance()->delete('gm_omniprice_index', '`id_product` = ' . $productId . ' AND `date` = \'' . $this->today . '\'');
- }
-
- public function removeProductFromTodaysHistory($productId)
- {
- Db::getInstance()->delete('gm_omniprice_history', '`id_product` = ' . $productId . ' AND `date` = \'' . $this->today . '\'');
- }
-
- public function hookDisplayHeader($params)
- {
- if (Tools::isSubmit('id_product'))
- {
- $this->context->controller->addCSS($this->_path . 'views/css/gm_omniprice.css', 'all');
- if (!$this->ignoreCombinations)
- {
- $params = $this->getCurrentParams((int) Tools::getValue('id_product'));
- $prices = $this->getLowestCachedPricesForCombinations($params);
- if (count($prices) > 0)
- {
- $this->context->controller->addJS($this->_path . 'views/js/gm_omniprice.js');
- Media::addJsDef(['gm_omniprice_attr_prices' => $prices]);
- }
- }
- }
- }
-
- public function cleanUp($verbose = false)
- {
- $output = '';
- //general cleanup
- if (Tools::issubmit('zero'))
- {
- Db::getInstance()->delete('gm_omniprice_history', '`price_tin` < 0.001');
- Db::getInstance()->delete('gm_omniprice_cache', '`price_tin` < 0.001');
- }
- Db::getInstance()->delete('gm_omniprice_history', '`id_product` NOT IN (SELECT `id_product` FROM `' . _DB_PREFIX_ . 'product`)');
- Db::getInstance()->delete('gm_omniprice_cache', '`id_product` NOT IN (SELECT `id_product` FROM `' . _DB_PREFIX_ . 'product`)');
- Db::getInstance()->delete(
- 'gm_omniprice_history',
- '`id_product_attribute` > 0 AND `id_product_attribute` NOT IN (SELECT `id_product_attribute` FROM `' . _DB_PREFIX_ . 'product_attribute`)'
- );
- Db::getInstance()->delete(
- 'gm_omniprice_cache',
- '`id_product_attribute` > 0 AND `id_product_attribute` NOT IN (SELECT `id_product_attribute` FROM `' . _DB_PREFIX_ . 'product_attribute`)'
- );
- Db::getInstance()->delete('gm_omniprice_history', '`id_shop` NOT IN (SELECT `id_shop` FROM `' . _DB_PREFIX_ . 'shop`)');
- Db::getInstance()->delete('gm_omniprice_cache', '`id_shop` NOT IN (SELECT `id_shop` FROM `' . _DB_PREFIX_ . 'shop`)');
- Db::getInstance()->delete('gm_omniprice_history', '`id_currency` NOT IN (SELECT `id_currency` FROM `' . _DB_PREFIX_ . 'currency`)');
- Db::getInstance()->delete('gm_omniprice_cache', '`id_currency` NOT IN (SELECT `id_currency` FROM `' . _DB_PREFIX_ . 'currency`)');
- Db::getInstance()->delete('gm_omniprice_history', '`id_group` NOT IN (SELECT `id_group` FROM `' . _DB_PREFIX_ . 'group`)');
- Db::getInstance()->delete('gm_omniprice_cache', '`id_group` NOT IN (SELECT `id_group` FROM `' . _DB_PREFIX_ . 'group`)');
- Db::getInstance()->delete('gm_omniprice_history', '`id_country` NOT IN (SELECT `id_country` FROM `' . _DB_PREFIX_ . 'country` WHERE `active` = 1)');
- Db::getInstance()->delete('gm_omniprice_cache', '`id_country` NOT IN (SELECT `id_country` FROM `' . _DB_PREFIX_ . 'country` WHERE `active` = 1)');
- if ($this->ignoreCountries)
- {
- if (Shop::isFeatureActive())
- {
- //for the future
- }
- else
- {
- Db::getInstance()->delete('gm_omniprice_history', '`id_country` != ' . $this->defaultCountryId);
- Db::getInstance()->delete('gm_omniprice_cache', '`id_country` != ' . $this->defaultCountryId);
- }
- }
- foreach ($this->ignoredGroups as $ignoredGroupId)
- {
- if ($ignoredGroupId && ((int) $ignoredGroupId !== (int) $this->defaultGroupId))
- {
- Db::getInstance()->delete('gm_omniprice_history', '`id_group` = ' . $ignoredGroupId);
- Db::getInstance()->delete('gm_omniprice_cache', '`id_group` = ' . $ignoredGroupId);
- }
- }
- $date = date("Y-m-d", strtotime("-" . $this->daysBack . " days"));
- $output .= $this->l('Period') . ': ' . $this->daysBack . ' (' . $date . ')
';
- $shopIds = $this->getShopsIds();
- foreach ($shopIds as $shopId)
- {
- $currencyIds = $this->getCurrencyIds($shopId);
- $countryIds = $this->getCountryIds($shopId);
- $groupIds = $this->getGroupIds($shopId);
- $productIds = $this->getProductIdsInHistory($shopId);
- foreach ($currencyIds as $currencyId)
- {
- foreach ($countryIds as $countryId)
- {
- foreach ($groupIds as $groupId)
- {
- foreach ($productIds as $productId)
- {
- $query = 'SELECT `date`, `id_product`, `id_product_attribute` FROM `' . _DB_PREFIX_ . 'gm_omniprice_history` '
- . ' WHERE `id_product` = ' . $productId . ' AND `id_shop` = ' . $shopId . ' AND `id_currency` = ' . $currencyId .
- ' AND `id_country` = ' . $countryId . ' AND `id_group` = ' . $groupId . ' ORDER BY `date` ASC';
- $res = Db::getInstance()->executeS($query);
- $datesMap = [];
- if ($res)
- {
- foreach ($res as $row)
- {
- $day = $row['date'];
- $productId = $row['id_product'];
- $attributeId = $row['id_product_attribute'];
- if ($day < $date)
- {
- $datesMap[$productId][$attributeId][] = $day;
- }
- }
- foreach ($datesMap as $productId => $dateItem)
- {
- foreach ($dateItem as $attributeId => $dates)
- {
- $output .= "Product ID {$productId}, attribute ID: {$attributeId}
";
- $datesCount = count($dates);
- if ($datesCount > 2)
- {
- for ($i = 0; $i < $datesCount - 2; $i++)
- {
- $output .= ' ' . $dates[$i] . ' ' . $this->l('this price may be deleted') . '
';
- $where = '`id_shop` = ' . $shopId . ' AND `id_currency` = ' . $currencyId .
- ' AND `id_country` = ' . $countryId . ' AND `id_group` = ' . $groupId;
- $where .= ' AND `id_product` = ' . $productId . ' AND `id_product_attribute` = ' . $attributeId;
- $where .= ' AND `date` = \'' . $dates[$i] . '\'';
- Db::getInstance()->delete('gm_omniprice_history', $where);
- }
- }
- $output .= ' ' . $dates[$datesCount - 1] . ' ' . $this->l('this price is still needed') . '
';
- }
- }
- }
+ $output = '';
+ if (Tools::isSubmit('submit'.$this->name)) {
+ $this->ignoredGroups = Tools::getValue('groupBox');
+ if (!is_array($this->ignoredGroups)) {
+ $this->ignoredGroups = [];
}
- }
+ $groupsString = implode(',', $this->ignoredGroups);
+ Configuration::updateValue($this->prefix.'_GROUPS', $groupsString);
+
+ $this->daysBack = Tools::getValue($this->prefix.'_DAYS');
+ Configuration::updateValue($this->prefix.'_DAYS', $this->daysBack);
+
+ $this->batchSize = Tools::getValue($this->prefix.'_BATCH');
+ Configuration::updateValue($this->prefix.'_BATCH', $this->batchSize);
+
+ $this->ignoreCountries = Tools::getValue($this->prefix.'_IGNORE_COUNTRIES');
+ Configuration::updateValue($this->prefix.'_IGNORE_COUNTRIES', $this->ignoreCountries);
+
+ $this->ignoreNonEuCountries = Tools::getValue($this->prefix.'_IGNORE_NON_EU');
+ Configuration::updateValue($this->prefix.'_IGNORE_NON_EU', $this->ignoreNonEuCountries);
+
+ $this->ignoreCombinations = Tools::getValue($this->prefix.'_IGNORE_COMBINATIONS');
+ Configuration::updateValue($this->prefix.'_IGNORE_COMBINATIONS', $this->ignoreCombinations);
+
+ $this->reindexOnSave = Tools::getValue($this->prefix.'_REINDEX');
+ Configuration::updateValue($this->prefix.'_REINDEX', $this->reindexOnSave);
+
+ $this->textColor = Tools::getValue($this->prefix.'_TEXT_COLOR');
+ Configuration::updateValue($this->prefix.'_TEXT_COLOR', $this->textColor);
+
+ $this->priceColor = Tools::getValue($this->prefix.'_PRICE_COLOR');
+ Configuration::updateValue($this->prefix.'_PRICE_COLOR', $this->priceColor);
+
+ $this->backgroundColor = Tools::getValue($this->prefix.'_BG_COLOR');
+ Configuration::updateValue($this->prefix.'_BG_COLOR', $this->backgroundColor);
+
+ $this->showIfNotEnoughHistoricalData = Tools::getValue($this->prefix.'_SHOW_IF_NO_HISTORY');
+ Configuration::updateValue($this->prefix.'_SHOW_IF_NO_HISTORY', $this->showIfNotEnoughHistoricalData);
+
+ $this->showRealDiscount = Tools::getValue($this->prefix.'_SHOW_REAL_DISCOUNT');
+ Configuration::updateValue($this->prefix.'_SHOW_REAL_DISCOUNT', $this->showRealDiscount);
+
+ $this->indexInactive = Tools::getValue($this->prefix.'_INDEX_INACTIVE');
+ Configuration::updateValue($this->prefix.'_INDEX_INACTIVE', $this->indexInactive);
+
+ $this->skipBelowCost = Tools::getValue($this->prefix.'_SKIP_BELOW_COST');
+ Configuration::updateValue($this->prefix.'_SKIP_BELOW_COST', $this->skipBelowCost);
+
+ $output .= $this->displayConfirmation($this->l('Settings updated'));
}
- }
+ return $output;
}
- if ($verbose)
+ public function displayForm()
{
- echo '
';
- echo $output;
- }
- }
-
- protected function getProductIdsInHistory($shopId)
- {
- $ids = [];
- $query = 'SELECT DISTINCT `id_product` FROM `' . _DB_PREFIX_ . 'gm_omniprice_history` '
- . ' WHERE `id_shop` = ' . $shopId;
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $ids[] = (int) $row['id_product'];
- }
- }
- return $ids;
- }
-
- public function hookDisplayAdminProductsExtra(array $params)
- {
- $data = [];
- if (isset($params['id_product']))
- {
- $productId = (int) $params['id_product'];
- }
- else
- {
- $productId = (int) Tools::getValue('id_product');
- }
- $shopId = (int) $this->context->shop->id;
- $currencyId = (int) $this->defaultCurrencyId;
- if (Shop::isFeatureActive())
- {
- $currencyId = Configuration::get('PS_CURRENCY_DEFAULT', null, null, $shopId);
- }
- $countryId = (int) $this->defaultCountryId;
- if (Shop::isFeatureActive())
- {
- $countryId = Configuration::get('PS_COUNTRY_DEFAULT', null, null, $shopId);
- }
- $groupId = (int) $this->defaultGroupId;
- $attributeId = 0;
-
- $query = 'SELECT `date`, `price_tin`, `is_specific_price` '
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_history`'
- . ' WHERE `id_shop` = ' . $shopId
- . ' AND `id_product` = ' . $productId
- . ' AND `id_product_attribute` = ' . $attributeId
- . ' AND `id_currency` = ' . $currencyId
- . ' AND `id_country` = ' . $countryId
- . ' AND `id_group` = ' . $groupId
- . ' ORDER BY `date` DESC';
-
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $data[$row['date']] = [
- 'date' => $row['date'],
- 'price_tin' => $row['price_tin'],
- 'is_specific_price' => $row['is_specific_price'],
- 'type' => ($row['is_specific_price'] ? $this->l('Reduced price') : $this->l('Regular price'))
- ];
- }
- }
-
- $query = 'SELECT `date`, `price_tin` '
- . ' FROM `' . _DB_PREFIX_ . 'gm_omniprice_cache`'
- . ' WHERE `id_shop` = ' . $shopId
- . ' AND `id_product` = ' . $productId
- . ' AND `id_product_attribute` = ' . $attributeId
- . ' AND `id_currency` = ' . $currencyId
- . ' AND `id_country` = ' . $countryId
- . ' AND `id_group` = ' . $groupId
- . ' ORDER BY `date` DESC';
-
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- if (!array_key_exists($row['date'], $data))
- {
- $data[$row['date']] = [
- 'date' => $row['date'],
- 'price_tin' => $row['price_tin'],
- 'is_specific_price' => '',
- 'type' => $this->l('Lowest previous price')
- ];
- }
- }
- }
- krsort($data);
- $indexed = (int) Db::getInstance()->getValue('SELECT `id_product` FROM `' . _DB_PREFIX_ . 'gm_omniprice_index` WHERE `id_product` = ' . $productId .
- ' AND `date` = \'' . $this->today . '\'');
- $this->context->smarty->assign(array(
- 'historyData' => $data,
- 'indexedToday' => $indexed
- ));
- $debug = '';
- if (Tools::isSubmit('omnidebug'))
- {
- $res = Db::getInstance()->executeS('SELECT * FROM `' . _DB_PREFIX_ . 'gm_omniprice_history` WHERE `id_product` = ' . $productId . ' ORDER BY `date` DESC');
- if ($res)
- {
- $debug = $this->displayTable($res, array_keys($res[0]));
- }
- }
- return $this->display(__FILE__, 'tab.tpl') . $debug;
- }
-
- public function displayTable($data, $columns)
- {
- $output = ' ';
- $output .= '';
- $output .= '';
- foreach ($columns as $columnHeader)
- {
- $output .= '' . $columnHeader . ' ';
- }
- $output .= ' ';
- $output .= '';
- foreach ($data as $row)
- {
- $output .= '';
- foreach ($columns as $key)
- {
- $output .= '' . $row[$key] . ' ';
- }
- $output .= ' ';
- }
- $output .= '
';
- return $output;
- }
-
- public function hookActionGetProductPropertiesAfter($params)
- {
- return;
- $product = &$params['product'];
- $sp = $product['specific_prices'];
- //var_export($product);
- $sp['reduction'] = (string) (rand(0, 10) / 100);
- $product['specific_prices'] = $sp;
- }
-
- public function fillMissingCache($verbose = false)
- {
- $output = '';
- $query = 'SELECT * FROM `' . _DB_PREFIX_ . 'gm_omniprice_history` '
- . ' WHERE `is_specific_price` = 1 AND `id_product` IN (SELECT `id_product` FROM `' . _DB_PREFIX_ . 'product` WHERE `active` = 1)'
- . ' ORDER BY `date` DESC ';
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $lowestPrice = $this->getLowestCachedPrice($row);
- if ($lowestPrice === false)
- {
- $shopId = (int) $row['id_shop'];
- $productId = (int) $row['id_product'];
- $groupId = (int) $row['id_group'];
- $currencyId = (int) $row['id_currency'];
- $countryId = (int) $row['id_country'];
- $attributeId = (int) $row['id_product_attribute'];
- $output .= var_export($row, true) . '
';
- $output .= ' - no lowest price!
';
- $lastChangeDate = $row['date'];
- $output .= ' Look for the lowest price before ' . $lastChangeDate . '
';
- $now = time();
- $your_date = strtotime($row['date']);
- $datediff = $now - $your_date;
- $daysOffset = floor($datediff / (60 * 60 * 24));
- $output .= ' days offset: ' . $daysOffset . '
';
- $lowestPrices = $this->getLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $daysOffset);
- if ($lowestPrices)
- {
- $output .= ' found price: ' . $lowestPrices['price_tin'] . ' (' . $lowestPrices['price_tex'] . ')
';
- $this->saveLowestPrice(
- $shopId,
- $productId,
- $currencyId,
- $countryId,
- $groupId,
- $attributeId,
- $lowestPrices['price_tex'],
- $lowestPrices['price_tin'],
- $lowestPrices['date']
+ $helper = new HelperForm();
+ $groups = Group::getGroups($this->context->language->id);
+ $inputs = array(
+ array(
+ 'type' => 'text',
+ 'label' => $this->l('Period'),
+ 'desc' => $this->l('Number of days before promotion start to analyze'),
+ 'name' => $this->prefix.'_DAYS',
+ 'class' => 'fixed-width-md',
+ ),
+ array(
+ 'type' => 'switch',
+ 'label' => $this->l('Ignore countries'),
+ 'name' => $this->prefix.'_IGNORE_COUNTRIES',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ 'hint' => $this->l('Analyze prices only for the default country, customers from other countries will see prices of the default country'),
+ 'desc' => $this->l('Analyze prices only for the default country, customers from other countries will see prices of the default country')
+ ),
+ array(
+ 'type' => 'switch',
+ 'label' => $this->l('Ignore non EU countries'),
+ 'name' => $this->prefix.'_IGNORE_NON_EU',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ 'hint' => $this->l('Skip non EU countries totally, customers from non EU countries will not see any message about previous price'),
+ 'desc' => $this->l('Skip non EU countries totally, customers from non EU countries will not see any message about previous price')
+ ),
+ array(
+ 'type' => 'switch',
+ 'label' => $this->l('Ignore combinations'),
+ 'name' => $this->prefix.'_IGNORE_COMBINATIONS',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ 'hint' => $this->l('Analyze prices only for the default combination, recommended if combinations don\'t have price impacts'),
+ 'desc' => $this->l('Analyze prices only for the default combination, recommended if combinations don\'t have price impacts')
+ ),
+ array(
+ 'type' => 'group',
+ 'label' => $this->l('Ignored groups'),
+ 'name' => 'groupBox',
+ 'values' => $groups,
+ 'hint' => $this->l('Ignore selected groups, customers from ignored groups will see prices for the default group (Customer), recommended if no group discounts in use'),
+ 'desc' => $this->l('Ignore selected groups, customers from ignored groups will see prices for the default group (Customer), recommended if no group discounts in use')
+ ),
+ array(
+ 'type' => 'text',
+ 'label' => $this->l('Batch size'),
+ 'desc' => $this->l('Number of products to process in a single CRON task run'),
+ 'name' => $this->prefix.'_BATCH',
+ 'class' => 'fixed-width-md',
+ ),
+ array(
+ 'type' => 'switch',
+ 'label' => $this->l('Reindex on product save'),
+ 'name' => $this->prefix.'_REINDEX',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ 'hint' => $this->l('Reindex product on save'),
+ 'desc' => $this->l('Reindex product on save')
+ ),
+ array(
+ 'type' => 'color',
+ 'label' => $this->l('Background color'),
+ 'name' => $this->prefix.'_BG_COLOR',
+ ),
+ array(
+ 'type' => 'color',
+ 'label' => $this->l('Text color'),
+ 'name' => $this->prefix.'_TEXT_COLOR',
+ ),
+ array(
+ 'type' => 'color',
+ 'label' => $this->l('Price color'),
+ 'name' => $this->prefix.'_PRICE_COLOR',
+ ),
+ array(
+ 'type' => 'switch',
+ 'label' => $this->l('Show label even if not enough history'),
+ 'name' => $this->prefix.'_SHOW_IF_NO_HISTORY',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ 'hint' => $this->l('For discounted products, if previous price is unknown, shows the current discounted price as the lowest one'),
+ 'desc' => $this->l('For discounted products, if previous price is unknown, shows the current discounted price as the lowest one')
+ ),
+ array(
+ 'type' => 'switch',
+ 'label' => $this->l('Index inactive products'),
+ 'name' => $this->prefix.'_INDEX_INACTIVE',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ 'hint' => $this->l('Store price history even if the product is not active'),
+ 'desc' => $this->l('Store price history even if the product is not active'),
+ ),
+ );
+ if (Tools::version_compare(_PS_VERSION_, '1.7.0.0', '>=')) {
+ $inputs[] = array(
+ 'type' => 'switch',
+ 'label' => $this->l('Show real discount from the previous price'),
+ 'name' => $this->prefix.'_SHOW_REAL_DISCOUNT',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ 'hint' => $this->l('Display price change percentage after the lowest previous price'),
+ 'desc' => $this->l('Display price change percentage after the lowest previous price')
);
- }
}
- }
- }
- if ($verbose)
- {
- echo $output;
- }
- }
+ $inputs[] = array(
+ 'type' => 'switch',
+ 'label' => $this->l('Skip products sold below cost price'),
+ 'name' => $this->prefix.'_SKIP_BELOW_COST',
+ 'values' => array(
+ array(
+ 'id' => 'active_on',
+ 'value' => 1,
+ 'label' => $this->l('Yes')
+ ),
+ array(
+ 'id' => 'active_off',
+ 'value' => 0,
+ 'label' => $this->l('No')
+ )
+ ),
+ );
+ $fieldsForm = array(
+ 'form' => array(
+ 'legend' => array(
+ 'title' => $this->l('Settings'),
+ 'icon' => 'icon-cogs'
+ ),
+ 'input' => $inputs,
+ 'submit' => array(
+ 'title' => $this->l('Save')
+ )
+ ),
+ );
- public function getActiveMap()
- {
- if ($this->activeMap == null)
- {
- $query = 'SELECT `id_shop`, `id_product`, `active` FROM `' . _DB_PREFIX_ . 'product_shop`';
- $res = Db::getInstance()->executeS($query);
- if ($res)
- {
- foreach ($res as $row)
- {
- $this->activeMap[(int) $row['id_shop']][(int) $row['id_product']] = (int) $row['active'];
+ $helper->show_toolbar = true;
+ $helper->toolbar_scroll = true;
+ $helper->table = $this->table;
+ $helper->default_form_language = (int) Configuration::get('PS_LANG_DEFAULT');
+ $helper->module = $this;
+ $helper->allow_employee_form_lang = Configuration::get('PS_BO_ALLOW_EMPLOYEE_FORM_LANG') ? Configuration::get('PS_BO_ALLOW_EMPLOYEE_FORM_LANG')
+ : 0;
+ $helper->identifier = $this->identifier;
+ $helper->submit_action = 'submit'.$this->name;
+ $helper->currentIndex = $this->context->link->getAdminLink('AdminModules', false).'&configure='.$this->name.'&tab_module='.$this->tab.'&module_name='.$this->name;
+ $helper->token = Tools::getAdminTokenLite('AdminModules');
+ foreach ($groups as $group) {
+ $helper->fields_value['groupBox_'.$group['id_group']] = in_array($group['id_group'], $this->ignoredGroups);
}
- }
- }
- return $this->activeMap;
- }
+ $helper->fields_value[$this->prefix.'_DAYS'] = $this->daysBack;
+ $helper->fields_value[$this->prefix.'_BATCH'] = $this->batchSize;
+ $helper->fields_value[$this->prefix.'_IGNORE_COUNTRIES'] = $this->ignoreCountries;
+ $helper->fields_value[$this->prefix.'_IGNORE_NON_EU'] = $this->ignoreNonEuCountries;
+ $helper->fields_value[$this->prefix.'_IGNORE_COMBINATIONS'] = $this->ignoreCombinations;
+ $helper->fields_value[$this->prefix.'_REINDEX'] = $this->reindexOnSave;
+ $helper->fields_value[$this->prefix.'_TEXT_COLOR'] = $this->textColor;
+ $helper->fields_value[$this->prefix.'_PRICE_COLOR'] = $this->priceColor;
+ $helper->fields_value[$this->prefix.'_BG_COLOR'] = $this->backgroundColor;
+ $helper->fields_value[$this->prefix.'_SHOW_REAL_DISCOUNT'] = $this->showRealDiscount;
+ $helper->fields_value[$this->prefix.'_INDEX_INACTIVE'] = $this->indexInactive;
+ $helper->fields_value[$this->prefix.'_SKIP_BELOW_COST'] = $this->skipBelowCost;
+ $helper->fields_value[$this->prefix.'_SHOW_IF_NO_HISTORY'] = $this->showIfNotEnoughHistoricalData;
- public function productIsActive($productId, $shopId)
- {
- $activeMap = $this->getActiveMap();
- if (isset($activeMap[$shopId][$productId]))
+ return $helper->generateForm(array($fieldsForm));
+ }
+
+ public function savePrices($verbose = false, $productId = null)
{
- return ($activeMap[$shopId][$productId] == 1);
- }
- return false;
- }
+ $this->clearIndex($this->yesterday);
+ $output = '';
+ $usetax = true;
+ if (Tax::excludeTaxeOption()) {
+ $usetax = false;
+ }
+ $basicPrices = [];
+ $stateId = 0;
+ $zipcode = '';
- public function getCostPriceMap()
- {
- $map = [];
- $query = 'SELECT `id_product`, `id_shop`, `wholesale_price` FROM `' . _DB_PREFIX_ . 'product_shop` WHERE `wholesale_price` > 0';
- $res = Db::getInstance()->executeS($query);
- if ($res)
+ $output .= $this->today.'
';
+ $output .= $this->l('Batch size').': '.$this->batchSize.'
';
+ $output .= $this->l('Default country ID:').' '.$this->defaultCountryId.'
';
+ $output .= $this->l('Default group ID:').' '.$this->defaultGroupId.'
';
+
+ $shopIds = $this->getShopsIds();
+ $useReduction = true;
+ if (Tools::isSubmit('init')) {
+ $useReduction = false;
+ }
+ if ($this->skipBelowCost) {
+ $rates = $this->getConversionRates();
+ $costPriceMap = $this->getCostPriceMap();
+ }
+ $specificPriceOutput = null;
+ foreach ($shopIds as $shopId) {
+ $currencyIds = $this->getCurrencyIds($shopId);
+ $countryIds = $this->getCountryIds($shopId);
+ $groupIds = $this->getGroupIds($shopId);
+ $lastCurrencyId = end($currencyIds);
+ $lastCountryId = end($countryIds);
+ $lastGroupId = end($groupIds);
+ $attributesMap = $this->getProductAttributeMap($shopId);
+ if (!$productId) {
+ $productIds = $this->getProductIds($shopId);
+ } else {
+ if (!$this->indexInactive && !$this->productIsActive($productId, $shopId)) {
+ continue;
+ }
+ $productIds = [$productId];
+ }
+ $output .= '
'.$this->l('Shop ID:').' '.$shopId.' ';
+ if (count($productIds) < 1) {
+ $output .= '
'.$this->l('All products indexed').'
';
+ continue;
+ } else {
+ $output .= '
'.$this->l('Not finished yet, please run me again').'
';
+ }
+ $output .= '
'
+ .' '
+ .''.$this->l('Product ID').' '
+ .''.$this->l('Attribute ID').' '
+ .''.$this->l('Country ID').' '
+ .''.$this->l('Currency ID').' '
+ .''.$this->l('Group ID').' '
+ .''.$this->l('Price').' '
+ .''.$this->l('Previous price').' '
+ .''.$this->l('Is discounted').' '
+ .''.$this->l('Action').' '
+ .''.$this->l('Lowest price').' '
+ .' ';
+ $counter = 0;
+ foreach ($currencyIds as $currencyId) {
+ foreach ($countryIds as $countryId) {
+ foreach ($groupIds as $groupId) {
+ $discountedIds = $this->getDiscountedProductIds($shopId, $currencyId, $countryId, $groupId);
+ foreach ($productIds as $productId) {
+ $attributeId = 0;
+ $basicKey = $shopId.'-'.$productId.'-'.$attributeId.'-'.$currencyId.'-'.$countryId.'-'.$groupId;
+ $priceTin = Product::priceCalculation(
+ $shopId, $productId, $attributeId, $countryId, $stateId, $zipcode, $currencyId, $groupId, 1, //quantity
+ $usetax, 6, //decimals
+ false, //only_reduc
+ $useReduction, //use_reduc
+ true, //with_ecotax
+ $specificPriceOutput, true //use_group_reduction
+ );
+ $priceTin = sprintf("%.6f", $priceTin);
+ $basicPrices[$basicKey] = $priceTin;
+ $priceTex = $priceTin;
+ if ($usetax) {
+ $priceTex = Product::priceCalculation(
+ $shopId, $productId, $attributeId, $countryId, $stateId, $zipcode, $currencyId, $groupId, 1, //quantity
+ false, //no tax
+ 6, //decimals
+ false, //only_reduc
+ $useReduction, //use_reduc
+ true, //with_ecotax
+ $specificPriceOutput, true //use_group_reduction
+ );
+ }
+ $previously = $this->getPreviousPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ if ($previously) {
+ $previousPrice = (float) $previously['price_tin'];
+ $previousDiscount = (bool) $previously['is_specific_price'];
+ } else {
+ $previousPrice = 0;
+ $previousDiscount = false;
+ }
+ if (Tools::isSubmit('init')) {
+ $onDiscount = false;
+ } else {
+ if (Module::isEnabled('groupinc')) {
+ $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId) || (is_array($specificPriceOutput)
+ && (count($specificPriceOutput) > 1)); //groupinc module support
+ } else {
+ $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId);
+ }
+ }
+ $onDiscountText = ($onDiscount ? $this->l('Yes') : $this->l('No'));
+ //check if product is sold below cost price
+ if ($this->skipBelowCost) {
+ if ($this->checkIfProductIsSoldBelowCost($priceTex, $costPriceMap, $rates, $shopId, $productId, $attributeId,
+ $currencyId)) {
+ $onDiscount = false;
+ $onDiscountText = $this->l('Below cost');
+ }
+ }
+ $output .= ''
+ .''.++$counter.' '
+ .''.$productId.' '
+ .''.$attributeId.' '
+ .''.$countryId.' '
+ .''.$currencyId.' '
+ .''.$groupId.' '
+ .''.$priceTin.' ('.$priceTex.') '
+ .''.$previousPrice.' '
+ .''.$onDiscountText.' ';
+ $priceIsCorrect = ($priceTin > 0);
+ $priceChanged = (abs($previousPrice - $priceTin) > 0.01);
+ $discountChanged = ($previousDiscount != $onDiscount);
+ if (Tools::isSubmit('cache')) {
+ $discountChanged = true;
+ }
+ if ($priceIsCorrect && ($priceChanged || $discountChanged)) {
+ $output .= ''.$this->l('Save').' ';
+ $this->savePrice($this->today, $shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $priceTex,
+ $priceTin, $onDiscount);
+ //calculate lowest price and add it to the cache
+ if ($onDiscount) {
+ $lowestPrices = $this->getLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ if ($lowestPrices) {
+ $output .= ''.$lowestPrices['price_tin'].' ('.$lowestPrices['price_tex'].') ';
+ $this->saveLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId,
+ $lowestPrices['price_tex'], $lowestPrices['price_tin'], $lowestPrices['date']);
+ } else {
+ $output .= ''.$this->l('Unknown').' ';
+ }
+ } else {
+ $output .= ''.$this->l('Not applicable').' ';
+ }
+ } else {
+ $output .= ''.$this->l('No change').' ';
+ $output .= ''.$this->l('No change').' ';
+ }
+ if (!$onDiscount) {
+ $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ }
+ $output .= ' ';
+ //attributes
+ if (array_key_exists($productId, $attributesMap)) {
+ foreach ($attributesMap[$productId] as $attributeId) {
+ $priceTin = Product::priceCalculation(
+ $shopId, $productId, $attributeId, $countryId, $stateId, $zipcode, $currencyId, $groupId, 1, //quantity
+ $usetax, 6, //decimals
+ false, //only_reduc
+ $useReduction, //use_reduc
+ true, //with_ecotax
+ $specificPriceOutput, true //use_group_reduction
+ );
+ $priceTin = sprintf("%.6f", $priceTin);
+ $priceTex = $priceTin;
+ if ($usetax) {
+ $priceTex = Product::priceCalculation(
+ $shopId, $productId, $attributeId, $countryId, $stateId, $zipcode, $currencyId, $groupId,
+ 1, //quantity
+ false, //no tax
+ 6, //decimals
+ false, //only_reduc
+ $useReduction, //use_reduc
+ true, //with_ecotax
+ $specificPriceOutput, true //use_group_reduction
+ );
+ }
+ if (abs($priceTin - $basicPrices[$basicKey]) > 0.01) {
+ $previously = $this->getPreviousPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ if ($previously) {
+ $previousPrice = (float) $previously['price_tin'];
+ $previousDiscount = (bool) $previously['is_specific_price'];
+ } else {
+ $previousPrice = 0;
+ $previousDiscount = false;
+ }
+ if (Tools::isSubmit('init')) {
+ $onDiscount = false;
+ } else {
+ if (Module::isEnabled('groupinc')) {
+ $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId) || (is_array($specificPriceOutput)
+ && (count($specificPriceOutput) > 1)); //groupinc module support
+ } else {
+ $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId);
+ }
+ }
+ $onDiscountText = ($onDiscount ? $this->l('Yes') : $this->l('No'));
+ if ($this->skipBelowCost) {
+ if ($this->checkIfProductIsSoldBelowCost($priceTex, $costPriceMap, $rates, $shopId, $productId,
+ $attributeId, $currencyId)) {
+ $onDiscount = false;
+ $onDiscountText = $this->l('Below cost');
+ }
+ }
+ $output .= ''
+ .''.++$counter.' '
+ .''.$productId.' '
+ .''.$attributeId.' '
+ .''.$countryId.' '
+ .''.$currencyId.' '
+ .''.$groupId.' '
+ .''.$priceTin.' ('.$priceTex.') '
+ .''.$previousPrice.' '
+ .''.$onDiscountText.' ';
+ $priceIsCorrect = ($priceTin > 0);
+ $priceChanged = (abs($previousPrice - $priceTin) > 0.01);
+ $discountChanged = ($previousDiscount != $onDiscount);
+ if (Tools::isSubmit('cache')) {
+ $discountChanged = true;
+ }
+ if ($priceIsCorrect && ($priceChanged || $discountChanged)) {
+ $output .= ''.$this->l('Save').' ';
+ $this->savePrice($this->today, $shopId, $productId, $currencyId, $countryId, $groupId, $attributeId,
+ $priceTex, $priceTin, $onDiscount);
+ if ($onDiscount) {
+ $lowestPrices = $this->getLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId,
+ $attributeId);
+ if ($lowestPrices) {
+ $output .= ''.$lowestPrices['price_tin'].' ('.$lowestPrices['price_tex'].') ';
+ $this->saveLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId,
+ $lowestPrices['price_tex'], $lowestPrices['price_tin'], $lowestPrices['date']);
+ } else {
+ $output .= ''.$this->l('Unknown').' ';
+ }
+ } else {
+ $output .= ''.$this->l('Not applicable').' ';
+ }
+ } else {
+ $output .= ''.$this->l('No change').' ';
+ $output .= ''.$this->l('No change').' ';
+ }
+ if (!$onDiscount) {
+ $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ }
+ } else {
+ //skip analyzing attribute if price is the same as basic
+ //delete if the attribute is not on discount
+ $onDiscount = $this->checkIfProductIsDiscounted($discountedIds, $productId, $attributeId);
+ if (!$onDiscount) {
+ $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ }
+ }
+ }
+ }
+ if ($currencyId == $lastCurrencyId && $groupId == $lastGroupId && $countryId == $lastCountryId) {
+ $this->addProductToIndex($shopId, $productId, $this->today);
+ }
+ }
+ }
+ }
+ }
+ $output .= '
';
+ }
+ if ($verbose) {
+ echo $output;
+ }
+ return true;
+ }
+
+ public function getLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $daysOffset = 0)
{
- foreach ($res as $row)
- {
- $shopId = (int) $row['id_shop'];
- $productId = (int) $row['id_product'];
- $costPrice = $row['wholesale_price'];
- $map[$shopId][$productId][0] = $costPrice;
- }
+ $lowestPriceTin = INF;
+ $lowestPriceTex = INF;
+ $lowestDate = '0000-00-00';
+ for ($d = 1; $d <= $this->daysBack; $d++) {
+ $days = $d + $daysOffset;
+ $date = date('Y-m-d', strtotime("-$days days"));
+ $row = Db::getInstance()->getRow('SELECT `price_tin`, `price_tex` '
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_history` '
+ .' WHERE `id_shop` = '.$shopId
+ .' AND `id_product` = '.$productId
+ .' AND `id_currency` = '.$currencyId
+ .' AND `id_country` = '.$countryId
+ .' AND `id_group` = '.$groupId
+ .' AND `id_product_attribute` = '.$attributeId
+ .' AND `date` <= \''.$date.'\''
+ .' ORDER BY `date` DESC'
+ );
+ if ($attributeId != 0 && $row == false) {
+ $attributeId = 0;
+ $row = Db::getInstance()->getRow('SELECT `price_tin`, `price_tex` '
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_history` '
+ .' WHERE `id_shop` = '.$shopId
+ .' AND `id_product` = '.$productId
+ .' AND `id_currency` = '.$currencyId
+ .' AND `id_country` = '.$countryId
+ .' AND `id_group` = '.$groupId
+ .' AND `id_product_attribute` = '.$attributeId
+ .' AND `date` <= \''.$date.'\''
+ .' ORDER BY `date` DESC'
+ );
+ }
+ if ($row) {
+ $priceTin = $row['price_tin'];
+ if ($priceTin < $lowestPriceTin) {
+ $lowestPriceTin = $priceTin;
+ }
+ $priceTex = $row['price_tex'];
+ if ($priceTex < $lowestPriceTex) {
+ $lowestPriceTex = $priceTex;
+ $lowestDate = $date;
+ }
+ } else {
+ break;
+ }
+ }
+ if ($lowestPriceTex < INF) {
+ return [
+ 'price_tin' => $lowestPriceTin,
+ 'price_tex' => $lowestPriceTex,
+ 'date' => $lowestDate
+ ];
+ } else {
+ return false;
+ }
}
- $query = 'SELECT `id_product`, `id_product_attribute`, `id_shop`, `wholesale_price` FROM `' . _DB_PREFIX_ . 'product_attribute_shop` WHERE `wholesale_price` > 0';
- $res = Db::getInstance()->executeS($query);
- if ($res)
+ public function checkIfProductIsDiscounted($discountedIds, $productId, $attributeId)
{
- foreach ($res as $row)
- {
- $shopId = (int) $row['id_shop'];
- $productId = (int) $row['id_product'];
- $attributeId = (int) $row['id_product_attribute'];
- $costPrice = $row['wholesale_price'];
- $map[$shopId][$productId][$attributeId] = $costPrice;
- }
+ if (Tools::isSubmit('init')) {
+ return false;
+ }
+ foreach ($discountedIds as $item) {
+ if (($item['id_product'] == $productId) && ($item['id_product_attribute'] == $attributeId)) {
+ return true;
+ }
+ if (($item['id_product'] == $productId) && ($item['id_product_attribute'] == 0)) {
+ return true;
+ }
+ }
+ return false;
}
- return $map;
- }
- public function getConversionRates()
- {
- $rates = [];
- $currencies = Db::getInstance()->executeS('
+ public function clearIndex($date)
+ {
+ return Db::getInstance()->delete('gm_omniprice_index', '`date` <= \''.$date.'\'');
+ }
+
+ public function addProductToIndex($shopId, $productId, $date)
+ {
+ Db::getInstance()->insert('gm_omniprice_index',
+ [
+ 'date' => $date,
+ 'id_shop' => $shopId,
+ 'id_product' => $productId
+ ]);
+ }
+
+ public function getPreviousPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId)
+ {
+ return Db::getInstance()->getRow('SELECT `price_tin`, `is_specific_price` FROM `'._DB_PREFIX_.'gm_omniprice_history`'
+ .' WHERE `id_shop` = '.$shopId.' AND `id_product` = '.$productId
+ .' AND `id_currency` = '.$currencyId.' AND `id_country` = '.$countryId
+ .' AND `id_group` = '.$groupId.' AND `id_product_attribute` = '.$attributeId
+ .' AND `date` < \''.$this->today.'\''
+ .' ORDER BY `date` DESC');
+ }
+
+ public function saveLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $priceTex, $priceTin, $date)
+ {
+ $this->deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ return Db::getInstance()->insert('gm_omniprice_cache',
+ [
+ 'id_shop' => $shopId,
+ 'id_product' => $productId,
+ 'id_currency' => $currencyId,
+ 'id_country' => $countryId,
+ 'id_group' => $groupId,
+ 'id_product_attribute' => $attributeId,
+ 'price_tex' => $priceTex,
+ 'price_tin' => $priceTin,
+ 'date' => $date
+ ]);
+ }
+
+ public function deleteLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId)
+ {
+ return Db::getInstance()->delete('gm_omniprice_cache',
+ '`id_shop` = '.$shopId
+ .' AND `id_product` = '.$productId
+ .' AND `id_product_attribute` = '.$attributeId
+ .' AND `id_currency` = '.$currencyId
+ .' AND `id_country` = '.$countryId
+ .' AND `id_group` = '.$groupId
+ );
+ }
+
+ public function savePrice($date, $shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $priceTex, $priceTin, $onDiscount = false)
+ {
+ if (Tools::isSubmit('cache')) {
+ $this->deleteTodaysPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId);
+ }
+ Db::getInstance()->insert('gm_omniprice_history',
+ [
+ 'date' => $date,
+ 'id_shop' => $shopId,
+ 'id_product' => $productId,
+ 'id_currency' => $currencyId,
+ 'id_country' => $countryId,
+ 'id_group' => $groupId,
+ 'id_product_attribute' => $attributeId,
+ 'price_tex' => $priceTex,
+ 'price_tin' => $priceTin,
+ 'is_specific_price' => $onDiscount
+ ]);
+ }
+
+ public function deleteTodaysPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId)
+ {
+ return Db::getInstance()->delete('gm_omniprice_history',
+ '`id_shop` = '.$shopId
+ .' AND `id_product` = '.$productId
+ .' AND `id_currency` = '.$currencyId
+ .' AND `id_country` = '.$countryId
+ .' AND `id_group` = '.$groupId
+ .' AND `id_product_attribute` = '.$attributeId
+ .' AND `date` = \''.$this->today.'\''
+ );
+ }
+
+ public function getGroupIds($shopId)
+ {
+ $ids = [$this->defaultGroupId];
+ if (!Group::isFeatureActive()) {
+ return $ids;
+ }
+ $query = 'SELECT `gs`.`id_group`
+ FROM `'._DB_PREFIX_.'group_shop` `gs`
+ WHERE `gs`.`id_shop` = '.$shopId;
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ if (($row['id_group'] != $this->defaultGroupId) && !in_array($row['id_group'], $this->ignoredGroups)) {
+ $ids[] = (int) $row['id_group'];
+ }
+ }
+ }
+ return $ids;
+ }
+
+ public function getCountryIds($shopId)
+ {
+ $ids = [$this->defaultCountryId];
+ if (Shop::isFeatureActive()) {
+ $ids = [Configuration::get('PS_COUNTRY_DEFAULT', null, null, $shopId)];
+ }
+ if (!$this->ignoreCountries) {
+ $query = 'SELECT `cs`.`id_country`
+ FROM `'._DB_PREFIX_.'country_shop` `cs`
+ LEFT JOIN `'._DB_PREFIX_.'country` `c` ON (`cs`.`id_country` = `c`.`id_country`)
+ WHERE `cs`.`id_shop` = '.$shopId
+ .' AND `c`.`active` = 1';
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ if (!in_array($row['id_country'], $ids)) {
+ if ($this->ignoreNonEuCountries) {
+ $country = new Country($row['id_country']);
+ if (in_array($country->iso_code, $this->euCountries)) {
+ $ids[] = (int) $row['id_country'];
+ }
+ } else {
+ $ids[] = (int) $row['id_country'];
+ }
+ }
+ }
+ }
+ }
+ return $ids;
+ }
+
+ public function getCurrencyIds($shopId)
+ {
+ $ids = [];
+ $query = 'SELECT `cs`.`id_currency`
+ FROM `'._DB_PREFIX_.'currency` c
+ LEFT JOIN `'._DB_PREFIX_.'currency_shop` cs ON (cs.`id_currency` = c.`id_currency`)
+ WHERE cs.`id_shop` = '.(int) $shopId
+ .' AND c.`active` = 1';
+ $currencies = Db::getInstance()->executeS($query);
+ foreach ($currencies as $currency) {
+ $ids[] = (int) $currency['id_currency'];
+ }
+ return $ids;
+ }
+
+ public function getProductIds($shopId)
+ {
+ $productIds = [];
+ $query = 'SELECT `ps`.`id_product` '
+ .' FROM `'._DB_PREFIX_.'product_shop` `ps`'
+ .' WHERE `ps`.`id_product` NOT IN '
+ .' (SELECT `id_product` FROM `'._DB_PREFIX_.'gm_omniprice_index`'
+ .' WHERE `date` = \''.$this->today.'\' AND `id_shop` = '.$shopId.')'
+ .($this->indexInactive ? ' ' : ' AND `ps`.`active` = 1 ')
+ .' AND `ps`.`id_shop` = '.$shopId.' '
+ .' ORDER BY `ps`.`id_product` ASC LIMIT '.$this->batchSize;
+
+ $res = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($query, true, false);
+ if ($res) {
+ foreach ($res as $row) {
+ $productIds[] = (int) $row['id_product'];
+ }
+ }
+ return $productIds;
+ }
+
+ public function getProductAttributeMap($shopId)
+ {
+ $map = [];
+ if (!$this->ignoreCombinations) {
+ $query = 'SELECT `id_product`, `id_product_attribute` '
+ .' FROM `'._DB_PREFIX_.'product_attribute_shop` '
+ .' WHERE `id_shop` = '.$shopId;
+ $res = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $map[(int) $row['id_product']][] = (int) $row['id_product_attribute'];
+ }
+ }
+ }
+ return $map;
+ }
+
+ public function getShopsIds()
+ {
+ $list = [];
+ $sql = 'SELECT `id_shop` FROM `'._DB_PREFIX_.'shop`
+ WHERE `active` = 1 AND `deleted` = 0';
+ $res = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($sql);
+ if ($res) {
+ foreach ($res as $row) {
+ $list[] = (int) $row['id_shop'];
+ }
+ }
+ return $list;
+ }
+
+ public function hookDisplayProductPriceBlock($hookParams)
+ {
+ if (($hookParams['type'] == 'after_price') &&
+ ((isset($hookParams['product']->id)) || (isset($hookParams['product']['id_product'])) || Tools::isSubmit('id_product') )) {
+ if (isset($hookParams['product']->id)) {
+ $productId = (int) $hookParams['product']->id;
+ } else if (isset($hookParams['product']['id_product'])) {
+ $productId = (int) $hookParams['product']['id_product'];
+ } else {
+ $productId = (int) Tools::getValue('id_product');
+ }
+ $showRealDiscount = $this->showRealDiscount;
+ if (Tools::isSubmit('omnipricetest')) {
+ $lowestCachedPrice = [
+ 'formatted' => Tools::getValue('omnipricetest'),
+ 'raw' => 1
+ ];
+ $showRealDiscount = false;
+ } else {
+ $params = $this->getCurrentParams($productId);
+ if (Tools::isSubmit('omnidebug')) {
+ var_export($params);
+ echo $this->context->country->iso_code;
+ }
+ if ($this->ignoreNonEuCountries) {
+ if (!in_array($this->context->country->iso_code, $this->euCountries)) {
+ return false;
+ }
+ }
+ $lowestCachedPrice = $this->getLowestCachedPrice($params);
+ }
+ $realDiscount = '';
+ if ($showRealDiscount && $lowestCachedPrice && isset($hookParams['product']['price_amount'])) {
+ $currentPrice = $hookParams['product']['price_amount'];
+ $previousPrice = $lowestCachedPrice['raw'];
+ $realDiscount = $this->calculateRealDisount($currentPrice, $previousPrice);
+ }
+ if (!$lowestCachedPrice) {
+ //may have a promotion for an individual combination
+ if (Tools::version_compare(_PS_VERSION_, '1.7.0.0', '<') && $this->hasAttributePrices($productId)) {
+ $lowestCachedPrice = [
+ 'formatted' => '---',
+ 'raw' => '0'
+ ];
+ }
+ }
+ if ($lowestCachedPrice) {
+ $this->context->smarty->assign(
+ [
+ 'gm_omniprice_lowest' => $lowestCachedPrice['formatted'],
+ 'gm_omniprice_lowest_raw' => $lowestCachedPrice['raw'],
+ 'gm_omniprice_days' => $this->daysBack,
+ 'gm_omniprice_color' => $this->textColor,
+ 'gm_omniprice_price_color' => $this->priceColor,
+ 'gm_omniprice_background' => $this->backgroundColor,
+ 'gm_omniprice_show_real_discount' => $showRealDiscount,
+ 'gm_omniprice_real_discount' => $realDiscount
+ ]
+ );
+ return $this->display(__FILE__, 'price.tpl');
+ }
+ }
+ }
+
+ public function calculateRealDisount($currentPrice, $previousPrice)
+ {
+ if (!$currentPrice || !$previousPrice) {
+ return false;
+ }
+ $realDiscount = '0%';
+ if ($currentPrice < $previousPrice) {
+ $discount = round((1 - $currentPrice / $previousPrice) * 100);
+ $realDiscount = '-'.$discount.'%';
+ }
+ if ($currentPrice > $previousPrice) {
+ $discount = round(($currentPrice / $previousPrice - 1) * 100);
+ $realDiscount = '+'.$discount.'%';
+ }
+ return $realDiscount;
+ }
+
+ public function getLowestCachedPrice($params)
+ {
+ $displayMethod = Group::getPriceDisplayMethod($params['id_group']);
+ if ($displayMethod) {
+ $field = '`price_tex`';
+ } else {
+ $field = '`price_tin`';
+ }
+ $price = Db::getInstance()->getValue('SELECT '.$field
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_cache`'
+ .' WHERE `id_shop` = '.$params['id_shop']
+ .' AND `id_product` = '.$params['id_product']
+ .' AND `id_product_attribute` = '.$params['id_product_attribute']
+ .' AND `id_currency` = '.$params['id_currency']
+ .' AND `id_country` = '.$params['id_country']
+ .' AND `id_group` = '.$params['id_group']
+ );
+ if ($price) {
+ return [
+ 'formatted' => $this->getFormattedPrice($price),
+ 'raw' => $price
+ ];
+ } else if ($params['id_product_attribute'] != 0) {
+ $price = Db::getInstance()->getValue('SELECT '.$field
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_cache`'
+ .' WHERE `id_shop` = '.$params['id_shop']
+ .' AND `id_product` = '.$params['id_product']
+ .' AND `id_product_attribute` = 0'
+ .' AND `id_currency` = '.$params['id_currency']
+ .' AND `id_country` = '.$params['id_country']
+ .' AND `id_group` = '.$params['id_group']
+ );
+ if ($price) {
+ return [
+ 'formatted' => $this->getFormattedPrice($price),
+ 'raw' => $price
+ ];
+ }
+ }
+ if (!$price) {
+ if ($this->showIfNotEnoughHistoricalData) {
+ return $this->getLatestHistoricalPrice($params);
+ }
+ }
+ return false;
+ }
+
+ protected function getLatestHistoricalPrice($params)
+ {
+ $displayMethod = Group::getPriceDisplayMethod($params['id_group']);
+ if ($displayMethod) {
+ $field = '`price_tex`';
+ $arrayField = 'price_tex';
+ } else {
+ $field = '`price_tin`';
+ $arrayField = 'price_tin';
+ }
+ $prices = Db::getInstance()->executeS('SELECT '.$field.', `is_specific_price`'
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_history`'
+ .' WHERE `id_shop` = '.$params['id_shop']
+ .' AND `id_product` = '.$params['id_product']
+ .' AND `id_currency` = '.$params['id_currency']
+ .' AND `id_country` = '.$params['id_country']
+ .' AND `id_group` = '.$params['id_group']
+ .' AND `id_product_attribute` = '.$params['id_product_attribute']
+ );
+ if ((count($prices) == 1) && ($prices[0]['is_specific_price'])) {
+ return
+ [
+ 'formatted' => $this->getFormattedPrice($prices[0][$arrayField]),
+ 'raw' => $prices[0][$arrayField]
+ ];
+ } else if ($params['id_product_attribute'] != 0) {
+ $prices = Db::getInstance()->executeS('SELECT '.$field.', `is_specific_price`'
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_history`'
+ .' WHERE `id_shop` = '.$params['id_shop']
+ .' AND `id_product` = '.$params['id_product']
+ .' AND `id_currency` = '.$params['id_currency']
+ .' AND `id_country` = '.$params['id_country']
+ .' AND `id_group` = '.$params['id_group']
+ .' AND `id_product_attribute` = 0'
+ );
+ if ((count($prices) == 1) && ($prices[0]['is_specific_price'])) {
+ return
+ [
+ 'formatted' => $this->getFormattedPrice($prices[0][$arrayField]),
+ 'raw' => $prices[0][$arrayField]
+ ];
+ }
+ }
+ return false;
+ }
+
+ public function getLowestCachedPricesForCombinations($params)
+ {
+ $prices = [];
+ $displayMethod = Group::getPriceDisplayMethod($params['id_group']);
+ if ($displayMethod) {
+ $field = '`price_tex`';
+ } else {
+ $field = '`price_tin`';
+ }
+ $result = Db::getInstance()->executeS('SELECT '.$field.' AS `price`, `id_product_attribute` '
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_cache`'
+ .' WHERE `id_shop` = '.$params['id_shop']
+ .' AND `id_product` = '.$params['id_product']
+ .' AND `id_currency` = '.$params['id_currency']
+ .' AND `id_country` = '.$params['id_country']
+ .' AND `id_group` = '.$params['id_group']
+ );
+ if ($result) {
+ foreach ($result as $row) {
+ $prices[$row['id_product_attribute']] = $this->getFormattedPrice($row['price']);
+ }
+ } else {
+ if ($this->showIfNotEnoughHistoricalData) {
+ $result = Db::getInstance()->executeS('SELECT '.$field.' AS `price`, `id_product_attribute` '
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_history`'
+ .' WHERE `id_shop` = '.$params['id_shop']
+ .' AND `id_product` = '.$params['id_product']
+ .' AND `id_currency` = '.$params['id_currency']
+ .' AND `id_country` = '.$params['id_country']
+ .' AND `id_group` = '.$params['id_group']
+ .' AND `is_specific_price` = 1 '
+ );
+ if ($result) {
+ foreach ($result as $row) {
+ $prices[$row['id_product_attribute']] = $this->getFormattedPrice($row['price']);
+ }
+ }
+ }
+ }
+ return $prices;
+ }
+
+ public function getFormattedPrice($price)
+ {
+ $context = Context::getContext();
+ if (isset($context->currentLocale)) {
+ return $context->currentLocale->formatPrice($price, $context->currency->iso_code);
+ } else {
+ return Tools::displayPrice($price);
+ }
+ }
+
+ public function hasAttributePrices($productId)
+ {
+ $res = Db::getInstance()->getValue('SELECT `id_product` FROM `'._DB_PREFIX_.'gm_omniprice_cache` '
+ .' WHERE `id_product` = '.$productId.' AND `id_product_attribute` > 0');
+ if ($res == $productId) {
+ return true;
+ }
+ if ($this->showIfNotEnoughHistoricalData) {
+ $res = Db::getInstance()->getValue('SELECT `id_product` FROM `'._DB_PREFIX_.'gm_omniprice_history` '
+ .' WHERE `id_product` = '.$productId.' AND `id_product_attribute` > 0 AND `is_specific_price` = 1');
+ if ($res == $productId) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ public function getCurrentParams($productId)
+ {
+ $params = [];
+ $params['id_shop'] = (int) $this->context->shop->id;
+ $params['id_currency'] = (int) $this->context->currency->id;
+ $params['id_product'] = (int) $productId;
+ if ($this->ignoreCombinations) {
+ $params['id_product_attribute'] = 0;
+ } else {
+ $params['id_product_attribute'] = $this->getIdProductAttribute($params['id_product']);
+ }
+ if ($this->ignoreCountries) {
+ $params['id_country'] = $this->defaultCountryId;
+ if (Shop::isFeatureActive()) {
+ $params['id_country'] = Configuration::get('PS_COUNTRY_DEFAULT', null, null, $params['id_shop']);
+ }
+ } else {
+ $params['id_country'] = $this->context->country->id;
+ }
+ $currentGroup = $this->context->customer->id_default_group;
+ if (in_array($currentGroup, $this->ignoredGroups)) {
+ $params['id_group'] = $this->defaultGroupId;
+ } else {
+ $params['id_group'] = $currentGroup;
+ }
+ return $params;
+ }
+
+ public function getDiscountedProductIds($shopId, $currencyId, $countryId, $groupId)
+ {
+ if ($this->globalRuleExists($shopId, $currencyId, $countryId, $groupId)) {
+ return $this->getAllProductIdsFromShop($shopId);
+ }
+ $beginning = null;
+ $ending = null;
+ if (Tools::version_compare(_PS_VERSION_, '1.6.1.10', '<=')) {
+ $now = date('Y-m-d H:i:00');
+ $beginning = $now;
+ $ending = $now;
+ }
+ $ids = SpecificPrice::getProductIdByDate($shopId, $currencyId, $countryId, $groupId, $beginning, $ending, 0, true);
+ return $ids;
+ }
+
+ protected function getAllProductIdsFromShop($shopId)
+ {
+ $ids = [];
+ $query = 'SELECT `id_product` FROM `'._DB_PREFIX_.'product_shop` WHERE `id_shop` = '.$shopId;
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $ids[] = [
+ 'id_product' => (int) $row['id_product'],
+ 'id_product_attribute' => 0
+ ];
+ }
+ }
+ return $ids;
+ }
+
+ public function globalRuleExists($shopId, $currencyId, $countryId, $groupId)
+ {
+ $query = 'SELECT `id_specific_price` FROM `'._DB_PREFIX_.'specific_price` '
+ .' WHERE (`id_shop` = 0 OR `id_shop` = '.$shopId.') '
+ .' AND (`id_currency` = 0 OR `id_currency` = '.$currencyId.') '
+ .' AND (`id_country` = 0 OR `id_country` = '.$countryId.') '
+ .' AND (`id_group` = 0 OR `id_group` = '.$groupId.') '
+ .' AND (`from` <= NOW() OR `from` = \'0000-00-00 00:00:00\') '
+ .' AND (`to` >= NOW() OR `to` = \'0000-00-00 00:00:00\' ) '
+ .' AND `id_product` = 0 '
+ .' AND `id_product_attribute` = 0 '
+ .' AND `from_quantity` > 0 ';
+ $result = (int) Db::getInstance()->getValue($query);
+ return ($result > 0);
+ }
+
+ public function getIdProductAttribute($productId)
+ {
+ $idProductAttribute = $this->getIdProductAttributeByGroup($productId);
+ if (null === $idProductAttribute) {
+ $idProductAttribute = (int) Tools::getValue('id_product_attribute');
+ }
+ if (!$idProductAttribute) {
+ $idProductAttribute = $this->getDefaultAttributeIdForProduct($productId);
+ }
+ return $idProductAttribute;
+ }
+
+ protected function getDefaultAttributeIdForProduct($productId)
+ {
+ $shopId = $this->context->shop->id;
+ return (int) Db::getInstance()->getValue('SELECT `id_product_attribute` FROM `'._DB_PREFIX_.'product_attribute_shop` '
+ .' WHERE `default_on` = 1 AND `id_shop` = '.$shopId.' AND `id_product` = '.$productId);
+ }
+
+ protected function getIdProductAttributeByGroup($productId)
+ {
+ $groups = Tools::getValue('group');
+ if (empty($groups)) {
+ return null;
+ }
+ return (int) Product::getIdProductAttributeByIdAttributes(
+ $productId, $groups, true
+ );
+ }
+
+ public function hookActionFrontControllerSetMedia($params)
+ {
+ $this->context->controller->registerStylesheet(
+ 'module-gm_omniprice-style', 'modules/'.$this->name.'/views/css/gm_omniprice.css',
+ [
+ 'media' => 'all',
+ 'priority' => 200,
+ ]
+ );
+ }
+
+ protected function displayInfo()
+ {
+ $output = '
'
+ .'
'
+ .$this->l('Gathering price history')
+ .'
';
+ $indexUrl = $this->context->link->getModuleLink($this->name, 'cron',
+ [
+ 'action' => 'index',
+ 'token' => $this->token
+ ]);
+ $output .= '
';
+ $output .= '
';
+ $output .= '
'
+ .'
'
+ .$this->l('Cleaning old price history')
+ .'
';
+ $cleanupUrl = $this->context->link->getModuleLink($this->name, 'cron',
+ [
+ 'action' => 'cleanup',
+ 'token' => $this->token
+ ]);
+ $output .= '
';
+ $output .= '
';
+ return $output;
+ }
+
+ protected function displayInformationPanel()
+ {
+ $output = '
'
+ .'
'
+ .$this->l('Information')
+ .'
';
+ if (!defined('_TB_VERSION_')) { //TB has a nasty bug here
+ $output .= '
'.$this->l('Groups with no customers:').' '.implode(', ', $this->findEmptyGroups()).'
';
+ }
+ $output .= '
'.$this->l('Groups with group reductions:').' '.implode(', ', $this->findGroupsWithGroupReduction()).'
';
+ $output .= '
'.$this->l('Groups with specific prices:').' '.implode(', ', $this->findGroupsWithSpecificPrices()).'
';
+ $output .= '
'.$this->l('Groups with specific price rules:').' '.implode(', ', $this->findGroupsWithSpecifiPriceRules()).'
';
+ $output .= '
'.$this->l('Products have combinations with price impacts:').' '.($this->getCombinationsPriceImpactsInfo() ? $this->l('Yes') : $this->l('No')).'
';
+ $output .= '
'.$this->l('Individual combinations have discounts:').' '.($this->getCombinationsDiscountsInfo() ? $this->l('Yes') : $this->l('No')).'
';
+ $output .= '
'.$this->l('Number of active countries:').' '.$this->countActiveCountries().'
';
+ $output .= '
'.$this->l('Number of active currencies:').' '.$this->countActiveCurrencies().'
';
+ $output .= '
'.$this->l('Number of prices stored in history:').' '.$this->countStoredPrices().'
';
+ $output .= '
';
+ return $output;
+ }
+
+ protected function countActiveCurrencies()
+ {
+ return (int) Db::getInstance()->getValue('SELECT COUNT(`id_currency`) FROM `'._DB_PREFIX_.'currency` WHERE `active` = 1');
+ }
+
+ protected function countActiveCountries()
+ {
+ return (int) Db::getInstance()->getValue('SELECT COUNT(`id_country`) FROM `'._DB_PREFIX_.'country` WHERE `active` = 1');
+ }
+
+ protected function countStoredPrices()
+ {
+ return (int) Db::getInstance()->getValue('SELECT COUNT(`id_product`) FROM `'._DB_PREFIX_.'gm_omniprice_history`');
+ }
+
+ protected function getCombinationsPriceImpactsInfo()
+ {
+ $query = 'SELECT `id_product` FROM `'._DB_PREFIX_.'product_attribute` WHERE `price` != 0';
+ $res = Db::getInstance()->getValue($query);
+ if ($res) {
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ protected function getCombinationsDiscountsInfo()
+ {
+ $query = 'SELECT `id_product` FROM `'._DB_PREFIX_.'specific_price` WHERE `id_product_attribute` > 0';
+ $res = Db::getInstance()->getValue($query);
+ if ($res) {
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ protected function getGroupNames()
+ {
+ $langId = $this->context->language->id;
+ $query = 'SELECT `id_group`, `name` FROM `'._DB_PREFIX_.'group_lang` WHERE `id_lang` = '.$langId;
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $this->groupNames[(int) $row['id_group']] = $row['name'];
+ }
+ }
+ }
+
+ protected function findGroupsToSafelyIgnore()
+ {
+ $groups = $this->findEmptyGroups(true);
+ $guestGroupId = Configuration::get('PS_GUEST_GROUP');
+ $unidentifiedGroupId = Configuration::get('PS_UNIDENTIFIED_GROUP');
+ $groups[] = $guestGroupId;
+ $groups[] = $unidentifiedGroupId;
+ $groups = array_unique($groups);
+ sort($groups);
+ $ignoredGroups = [];
+ foreach ($groups as $groupId) {
+ if ($groupId != $this->defaultGroupId) {
+ $ignoredGroups[] = $groupId;
+ }
+ }
+ return $ignoredGroups;
+ }
+
+ protected function findEmptyGroups($returnIds = false)
+ {
+ $emptyGroups = [];
+ $emptyIds = [];
+ $res = Group::getGroups($this->context->language->id);
+ foreach ($res as $row) {
+ $group = new Group((int) $row['id_group']);
+ $customerCount = $group->getCustomers(true);
+ if ($customerCount < 1) {
+ $emptyGroups[] = $row['name'];
+ $emptyIds[] = $row['id_group'];
+ }
+ }
+ if ($returnIds) {
+ return $emptyIds;
+ }
+ if (!count($emptyGroups)) {
+ return [$this->l('None')];
+ }
+ return $emptyGroups;
+ }
+
+ protected function findGroupsWithSpecifiPriceRules()
+ {
+ $groupIds = [];
+ $query = 'SELECT `id_group` FROM `'._DB_PREFIX_.'specific_price_rule` WHERE `id_group` > 0';
+ $res = Db::getInstance()->executes($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $groupIds[] = (int) $row['id_group'];
+ }
+ }
+ $groupIds = array_unique($groupIds);
+ sort($groupIds);
+ return $this->getGroupNamesForIds($groupIds);
+ }
+
+ protected function findGroupsWithSpecificPrices()
+ {
+ $groupIds = [];
+ $query = 'SELECT `id_group` FROM `'._DB_PREFIX_.'specific_price` WHERE `id_group` > 0';
+ $res = Db::getInstance()->executes($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $groupIds[] = (int) $row['id_group'];
+ }
+ }
+ $groupIds = array_unique($groupIds);
+ sort($groupIds);
+ return $this->getGroupNamesForIds($groupIds);
+ }
+
+ protected function findGroupsWithGroupReduction()
+ {
+ $groupIds = [];
+ $query = 'SELECT `id_group` FROM `'._DB_PREFIX_.'group` WHERE `reduction` > 0';
+ $res = Db::getInstance()->executes($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $groupIds[] = (int) $row['id_group'];
+ }
+ }
+ $query = 'SELECT `id_group` FROM `'._DB_PREFIX_.'group_reduction` WHERE `reduction` > 0';
+ $res = Db::getInstance()->executes($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $groupIds[] = (int) $row['id_group'];
+ }
+ }
+ $groupIds = array_unique($groupIds);
+ sort($groupIds);
+ return $this->getGroupNamesForIds($groupIds);
+ }
+
+ protected function getGroupNamesForIds($groupIds)
+ {
+ if (!count($groupIds)) {
+ return [$this->l('None')];
+ }
+ $names = [];
+ $this->getGroupNames();
+ foreach ($groupIds as $groupId) {
+ $names[] = $this->groupNames[$groupId];
+ }
+ return $names;
+ }
+
+ public function hookActionProductUpdate($params)
+ {
+ $productId = $params['id_product'];
+ $this->reindexProduct($productId);
+ }
+
+ public function hookActionObjectSpecificPriceAddAfter($params)
+ {
+ $sp = $params['object'];
+ if ($sp->id_product) {
+ $this->reindexProduct($sp->id_product);
+ }
+ }
+
+ public function hookActionObjectSpecificPriceUpdateAfter($params)
+ {
+ $sp = $params['object'];
+ if ($sp->id_product) {
+ $this->reindexProduct($sp->id_product);
+ }
+ }
+
+ public function hookActionObjectSpecificPriceDeleteAfter($params)
+ {
+ $sp = $params['object'];
+ if ($sp->id_product) {
+ $this->reindexProduct($sp->id_product);
+ }
+ }
+
+ public function reindexProduct($productId)
+ {
+ $this->removeProductFromTodaysIndex($productId);
+ $this->removeProductFromTodaysHistory($productId);
+ if ($this->reindexOnSave) {
+ $this->savePrices(false, $productId);
+ }
+ }
+
+ public function resetIndex()
+ {
+ Db::getInstance()->delete('gm_omniprice_index');
+ Db::getInstance()->delete('gm_omniprice_history', '`date` = \''.$this->today.'\'');
+ }
+
+ public function removeProductFromTodaysIndex($productId)
+ {
+ Db::getInstance()->delete('gm_omniprice_index', '`id_product` = '.$productId.' AND `date` = \''.$this->today.'\'');
+ }
+
+ public function removeProductFromTodaysHistory($productId)
+ {
+ Db::getInstance()->delete('gm_omniprice_history', '`id_product` = '.$productId.' AND `date` = \''.$this->today.'\'');
+ }
+
+ public function hookDisplayHeader($params)
+ {
+ if (Tools::isSubmit('id_product')) {
+ $this->context->controller->addCSS($this->_path.'views/css/gm_omniprice.css', 'all');
+ if (!$this->ignoreCombinations) {
+ $params = $this->getCurrentParams((int) Tools::getValue('id_product'));
+ $prices = $this->getLowestCachedPricesForCombinations($params);
+ if (count($prices) > 0) {
+ $this->context->controller->addJS($this->_path.'views/js/gm_omniprice.js');
+ Media::addJsDef(['gm_omniprice_attr_prices' => $prices]);
+ }
+ }
+ }
+ }
+
+ public function cleanUp($verbose = false)
+ {
+ $output = '';
+ //general cleanup
+ if (Tools::issubmit('zero')) {
+ Db::getInstance()->delete('gm_omniprice_history', '`price_tin` < 0.001');
+ Db::getInstance()->delete('gm_omniprice_cache', '`price_tin` < 0.001');
+ }
+ Db::getInstance()->delete('gm_omniprice_history', '`id_product` NOT IN (SELECT `id_product` FROM `'._DB_PREFIX_.'product`)');
+ Db::getInstance()->delete('gm_omniprice_cache', '`id_product` NOT IN (SELECT `id_product` FROM `'._DB_PREFIX_.'product`)');
+ Db::getInstance()->delete('gm_omniprice_history',
+ '`id_product_attribute` > 0 AND `id_product_attribute` NOT IN (SELECT `id_product_attribute` FROM `'._DB_PREFIX_.'product_attribute`)');
+ Db::getInstance()->delete('gm_omniprice_cache',
+ '`id_product_attribute` > 0 AND `id_product_attribute` NOT IN (SELECT `id_product_attribute` FROM `'._DB_PREFIX_.'product_attribute`)');
+ Db::getInstance()->delete('gm_omniprice_history', '`id_shop` NOT IN (SELECT `id_shop` FROM `'._DB_PREFIX_.'shop`)');
+ Db::getInstance()->delete('gm_omniprice_cache', '`id_shop` NOT IN (SELECT `id_shop` FROM `'._DB_PREFIX_.'shop`)');
+ Db::getInstance()->delete('gm_omniprice_history', '`id_currency` NOT IN (SELECT `id_currency` FROM `'._DB_PREFIX_.'currency`)');
+ Db::getInstance()->delete('gm_omniprice_cache', '`id_currency` NOT IN (SELECT `id_currency` FROM `'._DB_PREFIX_.'currency`)');
+ Db::getInstance()->delete('gm_omniprice_history', '`id_group` NOT IN (SELECT `id_group` FROM `'._DB_PREFIX_.'group`)');
+ Db::getInstance()->delete('gm_omniprice_cache', '`id_group` NOT IN (SELECT `id_group` FROM `'._DB_PREFIX_.'group`)');
+ Db::getInstance()->delete('gm_omniprice_history', '`id_country` NOT IN (SELECT `id_country` FROM `'._DB_PREFIX_.'country` WHERE `active` = 1)');
+ Db::getInstance()->delete('gm_omniprice_cache', '`id_country` NOT IN (SELECT `id_country` FROM `'._DB_PREFIX_.'country` WHERE `active` = 1)');
+ if ($this->ignoreCountries) {
+ if (Shop::isFeatureActive()) {
+ //for the future
+ } else {
+ Db::getInstance()->delete('gm_omniprice_history', '`id_country` != '.$this->defaultCountryId);
+ Db::getInstance()->delete('gm_omniprice_cache', '`id_country` != '.$this->defaultCountryId);
+ }
+ }
+ foreach ($this->ignoredGroups as $ignoredGroupId) {
+ if ($ignoredGroupId && ((int) $ignoredGroupId !== (int) $this->defaultGroupId)) {
+ Db::getInstance()->delete('gm_omniprice_history', '`id_group` = '.$ignoredGroupId);
+ Db::getInstance()->delete('gm_omniprice_cache', '`id_group` = '.$ignoredGroupId);
+ }
+ }
+ $date = date("Y-m-d", strtotime("-".$this->daysBack." days"));
+ $output .= $this->l('Period').': '.$this->daysBack.' ('.$date.')
';
+ $shopIds = $this->getShopsIds();
+ foreach ($shopIds as $shopId) {
+ $currencyIds = $this->getCurrencyIds($shopId);
+ $countryIds = $this->getCountryIds($shopId);
+ $groupIds = $this->getGroupIds($shopId);
+ $productIds = $this->getProductIdsInHistory($shopId);
+ foreach ($currencyIds as $currencyId) {
+ foreach ($countryIds as $countryId) {
+ foreach ($groupIds as $groupId) {
+ foreach ($productIds as $productId) {
+ $query = 'SELECT `date`, `id_product`, `id_product_attribute` FROM `'._DB_PREFIX_.'gm_omniprice_history` '
+ .' WHERE `id_shop` = '.$shopId.' AND `id_product` = '.$productId.' AND `id_currency` = '.$currencyId.
+ ' AND `id_country` = '.$countryId.' AND `id_group` = '.$groupId.' ORDER BY `date` ASC';
+ $res = Db::getInstance()->executeS($query);
+ $datesMap = [];
+ if ($res) {
+ foreach ($res as $row) {
+ $day = $row['date'];
+ $productId = $row['id_product'];
+ $attributeId = $row['id_product_attribute'];
+ if ($day < $date) {
+ $datesMap[$productId][$attributeId][] = $day;
+ }
+ }
+ foreach ($datesMap as $productId => $dateItem) {
+ foreach ($dateItem as $attributeId => $dates) {
+ $output .= "Product ID {$productId}, attribute ID: {$attributeId}
";
+ $datesCount = count($dates);
+ if ($datesCount > 2) {
+ for ($i = 0; $i < $datesCount - 2; $i++) {
+ $output .= ' '.$dates[$i].' '.$this->l('this price may be deleted').'
';
+ $where = '`id_shop` = '.$shopId.' AND `id_currency` = '.$currencyId.
+ ' AND `id_country` = '.$countryId.' AND `id_group` = '.$groupId;
+ $where .= ' AND `id_product` = '.$productId.' AND `id_product_attribute` = '.$attributeId;
+ $where .= ' AND `date` = \''.$dates[$i].'\'';
+ Db::getInstance()->delete('gm_omniprice_history', $where);
+ }
+ }
+ $output .= ' '.$dates[$datesCount - 1].' '.$this->l('this price is still needed').'
';
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+
+ if ($verbose) {
+ echo '
';
+ echo $output;
+ }
+ }
+
+ protected function getProductIdsInHistory($shopId)
+ {
+ $ids = [];
+ $query = 'SELECT DISTINCT `id_product` FROM `'._DB_PREFIX_.'gm_omniprice_history` '
+ .' WHERE `id_shop` = '.$shopId;
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $ids[] = (int) $row['id_product'];
+ }
+ }
+ return $ids;
+ }
+
+ public function hookDisplayAdminProductsExtra(array $params)
+ {
+ $data = [];
+ if (isset($params['id_product'])) {
+ $productId = (int) $params['id_product'];
+ } else {
+ $productId = (int) Tools::getValue('id_product');
+ }
+ $shopId = (int) $this->context->shop->id;
+ $currencyId = (int) $this->defaultCurrencyId;
+ if (Shop::isFeatureActive()) {
+ $currencyId = Configuration::get('PS_CURRENCY_DEFAULT', null, null, $shopId);
+ }
+ $countryId = (int) $this->defaultCountryId;
+ if (Shop::isFeatureActive()) {
+ $countryId = Configuration::get('PS_COUNTRY_DEFAULT', null, null, $shopId);
+ }
+ $groupId = (int) $this->defaultGroupId;
+ $attributeId = 0;
+
+ $query = 'SELECT `date`, `price_tin`, `is_specific_price` '
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_history`'
+ .' WHERE `id_shop` = '.$shopId
+ .' AND `id_product` = '.$productId
+ .' AND `id_product_attribute` = '.$attributeId
+ .' AND `id_currency` = '.$currencyId
+ .' AND `id_country` = '.$countryId
+ .' AND `id_group` = '.$groupId
+ .' ORDER BY `date` DESC';
+
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $data[$row['date']] = [
+ 'date' => $row['date'],
+ 'price_tin' => $row['price_tin'],
+ 'is_specific_price' => $row['is_specific_price'],
+ 'type' => ($row['is_specific_price'] ? $this->l('Reduced price') : $this->l('Regular price'))
+ ];
+ }
+ }
+
+ $query = 'SELECT `date`, `price_tin` '
+ .' FROM `'._DB_PREFIX_.'gm_omniprice_cache`'
+ .' WHERE `id_shop` = '.$shopId
+ .' AND `id_product` = '.$productId
+ .' AND `id_product_attribute` = '.$attributeId
+ .' AND `id_currency` = '.$currencyId
+ .' AND `id_country` = '.$countryId
+ .' AND `id_group` = '.$groupId
+ .' ORDER BY `date` DESC';
+
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ if (!array_key_exists($row['date'], $data)) {
+ $data[$row['date']] = [
+ 'date' => $row['date'],
+ 'price_tin' => $row['price_tin'],
+ 'is_specific_price' => '',
+ 'type' => $this->l('Lowest previous price')
+ ];
+ }
+ }
+ }
+ krsort($data);
+ $indexed = (int) Db::getInstance()->getValue('SELECT `id_product` FROM `'._DB_PREFIX_.'gm_omniprice_index` WHERE `id_product` = '.$productId.
+ ' AND `date` = \''.$this->today.'\'');
+ $this->context->smarty->assign(array(
+ 'historyData' => $data,
+ 'indexedToday' => $indexed
+ ));
+ $debug = '';
+ if (Tools::isSubmit('omnidebug')) {
+ $res = Db::getInstance()->executeS('SELECT * FROM `'._DB_PREFIX_.'gm_omniprice_history` WHERE `id_product` = '.$productId.' ORDER BY `date` DESC');
+ if ($res) {
+ $debug = $this->displayTable($res, array_keys($res[0]));
+ }
+ }
+ return $this->display(__FILE__, 'tab.tpl').$debug;
+ }
+
+ public function displayTable($data, $columns)
+ {
+ $output = ' ';
+ $output .= '';
+ $output .= '';
+ foreach ($columns as $columnHeader) {
+ $output .= ''.$columnHeader.' ';
+ }
+ $output .= ' ';
+ $output .= '';
+ foreach ($data as $row) {
+ $output .= '';
+ foreach ($columns as $key) {
+ $output .= ''.$row[$key].' ';
+ }
+ $output .= ' ';
+ }
+ $output .= '
';
+ return $output;
+ }
+
+ public function hookActionGetProductPropertiesAfter($params)
+ {
+ return;
+ $product = &$params['product'];
+ $sp = $product['specific_prices'];
+ //var_export($product);
+ $sp['reduction'] = (string) (rand(0, 10) / 100);
+ $product['specific_prices'] = $sp;
+ }
+
+ public function fillMissingCache($verbose = false)
+ {
+ $output = '';
+ $query = 'SELECT * FROM `'._DB_PREFIX_.'gm_omniprice_history` '
+ .' WHERE `is_specific_price` = 1 AND `id_product` IN (SELECT `id_product` FROM `'._DB_PREFIX_.'product` WHERE `active` = 1)'
+ .' ORDER BY `date` DESC ';
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $lowestPrice = $this->getLowestCachedPrice($row);
+ if ($lowestPrice === false) {
+ $shopId = (int) $row['id_shop'];
+ $productId = (int) $row['id_product'];
+ $groupId = (int) $row['id_group'];
+ $currencyId = (int) $row['id_currency'];
+ $countryId = (int) $row['id_country'];
+ $attributeId = (int) $row['id_product_attribute'];
+ $output .= var_export($row, true).'
';
+ $output .= ' - no lowest price!
';
+ $lastChangeDate = $row['date'];
+ $output .= ' Look for the lowest price before '.$lastChangeDate.'
';
+ $now = time();
+ $your_date = strtotime($row['date']);
+ $datediff = $now - $your_date;
+ $daysOffset = floor($datediff / (60 * 60 * 24));
+ $output .= ' days offset: '.$daysOffset.'
';
+ $lowestPrices = $this->getLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $daysOffset);
+ if ($lowestPrices) {
+ $output .= ' found price: '.$lowestPrices['price_tin'].' ('.$lowestPrices['price_tex'].')
';
+ $this->saveLowestPrice($shopId, $productId, $currencyId, $countryId, $groupId, $attributeId, $lowestPrices['price_tex'],
+ $lowestPrices['price_tin'], $lowestPrices['date']);
+ }
+ }
+ }
+ }
+ if ($verbose) {
+ echo $output;
+ }
+ }
+
+ public function getActiveMap()
+ {
+ if ($this->activeMap == null) {
+ $query = 'SELECT `id_shop`, `id_product`, `active` FROM `'._DB_PREFIX_.'product_shop`';
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $this->activeMap[(int) $row['id_shop']][(int) $row['id_product']] = (int) $row['active'];
+ }
+ }
+ }
+ return $this->activeMap;
+ }
+
+ public function productIsActive($productId, $shopId)
+ {
+ $activeMap = $this->getActiveMap();
+ if (isset($activeMap[$shopId][$productId])) {
+ return ($activeMap[$shopId][$productId] == 1);
+ }
+ return false;
+ }
+
+ public function getCostPriceMap()
+ {
+ $map = [];
+ $query = 'SELECT `id_product`, `id_shop`, `wholesale_price` FROM `'._DB_PREFIX_.'product_shop` WHERE `wholesale_price` > 0';
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $shopId = (int) $row['id_shop'];
+ $productId = (int) $row['id_product'];
+ $costPrice = $row['wholesale_price'];
+ $map[$shopId][$productId][0] = $costPrice;
+ }
+ }
+
+ $query = 'SELECT `id_product`, `id_product_attribute`, `id_shop`, `wholesale_price` FROM `'._DB_PREFIX_.'product_attribute_shop` WHERE `wholesale_price` > 0';
+ $res = Db::getInstance()->executeS($query);
+ if ($res) {
+ foreach ($res as $row) {
+ $shopId = (int) $row['id_shop'];
+ $productId = (int) $row['id_product'];
+ $attributeId = (int) $row['id_product_attribute'];
+ $costPrice = $row['wholesale_price'];
+ $map[$shopId][$productId][$attributeId] = $costPrice;
+ }
+ }
+ return $map;
+ }
+
+ public function getConversionRates()
+ {
+ $rates = [];
+ $currencies = Db::getInstance()->executeS('
SELECT `id_shop`, `id_currency`, `conversion_rate`
- FROM `' . _DB_PREFIX_ . 'currency_shop`');
- if ($currencies)
- {
- foreach ($currencies as $currency)
- {
- $shopId = (int) $currency['id_shop'];
- $currencyId = (int) $currency['id_currency'];
- $rate = $currency['conversion_rate'];
- $rates[$currencyId][$shopId] = $rate;
- }
+ FROM `'._DB_PREFIX_.'currency_shop`');
+ if ($currencies) {
+ foreach ($currencies as $currency) {
+ $shopId = (int) $currency['id_shop'];
+ $currencyId = (int) $currency['id_currency'];
+ $rate = $currency['conversion_rate'];
+ $rates[$currencyId][$shopId] = $rate;
+ }
+ }
+ return $rates;
}
- return $rates;
- }
- public function checkIfProductIsSoldBelowCost($priceTex, $costPriceMap, $rates, $shopId, $productId, $attributeId, $currencyId)
- {
- $conversionRate = $rates[$currencyId][$shopId];
- $costPrice = $costPriceMap[$shopId][$productId][$attributeId];
- $convertedCostPrice = $costPrice / $conversionRate;
- return ($priceTex < $convertedCostPrice);
- }
+ public function checkIfProductIsSoldBelowCost($priceTex, $costPriceMap, $rates, $shopId, $productId, $attributeId, $currencyId)
+ {
+ $conversionRate = $rates[$currencyId][$shopId];
+ $costPrice = $costPriceMap[$shopId][$productId][$attributeId];
+ $convertedCostPrice = $costPrice / $conversionRate;
+ return ($priceTex < $convertedCostPrice);
+ }
- protected function displayGreenMouseModulesPanel()
- {
- $url = 'https://codecanyon.net/user/greenmousestudio/portfolio';
- $isoCode = Context::getContext()->language->iso_code;
- $translations = [
- 'en' => "Check out more
PrestaShop modules from GreenMouseStudio ",
- 'fr' => "Découvrez plus de
modules PrestaShop de GreenMouseStudio ",
- 'es' => "Descubra más
módulos de PrestaShop de GreenMouseStudio ",
- 'de' => "Entdecken Sie mehr
PrestaShop-Module von GreenMouseStudio ",
- 'it' => "Scopri di più
moduli PrestaShop di GreenMouseStudio ",
- 'pl' => "Zobacz więcej
modułów PrestaShop od GreenMouseStudio ",
- 'pt' => "Confira mais
módulos PrestaShop do GreenMouseStudio ",
- 'nl' => "Bekijk meer
PrestaShop-modules van GreenMouseStudio ",
- 'sv' => "Upptäck fler
PrestaShop-moduler från GreenMouseStudio ",
- 'da' => "Se flere
PrestaShop-moduler fra GreenMouseStudio ",
- 'fi' => "Tutustu lisää
GreenMouseStudion PrestaShop-moduuleihin ",
- 'cs' => "Podívejte se na další
moduly PrestaShop od GreenMouseStudio ",
- 'sk' => "Pozrite si viac
modulov PrestaShop od GreenMouseStudio ",
- 'hu' => "Nézzen meg több
PrestaShop modult a GreenMouseStudio-tól ",
- 'ro' => "Descoperiți mai multe
module PrestaShop de la GreenMouseStudio ",
- 'el' => "Δείτε περισσότερες
μονάδες PrestaShop από το GreenMouseStudio ",
- ];
- $message = isset($translations[$isoCode]) ? $translations[$isoCode] : $translations['en'];
- $content = '';
- $content .= '
' . $message . '
';
- return $content;
- }
+ protected function displayGreenMouseModulesPanel()
+ {
+ $url = 'https://codecanyon.net/user/greenmousestudio/portfolio';
+ $isoCode = Context::getContext()->language->iso_code;
+ $translations = [
+ 'en' => "Check out more
PrestaShop modules from GreenMouseStudio ",
+ 'fr' => "Découvrez plus de
modules PrestaShop de GreenMouseStudio ",
+ 'es' => "Descubra más
módulos de PrestaShop de GreenMouseStudio ",
+ 'de' => "Entdecken Sie mehr
PrestaShop-Module von GreenMouseStudio ",
+ 'it' => "Scopri di più
moduli PrestaShop di GreenMouseStudio ",
+ 'pl' => "Zobacz więcej
modułów PrestaShop od GreenMouseStudio ",
+ 'pt' => "Confira mais
módulos PrestaShop do GreenMouseStudio ",
+ 'nl' => "Bekijk meer
PrestaShop-modules van GreenMouseStudio ",
+ 'sv' => "Upptäck fler
PrestaShop-moduler från GreenMouseStudio ",
+ 'da' => "Se flere
PrestaShop-moduler fra GreenMouseStudio ",
+ 'fi' => "Tutustu lisää
GreenMouseStudion PrestaShop-moduuleihin ",
+ 'cs' => "Podívejte se na další
moduly PrestaShop od GreenMouseStudio ",
+ 'sk' => "Pozrite si viac
modulov PrestaShop od GreenMouseStudio ",
+ 'hu' => "Nézzen meg több
PrestaShop modult a GreenMouseStudio-tól ",
+ 'ro' => "Descoperiți mai multe
module PrestaShop de la GreenMouseStudio ",
+ 'el' => "Δείτε περισσότερες
μονάδες PrestaShop από το GreenMouseStudio ",
+ ];
+ $message = isset($translations[$isoCode]) ? $translations[$isoCode] : $translations['en'];
+ $content = '';
+ $content .= '
'.$message.'
';
+ return $content;
+ }
+
+ public function getTokenForScripts()
+ {
+ if (method_exists('Tools', 'encrypt')) {
+ return Tools::encrypt($this->name);
+ } elseif (method_exists('Tools', 'hash')) {
+ return Tools::hash($this->name);
+ } else {
+ return hash('sha256', $this->name._COOKIE_KEY_);
+ }
+ }
}
diff --git a/modules/gm_omniprice/translations/de.php b/modules/gm_omniprice/translations/de.php
new file mode 100644
index 00000000..80da4cc9
--- /dev/null
+++ b/modules/gm_omniprice/translations/de.php
@@ -0,0 +1,80 @@
+gm_omniprice_90a0c7b2104a67d391df6f2db66300e3'] = 'OmniPrice - Preiskonformität mit der Omnibus-Richtlinie';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2f2aaa2e0f7ba09de9a5f449ba5f45af'] = 'Zeigt Informationen über den niedrigsten Preis vor dem Rabatt an';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c888438d14855d7d96a2724ee9c306bd'] = 'Einstellungen gespeichert';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1901606ea069a83dc7beea17881ef95a'] = 'Zeitraum';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b1e1f9076cca4dd59d55975e7a318f38'] = 'Anzahl der Tage vor der Aktion zur Analyse';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_62fefba7aea0bdb51b8935c165195610'] = 'Länder ignorieren';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_93cba07454f06a4a960172bbd6e2a435'] = 'Ja';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bafd7322c6e97d25b6299b5d6fe8920b'] = 'Nein';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dc4143a87bf30fc020b5285c0943567c'] = 'Analysiere Preise nur für das Standardland, Kunden aus anderen Ländern sehen die Preise des Standardlandes';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7f01c3611adcbec6862b1c4001f0f300'] = 'Länder außerhalb der EU ignorieren';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f0e0af7ffec706830ed933f0aa52c841'] = 'Ignoriert vollständig Länder außerhalb der EU, Kunden aus diesen Ländern sehen keine Informationen zu früheren Preisen';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b7b08b9fdd4d8d7a01eaf832777db241'] = 'Kombinationen ignorieren';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a9a3387e6b5111e07b969cfa06d68586'] = 'Analysiere Preise nur für die Standardkombination des Produkts, empfohlen, wenn Kombinationen keinen Einfluss auf den Preis haben';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_09c12c14a8bdcb5579a6163a4ce736e8'] = 'Ignorierte Gruppen';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c8885049351230f4d9e65f2997e2de57'] = 'Ignoriere ausgewählte Gruppen, Kunden dieser Gruppen sehen den Preis der Standardgruppe (Kunde), empfohlen, wenn keine Gruppenrabatte verwendet werden';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1300769d8d72fc8218b40772f1c25efc'] = 'Produktpaket';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_419e727dd8d9ac44fd248de2eda589b4'] = 'Anzahl der Produkte, die pro Ausführung eines Cron-Jobs verarbeitet werden';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e09109328229ca6967e3ea981ee158dd'] = 'Neuindexierung beim Speichern des Produkts';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bd0b2b3a1ded97ddd1d70591f1af8960'] = 'Produkt wird beim Speichern neu indexiert';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_368d9ac76af05f714092bc808a426bfc'] = 'Hintergrundfarbe';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_5f111ae4c490902059da2004cbc8b424'] = 'Textfarbe';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_d6a3bb2945a3fa2ac63739ec31c00060'] = 'Preisfarbe';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_ad1338e53c6bec090eaab52628716805'] = 'Nachricht auch bei unzureichendem Verlauf anzeigen';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_0a7291f2167ca2f321c44157ded8e2f8'] = 'Für reduzierte Produkte ohne Informationen zu früheren Preisen wird der einzige gespeicherte Aktionspreis als historisch niedrigster Preis angezeigt';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38ce18494ca0426bdbd483c5c4cf9ec2'] = 'Inaktive Produkte indexieren';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_37d66737bda18cffdc0342145c644e52'] = 'Speichert die Preisverlaufshistorie des Produkts, auch wenn es inaktiv ist';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_90ce4a97e9f26453b3deca306fa6a1d5'] = 'Zeigt den tatsächlichen Rabatt im Vergleich zum vorherigen Preis an';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dad8fdc91311e7e8cd8431bc54036090'] = 'Zeigt die prozentuale Differenz zwischen dem aktuellen Produktpreis und dem niedrigsten vorherigen Preis an';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8dcea44ea2df2fb48f9f2eab63cbe8e6'] = 'Produkte ignorieren, die unter den Kosten verkauft werden';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f4f70727dc34561dfde1a3c529b6205c'] = 'Einstellungen';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c9cc8cce247e49bae79f15173ce97354'] = 'Speichern';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1033eb0896e0e3ccde90fe8ea13c1fb2'] = 'ID des Standardlandes:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f770b9c02b33fe4e7246f96b12887a01'] = 'ID der Standardgruppe:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_212713efb37cd2f521ee584f1dbb5f0b'] = 'ID des Geschäfts:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_36f12776fd15f301a8b51336b49a7043'] = 'Alle Produkte wurden indexiert';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f2f4e21b8a93962f211c50a54d20653d'] = 'Das ist noch nicht alles, starte mich erneut';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_97f08a40f22a625d0cbfe03db3349108'] = 'Produkt-ID';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b9a7a7f4250389169ecdbe30bf388e62'] = 'Kombinations-ID';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_28a382bd262d1e28a94c3ef716364f45'] = 'Länder-ID';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e3bd5374568ecf9da8cf9603b469ea1f'] = 'Währungs-ID';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38a915ac6509a0c3af497a3ad669e247'] = 'Gruppen-ID';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_3601146c4e948c32b6424d2c0a7f0118'] = 'Preis';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_51aa40e214d39cada27aec2074df80d9'] = 'Vorheriger Preis';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_50ead5491751f11a8f21884a66532f20'] = 'Im Angebot';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_004bf6c9a40003140292e97330236c53'] = 'Aktion';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_13f5e3a5ca5014256ec30d986f6365fb'] = 'Niedrigster Preis';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2486a303176f5a6a68ecf83455ddc55c'] = 'Unter den Kosten';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_88183b946cc5f0e8c96b2e66e1c74a7e'] = 'Unbekannt';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e681a3b45989b468533c4b90ee960bf9'] = 'Nicht zutreffend';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7b44391e916811603c318ffd2caaf1b1'] = 'Keine Änderungen';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c017b7425d07d95d17494f3ed6830de9'] = 'Erfassung der Preisverlaufshistorie';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fe25cfca4b1b64ab36d337972864b82e'] = 'Löschung des alten Preisverlaufs';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a82be0f551b8708bc08eb33cd9ded0cf'] = 'Informationen';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c245f6a0334e2490637a2fefc91f84ce'] = 'Gruppen ohne Kunden:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8b550b54d30d109322b24fd570f14c08'] = 'Gruppen mit Gruppenrabatten:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_85ddea2392785df2fb727165e63e7266'] = 'Gruppen mit spezifischen Preisen:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c855e004485babe5c373301a3efe35c3'] = 'Gruppen mit Katalogpreisregeln:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b23c2990245b2f2e9547f28992096e35'] = 'Produkte mit Kombinationen, die den Preis beeinflussen:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_9e003b5f5cd7e7715720a6621894b655'] = 'Individuelle Kombinationen mit Rabatten:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8d355f74fb73e3c11bb9239e54cde7a7'] = 'Anzahl aktiver Länder:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a2c5b5f105f1e71608e3c9d9dee9f2a4'] = 'Anzahl aktiver Währungen:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2b3720269ac2364ac58c8769ba8c9c25'] = 'Anzahl der im Verlauf gespeicherten Preise:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_6adf97f83acf6453d4a6a4b1070f3754'] = 'Keine';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_114d3c884cee5cdb580d88fd277e847b'] = 'Dieser Preis kann gelöscht werden';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fa19e91aa306519181f7b8a19743b5f1'] = 'Dieser Preis wird noch benötigt';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_63b539babcf7978229d66ba4052ca71f'] = 'Aktionspreis';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_4d8adffdc001189e0202c01ac529a3a9'] = 'Regulärer Preis';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_148b76150603892408248b0ed5a5dd51'] = 'Niedrigster vorheriger Preis';
+$_MODULE['<{gm_omniprice}prestashop>price_7a6e48674dee5dd4a09f41e487d2c896'] = 'Niedrigster Preis im Zeitraum von %d Tagen vor dem Rabatt:';
+$_MODULE['<{gm_omniprice}prestashop>tab_11ac0a790117ce9772284501afb324e5'] = 'Produkt heute indexiert:';
+$_MODULE['<{gm_omniprice}prestashop>tab_93cba07454f06a4a960172bbd6e2a435'] = 'Ja';
+$_MODULE['<{gm_omniprice}prestashop>tab_bafd7322c6e97d25b6299b5d6fe8920b'] = 'Nein';
+$_MODULE['<{gm_omniprice}prestashop>tab_0968b8dc12087a20de5b608d6617b925'] = 'Zur Vereinfachung zeigt die folgende Tabelle den Preisverlauf für die Standardwährung, das Standardland, die Standardkundengruppe und das Standardattribut.';
+$_MODULE['<{gm_omniprice}prestashop>tab_44749712dbec183e983dcd78a7736c41'] = 'Datum';
+$_MODULE['<{gm_omniprice}prestashop>tab_3601146c4e948c32b6424d2c0a7f0118'] = 'Preis';
+$_MODULE['<{gm_omniprice}prestashop>tab_58b2e2eff900334f1aea87c9bf05903c'] = 'Preisart';
diff --git a/modules/gm_omniprice/translations/es.php b/modules/gm_omniprice/translations/es.php
index e69de29b..f3506b4a 100644
--- a/modules/gm_omniprice/translations/es.php
+++ b/modules/gm_omniprice/translations/es.php
@@ -0,0 +1,80 @@
+gm_omniprice_90a0c7b2104a67d391df6f2db66300e3'] = 'OmniPrice - conformidad de precios con la directiva Omnibus';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2f2aaa2e0f7ba09de9a5f449ba5f45af'] = 'Muestra información sobre el precio más bajo antes del descuento';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c888438d14855d7d96a2724ee9c306bd'] = 'Configuraciones guardadas';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1901606ea069a83dc7beea17881ef95a'] = 'Periodo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b1e1f9076cca4dd59d55975e7a318f38'] = 'Número de días antes de la promoción a analizar';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_62fefba7aea0bdb51b8935c165195610'] = 'Ignorar países';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_93cba07454f06a4a960172bbd6e2a435'] = 'Sí';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bafd7322c6e97d25b6299b5d6fe8920b'] = 'No';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dc4143a87bf30fc020b5285c0943567c'] = 'Analizar precios solo para el país predeterminado, los clientes de otros países verán los precios del país predeterminado';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7f01c3611adcbec6862b1c4001f0f300'] = 'Ignorar países fuera de la UE';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f0e0af7ffec706830ed933f0aa52c841'] = 'Ignora completamente los países fuera de la UE, los clientes de estos países no verán información sobre precios anteriores';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b7b08b9fdd4d8d7a01eaf832777db241'] = 'Ignorar combinaciones';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a9a3387e6b5111e07b969cfa06d68586'] = 'Analizar precios solo para la combinación predeterminada del producto, recomendado si las combinaciones no afectan el precio';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_09c12c14a8bdcb5579a6163a4ce736e8'] = 'Grupos ignorados';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c8885049351230f4d9e65f2997e2de57'] = 'Ignorar grupos seleccionados, los clientes de estos grupos verán el precio para el grupo predeterminado (Cliente), recomendado si no se utilizan descuentos grupales';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1300769d8d72fc8218b40772f1c25efc'] = 'Paquete de productos';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_419e727dd8d9ac44fd248de2eda589b4'] = 'Número de productos procesados por ejecución del cron job';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e09109328229ca6967e3ea981ee158dd'] = 'Reindexar al guardar el producto';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bd0b2b3a1ded97ddd1d70591f1af8960'] = 'Reindexa el producto al momento de guardarlo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_368d9ac76af05f714092bc808a426bfc'] = 'Color de fondo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_5f111ae4c490902059da2004cbc8b424'] = 'Color del texto';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_d6a3bb2945a3fa2ac63739ec31c00060'] = 'Color del precio';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_ad1338e53c6bec090eaab52628716805'] = 'Mostrar mensaje incluso con historial insuficiente';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_0a7291f2167ca2f321c44157ded8e2f8'] = 'Para productos en promoción sin información sobre precios anteriores, muestra el único precio promocional registrado como el precio histórico más bajo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38ce18494ca0426bdbd483c5c4cf9ec2'] = 'Indexar productos inactivos';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_37d66737bda18cffdc0342145c644e52'] = 'Guarda el historial de precios del producto incluso si está inactivo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_90ce4a97e9f26453b3deca306fa6a1d5'] = 'Mostrar la reducción real con respecto al precio anterior';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dad8fdc91311e7e8cd8431bc54036090'] = 'Muestra la diferencia porcentual entre el precio actual del producto y el precio más bajo anterior';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8dcea44ea2df2fb48f9f2eab63cbe8e6'] = 'Ignorar productos vendidos por debajo del costo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f4f70727dc34561dfde1a3c529b6205c'] = 'Configuraciones';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c9cc8cce247e49bae79f15173ce97354'] = 'Guardar';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1033eb0896e0e3ccde90fe8ea13c1fb2'] = 'ID del país predeterminado:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f770b9c02b33fe4e7246f96b12887a01'] = 'ID del grupo predeterminado:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_212713efb37cd2f521ee584f1dbb5f0b'] = 'ID de la tienda:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_36f12776fd15f301a8b51336b49a7043'] = 'Todos los productos han sido indexados';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f2f4e21b8a93962f211c50a54d20653d'] = 'Aún no ha terminado, vuelve a ejecutarme';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_97f08a40f22a625d0cbfe03db3349108'] = 'ID del producto';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b9a7a7f4250389169ecdbe30bf388e62'] = 'ID de la combinación';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_28a382bd262d1e28a94c3ef716364f45'] = 'ID del país';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e3bd5374568ecf9da8cf9603b469ea1f'] = 'ID de la moneda';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38a915ac6509a0c3af497a3ad669e247'] = 'ID del grupo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_3601146c4e948c32b6424d2c0a7f0118'] = 'Precio';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_51aa40e214d39cada27aec2074df80d9'] = 'Precio anterior';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_50ead5491751f11a8f21884a66532f20'] = 'En promoción';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_004bf6c9a40003140292e97330236c53'] = 'Acción';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_13f5e3a5ca5014256ec30d986f6365fb'] = 'Precio más bajo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2486a303176f5a6a68ecf83455ddc55c'] = 'Debajo del costo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_88183b946cc5f0e8c96b2e66e1c74a7e'] = 'Desconocido';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e681a3b45989b468533c4b90ee960bf9'] = 'No aplicable';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7b44391e916811603c318ffd2caaf1b1'] = 'Sin cambios';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c017b7425d07d95d17494f3ed6830de9'] = 'Recolección del historial de precios';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fe25cfca4b1b64ab36d337972864b82e'] = 'Limpieza del historial antiguo de precios';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a82be0f551b8708bc08eb33cd9ded0cf'] = 'Información';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c245f6a0334e2490637a2fefc91f84ce'] = 'Grupos sin clientes:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8b550b54d30d109322b24fd570f14c08'] = 'Grupos con descuentos grupales:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_85ddea2392785df2fb727165e63e7266'] = 'Grupos con precios específicos:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c855e004485babe5c373301a3efe35c3'] = 'Grupos con reglas de precios de catálogo:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b23c2990245b2f2e9547f28992096e35'] = 'Productos con combinaciones que afectan el precio:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_9e003b5f5cd7e7715720a6621894b655'] = 'Combinaciones individuales con descuentos:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8d355f74fb73e3c11bb9239e54cde7a7'] = 'Número de países activos:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a2c5b5f105f1e71608e3c9d9dee9f2a4'] = 'Número de monedas activas:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2b3720269ac2364ac58c8769ba8c9c25'] = 'Número de precios registrados en el historial:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_6adf97f83acf6453d4a6a4b1070f3754'] = 'Ninguno';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_114d3c884cee5cdb580d88fd277e847b'] = 'este precio puede ser eliminado';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fa19e91aa306519181f7b8a19743b5f1'] = 'este precio aún es necesario';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_63b539babcf7978229d66ba4052ca71f'] = 'Precio promocional';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_4d8adffdc001189e0202c01ac529a3a9'] = 'Precio regular';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_148b76150603892408248b0ed5a5dd51'] = 'Precio más bajo anterior';
+$_MODULE['<{gm_omniprice}prestashop>price_7a6e48674dee5dd4a09f41e487d2c896'] = 'Precio más bajo durante un período de %d días antes del descuento:';
+$_MODULE['<{gm_omniprice}prestashop>tab_11ac0a790117ce9772284501afb324e5'] = 'Producto indexado hoy:';
+$_MODULE['<{gm_omniprice}prestashop>tab_93cba07454f06a4a960172bbd6e2a435'] = 'Sí';
+$_MODULE['<{gm_omniprice}prestashop>tab_bafd7322c6e97d25b6299b5d6fe8920b'] = 'No';
+$_MODULE['<{gm_omniprice}prestashop>tab_0968b8dc12087a20de5b608d6617b925'] = 'Para simplificar, la siguiente tabla muestra el historial de cambios de precios para la moneda, país, grupo de clientes y atributo predeterminado.';
+$_MODULE['<{gm_omniprice}prestashop>tab_44749712dbec183e983dcd78a7736c41'] = 'Fecha';
+$_MODULE['<{gm_omniprice}prestashop>tab_3601146c4e948c32b6424d2c0a7f0118'] = 'Precio';
+$_MODULE['<{gm_omniprice}prestashop>tab_58b2e2eff900334f1aea87c9bf05903c'] = 'Tipo de precio';
diff --git a/modules/gm_omniprice/translations/fr.php b/modules/gm_omniprice/translations/fr.php
index e69de29b..d159858b 100644
--- a/modules/gm_omniprice/translations/fr.php
+++ b/modules/gm_omniprice/translations/fr.php
@@ -0,0 +1,81 @@
+gm_omniprice_90a0c7b2104a67d391df6f2db66300e3'] = 'OmniPrice - conformité des prix avec la directive Omnibus';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2f2aaa2e0f7ba09de9a5f449ba5f45af'] = 'Affiche les informations sur le prix le plus bas avant la réduction';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c888438d14855d7d96a2724ee9c306bd'] = 'Paramètres enregistrés';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1901606ea069a83dc7beea17881ef95a'] = 'Période';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b1e1f9076cca4dd59d55975e7a318f38'] = 'Nombre de jours avant la promotion à analyser';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_62fefba7aea0bdb51b8935c165195610'] = 'Ignorer les pays';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_93cba07454f06a4a960172bbd6e2a435'] = 'Oui';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bafd7322c6e97d25b6299b5d6fe8920b'] = 'Non';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dc4143a87bf30fc020b5285c0943567c'] = 'Analyser les prix uniquement pour le pays par défaut, les clients d\'autres pays verront les prix du pays par défaut';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7f01c3611adcbec6862b1c4001f0f300'] = 'Ignorer les pays hors UE';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f0e0af7ffec706830ed933f0aa52c841'] = 'Ignore complètement les pays hors UE, les clients de ces pays ne verront aucune information sur les anciens prix';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b7b08b9fdd4d8d7a01eaf832777db241'] = 'Ignorer les combinaisons';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a9a3387e6b5111e07b969cfa06d68586'] = 'Analyser les prix uniquement pour la combinaison par défaut du produit, recommandé si les combinaisons n\'ont pas d\'impact sur le prix';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_09c12c14a8bdcb5579a6163a4ce736e8'] = 'Groupes ignorés';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c8885049351230f4d9e65f2997e2de57'] = 'Ignorer les groupes sélectionnés, les clients de ces groupes verront le prix du groupe par défaut (Client), recommandé si les remises de groupe ne sont pas utilisées';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1300769d8d72fc8218b40772f1c25efc'] = 'Pack de produits';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_419e727dd8d9ac44fd248de2eda589b4'] = 'Nombre de produits traités par exécution de tâche CRON';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e09109328229ca6967e3ea981ee158dd'] = 'Réindexer lors de l\'enregistrement du produit';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bd0b2b3a1ded97ddd1d70591f1af8960'] = 'Réindexe le produit lors de son enregistrement';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_368d9ac76af05f714092bc808a426bfc'] = 'Couleur de fond';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_5f111ae4c490902059da2004cbc8b424'] = 'Couleur du texte';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_d6a3bb2945a3fa2ac63739ec31c00060'] = 'Couleur du prix';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_ad1338e53c6bec090eaab52628716805'] = 'Afficher un message même avec un historique insuffisant';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_0a7291f2167ca2f321c44157ded8e2f8'] = 'Pour les produits en promotion sans informations sur les anciens prix, affiche le seul prix promotionnel enregistré comme le plus bas prix historique';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38ce18494ca0426bdbd483c5c4cf9ec2'] = 'Indexer les produits inactifs';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_37d66737bda18cffdc0342145c644e52'] = 'Enregistre l\'historique des prix du produit même s\'il est inactif';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_90ce4a97e9f26453b3deca306fa6a1d5'] = 'Afficher la réduction réelle par rapport au prix précédent';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dad8fdc91311e7e8cd8431bc54036090'] = 'Affiche la différence en pourcentage entre le prix actuel du produit et le prix le plus bas précédent';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8dcea44ea2df2fb48f9f2eab63cbe8e6'] = 'Ignorer les produits vendus en dessous du prix d\'achat';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f4f70727dc34561dfde1a3c529b6205c'] = 'Paramètres';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c9cc8cce247e49bae79f15173ce97354'] = 'Enregistrer';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1033eb0896e0e3ccde90fe8ea13c1fb2'] = 'ID du pays par défaut:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f770b9c02b33fe4e7246f96b12887a01'] = 'ID du groupe par défaut:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_212713efb37cd2f521ee584f1dbb5f0b'] = 'ID du magasin:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_36f12776fd15f301a8b51336b49a7043'] = 'Tous les produits sont indexés';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f2f4e21b8a93962f211c50a54d20653d'] = 'Ce n\'est pas encore fini, relancez-moi';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_97f08a40f22a625d0cbfe03db3349108'] = 'ID produit';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b9a7a7f4250389169ecdbe30bf388e62'] = 'ID combinaison';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_28a382bd262d1e28a94c3ef716364f45'] = 'ID pays';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e3bd5374568ecf9da8cf9603b469ea1f'] = 'ID devise';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38a915ac6509a0c3af497a3ad669e247'] = 'ID groupe';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_3601146c4e948c32b6424d2c0a7f0118'] = 'Prix';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_51aa40e214d39cada27aec2074df80d9'] = 'Prix précédent';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_50ead5491751f11a8f21884a66532f20'] = 'En promotion';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_004bf6c9a40003140292e97330236c53'] = 'Action';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_13f5e3a5ca5014256ec30d986f6365fb'] = 'Prix le plus bas';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2486a303176f5a6a68ecf83455ddc55c'] = 'En dessous du coût';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_88183b946cc5f0e8c96b2e66e1c74a7e'] = 'Inconnu';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e681a3b45989b468533c4b90ee960bf9'] = 'Non applicable';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7b44391e916811603c318ffd2caaf1b1'] = 'Aucun changement';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c017b7425d07d95d17494f3ed6830de9'] = 'Collecte de l\'historique des prix';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fe25cfca4b1b64ab36d337972864b82e'] = 'Nettoyage de l\'ancien historique des prix';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a82be0f551b8708bc08eb33cd9ded0cf'] = 'Informations';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c245f6a0334e2490637a2fefc91f84ce'] = 'Groupes sans clients :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8b550b54d30d109322b24fd570f14c08'] = 'Groupes avec remises groupées :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_85ddea2392785df2fb727165e63e7266'] = 'Groupes avec des prix spécifiques :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c855e004485babe5c373301a3efe35c3'] = 'Groupes avec des règles de prix catalogue :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b23c2990245b2f2e9547f28992096e35'] = 'Produits avec des combinaisons affectant le prix :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_9e003b5f5cd7e7715720a6621894b655'] = 'Combinaisons individuelles avec remises :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8d355f74fb73e3c11bb9239e54cde7a7'] = 'Nombre de pays actifs :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a2c5b5f105f1e71608e3c9d9dee9f2a4'] = 'Nombre de devises actives :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2b3720269ac2364ac58c8769ba8c9c25'] = 'Nombre de prix enregistrés dans l\'historique :';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_6adf97f83acf6453d4a6a4b1070f3754'] = 'Aucun';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_114d3c884cee5cdb580d88fd277e847b'] = 'ce prix peut être supprimé';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fa19e91aa306519181f7b8a19743b5f1'] = 'ce prix est toujours nécessaire';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_63b539babcf7978229d66ba4052ca71f'] = 'Prix promotionnel';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_4d8adffdc001189e0202c01ac529a3a9'] = 'Prix régulier';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_148b76150603892408248b0ed5a5dd51'] = 'Prix le plus bas précédent';
+$_MODULE['<{gm_omniprice}prestashop>price_7a6e48674dee5dd4a09f41e487d2c896'] = 'Prix le plus bas sur une période de %d jours avant la réduction :';
+$_MODULE['<{gm_omniprice}prestashop>tab_11ac0a790117ce9772284501afb324e5'] = 'Produit indexé aujourd\'hui :';
+$_MODULE['<{gm_omniprice}prestashop>tab_93cba07454f06a4a960172bbd6e2a435'] = 'Oui';
+$_MODULE['<{gm_omniprice}prestashop>tab_bafd7322c6e97d25b6299b5d6fe8920b'] = 'Non';
+$_MODULE['<{gm_omniprice}prestashop>tab_0968b8dc12087a20de5b608d6617b925'] = 'Pour simplifier, le tableau ci-dessous montre l\'historique des changements de prix pour la devise, le pays, le groupe client et l\'attribut par défaut.';
+$_MODULE['<{gm_omniprice}prestashop>tab_44749712dbec183e983dcd78a7736c41'] = 'Date';
+$_MODULE['<{gm_omniprice}prestashop>tab_3601146c4e948c32b6424d2c0a7f0118'] = 'Prix';
+$_MODULE['<{gm_omniprice}prestashop>tab_58b2e2eff900334f1aea87c9bf05903c'] = 'Type de prix';
+
diff --git a/modules/gm_omniprice/translations/it.php b/modules/gm_omniprice/translations/it.php
index e69de29b..4bb2d310 100644
--- a/modules/gm_omniprice/translations/it.php
+++ b/modules/gm_omniprice/translations/it.php
@@ -0,0 +1,80 @@
+gm_omniprice_90a0c7b2104a67d391df6f2db66300e3'] = 'OmniPrice - conformità dei prezzi con la direttiva Omnibus';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2f2aaa2e0f7ba09de9a5f449ba5f45af'] = 'Mostra informazioni sul prezzo più basso prima dello sconto';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c888438d14855d7d96a2724ee9c306bd'] = 'Impostazioni salvate';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1901606ea069a83dc7beea17881ef95a'] = 'Periodo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b1e1f9076cca4dd59d55975e7a318f38'] = 'Numero di giorni precedenti la promozione da analizzare';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_62fefba7aea0bdb51b8935c165195610'] = 'Ignora paesi';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_93cba07454f06a4a960172bbd6e2a435'] = 'Sì';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bafd7322c6e97d25b6299b5d6fe8920b'] = 'No';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dc4143a87bf30fc020b5285c0943567c'] = 'Analizza i prezzi solo per il paese predefinito, i clienti di altri paesi vedranno i prezzi per il paese predefinito';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7f01c3611adcbec6862b1c4001f0f300'] = 'Ignora paesi non UE';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f0e0af7ffec706830ed933f0aa52c841'] = 'Ignora completamente i paesi non UE, i clienti di questi paesi non vedranno informazioni sui prezzi precedenti';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b7b08b9fdd4d8d7a01eaf832777db241'] = 'Ignora combinazioni';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a9a3387e6b5111e07b969cfa06d68586'] = 'Analizza i prezzi solo per la combinazione predefinita del prodotto, consigliato se le combinazioni non influenzano il prezzo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_09c12c14a8bdcb5579a6163a4ce736e8'] = 'Gruppi ignorati';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c8885049351230f4d9e65f2997e2de57'] = 'Ignora i gruppi selezionati, i clienti di questi gruppi vedranno il prezzo per il gruppo predefinito (Cliente), consigliato se non si utilizzano sconti per gruppi';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1300769d8d72fc8218b40772f1c25efc'] = 'Pacchetto di prodotti';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_419e727dd8d9ac44fd248de2eda589b4'] = 'Numero di prodotti elaborati per esecuzione del cron job';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e09109328229ca6967e3ea981ee158dd'] = 'Reindicizza durante il salvataggio del prodotto';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_bd0b2b3a1ded97ddd1d70591f1af8960'] = 'Reindicizza il prodotto al momento del salvataggio';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_368d9ac76af05f714092bc808a426bfc'] = 'Colore dello sfondo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_5f111ae4c490902059da2004cbc8b424'] = 'Colore del testo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_d6a3bb2945a3fa2ac63739ec31c00060'] = 'Colore del prezzo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_ad1338e53c6bec090eaab52628716805'] = 'Mostra messaggio anche con cronologia insufficiente';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_0a7291f2167ca2f321c44157ded8e2f8'] = 'Per i prodotti scontati senza informazioni sui prezzi precedenti, mostra l\'unico prezzo promozionale salvato come prezzo storico più basso';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38ce18494ca0426bdbd483c5c4cf9ec2'] = 'Indicizza i prodotti inattivi';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_37d66737bda18cffdc0342145c644e52'] = 'Salva la cronologia dei prezzi del prodotto anche se inattivo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_90ce4a97e9f26453b3deca306fa6a1d5'] = 'Mostra la reale riduzione rispetto al prezzo precedente';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_dad8fdc91311e7e8cd8431bc54036090'] = 'Mostra la differenza percentuale tra il prezzo attuale del prodotto e il prezzo più basso precedente';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8dcea44ea2df2fb48f9f2eab63cbe8e6'] = 'Ignora i prodotti venduti sotto costo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f4f70727dc34561dfde1a3c529b6205c'] = 'Impostazioni';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c9cc8cce247e49bae79f15173ce97354'] = 'Salva';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_1033eb0896e0e3ccde90fe8ea13c1fb2'] = 'ID del paese predefinito:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f770b9c02b33fe4e7246f96b12887a01'] = 'ID del gruppo predefinito:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_212713efb37cd2f521ee584f1dbb5f0b'] = 'ID del negozio:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_36f12776fd15f301a8b51336b49a7043'] = 'Tutti i prodotti sono stati indicizzati';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_f2f4e21b8a93962f211c50a54d20653d'] = 'Non è ancora finita, rilanciami';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_97f08a40f22a625d0cbfe03db3349108'] = 'ID prodotto';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b9a7a7f4250389169ecdbe30bf388e62'] = 'ID combinazione';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_28a382bd262d1e28a94c3ef716364f45'] = 'ID paese';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e3bd5374568ecf9da8cf9603b469ea1f'] = 'ID valuta';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_38a915ac6509a0c3af497a3ad669e247'] = 'ID gruppo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_3601146c4e948c32b6424d2c0a7f0118'] = 'Prezzo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_51aa40e214d39cada27aec2074df80d9'] = 'Prezzo precedente';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_50ead5491751f11a8f21884a66532f20'] = 'In promozione';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_004bf6c9a40003140292e97330236c53'] = 'Azione';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_13f5e3a5ca5014256ec30d986f6365fb'] = 'Prezzo più basso';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2486a303176f5a6a68ecf83455ddc55c'] = 'Sotto costo';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_88183b946cc5f0e8c96b2e66e1c74a7e'] = 'Sconosciuto';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_e681a3b45989b468533c4b90ee960bf9'] = 'Non applicabile';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_7b44391e916811603c318ffd2caaf1b1'] = 'Nessun cambiamento';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c017b7425d07d95d17494f3ed6830de9'] = 'Raccolta della cronologia dei prezzi';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fe25cfca4b1b64ab36d337972864b82e'] = 'Pulizia della vecchia cronologia dei prezzi';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a82be0f551b8708bc08eb33cd9ded0cf'] = 'Informazioni';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c245f6a0334e2490637a2fefc91f84ce'] = 'Gruppi senza clienti:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8b550b54d30d109322b24fd570f14c08'] = 'Gruppi con sconti di gruppo:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_85ddea2392785df2fb727165e63e7266'] = 'Gruppi con prezzi specifici:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_c855e004485babe5c373301a3efe35c3'] = 'Gruppi con regole di prezzo catalogo:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_b23c2990245b2f2e9547f28992096e35'] = 'Prodotti con combinazioni che influenzano il prezzo:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_9e003b5f5cd7e7715720a6621894b655'] = 'Combinazioni individuali con sconti:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_8d355f74fb73e3c11bb9239e54cde7a7'] = 'Numero di paesi attivi:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_a2c5b5f105f1e71608e3c9d9dee9f2a4'] = 'Numero di valute attive:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_2b3720269ac2364ac58c8769ba8c9c25'] = 'Numero di prezzi registrati nella cronologia:';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_6adf97f83acf6453d4a6a4b1070f3754'] = 'Nessuno';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_114d3c884cee5cdb580d88fd277e847b'] = 'questo prezzo può essere eliminato';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_fa19e91aa306519181f7b8a19743b5f1'] = 'questo prezzo è ancora necessario';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_63b539babcf7978229d66ba4052ca71f'] = 'Prezzo promozionale';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_4d8adffdc001189e0202c01ac529a3a9'] = 'Prezzo regolare';
+$_MODULE['<{gm_omniprice}prestashop>gm_omniprice_148b76150603892408248b0ed5a5dd51'] = 'Prezzo più basso precedente';
+$_MODULE['<{gm_omniprice}prestashop>price_7a6e48674dee5dd4a09f41e487d2c896'] = 'Prezzo più basso nel periodo di %d giorni prima dello sconto:';
+$_MODULE['<{gm_omniprice}prestashop>tab_11ac0a790117ce9772284501afb324e5'] = 'Prodotto indicizzato oggi:';
+$_MODULE['<{gm_omniprice}prestashop>tab_93cba07454f06a4a960172bbd6e2a435'] = 'Sì';
+$_MODULE['<{gm_omniprice}prestashop>tab_bafd7322c6e97d25b6299b5d6fe8920b'] = 'No';
+$_MODULE['<{gm_omniprice}prestashop>tab_0968b8dc12087a20de5b608d6617b925'] = 'Per semplicità, la tabella seguente mostra la cronologia delle modifiche dei prezzi per la valuta, il paese, il gruppo cliente e l\'attributo predefinito.';
+$_MODULE['<{gm_omniprice}prestashop>tab_44749712dbec183e983dcd78a7736c41'] = 'Data';
+$_MODULE['<{gm_omniprice}prestashop>tab_3601146c4e948c32b6424d2c0a7f0118'] = 'Prezzo';
+$_MODULE['<{gm_omniprice}prestashop>tab_58b2e2eff900334f1aea87c9bf05903c'] = 'Tipo di prezzo';