Il s'agit d'une continuation de la série "Créer un site EC avec Rails 5 ⑧](https://qiita.com/GreenFingers_tk/items/0d2caea916a82e234af2), qui crée un site EC où vous pouvez faire vos achats dans une boulangerie fictive. Cette fois, nous allons faire une fonction de panier. L'apparition du site EC est enfin prête.
https://github.com/Sn16799/bakeryFUMIZUKI
Les modèles liés à la fonction panier sont principalement le client et le produit. Le corps principal du panier n'existe pas dans la fonction panier, et lorsque vous sélectionnez un produit et appuyez sur le bouton «Ajouter au panier», une donnée est enregistrée pour chaque produit. Le modèle CartItem agit comme une table intermédiaire qui stocke uniquement les ID client et produit et le nombre de produits.
Controller
app/controllers/cart_items_controller.rb
class CartItemsController < ApplicationController
before_action :authenticate_customer!
before_action :set_cart_item, only: [:show, :update, :destroy, :edit]
before_action :set_customer
def create
@cart_item = current_customer.cart_items.build(cart_item_params)
@current_item = CartItem.find_by(product_id: @cart_item.product_id,customer_id: @cart_item.customer_id)
#S'il n'y a pas le même produit dans le panier, ajoutez-en un nouveau, s'il y en a un, ajoutez-le aux données existantes
if @current_item.nil?
if @cart_item.save
flash[:success] = 'L'article a été ajouté au panier!'
redirect_to cart_items_path
else
@carts_items = @customer.cart_items.all
render 'index'
flash[:danger] = 'L'article n'a pas pu être ajouté au panier.'
end
else
@current_item.quantity += params[:quantity].to_i
@current_item.update(cart_item_params)
redirect_to cart_items_path
end
end
def destroy
@cart_item.destroy
redirect_to cart_items_path
flash[:info] = 'J'ai annulé l'article dans le panier.'
end
def index
@cart_items = @customer.cart_items.all
end
def update
if @cart_item.update(cart_item_params)
redirect_to cart_items_path
flash[:success] = 'Les articles du panier ont été mis à jour!'
end
end
def destroy_all #Effacer tous les articles du panier
@customer.cart_items.destroy_all
redirect_to cart_items_path
flash[:info] = 'J'ai vidé mon chariot.'
end
private
def set_customer
@customer = current_customer
end
def set_cart_item
@cart_item = CartItem.find(params[:id])
end
def cart_item_params
params.require(:cart_item).permit(:product_id, :customer_id, :quantity)
end
end
Si vous écrivez simplement enregistrer dans l'action de création, lorsque vous essayez d'acheter le même produit, le même produit sera enregistré en tant que données différentes, telles que ** "Pain 1, Pain 2, Pain 1, ..." **. Cela se produit en raison de la structure de la table, mais comme il est pratique de pouvoir afficher les éléments supplémentaires ajoutés au panier ultérieurement, le traitement est divisé par l'instruction if.
De plus, lorsque je voulais pouvoir annuler les articles du panier individuellement et vider le contenu du panier en une seule fois, la commodité de destroy_all J'ai trouvé une méthode.
View
html:app/views/cart_items/index.html.erb
<div class="col-lg-10 offset-lg-1 space">
<div class="container-fluid">
<!--Titre+Effacer toute la méthode-->
<div class="row">
<div class="col-lg-4">
<h2>
<span style="display: inline-block;">achats</span>
<span style="display: inline-block;">Chariot</span>
</h2>
</div>
<div class="col-lg-4">
<%= link_to 'Vider le chariot', destroy_all_cart_items_path, method: :delete, class: 'btn btn-danger' %>
</div>
</div>
<!--Liste des produits dans le panier-->
<div class="d-none d-lg-block">
<div class="row space">
<div class="col-lg-5"><h4>Nom du produit</h4></div>
<div class="col-lg-2"><h4>Prix unitaire (taxes incluses)</h4></div>
<div class="col-lg-2"><h4>quantité</h4></div>
<div class="col-lg-2"><h4>total</h4></div>
</div>
</div>
<% sum_all = 0 %>
<% @cart_items.each do |cart_item| %>
<div class="row space-sm">
<div class="col-lg-3">
<%= link_to product_path(cart_item.product) do %>
<%= attachment_image_tag(cart_item.product, :image, :fill, 100, 100, fallback: "no_img.jpg ") %>
<% end %>
</div>
<div class="col-lg-2">
<%= link_to product_path(cart_item.product) do %>
<%= cart_item.product.name %>
<% end %>
</div>
<div class="col-lg-2">
<%= price_include_tax(cart_item.product.price) %>
</div>
<div class="col-lg-2">
<%= form_with model: cart_item, local: true do |f| %>
<%= f.number_field :quantity, value: cart_item.quantity, min:1, max:99 %>
<%= f.submit "Changement", class: "btn btn-primary" %>
<% end %>
</div>
<div class="col-lg-2">
<%= sum_product = price_include_tax(cart_item.product.price).to_i * cart_item.quantity %>Cercle
<% sum_all += sum_product %>
</div>
<div class="col-lg-1">
<%= link_to "effacer", cart_item_path(cart_item), method: :delete, class: "btn btn-danger"%>
</div>
</div>
<% end %>
<!--montant total+Saisie d'informations-->
<div class="row space">
<div class="col-lg-2 offset-lg-7 space-sm">
<%= link_to "Continuer vos achats", customer_top_path, class: "btn btn-danger "%>
</div>
<div class="col-lg-3 space-sm">
<div class="row">
<h4>montant total:<%= sum_all %>Cercle</h4>
</div>
</div>
</div>
<div class="row space">
<div class="col-lg-3 offset-lg-9">
<%= link_to "Procéder à la saisie d'informations", new_order_path, class: "btn btn-danger btn-lg" %>
</div>
</div>
</div>
</div>
Le sous-total de chaque produit et le total de tous les produits sont affichés en incorporant une formule de calcul dans chaque relevé de la vue. En général, il semble qu'il ne soit pas souhaitable d'effectuer des calculs détaillés et un traitement de branche en vue, y a-t-il donc une autre bonne méthode?
app/helpers/application_helper.rb
def price_include_tax(price)
price = price * 1.08
"#{price.floor}Cercle"
end
Il s'agit de l'assistant utilisé pour afficher le prix TTC du produit dans le code HTML ci-dessus. La partie après la virgule décimale est tronquée par étage. Pour plus d'informations sur le traitement des points décimaux, voir ici.
app/assets/stylesheets/application.scss
.space-sm {
padding-top: 20px;
}
L'implémentation des fonctionnalités est devenue un peu plus compliquée, et ça devient finalement intéressant. Même si vous regardez à l'intérieur du site, vous pouvez ressentir beaucoup de shopping lorsque vous mettez les articles dans le panier. Après cela, si vous créez autour de la commande (informations de commande), le site client est terminé!
Cependant, dans cette série, le site d'administration est également créé par moi-même, donc la quantité de code est d'environ la moitié. Cependant, la fonction du modèle de l'Ordre était extrêmement difficile à comprendre lorsque je l'ai fait la dernière fois, donc si je pouvais faire cela, je pourrais faire quelque chose à ce sujet.
Maintenant, puis-je expliquer le modèle de commande le plus difficile d'une manière facile à comprendre? Continuez à la prochaine fois!
Pikawaka [Ruby] Arrondissez, arrondissez vers le haut et arrondissez vers le bas en spécifiant le nombre de chiffres après la virgule décimale!
Recommended Posts