[['id_user', 'date', 'id_point_sale', 'id_production'], 'required', 'message' => ''], | [['id_user', 'date', 'id_point_sale', 'id_production'], 'required', 'message' => ''], | ||||
[['id_user', 'id_point_sale', 'id_production'], 'integer'], | [['id_user', 'id_point_sale', 'id_production'], 'integer'], | ||||
[['auto_payment'], 'boolean'], | [['auto_payment'], 'boolean'], | ||||
[['date', 'date_update', 'comment', 'point_sale_comment'], 'safe'] | |||||
[['date', 'date_update', 'comment', 'comment_point_sale'], 'safe'] | |||||
]; | ]; | ||||
} | } | ||||
if (strlen($this->sale_point_comment)) { | if (strlen($this->sale_point_comment)) { | ||||
$html .= '<div class="commentaire"><span>' | $html .= '<div class="commentaire"><span>' | ||||
. Html::encode($this->sale_point_comment) | |||||
. Html::encode($this->comment_point_sale) | |||||
. '</span></div>'; | . '</span></div>'; | ||||
} | } | ||||
} else { | } else { |
* Relations | * Relations | ||||
*/ | */ | ||||
public function getPointSaleUser() | |||||
public function getUserPointSale() | |||||
{ | { | ||||
return $this->hasMany( | return $this->hasMany( | ||||
PointSaleUser::className(), | |||||
UserPointSale::className(), | |||||
['id_point_sale' => 'id'] | ['id_point_sale' => 'id'] | ||||
); | ); | ||||
} | } | ||||
public function getProductionPointVente() | |||||
public function getPointSaleDistribution() | |||||
{ | { | ||||
return $this->hasMany( | return $this->hasMany( | ||||
ProductionPointVente::className(), | |||||
PointSaleDistribution::className(), | |||||
['id_point_sale' => 'id'] | ['id_point_sale' => 'id'] | ||||
); | ); | ||||
} | } |
* | * | ||||
* @return array | * @return array | ||||
*/ | */ | ||||
public function getBookmarksProducers() | |||||
public function getBookmarkedProducers() | |||||
{ | { | ||||
$producers = (new \yii\db\Query()) | $producers = (new \yii\db\Query()) | ||||
->select('*') | ->select('*') |
<?php | |||||
/** | |||||
Copyright La boîte à pain (2018) | |||||
contact@laboiteapain.net | |||||
Ce logiciel est un programme informatique servant à aider les producteurs | |||||
à distribuer leur production en circuits courts. | |||||
Ce logiciel est régi par la licence CeCILL soumise au droit français et | |||||
respectant les principes de diffusion des logiciels libres. Vous pouvez | |||||
utiliser, modifier et/ou redistribuer ce programme sous les conditions | |||||
de la licence CeCILL telle que diffusée par le CEA, le CNRS et l'INRIA | |||||
sur le site "http://www.cecill.info". | |||||
En contrepartie de l'accessibilité au code source et des droits de copie, | |||||
de modification et de redistribution accordés par cette licence, il n'est | |||||
offert aux utilisateurs qu'une garantie limitée. Pour les mêmes raisons, | |||||
seule une responsabilité restreinte pèse sur l'auteur du programme, le | |||||
titulaire des droits patrimoniaux et les concédants successifs. | |||||
A cet égard l'attention de l'utilisateur est attirée sur les risques | |||||
associés au chargement, à l'utilisation, à la modification et/ou au | |||||
développement et à la reproduction du logiciel par l'utilisateur étant | |||||
donné sa spécificité de logiciel libre, qui peut le rendre complexe à | |||||
manipuler et qui le réserve donc à des développeurs et des professionnels | |||||
avertis possédant des connaissances informatiques approfondies. Les | |||||
utilisateurs sont donc invités à charger et tester l'adéquation du | |||||
logiciel à leurs besoins dans des conditions permettant d'assurer la | |||||
sécurité de leurs systèmes et ou de leurs données et, plus généralement, | |||||
à l'utiliser et l'exploiter dans les mêmes conditions de sécurité. | |||||
Le fait que vous puissiez accéder à cet en-tête signifie que vous avez | |||||
pris connaissance de la licence CeCILL, et que vous en avez accepté les | |||||
termes. | |||||
*/ | |||||
namespace producer\controllers; | |||||
class CommandeController extends ProducerBaseController | |||||
{ | |||||
public function behaviors() | |||||
{ | |||||
return [ | |||||
'access' => [ | |||||
'class' => AccessControl::className(), | |||||
'rules' => [ | |||||
[ | |||||
'allow' => true, | |||||
'roles' => ['@'], | |||||
] | |||||
], | |||||
], | |||||
]; | |||||
} | |||||
/** | |||||
* Retourne au format JSON toutes les informations relatives à une | |||||
* production donnée. | |||||
* | |||||
* @param integer $id_production | |||||
* @return mixed | |||||
*/ | |||||
public function actionInfosProduction($id_production) | |||||
{ | |||||
$production = Production::findOne($id_production); | |||||
if ($production) { | |||||
$arr = []; | |||||
$produits_dispos = ProductionProduit::findProduits($production->id); | |||||
$arr['produits_dispos'] = $produits_dispos; | |||||
$points_vente = PointVente::find() | |||||
->joinWith(['productionPointVente' => function($q) use ($production) { | |||||
$q->where(['id_production' => $production->id]); | |||||
}]) | |||||
->where([ | |||||
'id_etablissement' => $production->id_etablissement, | |||||
]) | |||||
->all(); | |||||
$arr['points_vente'] = []; | |||||
foreach ($points_vente as $pv) { | |||||
if (isset($pv->productionPointVente) && | |||||
isset($pv->productionPointVente[0])) { | |||||
$arr['points_vente'][$pv->id] = $pv->productionPointVente[0]->livraison; | |||||
} else { | |||||
$arr['points_vente'][$pv->id] = false; | |||||
} | |||||
} | |||||
return json_encode($arr); | |||||
} | |||||
return json_encode([]); | |||||
} | |||||
/** | |||||
* Initialise le formulaire de création/modification de commande. | |||||
* | |||||
* @param Commande $commande | |||||
* @return array | |||||
*/ | |||||
public function initForm($commande = null) { | |||||
// etablissements | |||||
$etablissements = Yii::$app->user->identity->getEtablissementsFavoris(); | |||||
$id_etablissement = $this->getProducer()->id; | |||||
// etablissement | |||||
$etablissement = Etablissement::findOne($id_etablissement); | |||||
// points de vente | |||||
$points_vente = PointVente::find() | |||||
->with('pointVenteUser') | |||||
->where(['id_etablissement' => $id_etablissement]) | |||||
->andWhere('acces_restreint = 0 OR (acces_restreint = 1 AND (SELECT COUNT(*) FROM point_vente_user WHERE point_vente.id = point_vente_user.id_point_vente AND point_vente_user.id_user = :id_user) > 0)') | |||||
->params([':id_user' => Yii::$app->user->identity->id]) | |||||
->all(); | |||||
$arr_points_vente = $points_vente; | |||||
// jours de production | |||||
$heure_limite = 20; | |||||
$date = date('Y-m-d'); | |||||
if (isset($etablissement)) { | |||||
$heure_limite = $etablissement->heure_limite_commande; | |||||
if (date('H') >= $heure_limite) { | |||||
$date = date('Y-m-d', strtotime(date('Y-m-d')) + ($etablissement->delai_commande) * (24 * 60 * 60)); | |||||
} else { | |||||
$date = date('Y-m-d', strtotime(date('Y-m-d')) + ($etablissement->delai_commande - 1) * (24 * 60 * 60)); | |||||
} | |||||
} | |||||
$jours_production = Production::find() | |||||
->where(['actif' => 1]) | |||||
->andWhere('date > :date') | |||||
->andWhere(['id_etablissement' => $id_etablissement]) | |||||
->addParams([':date' => $date]) | |||||
->all(); | |||||
$arr_jours_production = array('' => '--'); | |||||
foreach ($jours_production as $j) | |||||
$arr_jours_production[$j->id] = date('d/m/Y', strtotime($j->date)); | |||||
// produits | |||||
$produits = Produit::find() | |||||
->leftJoin('production_produit', 'produit.id = production_produit.id_produit') | |||||
->where(['produit.actif' => 1, 'id_etablissement' => $id_etablissement]) | |||||
->andWhere('produit.vrac IS NULL OR produit.vrac = 0') | |||||
->orderBy('produit.order ASC')->all(); | |||||
$arr_produits = array(); | |||||
foreach ($produits as $p) | |||||
$arr_produits[] = $p; | |||||
// produits vrac | |||||
$produits_vrac = Produit::find()->where(['actif' => 1, 'vrac' => 1])->orderBy('order ASC')->all(); | |||||
// produits selec | |||||
$posts = Yii::$app->request->post(); | |||||
$produits_selec = []; | |||||
if (isset($posts['Produit'])) { | |||||
foreach ($posts['Produit'] as $key => $quantity) { | |||||
$key = (int) str_replace('produit_', '', $key); | |||||
$p = Produit::find()->where(['id' => $key])->one(); | |||||
if ($p && $quantity) | |||||
$produits_selec[$p->id] = (int) $quantity; | |||||
} | |||||
} | |||||
elseif (!is_null($commande)) { | |||||
$produits_commande = CommandeProduit::find()->where(['id_commande' => $commande->id])->all(); | |||||
foreach ($produits_commande as $pc) { | |||||
$produits_selec[$pc->id_produit] = (int) $pc->quantite; | |||||
} | |||||
} | |||||
$produits_dispos = []; | |||||
$production = null; | |||||
if (!is_null($commande) && $commande->id_production) { | |||||
$produits_dispos = ProductionProduit::findProduits($commande->id_production); | |||||
$production = Production::find()->where(['id' => $commande->id_production])->one(); | |||||
} | |||||
$commandes = Commande::find() | |||||
->where(['id_user' => Yii::$app->user->identity->id]) | |||||
->all(); | |||||
if ($id_etablissement) { | |||||
$user_etablissement = UserEtablissement::find() | |||||
->where([ | |||||
'id_etablissement' => $id_etablissement, | |||||
'id_user' => Yii::$app->user->identity->id | |||||
]) | |||||
->one(); | |||||
$credit = $user_etablissement->credit; | |||||
} else { | |||||
$credit = 0; | |||||
} | |||||
return [ | |||||
'points_vente' => $arr_points_vente, | |||||
'jours_production' => $arr_jours_production, | |||||
'produits' => $produits, | |||||
'produits_selec' => $produits_selec, | |||||
'produits_dispos' => $produits_dispos, | |||||
'production' => $production, | |||||
'commandes_en_cours' => $commandes, | |||||
'produits_vrac' => $produits_vrac, | |||||
'etablissements' => $etablissements, | |||||
'id_etablissement' => $id_etablissement, | |||||
'etablissement' => $etablissement, | |||||
'credit' => $credit | |||||
]; | |||||
} | |||||
/** | |||||
* Affiche l'historique des commandes de l'utilisateur | |||||
* | |||||
* @return ProducerView | |||||
*/ | |||||
public function actionHistorique() | |||||
{ | |||||
$data_provider_commandes = new ActiveDataProvider([ | |||||
'query' => Commande::find() | |||||
->with('commandeProduits', 'pointVente', 'creditHistorique') | |||||
->joinWith('production', 'production.etablissement') | |||||
->where([ | |||||
'id_user' => Yii::$app->user->id, | |||||
'production.id_etablissement' => $this->getProducer()->id | |||||
]) | |||||
->andWhere('date_delete IS NULL') | |||||
->orderBy('production.date DESC'), | |||||
'pagination' => [ | |||||
'pageSize' => 10, | |||||
], | |||||
]); | |||||
return $this->render('historique', [ | |||||
'data_provider_commandes' => $data_provider_commandes, | |||||
'commande_ok' => Yii::$app->getRequest()->get('commande_ok', false), | |||||
'annule_ok' => Yii::$app->getRequest()->get('annule_ok', false), | |||||
]); | |||||
} | |||||
/** | |||||
* Supprime un producteur. | |||||
* | |||||
* @param integer $id | |||||
*/ | |||||
public function actionRemoveEtablissement($id = 0) | |||||
{ | |||||
$user_etablissement = UserEtablissement::find() | |||||
->where(['id_etablissement' => $id, 'id_user' => Yii::$app->user->identity->id]) | |||||
->one(); | |||||
$user_etablissement->actif = 0; | |||||
$user_etablissement->save(); | |||||
$this->redirect(['commande/index']); | |||||
} | |||||
/** | |||||
* Crée une commande. | |||||
* | |||||
* @return mixed | |||||
*/ | |||||
public function actionCreate() | |||||
{ | |||||
$id_etablissement = $this->getProducer()->id ; | |||||
$commande = new Commande; | |||||
$posts = Yii::$app->request->post(); | |||||
if ($id_etablissement) | |||||
$this->_verifEtablissementActif($id_etablissement); | |||||
if ($commande->load($posts)) { | |||||
$commande = Commande::find()->where('id_production = ' . $posts['Commande']['id_production'])->andWhere('id_user = ' . Yii::$app->user->id)->one(); | |||||
if (!$commande) { | |||||
$commande = new Commande; | |||||
$commande->load(Yii::$app->request->post()); | |||||
$commande->id_user = Yii::$app->user->id; | |||||
$commande->date = date('Y-m-d H:i:s'); | |||||
$commande->type = Commande::TYPE_USER; | |||||
} | |||||
$this->gestionForm($commande); | |||||
} | |||||
return $this->render('create', array_merge($this->initForm($commande), [ | |||||
'model' => $commande | |||||
])); | |||||
} | |||||
/** | |||||
* Modifie une commande. | |||||
* | |||||
* @param integer $id | |||||
* @return mixed | |||||
* @throws UserException | |||||
*/ | |||||
public function actionUpdate($id) | |||||
{ | |||||
$commande = Commande::find() | |||||
->with('production') | |||||
->where(['id' => $id]) | |||||
->one(); | |||||
if ($commande->getEtat() != Commande::ETAT_MODIFIABLE) { | |||||
throw new UserException('Cette commande n\'est pas modifiable.'); | |||||
} | |||||
$this->_verifEtablissementActif($commande->production->id_etablissement); | |||||
if ($commande && $commande->load(Yii::$app->request->post())) { | |||||
$commande->date_update = date('Y-m-d H:i:s'); | |||||
$this->gestionForm($commande); | |||||
} | |||||
return $this->render('update', array_merge($this->initForm($commande), [ | |||||
'model' => $commande, | |||||
'commande_introuvable' => !$commande, | |||||
])); | |||||
} | |||||
/** | |||||
* Vérifie si un producteur est actif. | |||||
* | |||||
* @param integer $id_etablissement | |||||
* @throws NotFoundHttpException | |||||
*/ | |||||
public function _verifEtablissementActif($id_etablissement) | |||||
{ | |||||
$etablissement = Etablissement::findOne($id_etablissement); | |||||
if ($etablissement && !$etablissement->actif) { | |||||
throw new NotFoundHttpException('Cet établissement est actuellement hors ligne.'); | |||||
} | |||||
} | |||||
/** | |||||
* Traite le formulaire de création/modification de commande. | |||||
* | |||||
* @param Commande $commande | |||||
*/ | |||||
public function gestionForm($commande) | |||||
{ | |||||
$posts = Yii::$app->request->post(); | |||||
$produits = array(); | |||||
$quantite_totale = 0; | |||||
foreach ($posts['Produit'] as $key => $quantity) { | |||||
$key = (int) str_replace('produit_', '', $key); | |||||
$p = Produit::find()->where(['id' => $key])->one(); | |||||
$quantite_totale += $quantity; | |||||
if ($p && $quantity) | |||||
$produits[] = $p; | |||||
} | |||||
// nombre de produits | |||||
$err_nb_produits = false; | |||||
if (!Yii::$app->user->identity->confiance && $quantite_totale > 3) { | |||||
$err_nb_produits = true; | |||||
} | |||||
// date | |||||
$err_date = false; | |||||
$pate_deja_petrie = false; | |||||
if (isset($commande->id_production)) { | |||||
// date de commande | |||||
$production = Production::find()->where(['id' => $commande->id_production])->one(); | |||||
if (date('H') >= 20) { | |||||
$date = date('Y-m-d', strtotime(date('Y-m-d')) + 60 * 60 * 24); | |||||
} else { | |||||
$date = date('Y-m-d'); | |||||
} | |||||
if ($production->date < $date) { | |||||
$err_date = true; | |||||
} | |||||
} | |||||
// point de vente | |||||
$err_point_vente = false; | |||||
if (isset($production) && $production) { | |||||
$ppv = ProductionPointVente::find() | |||||
->where([ | |||||
'id_production' => $production->id, | |||||
'id_point_vente' => $posts['Commande']['id_point_vente'] | |||||
]) | |||||
->one(); | |||||
if (!$ppv || !$ppv->livraison) { | |||||
$err_point_vente = true; | |||||
} | |||||
$point_vente = PointVente::findOne($posts['Commande']['id_point_vente']); | |||||
if ($point_vente) { | |||||
if (strlen($point_vente->code) && !$point_vente->verifCode($posts['code_point_vente_' . $point_vente->id])) { | |||||
$err_point_vente = true; | |||||
} | |||||
} else { | |||||
$err_point_vente = true; | |||||
} | |||||
} | |||||
if ($commande->validate() && count($produits) && !$err_nb_produits && !$err_date && !$err_point_vente) { | |||||
// gestion point de vente | |||||
$pv = PointVente::find() | |||||
->with('pointVenteUser') | |||||
->where(['id' => $commande->id_point_vente]) | |||||
->one(); | |||||
if ($pv && strlen($pv->getCommentaire())) | |||||
$commande->commentaire_point_vente = $pv->getCommentaire(); | |||||
else | |||||
$commande->commentaire_point_vente = ''; | |||||
// sauvegarde de la commande | |||||
$commande->save(); | |||||
// ajout de l'utilisateur à l'établissement | |||||
Etablissement::addUser(Yii::$app->user->identity->id, $production->id_etablissement) ; | |||||
// suppression de tous les enregistrements CommandeProduit | |||||
if (!is_null($commande)) { | |||||
CommandeProduit::deleteAll(['id_commande' => $commande->id]); | |||||
} | |||||
// produits dispos | |||||
$produits_dispos = ProductionProduit::findProduits($production->id); | |||||
// sauvegarde des produits | |||||
foreach ($produits as $p) { | |||||
if (isset($produits_dispos[$p->id])) { | |||||
$commande_produit = new CommandeProduit(); | |||||
$commande_produit->id_commande = $commande->id; | |||||
$commande_produit->id_produit = $p->id; | |||||
$commande_produit->prix = $p->prix; | |||||
$quantite_voulue = (int) $posts['Produit']['produit_' . $p->id]; | |||||
if ($produits_dispos[$p->id]['quantite_max'] && $quantite_voulue > $produits_dispos[$p->id]['quantite_restante']) | |||||
$quantite_voulue = $produits_dispos[$p->id]['quantite_restante']; | |||||
$commande_produit->quantite = $quantite_voulue; | |||||
$commande_produit->save(); | |||||
} | |||||
} | |||||
// credit pain | |||||
$credit_pain = isset($posts['credit_pain']) && $posts['credit_pain']; | |||||
if ($credit_pain && ($pv->credit_pain || $commande->getMontantPaye())) { | |||||
$commande = Commande::find() | |||||
->with('commandeProduits') | |||||
->where(['id' => $commande->id]) | |||||
->one(); | |||||
$commande->init(); | |||||
$montant_paye = $commande->getMontantPaye(); | |||||
// à payer | |||||
if ($commande->getStatutPaiement() == Commande::STATUT_IMPAYEE) { | |||||
$montant_payer = $commande->montant - $montant_paye; | |||||
$credit = Yii::$app->user->identity->getCredit($production->id_etablissement); | |||||
if ($montant_payer > $credit) { | |||||
$montant_payer = $credit; | |||||
} | |||||
if ($montant_payer > 0) { | |||||
$commande->creditHistorique( | |||||
CreditHistorique::TYPE_PAIEMENT, | |||||
$montant_payer, | |||||
$production->id_etablissement, | |||||
Yii::$app->user->identity->id, | |||||
Yii::$app->user->identity->id | |||||
); | |||||
} | |||||
} | |||||
// surplus à rembourser | |||||
elseif ($commande->getStatutPaiement() == Commande::STATUT_SURPLUS) { | |||||
$montant_rembourser = $montant_paye - $commande->montant; | |||||
$commande->creditHistorique( | |||||
CreditHistorique::TYPE_REMBOURSEMENT, | |||||
$montant_rembourser, | |||||
$production->id_etablissement, | |||||
Yii::$app->user->identity->id, | |||||
Yii::$app->user->identity->id | |||||
); | |||||
} | |||||
} | |||||
// redirection | |||||
$this->redirect(Yii::$app->urlManager->createUrl(['commande/historique', 'commande_ok' => true, 'pate_deja_petrie' => $pate_deja_petrie])); | |||||
} else { | |||||
if (!count($produits)) | |||||
Yii::$app->session->setFlash('error', "Vous n'avez choisi aucun produit"); | |||||
if ($err_nb_produits) | |||||
Yii::$app->session->setFlash('error', "Vous ne pouvez pas commander plus de 3 produits"); | |||||
if ($err_date) | |||||
Yii::$app->session->setFlash('error', "Vous ne pouvez pas commander pour cette date."); | |||||
if ($err_point_vente) | |||||
Yii::$app->session->setFlash('error', "Point de vente invalide."); | |||||
} | |||||
} | |||||
/** | |||||
* Annule une commande. | |||||
* | |||||
* @param integer $id | |||||
* @throws \yii\web\NotFoundHttpException | |||||
* @throws UserException | |||||
*/ | |||||
public function actionAnnuler($id) | |||||
{ | |||||
$commande = Commande::find() | |||||
->with('production', 'creditHistorique', 'commandeProduits') | |||||
->where(['id' => $id]) | |||||
->one(); | |||||
if(!$commande) | |||||
throw new \yii\web\NotFoundHttpException('Commande introuvable'); | |||||
if ($commande->getEtat() != Commande::ETAT_MODIFIABLE) { | |||||
throw new UserException('Vous ne pouvez plus annuler cette commande.'); | |||||
} | |||||
$commande->init(); | |||||
if ($commande && Yii::$app->user->id == $commande->id_user) { | |||||
// remboursement | |||||
if ($commande->getMontantPaye()) { | |||||
$commande->creditHistorique( | |||||
CreditHistorique::TYPE_REMBOURSEMENT, | |||||
$commande->getMontantPaye(), | |||||
$commande->production->id_etablissement, | |||||
Yii::$app->user->identity->id, | |||||
Yii::$app->user->identity->id | |||||
); | |||||
} | |||||
// delete | |||||
$commande->date_delete = date('Y-m-d H:i:s'); | |||||
$commande->save() ; | |||||
Yii::$app->session->setFlash('success','Votre commande a bien été annulée.') ; | |||||
} | |||||
$this->redirect(Yii::$app->urlManager->createUrl(['commande/historique'])); | |||||
} | |||||
/** | |||||
* Vérifie le code saisi pour un point de vente. | |||||
* | |||||
* @param integer $id_point_vente | |||||
* @param string $code | |||||
* @return boolean | |||||
*/ | |||||
public function actionVerifCodePointVente($id_point_vente, $code) | |||||
{ | |||||
$point_vente = PointVente::findOne($id_point_vente); | |||||
if ($point_vente) { | |||||
if ($point_vente->verifCode($code)) { | |||||
return true; | |||||
} | |||||
} | |||||
return false; | |||||
} | |||||
} | |||||
<?php | |||||
/** | |||||
Copyright La boîte à pain (2018) | |||||
contact@laboiteapain.net | |||||
Ce logiciel est un programme informatique servant à aider les producteurs | |||||
à distribuer leur production en circuits courts. | |||||
Ce logiciel est régi par la licence CeCILL soumise au droit français et | |||||
respectant les principes de diffusion des logiciels libres. Vous pouvez | |||||
utiliser, modifier et/ou redistribuer ce programme sous les conditions | |||||
de la licence CeCILL telle que diffusée par le CEA, le CNRS et l'INRIA | |||||
sur le site "http://www.cecill.info". | |||||
En contrepartie de l'accessibilité au code source et des droits de copie, | |||||
de modification et de redistribution accordés par cette licence, il n'est | |||||
offert aux utilisateurs qu'une garantie limitée. Pour les mêmes raisons, | |||||
seule une responsabilité restreinte pèse sur l'auteur du programme, le | |||||
titulaire des droits patrimoniaux et les concédants successifs. | |||||
A cet égard l'attention de l'utilisateur est attirée sur les risques | |||||
associés au chargement, à l'utilisation, à la modification et/ou au | |||||
développement et à la reproduction du logiciel par l'utilisateur étant | |||||
donné sa spécificité de logiciel libre, qui peut le rendre complexe à | |||||
manipuler et qui le réserve donc à des développeurs et des professionnels | |||||
avertis possédant des connaissances informatiques approfondies. Les | |||||
utilisateurs sont donc invités à charger et tester l'adéquation du | |||||
logiciel à leurs besoins dans des conditions permettant d'assurer la | |||||
sécurité de leurs systèmes et ou de leurs données et, plus généralement, | |||||
à l'utiliser et l'exploiter dans les mêmes conditions de sécurité. | |||||
Le fait que vous puissiez accéder à cet en-tête signifie que vous avez | |||||
pris connaissance de la licence CeCILL, et que vous en avez accepté les | |||||
termes. | |||||
*/ | |||||
namespace producer\controllers; | |||||
use common\models\ProductDistribution ; | |||||
class OrderController extends ProducerBaseController | |||||
{ | |||||
public function behaviors() | |||||
{ | |||||
return [ | |||||
'access' => [ | |||||
'class' => AccessControl::className(), | |||||
'rules' => [ | |||||
[ | |||||
'allow' => true, | |||||
'roles' => ['@'], | |||||
] | |||||
], | |||||
], | |||||
]; | |||||
} | |||||
/** | |||||
* Retourne au format JSON toutes les informations relatives à une | |||||
* production donnée. | |||||
* | |||||
* @param integer $idDistribution | |||||
* @return mixed | |||||
*/ | |||||
public function actionInfosDistribution($idDistribution) | |||||
{ | |||||
$distribution = Distribution::searchOne($idDistribution); | |||||
if ($distribution) { | |||||
$arr = []; | |||||
$productsArray = ProductDistribution::searchByDistribution($distribution->id) ; | |||||
$data['products'] = $productsArray; | |||||
$pointSaleArray = PointSale::find() | |||||
->joinWith(['pointSaleDistribution' => function($q) use ($distribution) { | |||||
$q->where(['id_distribution' => $distribution->id]); | |||||
}]) | |||||
->where([ | |||||
'id_producer' => $distribution->id_producer, | |||||
]) | |||||
->all(); | |||||
$data['pointsSale'] = []; | |||||
foreach ($pointSaleArray as $pointSale) { | |||||
if (isset($pointSale->pointSaleDistribution) && | |||||
isset($pointSale->pointSaleDistribution[0])) { | |||||
$data['points_vente'][$pointSale->id] = $pointSale->pointSaleDistribution[0]->delivery; | |||||
} else { | |||||
$data['points_vente'][$pointSale->id] = false; | |||||
} | |||||
} | |||||
return json_encode($data); | |||||
} | |||||
return json_encode([]); | |||||
} | |||||
/** | |||||
* Initialise le formulaire de création/modification de commande. | |||||
* | |||||
* @param Order $order | |||||
* @return array | |||||
*/ | |||||
public function initForm($order = null) { | |||||
// Producteurs | |||||
$producersArray = Yii::$app->user->identity->getBookmarkedProducers(); | |||||
$idProducer = $this->getProducer()->id; | |||||
// Producteur | |||||
$producer = Producer::findOne($idProducer); | |||||
// Points de vente | |||||
$pointsSaleArray = PointSale::find() | |||||
->with('userPointSale') | |||||
->where(['id_producer' => $idProducer]) | |||||
->andWhere('restricted_access = 0 OR (restricted_access = 1 AND (SELECT COUNT(*) FROM user_point_sale WHERE point_sale.id = user_point_sale.id_point_sale AND point_sale_user.id_user = :id_user) > 0)') | |||||
->params([':id_user' => User::getId()]) | |||||
->all(); | |||||
// jours de production | |||||
$deadline = 20; | |||||
$date = date('Y-m-d'); | |||||
if (isset($producer)) { | |||||
$deadline = $producer->order_deadline; | |||||
if (date('H') >= $deadline) { | |||||
$date = date('Y-m-d', strtotime(date('Y-m-d')) + ($producer->order_delay) * (24 * 60 * 60)); | |||||
} else { | |||||
$date = date('Y-m-d', strtotime(date('Y-m-d')) + ($producer->order_delay - 1) * (24 * 60 * 60)); | |||||
} | |||||
} | |||||
$distributionDays = Distribution::find() | |||||
->where(['active' => 1]) | |||||
->andWhere('date > :date') | |||||
->andWhere(['id_producer' => $idProducer]) | |||||
->addParams([':date' => $date]) | |||||
->all(); | |||||
$distributionDaysArray = array('' => '--'); | |||||
foreach ($distributionDays as $distribution) { | |||||
$distributionDaysArray[$distribution->id] = date('d/m/Y', strtotime($distribution->date)); | |||||
} | |||||
// produits | |||||
$products = Product::find() | |||||
->leftJoin('product_distribution', 'product.id = product_distribution.id_product') | |||||
->where(['product.active' => 1, 'id_producer' => $idProducer]) | |||||
->orderBy('product.order ASC')->all(); | |||||
$productsArray = [] ; | |||||
foreach ($products as $p) | |||||
$productsArray[] = $p; | |||||
// produits selec | |||||
$posts = Yii::$app->request->post(); | |||||
$selectedProducts = []; | |||||
if (isset($posts['Product'])) { | |||||
foreach ($posts['Product'] as $key => $quantity) { | |||||
$key = (int) str_replace('product_', '', $key); | |||||
$product = Product::find()->where(['id' => $key])->one(); | |||||
if ($product && $quantity) | |||||
$selectedProducts[$product->id] = (int) $quantity; | |||||
} | |||||
} | |||||
elseif (!is_null($order)) { | |||||
$productOrderArray = ProductOrder::searchAll([ | |||||
'id_order' => $order->id | |||||
]) ; | |||||
foreach ($productOrderArray as $productOrder) { | |||||
$selectedProducts[$productOrder->id_product] = (int) $productOrder->quantity; | |||||
} | |||||
} | |||||
$availableProducts = [] ; | |||||
$distribution = null; | |||||
if (!is_null($order) && $order->id_distribution) { | |||||
$availableProducts = ProductDistribution::searchByDistribution($order->id_distribution); | |||||
$distribution = Distribution::find()->where(['id' => $order->id_distribution])->one(); | |||||
} | |||||
$orders = Order::searchAll([ | |||||
'id_user' => User::getId() | |||||
]) ; | |||||
if ($idProducer) { | |||||
$userProducer = UserProducer::searchOne([ | |||||
'id_producer' => $idProducer, | |||||
'id_user' => User::getId() | |||||
]) ; | |||||
$credit = $userProducer->credit; | |||||
} else { | |||||
$credit = 0; | |||||
} | |||||
return [ | |||||
'pointsSaleArray' => $pointsSaleArray, | |||||
'distributionDaysArray' => $distributionDaysArray, | |||||
'productsArray' => $productsArray, | |||||
'selectedProducts' => $selectedProducts, | |||||
'availableProducts' => $availableProducts, | |||||
'distribution' => $distribution, | |||||
'ordersArray' => $orders, | |||||
'producersArray' => $producersArray, | |||||
'idProducer' => $idProducer, | |||||
'producer' => $producer, | |||||
'credit' => $credit | |||||
]; | |||||
} | |||||
/** | |||||
* Affiche l'historique des commandes de l'utilisateur | |||||
* | |||||
* @return ProducerView | |||||
*/ | |||||
public function actionHistory() | |||||
{ | |||||
$dataProviderOrders = new ActiveDataProvider([ | |||||
'query' => Order::find() | |||||
->with('productOrder', 'pointSale', 'creditHistory') | |||||
->joinWith('distribution', 'distribution.producer') | |||||
->where([ | |||||
'id_user' => Yii::$app->user->id, | |||||
'distribution.id_producer' => $this->getProducer()->id | |||||
]) | |||||
->andWhere('date_delete IS NULL') | |||||
->orderBy('distribution.date DESC'), | |||||
'pagination' => [ | |||||
'pageSize' => 10, | |||||
], | |||||
]); | |||||
return $this->render('history', [ | |||||
'dataProviderOrders' => $dataProviderOrders, | |||||
'orderOk' => Yii::$app->getRequest()->get('orderOk', false), | |||||
'cancelOk' => Yii::$app->getRequest()->get('cancelOk', false), | |||||
]); | |||||
} | |||||
/** | |||||
* Supprime un producteur. | |||||
* | |||||
* @param integer $id | |||||
*/ | |||||
public function actionRemoveProducer($id = 0) | |||||
{ | |||||
$userProducer = UserProducer::find() | |||||
->where(['id_producer' => $id, 'id_user' => User::getId()]) | |||||
->one(); | |||||
$userProducer->active = 0; | |||||
$userProducer->save(); | |||||
$this->redirect(['order/index']); | |||||
} | |||||
/** | |||||
* Crée une commande. | |||||
* | |||||
* @return mixed | |||||
*/ | |||||
public function actionCreate() | |||||
{ | |||||
$idProducer = $this->getProducer()->id ; | |||||
$order = new Order; | |||||
$posts = Yii::$app->request->post(); | |||||
if ($idProducer) { | |||||
$this->_verifyProducerActive($idProducer); | |||||
} | |||||
if ($order->load($posts)) { | |||||
$order = Order::find()->where('id_distribution = ' . $posts['Order']['id_distribution'])->andWhere('id_user = ' . User::getid())->one(); | |||||
if (!$order) { | |||||
$order = new Order; | |||||
$order->load(Yii::$app->request->post()); | |||||
$order->id_user = User::getId(); | |||||
$order->date = date('Y-m-d H:i:s'); | |||||
$order->type = Order::ORIGIN_USER; | |||||
} | |||||
$this->processForm($Order); | |||||
} | |||||
return $this->render('create', array_merge($this->initForm($order), [ | |||||
'model' => $order | |||||
])); | |||||
} | |||||
/** | |||||
* Modifie une commande. | |||||
* | |||||
* @param integer $id | |||||
* @return mixed | |||||
* @throws UserException | |||||
*/ | |||||
public function actionUpdate($id) | |||||
{ | |||||
$order = sOrder::searchOne([ | |||||
'id' => $id | |||||
]) ; | |||||
if ($order->getState() != Order::STATE_OPEN) { | |||||
throw new UserException('Cette commande n\'est pas modifiable.'); | |||||
} | |||||
$this->_verifyProducerActive($order->distribution->id_producer); | |||||
if ($order && $order->load(Yii::$app->request->post())) { | |||||
$order->date_update = date('Y-m-d H:i:s'); | |||||
$this->processForm($order); | |||||
} | |||||
return $this->render('update', array_merge($this->processForm($order), [ | |||||
'model' => $order, | |||||
'order_notfound' => !$order, | |||||
])); | |||||
} | |||||
/** | |||||
* Vérifie si un producteur est actif. | |||||
* | |||||
* @param integer $idProducer | |||||
* @throws NotFoundHttpException | |||||
*/ | |||||
public function _verifyProducerActive($idProducer) | |||||
{ | |||||
$producer = Producer::findOne($idProducer); | |||||
if ($producer && !$producer->active) { | |||||
throw new NotFoundHttpException('Ce producteur est actuellement hors ligne.'); | |||||
} | |||||
} | |||||
/** | |||||
* Traite le formulaire de création/modification de commande. | |||||
* | |||||
* @param Commande $order | |||||
*/ | |||||
public function processForm($order) | |||||
{ | |||||
$posts = Yii::$app->request->post(); | |||||
$productsArray = []; | |||||
$totalQuantity = 0; | |||||
foreach ($posts['Product'] as $key => $quantity) { | |||||
$key = (int) str_replace('product_', '', $key); | |||||
$product = Produit::find()->where(['id' => $key])->one(); | |||||
$totalQuantity += $quantity; | |||||
if ($product && $quantity) { | |||||
$productsArray[] = $product; | |||||
} | |||||
} | |||||
// date | |||||
$errorDate = false; | |||||
if (isset($order->id_distribution)) { | |||||
// date de commande | |||||
$distribution = Distribution::find()->where(['id' => $order->id_distribution])->one(); | |||||
if (date('H') >= 20) { | |||||
$date = date('Y-m-d', strtotime(date('Y-m-d')) + 60 * 60 * 24); | |||||
} else { | |||||
$date = date('Y-m-d'); | |||||
} | |||||
if ($distribution->date < $date) { | |||||
$errorDate = true; | |||||
} | |||||
} | |||||
// point de vente | |||||
$errorPointSale = false; | |||||
if (isset($distribution) && $distribution) { | |||||
$pointSaleDistribution = PointSaleDistribution::searchOne([ | |||||
'id_distribution' => $distribution->id, | |||||
'id_point_sale' => $posts['Order']['id_point_sale'] | |||||
]) ; | |||||
if (!$pointSaleDistribution || !$pointSaleDistribution->delivery) { | |||||
$errorPointSale = true; | |||||
} | |||||
$pointSale = PointSale::findOne($posts['Commande']['id_point_vente']); | |||||
if ($pointSale) { | |||||
if (strlen($pointSale->code) && !$pointSale->validateCode($posts['code_point_sale_' . $pointSale->id])) { | |||||
$errorPointSale = true; | |||||
} | |||||
} else { | |||||
$errorPointSale = true; | |||||
} | |||||
} | |||||
if ($order->validate() && count($productsArray) && !$errorDate && !$errorPointSale) { | |||||
// gestion point de vente | |||||
$pointSale = PointSale::searchOne([ | |||||
'id' => $order->id_point_sale | |||||
]) ; | |||||
if ($pointSale && strlen($pointSale->getComment())) | |||||
$order->comment_point_sale = $pv->getComment(); | |||||
else | |||||
$order->comment_point_sale = ''; | |||||
// sauvegarde de la commande | |||||
$order->save(); | |||||
// ajout de l'utilisateur à l'établissement | |||||
Producer::addUser(User::getId(), $distribution->id_producer) ; | |||||
// suppression de tous les enregistrements ProductOrder | |||||
if (!is_null($order)) { | |||||
ProductOrder::deleteAll(['id_order' => $order->id]); | |||||
} | |||||
// produits dispos | |||||
$availableProducts = ProductDistribution::searchByDistribution($distribution->id) ; | |||||
// sauvegarde des produits | |||||
foreach ($productsArray as $product) { | |||||
if (isset($availableProducts[$product->id])) { | |||||
$productOrder = new ProductOrder(); | |||||
$productOrder->id_order = $order->id; | |||||
$productOrder->id_product = $product->id; | |||||
$productOrder->price = $product->price; | |||||
$quantity = (int) $posts['Product']['product_' . $product->id]; | |||||
if ($produits_dispos[$product->id]['quantity_max'] && $quantity > $availableProducts[$product->id]['quantity_remaining']) { | |||||
$quantity = $availableProducts[$p->id]['quantity_remaining']; | |||||
} | |||||
$productOrder->quantity = $quantity; | |||||
$productOrder->save(); | |||||
} | |||||
} | |||||
// credit | |||||
$credit = isset($posts['credit']) && $posts['credit']; | |||||
if ($credit && ($pointSale->credit || $order->getAmount(Order::AMOUNT_PAID))) { | |||||
$order = Order::searchOne([ | |||||
'id' => $order->id | |||||
]) ; | |||||
$amountPaid = $order->getAmount(Order::AMOUNT_PAID); | |||||
// à payer | |||||
if ($order->getPaymentStatus() == Order::PAYMENT_UNPAID) { | |||||
$amountRemaining = $order->getAmount(Order::AMOUNT_REMAINING) ; | |||||
$credit = Yii::$app->user->identity->getCredit($distribution->id_producer); | |||||
if ($amountRemaining > $credit) { | |||||
$amountRemaining = $credit; | |||||
} | |||||
if ($amountRemaining > 0) { | |||||
$order->creditHistory( | |||||
CreditHistory::TYPE_PAYMENT, | |||||
$amountRemaining, | |||||
$distribution->id_producer, | |||||
User::getId(), | |||||
User::getId() | |||||
); | |||||
} | |||||
} | |||||
// surplus à rembourser | |||||
elseif ($order->getPaymentStatus() == Order::PAYMENT_SURPLUS) { | |||||
$amountSurplus = $order->getAmount(Order::AMOUNT_SURPLUS) ; | |||||
$order->creditHistory( | |||||
CreditHistory::TYPE_REFUND, | |||||
$amountSurplus, | |||||
$distribution->id_producer, | |||||
User::getId(), | |||||
User::getId() | |||||
); | |||||
} | |||||
} | |||||
// redirection | |||||
$this->redirect(Yii::$app->urlManager->createUrl(['order/history', 'orderOk' => true])); | |||||
} | |||||
else { | |||||
if (!count($productsArray)) { | |||||
Yii::$app->session->setFlash('error', "Vous n'avez choisi aucun produit"); | |||||
} | |||||
if ($errorDate) { | |||||
Yii::$app->session->setFlash('error', "Vous ne pouvez pas commander pour cette date."); | |||||
} | |||||
if ($errorPointSale) { | |||||
Yii::$app->session->setFlash('error', "Point de vente invalide."); | |||||
} | |||||
} | |||||
} | |||||
/** | |||||
* Annule une commande. | |||||
* | |||||
* @param integer $id | |||||
* @throws \yii\web\NotFoundHttpException | |||||
* @throws UserException | |||||
*/ | |||||
public function actionCancel($id) | |||||
{ | |||||
$order = Order::searchOne([ | |||||
'id' => $id | |||||
]) ; | |||||
if(!$order) { | |||||
throw new \yii\web\NotFoundHttpException('Commande introuvable'); | |||||
} | |||||
if ($order->getState() != Order::STATE_OPEN) { | |||||
throw new UserException('Vous ne pouvez plus annuler cette commande.'); | |||||
} | |||||
if ($order && User::getId() == $order->id_user) { | |||||
// remboursement | |||||
if ($order->getAmount(Order::AMOUNT_PAID)) { | |||||
$order->creditHistory( | |||||
CreditHistory::PAYMENT_REFUND, | |||||
$order->getAmount(Order::AMOUNT_PAID), | |||||
$order->distribution->id_producer, | |||||
User::getId(), | |||||
User::getId() | |||||
); | |||||
} | |||||
// delete | |||||
$order->date_delete = date('Y-m-d H:i:s'); | |||||
$order->save() ; | |||||
Yii::$app->session->setFlash('success','Votre commande a bien été annulée.') ; | |||||
} | |||||
$this->redirect(Yii::$app->urlManager->createUrl(['order/history'])); | |||||
} | |||||
/** | |||||
* Vérifie le code saisi pour un point de vente. | |||||
* | |||||
* @param integer $idPointSale | |||||
* @param string $code | |||||
* @return boolean | |||||
*/ | |||||
public function actionvalidateCodePointSale($idPointSale, $code) | |||||
{ | |||||
$pointSale = PointSale::findOne($idPointSale); | |||||
if ($pointSale) { | |||||
if ($pointSale->validateCode($code)) { | |||||
return true; | |||||
} | |||||
} | |||||
return false; | |||||
} | |||||
} | |||||