You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

OrderController.php 48KB

8 年之前
8 年之前
8 年之前
8 年之前
8 年之前
8 年之前
8 年之前
8 年之前
8 年之前
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311
  1. <?php
  2. /**
  3. Copyright La boîte à pain (2018)
  4. contact@laboiteapain.net
  5. Ce logiciel est un programme informatique servant à aider les producteurs
  6. à distribuer leur production en circuits courts.
  7. Ce logiciel est régi par la licence CeCILL soumise au droit français et
  8. respectant les principes de diffusion des logiciels libres. Vous pouvez
  9. utiliser, modifier et/ou redistribuer ce programme sous les conditions
  10. de la licence CeCILL telle que diffusée par le CEA, le CNRS et l'INRIA
  11. sur le site "http://www.cecill.info".
  12. En contrepartie de l'accessibilité au code source et des droits de copie,
  13. de modification et de redistribution accordés par cette licence, il n'est
  14. offert aux utilisateurs qu'une garantie limitée. Pour les mêmes raisons,
  15. seule une responsabilité restreinte pèse sur l'auteur du programme, le
  16. titulaire des droits patrimoniaux et les concédants successifs.
  17. A cet égard l'attention de l'utilisateur est attirée sur les risques
  18. associés au chargement, à l'utilisation, à la modification et/ou au
  19. développement et à la reproduction du logiciel par l'utilisateur étant
  20. donné sa spécificité de logiciel libre, qui peut le rendre complexe à
  21. manipuler et qui le réserve donc à des développeurs et des professionnels
  22. avertis possédant des connaissances informatiques approfondies. Les
  23. utilisateurs sont donc invités à charger et tester l'adéquation du
  24. logiciel à leurs besoins dans des conditions permettant d'assurer la
  25. sécurité de leurs systèmes et ou de leurs données et, plus généralement,
  26. à l'utiliser et l'exploiter dans les mêmes conditions de sécurité.
  27. Le fait que vous puissiez accéder à cet en-tête signifie que vous avez
  28. pris connaissance de la licence CeCILL, et que vous en avez accepté les
  29. termes.
  30. */
  31. namespace backend\controllers;
  32. use common\models\Order ;
  33. use common\models\ProductOrder ;
  34. use common\models\Product ;
  35. use common\models\User ;
  36. use common\models\ProductDistribution ;
  37. class OrderController extends BackendController
  38. {
  39. var $enableCsrfValidation = false;
  40. public function behaviors()
  41. {
  42. return [
  43. 'access' => [
  44. 'class' => AccessControl::className(),
  45. 'rules' => [
  46. [
  47. 'actions' => ['report-cron'],
  48. 'allow' => true,
  49. 'roles' => ['?']
  50. ],
  51. [
  52. 'allow' => true,
  53. 'roles' => ['@'],
  54. 'matchCallback' => function ($rule, $action) {
  55. return User::getCurrentStatus() == USER::STATUS_ADMIN
  56. || User::getCurrentStatus() == USER::STATUS_PRODUCER;
  57. }
  58. ]
  59. ],
  60. ],
  61. ];
  62. }
  63. /**
  64. * Génére un PDF récapitulatif des commandes d'un producteur pour une
  65. * date donnée.
  66. *
  67. * @param string $date
  68. * @param boolean $save
  69. * @param integer $id_etablissement
  70. * @return PDF|null
  71. */
  72. public function actionReport($date = '', $save = false, $idProducer = 0)
  73. {
  74. if (!Yii::$app->user->isGuest) {
  75. $idProducer = Producer::getId() ;
  76. }
  77. $ordersArray = Order::searchAll([
  78. 'distribution.date' => $date,
  79. ],
  80. [
  81. 'orderby' => 'comment_point_sale ASC, user.name ASC',
  82. 'conditions' => 'date_delete IS NULL'
  83. ]) ;
  84. $distribution = Distribution::searchOne([],[
  85. 'conditions' => 'date LIKE :date',
  86. 'params' => [':date' => $date]
  87. ]) ;
  88. if ($distribution) {
  89. $selectedProductsArray = ProductDistribution::searchByDistribution($distribution->id) ;
  90. $pointsSaleArray = PointSale::searchAll() ;
  91. foreach ($pointsSaleArray as $pointSale) {
  92. $pointSale->initOrders($ordersArray) ;
  93. }
  94. // produits
  95. $productsArray = Product::searchAll() ;
  96. // get your HTML raw content without any layouts or scripts
  97. $content = $this->renderPartial('report', [
  98. 'date' => $date,
  99. 'distribution' => $distribution,
  100. 'selectedProductsArray' => $selectedProductsArray,
  101. 'pointsSaleArray' => $pointsSaleArray,
  102. 'productsArray' => $productsArray,
  103. 'ordersArray' => $ordersArray
  104. ]);
  105. $dateStr = date('d/m/Y', strtotime($date));
  106. if ($save) {
  107. $destination = Pdf::DEST_FILE;
  108. } else {
  109. $destination = Pdf::DEST_BROWSER;
  110. }
  111. $pdf = new Pdf([
  112. // set to use core fonts only
  113. 'mode' => Pdf::MODE_UTF8,
  114. // A4 paper format
  115. 'format' => Pdf::FORMAT_A4,
  116. // portrait orientation
  117. 'orientation' => Pdf::ORIENT_PORTRAIT,
  118. // stream to browser inline
  119. 'destination' => $destination,
  120. 'filename' => Yii::getAlias('@app/web/pdf/Commandes-' . $date . '-' . $idProducer . '.pdf'),
  121. // your html content input
  122. 'content' => $content,
  123. // format content from your own css file if needed or use the
  124. // enhanced bootstrap css built by Krajee for mPDF formatting
  125. //'cssFile' => '@vendor/kartik-v/yii2-mpdf/assets/kv-mpdf-bootstrap.min.css',
  126. // any css to be embedded if required
  127. //'cssInline' => '.kv-heading-1{font-size:18px}',
  128. // set mPDF properties on the fly
  129. //'options' => ['title' => 'Krajee Report Title'],
  130. // call mPDF methods on the fly
  131. 'methods' => [
  132. 'SetHeader' => ['Commandes du ' . $dateStr],
  133. 'SetFooter' => ['{PAGENO}'],
  134. ]
  135. ]);
  136. // return the pdf output as per the destination setting
  137. return $pdf->render();
  138. }
  139. return null ;
  140. }
  141. /**
  142. * Supprime une commande.
  143. *
  144. * @param string $date
  145. * @param integer $id_commande
  146. */
  147. public function actionDeleteOrder($date, $idOrder)
  148. {
  149. $order = Order::searchOne(['id' =>$idOrder]) ;
  150. if ($order) {
  151. // remboursement de la commande
  152. if ($order->id_user && $order->getAmount(Order::AMOUNT_PAID) && Producer::getConfig('credit')) {
  153. $order->saveCreditHistory(
  154. CreditHistory::TYPE_REFUND,
  155. $order->getAmount(Order::AMOUNT_PAID),
  156. $order->distribution->id_producer,
  157. $order->id_user,
  158. User::getCurrentId()
  159. );
  160. }
  161. $order->delete();
  162. ProductOrder::deleteAll(['id_order' => $idOrder]);
  163. }
  164. $this->redirect(['index', 'date' => $date]);
  165. }
  166. /**
  167. * Traite le formulaire d'ajout/modification de commande.
  168. *
  169. * @param Distribution $distribution
  170. * @param string $date
  171. * @param array $points_vente
  172. * @param array $produits
  173. * @param array $users
  174. */
  175. public function processOrderForm(
  176. $distribution, $date, $pointsSale, $products, $users)
  177. {
  178. if ($date != '') {
  179. // commandes
  180. $orders = Order::searchAll([
  181. 'distribution.date' => $date
  182. ]) ;
  183. foreach ($pointsSale as $point) {
  184. $point->initOrders($orders);
  185. if (isset($_POST['submit_pv']) && $_POST['submit_pv']) {
  186. // modifs
  187. foreach ($point->orders as $order) {
  188. // suppression des product_order
  189. ProductOrder::deleteAll(['id_order' => $order->id]) ;
  190. // création des commande_produit modifiés
  191. foreach ($products as $product) {
  192. $quantity = Yii::$app->getRequest()->post('product_' . $point->id . '_' . $product->id, 0);
  193. if ($quantity) {
  194. $productOrder = new ProductOrder;
  195. $productOrder->id_order = $order->id;
  196. $productOrder->id_product = $product->id;
  197. $productOrder->quantity = $quantity;
  198. $productOrder->price = $p->price;
  199. $productOrder->save();
  200. }
  201. }
  202. }
  203. $username = Yii::$app->getRequest()->post('username_point_sale_' . $point->id, 0);
  204. $date = Yii::$app->getRequest()->post('date_order_point_sale_' . $point->id, 0);
  205. $oneProduct = false;
  206. foreach ($products as $product) {
  207. $quantity = Yii::$app->getRequest()->post('product_point_sale_' . $point->id . '_' . $product->id, 0);
  208. if ($quantity) {
  209. $oneProduct = true;
  210. }
  211. }
  212. if (strlen($username) && $date && $oneProduct) {
  213. $order = new Order;
  214. $order->id_point_sale = $point->id;
  215. $order->id_production = $distribution->id;
  216. $order->id_user = 0;
  217. $order->username = $username;
  218. $arrayDate = explode('/', $date);
  219. $order->date = $arrayDate[2] . '-' . $arrayDate[1] . '-' . $arrayDate[0] . ' 00:00:00';
  220. $order->save();
  221. foreach ($products as $product) {
  222. $quantity = Yii::$app->getRequest()->post('product_point_sale_' . $point->id . '_' . $product->id, 0);
  223. if ($quantity) {
  224. $productOrder = new ProductOrder;
  225. $productOrder->id_order = $order->id;
  226. $productOrder->id_product = $product->id;
  227. $productOrder->quantity = $quantity;
  228. $productOrder->price = $p->price;
  229. $productOrder->save();
  230. }
  231. }
  232. }
  233. }
  234. }
  235. }
  236. }
  237. /**
  238. * Page principale de la gestion des commandes.
  239. *
  240. * @param string $date
  241. * @param boolean $returnData
  242. * @return string
  243. */
  244. public function actionIndex($date = '', $returnData = false)
  245. {
  246. if (!Product::count() && !PointSale::count()) {
  247. $this->redirect(['site/index', 'error_products_points_sale' => 1]);
  248. }
  249. $orders = [];
  250. // users
  251. $arrayUsers = [0 => '--'];
  252. $users = User::searchAll([],['orderby' => 'lastname, name ASC']) ;
  253. foreach ($users as $user) {
  254. $arrayUsers[$user->id] = $user->name . ' ' . $user->lastname;
  255. }
  256. // création du jour de distribution
  257. $distribution = Distribution::initDistribution($date) ;
  258. // points de vente
  259. if ($distribution) {
  260. $arrayPointsSale = PointSale::find()
  261. ->joinWith(['pointSaleDistribution' => function($q) use ($distribution) {
  262. $q->where(['id_distribution' => $distribution->id]);
  263. }])
  264. ->where([
  265. 'id_producer' => Producer::getId(),
  266. ])
  267. ->all();
  268. } else {
  269. $arrayPointsSale = PointSale::searchAll() ;
  270. }
  271. // produits
  272. $arrayProducts = Product::searchAll();
  273. // gestion des commandes
  274. $this->processOrderForm($distribution, $date, $arrayPointsSale, $arrayProducts, $users);
  275. // commandes
  276. $arrayOrders = Order::searchAll([
  277. 'distribution.date' => $date,
  278. ], [
  279. 'conditions' => 'date_delete IS NULL'
  280. ]);
  281. $revenues = 0;
  282. $weight = 0 ;
  283. $revenuesDelivered = 0;
  284. if($arrayOrders) {
  285. foreach ($arrayOrders as $order) {
  286. if(is_null($order->date_delete)) {
  287. $revenues += $order->amount;
  288. if ($order->id_point_sale != 1) {
  289. $revenuesDelivered += $order->amount;
  290. }
  291. $weight += $order->weight;
  292. }
  293. }
  294. }
  295. $revenues = number_format($revenues, 2);
  296. // init commandes point de vente
  297. foreach ($arrayPointsSale as $pointSale) {
  298. $pointSale->initOrders($arrayOrders);
  299. $dataSelectOrders = [];
  300. $dataOptionsOrders = [];
  301. foreach ($pointSale->orders as $order) {
  302. if ($order->user) {
  303. $dataSelectOrders[$order->id] = $order->user->name . ' ' . $order->user->lastname;
  304. } else {
  305. $dataSelectOrders[$order->id] = $order->username;
  306. }
  307. $dataOptionsOrders[$order->id] = [];
  308. $arrayOptions = [];
  309. $arrayOptions[$order->id]['amount'] = $order->amount;
  310. $arrayOptions[$order->id]['str_amount'] = number_format($order->amount, 2, ',', '') . ' €';
  311. $arrayOptions[$order->id]['paid_amount'] = $order->paid_amount;
  312. $arrayOptions[$order->id]['products'] = [];
  313. $arrayOptions[$order->id]['comment'] = Html::encode($order->comment);
  314. foreach ($order->productOrder as $productOrder) {
  315. $arrayOptions[$order->id]['products'][$productOrder->id_product] = $productOrder->quantity;
  316. }
  317. $dataOptionsOrders[$order->id]['data-order'] = json_encode($arrayOptions[$order->id]);
  318. $dataOptionsOrders[$order->id]['value'] = $order->id;
  319. }
  320. $pointSale->data_select_orders = $dataSelectOrders ;
  321. $pointSale->data_options_orders = $dataOptionsOrders ;
  322. }
  323. // gestion produits selec
  324. if (isset($_POST['valider_produit_selec'])) {
  325. if (isset($_POST['Product'])) {
  326. foreach ($arrayProducts as $product) {
  327. $productDistribution = ProductDistribution::searchOne([
  328. 'id_distribution' => $distribution->id,
  329. 'id_product' => $product->id
  330. ]) ;
  331. if (!$productDistribution) {
  332. $productDistribution = new ProductDistribution();
  333. $productDistribution->id_distribution = $distribution->id;
  334. $productDistribution->id_product = $product->id;
  335. $productDistribution->active = 0;
  336. if (isset($product->quantity_max)) {
  337. $productDistribution->quantity_max = $product->quantity_max;
  338. }
  339. else {
  340. $productDistribution->quantity_max = null;
  341. }
  342. $productDistribution->save();
  343. }
  344. if (isset($_POST['Product'][$product->id]['active'])) {
  345. $productDistribution->active = 1;
  346. } else {
  347. $productDistribution->active = 0;
  348. }
  349. if ((isset($_POST['Product'][$product->id]['quantity_max']) && $_POST['Product'][$product->id]['quantity_max'] != '')) {
  350. $productDistribution->quantity_max = (int) $_POST['Product'][$product->id]['quantity_max'];
  351. } else {
  352. $productDistribution->quantity_max = null;
  353. }
  354. $productDistribution->save();
  355. }
  356. }
  357. }
  358. $arrayProductsSelected = [] ;
  359. if($distribution) {
  360. // produits selec pour production
  361. $arrayProductsSelected = ProductDistribution::searchByDistribution($distribution->id) ;
  362. }
  363. // produits
  364. if ($distribution) {
  365. $arrayProducts = Product::searchByDistribution($distribution->id) ;
  366. }
  367. // poids total de la production et CA potentiel
  368. $potentialTurnover = 0;
  369. $totalWeight = 0;
  370. foreach ($arrayProductsSelected as $idSelectedProduct => $selectedProduct) {
  371. if ($selectedProduct['active']) {
  372. foreach ($arrayProducts as $product) {
  373. if ($product->id == $idSelectedProduct) {
  374. $potentialTurnover += $selectedProduct['quantity_max'] * $product->price;
  375. $totalWeight += $selectedProduct['quantity_max'] * $product->weight / 1000;
  376. }
  377. }
  378. }
  379. }
  380. // jours de distribution
  381. $arrayDistributionDays = Distribution::searchAll([
  382. 'active' => 1
  383. ]) ;
  384. // commandes auto
  385. $subscriptionForm = new SubscriptionForm;
  386. // productions point vente
  387. $pointSaleDistribution = new PointSaleDistribution;
  388. $oointsSaleDistribution = [];
  389. if ($distribution) {
  390. $pointsSaleDistribution = PointSaleDistribution::searchAll([
  391. 'id_distribution' => $distribution->id
  392. ]) ;
  393. }
  394. $arrayPointsSaleDistribution = [];
  395. if(isset($pointsSaleDistribution)) {
  396. foreach ($pointsSaleDistribution as $pointSaleDistrib) {
  397. $key = $pointSaleDistrib->id_distribution . '-' . $pointSaleDistrib->id_point_sale;
  398. if ($pointSaleDistrib->delivery == 1) {
  399. $pointSaleDistribution->points_sale_distribution[] = $key;
  400. }
  401. if(isset($pointSaleDistrib->pointSale) && strlen($pointSaleDistrib->pointSale->name)) {
  402. $arrayPointsSaleDistribution[$key] = Html::encode($pointSaleDistrib->pointSale->name);
  403. }
  404. }
  405. }
  406. // une production de la semaine activée ou non
  407. $oneDistributionWeekActive = false ;
  408. $week = sprintf('%02d',date('W',strtotime($date)));
  409. $start = strtotime(date('Y',strtotime($date)).'W'.$week);
  410. $dateMonday = date('Y-m-d',strtotime('Monday',$start)) ;
  411. $dateTuesday = date('Y-m-d',strtotime('Tuesday',$start)) ;
  412. $dateWednesday = date('Y-m-d',strtotime('Wednesday',$start)) ;
  413. $dateThursday = date('Y-m-d',strtotime('Thursday',$start)) ;
  414. $dateFriday = date('Y-m-d',strtotime('Friday',$start)) ;
  415. $dateSaturday = date('Y-m-d',strtotime('Saturday',$start)) ;
  416. $dateSunday = date('Y-m-d',strtotime('Sunday',$start)) ;
  417. $weekDistribution = Distribution::find()
  418. ->andWhere([
  419. 'id_producer' => Producer::getId(),
  420. 'active' => 1,
  421. ])
  422. ->andWhere(['or',
  423. ['date' => $dateMonday],
  424. ['date' => $dateTuesday],
  425. ['date' => $dateWednesday],
  426. ['date' => $dateThursday],
  427. ['date' => $dateFriday],
  428. ['date' => $dateSaturday],
  429. ['date' => $dateSunday],
  430. ])
  431. ->one();
  432. if($weekDistribution) {
  433. $oneDistributionWeekActive = true ;
  434. }
  435. $datas = [
  436. 'arrayProducts' => $arrayProducts,
  437. 'arrayPointsSale' => $arrayPointsSale,
  438. 'arrayOrders' => $arrayOrders,
  439. 'date' => $date,
  440. 'distribution' => $distribution,
  441. 'arrayDistributionDays' => $arrayDistributionDays,
  442. 'selectedProducts' => $arrayProductsSelected,
  443. 'users' => $arrayUsers,
  444. 'revenues' => $revenues,
  445. 'revenuesDelivered' => $revenuesDelivered,
  446. 'weight' => $weight,
  447. 'potentialTurnover' => $potentialTurnover,
  448. 'totalWeight' => $totalWeight,
  449. 'subscriptionForm' => $subscriptionForm,
  450. 'pointSaleDistribution' => $pointSaleDistribution,
  451. 'arrayPointsSaleDistribution' => $arrayPointsSaleDistribution,
  452. 'oneDistributionWeekActive' => $oneDistributionWeekActive
  453. ];
  454. if ($returnData) {
  455. return $datas;
  456. } else {
  457. return $this->render('index', $datas);
  458. }
  459. }
  460. /**
  461. * Génère un fichier d'export des commandes au format CSV.
  462. *
  463. * @param string $date
  464. * @param integer $id_point_vente
  465. * @param boolean $global
  466. */
  467. public function actionDownload($date = '', $idPointSale = 0, $global = 0)
  468. {
  469. // commandes
  470. $ordersArray = Order::searchAll([
  471. 'distribution.date' => $date
  472. ]) ;
  473. // points de vente
  474. $pointsSaleArray = PointSale::searchAll() ;
  475. foreach ($pointsSaleArray as $pointSale) {
  476. $pv->initOrders($ordersArray);
  477. }
  478. // produits
  479. $productsArray = Product::find()->orderBy('order ASC')->all();
  480. $distribution = Distribution::find()
  481. ->where('date LIKE \':date\'')
  482. ->params([':date' => $date])
  483. ->one();
  484. $selectedProductsArray = ProductDistribution::searchByDistribution($distribution->id);
  485. /*
  486. * export global
  487. */
  488. if ($global) {
  489. $data = [];
  490. $filename = 'export_' . $date . '_global';
  491. $dayWeek = date('w', strtotime($date));
  492. $dayWeekArray = [0 => 'sunday', 1 => 'monday', 2 => 'tuesday', 3 => 'wednesday', 4 => 'thursday', 5 => 'friday', 6 => 'saturday'];
  493. $fieldsHoursPointSale = 'infos_' . $dayWeekArray[$dayWeek];
  494. // par point de vente
  495. foreach ($pointsSaleArray as $pointSale) {
  496. if (count($pointSale->orders) && strlen($pointSale->$fieldsHoursPointSale)) {
  497. $line = [$pointSale->name, 'Produits', 'Montant', 'Commentaire'];
  498. $data[] = $line;
  499. $res = $this->contentPointSaleCSV($date, $productsArray, $pointsSaleArray, $pointSale->id);
  500. foreach ($res['data'] as $line) {
  501. $data[] = $line;
  502. }
  503. }
  504. if (count($pointSale->orders) && strlen($pointSale->$fieldsHoursPointSale)) {
  505. $line = ['Total'];
  506. $strProducts = '';
  507. foreach ($productsArray as $product) {
  508. if ( isset($selectedProductsArray[$product->id]['active']) && $selectedProductsArray[$product->id]['active']) {
  509. $quantity = Order::getProductQuantity($product->id, $pointSale->orders);
  510. $strQuantity = '';
  511. if ($quantity) {
  512. $strQuantity = $quantity;
  513. $strProducts .= $strQuantity . ', ';
  514. }
  515. }
  516. }
  517. $line[] = substr($strProducts, 0, strlen($strProducts) - 2);
  518. $line[] = number_format($pointSale->revenues, 2) . ' €';
  519. $data[] = $line;
  520. $data[] = [];
  521. }
  522. }
  523. $line = ['Total'];
  524. $strProducts = '';
  525. foreach ($productsArray as $product) {
  526. if (isset($selectedProductsArray[$product->id]['active']) && $selectedProductsArray[$product->id]['active']) {
  527. $quantity = Order::getProductQuantity($product->id, $ordersArray);
  528. $strQuantity = '';
  529. if ($quantity) {
  530. $strQuantity = $quantity;
  531. $strQuantity .= $strQuantity . ', ';
  532. }
  533. }
  534. }
  535. $line[] = substr($strProducts, 0, strlen($strProducts) - 2);
  536. $data[] = $line;
  537. $infos = $this->actionIndex($date, true);
  538. CSV::downloadSendHeaders($filename . '.csv');
  539. echo CSV::array2csv($data);
  540. die();
  541. }
  542. /*
  543. * export individuel
  544. */
  545. else {
  546. if ($ordersArray && count($ordersArray)) {
  547. $data = [];
  548. // par point de vente
  549. if ($idPointSale) {
  550. $res = $this->contentPointSaleCSV($date, $productsArray, $pointsSaleArray, $idPointSale);
  551. $data = $res['data'];
  552. $filename = $res['filename'];
  553. }
  554. // récapitulatif
  555. else {
  556. $res = $this->contentRecapCSV($date, $productsArray, $pointsSaleArray, $ordersArray);
  557. $filename = 'summary_' . $date;
  558. $data = $res['data'];
  559. }
  560. CSV::downloadSendHeaders($filename . '.csv');
  561. echo CSV::array2csv($data);
  562. die();
  563. }
  564. }
  565. }
  566. /**
  567. * Génère le contenu nécessaire aux exports au format CSV.
  568. *
  569. * @see OrderController::actionDownload()
  570. * @param string $date
  571. * @param array $products
  572. * @param array $pointsSale
  573. * @param array $orders
  574. * @return array
  575. */
  576. public function contentRecapCSV($date, $products, $pointsSale, $orders)
  577. {
  578. $data = [];
  579. $filename = 'summary_' . $date;
  580. $distribution = Distribution::find()
  581. ->where('date LIKE \':date\'')
  582. ->params([':date' => $date])
  583. ->one();
  584. $selectedProductsArray = ProductDistribution::searchByDistribution($distribution->id);
  585. // head
  586. $data[0] = ['Lieu'];
  587. foreach ($products as $product) {
  588. if (isset($selectedProductsArray[$product->id]['active']) && $selectedProductsArray[$product->id]['active']) {
  589. $data[0][] = $product->description;
  590. }
  591. }
  592. $dayWeek = date('w', strtotime($date));
  593. $dayWeekArray = [0 => 'sunday', 1 => 'monday', 2 => 'tuesday', 3 => 'wednesday', 4 => 'thursday', 5 => 'friday', 6 => 'saturday'];
  594. $fieldHoursPointSale = 'infos_' . $dayWeekArray[$dayWeek];
  595. // datas
  596. foreach ($pointsSale as $pointSale) {
  597. if (count($pointSale->orders) && strlen($pointSale->$fieldHoursPointSale)) {
  598. $dataAdd = [$pointSale->name];
  599. foreach ($products as $product) {
  600. if (isset($selectedProductsArray[$product->id]['active']) && $selectedProductsArray[$product->id]['active']) {
  601. $dataAdd[] = Order::getProductQuantity($product->id, $pointSale->orders);
  602. }
  603. }
  604. $data[] = $dataAdd;
  605. }
  606. }
  607. $dataAdd = ['Total'];
  608. foreach ($products as $product) {
  609. if (isset($selectedProductsArray[$product->id]['active']) && $selectedProductsArray[$product->id]['active']) {
  610. $dataAdd[] = Order::getProductQuantity($product->id, $orders);
  611. }
  612. }
  613. $data[] = $dataAdd;
  614. return [
  615. 'data' => $data,
  616. 'filename' => $filename
  617. ];
  618. }
  619. /**
  620. * Génère le contenu relatif aux points de vente nécessaires aux exports au
  621. * format CSV.
  622. *
  623. * @param string $date
  624. * @param array $produits
  625. * @param array $points_vente
  626. * @param integer $id_point_vente
  627. * @return array
  628. */
  629. public function contentPointSaleCSV($date, $products, $pointsSale, $idPointSale)
  630. {
  631. $data = [];
  632. $distribution = Distribution::find()->where('date LIKE \':date\'')->params([':date' => $date])->one();
  633. $selectedProductsArray = ProductDistribution::searchByDistribution($distribution->id);
  634. // datas
  635. foreach ($pointsSale as $pointSale) {
  636. if ($pointSale->id == $idPointSale) {
  637. $filename = 'export_' . $date . '_' . strtolower(str_replace(' ', '-', $pointSale->name));
  638. foreach ($pointSale->orders as $order) {
  639. $strUser = '';
  640. // username
  641. if ($order->user) {
  642. $strUser = $order->user->name . " " . $order->user->lastname;
  643. } else {
  644. $strUser = $order->username;
  645. }
  646. // téléphone
  647. if (isset($order->user) && strlen($order->user->phone)) {
  648. $strUser .= ' (' . $order->user->phone . ')';
  649. }
  650. $dataAdd = [$strUser];
  651. // produits
  652. $strProducts = '';
  653. foreach ($products as $product) {
  654. if (isset($selectedProductsArray[$product->id]['active']) && $selectedProductsArray[$product->id]['active']) {
  655. $add = false;
  656. foreach ($product->productOrder as $productOrder) {
  657. if ($product->id == $productOrder->id_product) {
  658. $strProducts .= $productOrder->quantity ;
  659. $add = true;
  660. }
  661. }
  662. }
  663. }
  664. $dataAdd[] = substr($strProducts, 0, strlen($strProducts) - 2);
  665. $dataAdd[] = number_format($order->amount, 2) . ' €';
  666. $dataAdd[] = $order->comment;
  667. $data[] = $dataAdd;
  668. }
  669. }
  670. }
  671. return [
  672. 'data' => $data,
  673. 'filename' => $filename
  674. ];
  675. }
  676. /**
  677. * Ajoute les commandes récurrentes pour une date donnée.
  678. *
  679. * @param string $date
  680. */
  681. public function actionAddSubscriptions($date)
  682. {
  683. Subscription::addAll($date, true);
  684. $this->redirect(['index', 'date' => $date]);
  685. }
  686. /**
  687. * Change l'état d'un jour de production (activé, désactivé).
  688. *
  689. * @param string $date
  690. * @param integer $actif
  691. * @param boolean $redirect
  692. */
  693. public function actionChangeState($date, $active, $redirect = true)
  694. {
  695. // changement état
  696. $distribution = Distribution::initDistribution($date) ;
  697. $distribution->active = $active;
  698. $distribution->save();
  699. if ($active) {
  700. // add commandes automatiques
  701. Subscription::addAll($date);
  702. }
  703. if($redirect) {
  704. $this->redirect(['index', 'date' => $date]);
  705. }
  706. }
  707. /**
  708. * Change l'état d'une semaine de production (activé, désactivé).
  709. *
  710. * @param string $date
  711. * @param integer $actif
  712. */
  713. public function actionChangeStateWeek($date, $active)
  714. {
  715. $week = sprintf('%02d',date('W',strtotime($date)));
  716. $start = strtotime(date('Y',strtotime($date)).'W'.$week);
  717. $dateMonday = date('Y-m-d',strtotime('Monday',$start)) ;
  718. $dateTuesday = date('Y-m-d',strtotime('Tuesday',$start)) ;
  719. $dateWednesday = date('Y-m-d',strtotime('Wednesday',$start)) ;
  720. $dateThursday = date('Y-m-d',strtotime('Thursday',$start)) ;
  721. $dateFriday = date('Y-m-d',strtotime('Friday',$start)) ;
  722. $dateSaturday = date('Y-m-d',strtotime('Saturday',$start)) ;
  723. $dateSunday = date('Y-m-d',strtotime('Sunday',$start)) ;
  724. $pointsSaleArray = PointSale::searchAll() ;
  725. $activeMonday = false ;
  726. $activeTuesday = false ;
  727. $activeWednesday = false ;
  728. $activeThursday = false ;
  729. $activeFriday = false ;
  730. $activeSaturday = false ;
  731. $activeSunday = false ;
  732. foreach($pointsSaleArray as $pointSale) {
  733. if($pointSale->delivery_monday) $activeMonday = true ;
  734. if($pointSale->delivery_tuesday) $activeTuesday = true ;
  735. if($pointSale->delivery_wednesday) $activeWednesday = true ;
  736. if($pointSale->delivery_thursday) $activeThursday = true ;
  737. if($pointSale->delivery_friday) $activeFriday = true ;
  738. if($pointSale->delivery_saturday) $activeSaturday = true ;
  739. if($pointSale->delivery_sunday) $activeSunday = true ;
  740. }
  741. if($activeMonday || !$active) $this->actionChangeState($dateMonday, $active, false) ;
  742. if($activeTuesday || !$active) $this->actionChangeState($activeTuesday, $active, false) ;
  743. if($activeWednesday || !$active) $this->actionChangeState($activeWednesday, $active, false) ;
  744. if($activeThursday || !$active) $this->actionChangeState($activeThursday, $active, false) ;
  745. if($activeFriday || !$active) $this->actionChangeState($activeFriday, $active, false) ;
  746. if($activeSaturday || !$active) $this->actionChangeState($activeSaturday, $active, false) ;
  747. if($activeSunday || !$active) $this->actionChangeState($activeSunday, $active, false) ;
  748. $this->redirect(['index', 'date' => $date]);
  749. }
  750. /**
  751. * Met à jour une commande via une requête AJAX.
  752. *
  753. * @param integer $id_commande
  754. * @param array $produits
  755. * @param string $date
  756. * @param string $commentaire
  757. */
  758. public function actionAjaxUpdate(
  759. $idOrder, $products, $date, $comment)
  760. {
  761. $order = Order::searchOne(['id' => $idOrder]) ;
  762. if ($order &&
  763. $order->distribution->id_producer == Producer::getId()) {
  764. $products = json_decode($products);
  765. foreach ($products as $key => $quantity) {
  766. $productOrder = ProductOrder::findOne([
  767. 'id_order' => $idOrder,
  768. 'id_product' => $key
  769. ]);
  770. if ($quantity) {
  771. if ($productOrder) {
  772. $productOrder->quantity = $quantity;
  773. } else {
  774. $product = Product::findOne($key);
  775. if ($product) {
  776. $productOrder = new ProductOrder;
  777. $productOrder->id_order = $idOrder;
  778. $productOrder->id_product = $key;
  779. $productOrder->quantity = $quantity;
  780. $productOrder->price = $product->price;
  781. }
  782. }
  783. $productOrder->save();
  784. } else {
  785. if ($productOrder) {
  786. $productOrder->delete();
  787. }
  788. }
  789. }
  790. $order->date_update = date('Y-m-d H:i:s');
  791. $order->comment = $comment;
  792. $order->save();
  793. // data commande
  794. $jsonOrder = $order->getDataJson();
  795. // total point de vente
  796. $pointSale = PointSale::findOne($order->id_point_sale);
  797. $orders = Order::searchAll([
  798. 'distribution.date' => $date
  799. ]) ;
  800. $pointSale->initOrders($orders);
  801. echo json_encode([
  802. 'total_point_sale' => number_format($pointSale->revenues, 2) . ' €',
  803. 'json_order' => $jsonOrder
  804. ]);
  805. die();
  806. }
  807. }
  808. /**
  809. * Supprime une commande via une requête AJAX.
  810. *
  811. * @param string $date
  812. * @param integer $idOrder
  813. */
  814. public function actionAjaxDelete($date, $idOrder)
  815. {
  816. $order = Order::searchOne([
  817. 'id' => $idOrder
  818. ]) ;
  819. // delete
  820. if ($order) {
  821. // remboursement si l'utilisateur a payé pour cette commande
  822. $amountPaid = $order->getAmount(Order::AMOUNT_PAID);
  823. if ($amountPaid > 0.01) {
  824. $order->saveCreditHistory(
  825. CreditHistory::TYPE_REFUND,
  826. $amountPaid,
  827. Producer::getId(),
  828. $order->id_user,
  829. User::getCurrentId()
  830. );
  831. }
  832. $order->delete();
  833. ProductOrder::deleteAll(['id_order' => $idOrder]);
  834. }
  835. // total point de vente
  836. $pointSale = PointSale::findOne($order->id_point_sale);
  837. $orders = Order::searchAll([
  838. 'distribution.date' => $date,
  839. ]) ;
  840. $pointSale->initOrders($orders);
  841. echo json_encode([
  842. 'total_point_sale' => number_format($pointSale->revenues, 2) . ' €',
  843. ]);
  844. die();
  845. }
  846. /**
  847. * Crée une commande via une requête AJAX.
  848. *
  849. * @param string $date
  850. * @param integer $id_pv
  851. * @param integer $id_user
  852. * @param string $username
  853. * @param array $produits
  854. * @param string $commentaire
  855. */
  856. public function actionAjaxCreate(
  857. $date, $idPointSale, $idUser, $username, $products, $comment)
  858. {
  859. $products = json_decode($products);
  860. $pointSale = PointSale::findOne($idPointSale);
  861. $distribution = Distribution::searchOne([
  862. 'date' => $date
  863. ]);
  864. if (preg_match("/^[0-9]{4}-(0[1-9]|1[0-2])-(0[1-9]|[1-2][0-9]|3[0-1])$/", $date) &&
  865. ($idUser || strlen($username)) &&
  866. $pointSale &&
  867. count($products) &&
  868. $distribution) {
  869. $order = new Order;
  870. $order->date = date('Y-m-d H:i:s', strtotime($date . ' ' . date('H:i:s')));
  871. $order->id_point_sale = $idPointSale;
  872. $order->id_distribution = $distribution->id;
  873. $order->origin = Order::ORIGIN_ADMIN;
  874. $order->comment = $comment;
  875. if ($idUser) {
  876. $order->id_user = $idUser;
  877. // commentaire du point de vente
  878. $userPointSale = UserPointSale::searchOne([
  879. 'id_point_sale' => $idPointSale,
  880. 'id_user' => $idUser
  881. ]) ;
  882. if ($userPointSale && strlen($userPointSale->comment)) {
  883. $order->comment_point_sale = $userPointSale->comment;
  884. }
  885. } else {
  886. $order->username = $username;
  887. $order->id_user = 0;
  888. }
  889. $order->save();
  890. foreach ($products as $key => $quantity) {
  891. $product = Product::findOne($key);
  892. if ($product) {
  893. $productOrder = new ProductOrder;
  894. $productOrder->id_order = $order->id;
  895. $productOrder->id_product = $key;
  896. $productOrder->quantity = $quantity;
  897. $productOrder->price = $product->price;
  898. $productOrder->save();
  899. }
  900. }
  901. // total point de vente
  902. $pointSale = PointSale::findOne($order->id_point_sale);
  903. $orders = Order::searchAll([
  904. 'distribution.date' => $date
  905. ]) ;
  906. $pointSale->initOrders($orders);
  907. // json commande
  908. $order = Order::searchOne([
  909. 'id' => $order->id
  910. ]) ;
  911. $products = [];
  912. foreach ($order->productOrder as $productOrder) {
  913. $products[$productOrder->id_product] = $productOrder->quantity;
  914. }
  915. $jsonOrder = json_encode(['amount' => number_format($order->amount, 2), 'products' => $products]);
  916. $jsonOrder = $order->getDataJson();
  917. $str_user = '';
  918. if ($order->user) {
  919. $strUser = $order->user->name . ' ' . $order->user->lastname;
  920. }
  921. else {
  922. $strUser = $order->username;
  923. }
  924. $strComment = '';
  925. if (strlen($order->comment)) {
  926. $strComment = ' <span class="glyphicon glyphicon-comment"></span>';
  927. }
  928. $strLabelOrderOrigin = '';
  929. if ($order->origin) {
  930. $strLabelOrderOrigin = ' <span class="label label-warning">vous</span>';
  931. }
  932. echo json_encode([
  933. 'id_order' => $order->id,
  934. 'total_point_sale' => number_format($pointSale->revenues, 2) . ' €',
  935. 'order' => '<li>'
  936. . '<a class="btn btn-default" href="javascript:void(0);" '
  937. . 'data-pv-id="' . $idPointSale . '" '
  938. . 'data-id-commande="' . $order->id . '" '
  939. . 'data-commande=\'' . $jsonOrder. '\' '
  940. . 'data-date="' . date('d/m H:i', strtotime($order->date)) . '">'
  941. . '<span class="montant">' . number_format($order->amount, 2) . ' €</span>'
  942. . '<span class="user">' . $strLabelOrderOrigin . ' ' . $strUser . '</span>'
  943. . $strComment
  944. . '</a></li>',
  945. ]);
  946. die();
  947. }
  948. }
  949. /**
  950. * Retourne un récapitulatif du total des commandes (potentiel, commandé et
  951. * par produits) au format HTML;
  952. *
  953. * @param string $date
  954. */
  955. public function actionAjaxTotalOrders($date) {
  956. $distribution = Distribution::searchOne([
  957. 'date' => $date
  958. ]) ;
  959. if ($distribution) {
  960. // produits
  961. $products = Product::searchAll() ;
  962. // commandes
  963. $orders = Order::searchAll([
  964. 'distribution.date' => $date
  965. ]) ;
  966. $revenues = 0;
  967. $weight = 0;
  968. foreach ($orders as $c) {
  969. if(is_null($c->date_delete)) {
  970. $revenues += $c->amount;
  971. $weight += $c->weight;
  972. }
  973. }
  974. // produits selec pour production
  975. $selectedProducts = ProductDistribution::searchByDistribution($distribution->id);
  976. $potentialTurnover = 0;
  977. $totalWeight = 0;
  978. foreach ($selectedProducts as $idSelectedProduct => $selectedProduct) {
  979. if ($selectedProduct['active']) {
  980. foreach ($products as $product) {
  981. if ($product->id == $idSelectedProduct) {
  982. $potentialTurnover += $selectedProduct['quantity_max'] * $product->price;
  983. $totalWeight += $selectedProduct['quantity_max'] * $product->weight / 1000;
  984. }
  985. }
  986. }
  987. }
  988. $htmlTotals = $this->renderPartial('_total_orders.php', [
  989. 'arrayProducts' => $products,
  990. 'arrayOrders' => $orders,
  991. 'arrayProductsSelected' => $selectedProducts,
  992. 'revenues' => $revenues,
  993. 'totalWeight' => $totalWeight,
  994. 'potentialTurnover' => $potentialTurnover,
  995. 'weight' => $weight,
  996. ]);
  997. echo json_encode([
  998. 'html_totals' => $htmlTotals,
  999. ]);
  1000. }
  1001. die();
  1002. }
  1003. /**
  1004. * Active ou désactive la livraison dans un point de vente.
  1005. *
  1006. * @param integer $id_production
  1007. * @param integer $id_point_vente
  1008. * @param boolean $bool_livraison
  1009. */
  1010. public function actionAjaxPointSaleDelivery(
  1011. $idDistribution, $idPointSale, $boolDelivery)
  1012. {
  1013. $pointSaleDistribution = PointSaleDistribution::searchOne([
  1014. 'id_distribution' => $idDistribution,
  1015. 'id_point_sale' => $idPointSale,
  1016. ]) ;
  1017. if ($pointSaleDistribution) {
  1018. $pointSaleDistribution->delivery = $boolDelivery;
  1019. $pointSaleDistribution->save();
  1020. }
  1021. die();
  1022. }
  1023. /**
  1024. * Retourne l'état du paiement (historique, crédit) d'une commande donnée.
  1025. *
  1026. * @param integer $idOrder
  1027. */
  1028. public function actionPaymentStatus($idOrder)
  1029. {
  1030. $order = Order::searchOne(['id' => $idOrder]) ;
  1031. if ($order) {
  1032. $html = '';
  1033. if ($order->id_user) {
  1034. $userProducer = UserProducer::find()
  1035. ->where([
  1036. 'id_user' => $order->id_user,
  1037. 'id_producer' => $order->distribution->id_producer
  1038. ])
  1039. ->one();
  1040. $amountPaid = $order->getAmount(Order::AMOUNT_PAID);
  1041. if (abs($order->amount - $amountPaid) < 0.0001) {
  1042. $html .= '<span class="label label-success">Payé</span>';
  1043. $buttonsCredit = Html::a('Rembourser ' . $order->getAmount(Order::AMOUNT_TOTAL, true), 'javascript:void(0);', ['class' => 'btn btn-default btn-xs rembourser', 'data-montant' => $order->amount, 'data-type' => 'refund']);
  1044. } elseif ($order->amount > $amountPaid) {
  1045. $amountToPay = $order->amount - $amountPaid;
  1046. $html .= '<span class="label label-danger">Non payé</span> reste <strong>' . number_format($amountToPay, 2) . ' €</strong> à payer';
  1047. $buttonsCredit = Html::a('Payer ' . number_format($amountToPay, 2) . ' €', 'javascript:void(0);', ['class' => 'btn btn-default btn-xs payer', 'data-montant' => $amountToPay, 'data-type' => 'payment']);
  1048. } elseif ($order->amount < $amountPaid) {
  1049. $amountToRefund = $amountPaid - $order->amount;
  1050. $html .= ' <span class="label label-success">Payé</span> <strong>' . number_format($amountToRefund, 2) . ' €</strong> à rembourser';
  1051. $buttonsCredit = Html::a('Rembourser ' . number_format($amountToRefund, 2) . ' €', 'javascript:void(0);', ['class' => 'btn btn-default btn-xs rembourser', 'data-montant' => $amountToRefund, 'data-type' => 'refund']);
  1052. }
  1053. $html .= '<span class="buttons-credit">'
  1054. . 'Crédit : <strong>' . number_format($userProducer->credit, 2) . ' €</strong><br />'
  1055. . $buttonsCredit
  1056. . '</span>';
  1057. // historique
  1058. $history = CreditHistory::find()
  1059. ->with('userAction')
  1060. ->where(['id_order' => $idOrder])
  1061. ->all();
  1062. $html .= '<br /><br /><strong>Historique</strong><br /><table class="table table-condensed table-bordered">'
  1063. . '<thead><tr><th>Date</th><th>Utilisateur</th><th>Action</th><th>- Débit</th><th>+ Crédit</th></tr></thead>'
  1064. . '<tbody>';
  1065. if ($history && is_array($history) && count($history)) {
  1066. foreach ($history as $h) {
  1067. $html .= '<tr>'
  1068. . '<td>' . date('d/m/Y H:i:s', strtotime($h->date)) . '</td>'
  1069. . '<td>' . Html::encode($h->strUserAction()) . '</td>'
  1070. . '<td>' . $h->getStrWording() . '</td>'
  1071. . '<td>' . ($h->isTypeDebit() ? '- '.$h->getAmount(Order::AMOUNT_TOTAL,true) : '') . '</td>'
  1072. . '<td>' . ($h->isTypeCredit() ? '+ '.$h->getAmount(Order::AMOUNT_TOTAL,true) : '') . '</td>'
  1073. . '</tr>';
  1074. }
  1075. } else {
  1076. $html .= '<tr><td colspan="4">Aucun résultat</td></tr>';
  1077. }
  1078. $html .= '</tbody></table>';
  1079. } else {
  1080. $html .= '<div class="alert alert-warning">Pas de gestion de crédit pain pour cette commande car elle n\'est pas liée à un compte utilisateur.</div>';
  1081. }
  1082. echo json_encode([
  1083. 'html_payment_status' => $html,
  1084. 'json_order' => $order->getDataJson()
  1085. ]);
  1086. }
  1087. die();
  1088. }
  1089. /**
  1090. * Effectue le paiement/remboursement d'une commande.
  1091. *
  1092. * @param integer $id_commande
  1093. * @param string $type
  1094. * @param float $montant
  1095. * @return string
  1096. */
  1097. public function actionPayment($idOrder, $type, $amount)
  1098. {
  1099. $order = Order::searchOne([
  1100. 'id' => $idOrder
  1101. ]) ;
  1102. if ($order) {
  1103. $order->saveCreditHistory(
  1104. $type,
  1105. $amount,
  1106. Producer::getId(),
  1107. $order->id_user,
  1108. User::getCurrentId()
  1109. );
  1110. }
  1111. return $this->actionPaymentStatus($idOrder);
  1112. }
  1113. }