<order> 对象不可迭代
<order> object is not iterable
我正在尝试从订单模型中获取订单记录并将其作为上下文传递到模板中
但在模板中,当 我在循环 中使用循环时会出现问题,例如
{% for o in objects %}
{% for p in o %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{p.img.url}}</td>
<td>{{o.date}}</td>
<td>{{p.price}}</td>
{% if o.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{o.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{o.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
{% endfor %}
我正在获取与特定订单对象相关的产品,并作为该特定订单对象的上下文传递
比如
context=OrderProduct.fetch_customer_order_products(customer)
OrderProduct.py 型号
from django.db.models.deletion import DO_NOTHING
from django.shortcuts import get_object_or_404
from django.db.models import Case, When
from django.db import models
from django.db.models.fields.related import ForeignKey
from .order import Order
from .products import Products
from .customer import Customer
class OrderProduct(models.Model):
order = models.ForeignKey(Order, on_delete=models.CASCADE)
product = models.ForeignKey(Products, on_delete=models.DO_NOTHING)
customer = models.ForeignKey(Customer, on_delete=DO_NOTHING, default="")
quantity = models.IntegerField()
def __str__(self):
return self.product.name
@staticmethod
def fetch_customer_order_products(cust):
obj = Order.objects.filter(customer=cust)
dict = {}
context={}
for o in obj:
l = []
id = o.id
prods = list(Order.objects.filter(id=id).values('products'))
for a in range(0,len(prods)):
l.append(prods[a]['products'])
dict[o] = l
prods = list(Products.objects.filter(id__in=l)) # to be passed as context
context[o]=prods
context['objects'] = obj
return context
order.py 型号
from django.db import models
from django.db.models.enums import Choices
from django.db.models.fields.related import ManyToManyField
from .customer import Customer
from .products import Products
from .payment_method import Payment_method
from datetime import datetime
Order_status_choices = (
('created', 'Created'),
('approved', 'Approved'),
('paid','Paid'),
('packaged','Packaged'),
('shipped','Shipped'),
('completed','Completed'),
)
class Order(models.Model):
name = models.CharField(max_length=20, default="")
products = models.ManyToManyField(Products)
customer = models.ForeignKey(Customer, on_delete=models.DO_NOTHING)
address = models.CharField(max_length=100, default='')
order_status = models.CharField(max_length=20, choices = Order_status_choices, default='created')
shipping_address = models.CharField(max_length=100, default='')
phno = models.BigIntegerField(default=00000000000)
email = models.EmailField(default="")
date = models.DateTimeField(default=datetime.now,blank=True)
price = models.IntegerField(default=0)
payment_method = models.ForeignKey(Payment_method, on_delete=models.DO_NOTHING, null=True)
name_additional = models.CharField(max_length=20, null=True,blank=True)
phno_additional = models.BigIntegerField(null=True, blank=True)
def __str__(self):
return self.name
@staticmethod
def get_order_by_customer_id(customer):
return Order.objects.filter(customer=customer)
myaccount.html 文件
{% extends 'base.html' %}
{% load static %}
{% load cart %}
{% block content %}
<!-- Breadcrumb Start -->
<div class="breadcrumb-wrap">
<div class="container-fluid">
<ul class="breadcrumb">
<li class="breadcrumb-item"><a href="#">Home</a></li>
<li class="breadcrumb-item"><a href="#">Products</a></li>
<li class="breadcrumb-item active">My Account</li>
</ul>
</div>
</div>
<!-- Breadcrumb End -->
<!-- My Account Start -->
<div class="my-account">
<div class="container-fluid">
<div class="row">
<div class="col-md-3">
<div class="nav flex-column nav-pills" role="tablist" aria-orientation="vertical">
<a class="nav-link active" id="dashboard-nav" data-toggle="pill" href="#dashboard-tab" role="tab"><i class="fa fa-tachometer-alt"></i>Dashboard</a>
<a class="nav-link" id="orders-nav" data-toggle="pill" href="#orders-tab" role="tab"><i class="fa fa-shopping-bag"></i>Orders</a>
<a class="nav-link" id="payment-nav" data-toggle="pill" href="#payment-tab" role="tab"><i class="fa fa-credit-card"></i>Payment Method</a>
<a class="nav-link" id="address-nav" data-toggle="pill" href="#address-tab" role="tab"><i class="fa fa-map-marker-alt"></i>address</a>
<a class="nav-link" id="account-nav" data-toggle="pill" href="#account-tab" role="tab"><i class="fa fa-user"></i>Account Details</a>
<a class="nav-link" href="index.html"><i class="fa fa-sign-out-alt"></i>Logout</a>
</div>
</div>
<div class="col-md-9">
<div class="tab-content">
<div class="tab-pane fade show active" id="dashboard-tab" role="tabpanel" aria-labelledby="dashboard-nav">
<h4>Dashboard</h4>
<p>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In condimentum quam ac mi viverra dictum. In efficitur ipsum diam, at dignissim lorem tempor in. Vivamus tempor hendrerit finibus. Nulla tristique viverra nisl, sit amet bibendum ante suscipit non. Praesent in faucibus tellus, sed gravida lacus. Vivamus eu diam eros. Aliquam et sapien eget arcu rhoncus scelerisque.
</p>
</div>
<div class="tab-pane fade" id="orders-tab" role="tabpanel" aria-labelledby="orders-nav">
<div class="table-responsive">
<table class="table table-bordered">
<thead class="thead-dark">
<tr>
<th>Sno</th>
<th>image</th>
<th>DateTime</th>
<th>price</th>
<th>Order Status</th>
</tr>
</thead>
<tbody>
{% for o in objects %}
{% for p in o %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{p.img.url}}</td>
<td>{{o.date}}</td>
<td>{{p.price}}</td>
{% if order.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{order.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{order.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
{% endfor %}
</tbody>
</table>
</div>
</div>
<div class="tab-pane fade" id="payment-tab" role="tabpanel" aria-labelledby="payment-nav">
<h4>Payment Method</h4>
<p>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In condimentum quam ac mi viverra dictum. In efficitur ipsum diam, at dignissim lorem tempor in. Vivamus tempor hendrerit finibus. Nulla tristique viverra nisl, sit amet bibendum ante suscipit non. Praesent in faucibus tellus, sed gravida lacus. Vivamus eu diam eros. Aliquam et sapien eget arcu rhoncus scelerisque.
</p>
</div>
<div class="tab-pane fade" id="address-tab" role="tabpanel" aria-labelledby="address-nav">
<h4>Address</h4>
<div class="row">
<div class="col-md-6">
<h5>Payment Address</h5>
<p>123 Payment Street, Los Angeles, CA</p>
<p>Mobile: 012-345-6789</p>
<button class="btn">Edit Address</button>
</div>
<div class="col-md-6">
<h5>Shipping Address</h5>
<p>123 Shipping Street, Los Angeles, CA</p>
<p>Mobile: 012-345-6789</p>
<button class="btn">Edit Address</button>
</div>
</div>
</div>
<div class="tab-pane fade" id="account-tab" role="tabpanel" aria-labelledby="account-nav">
<h4>Account Details</h4>
<div class="row">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="profile-container">
{% if profile.img %}
<img width="50" height="70" id="profileImage" src="{{profile.img.url}}" />
{% else %}
<img width="50" height="70" id="profileImage" src="https://p1.pxfuel.com/preview/423/292/62/girl-studio-female-woman-profile-black-and-white.jpg" />
{% endif %}
</div><br><br><br><br><br><br>
<form action="/my-account" method="post" enctype="multipart/form-data">
{% csrf_token %}
{{form.as_p}}
{% if request.session.customer|check_customer_profile %}
<div class="col-md-12">
<button type="submit" class="btn">update profile</button>
<br><br>
</div>
{% else %}
<div class="col-md-12">
<button type="submit" class="btn">Create profile</button>
<br><br>
</div>
{% endif %}
</form>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- My Account End -->
{% endblock %}
myaccount.py
from django.utils.decorators import method_decorator
from ..middlewares.authorization import auth_middleware
from store.models.customer import Customer
from django.views import View
from django.shortcuts import render,redirect
from ..models.order import Order
from ..models.orderproduct import OrderProduct
from ..models.profile import Profile
from ..forms.ProfileForm import ProfileForm
class MyAccount(View):
@method_decorator(auth_middleware)
def get(self, request):
customer = request.session.get('customer')
if customer:
profile = Profile.whether_customer_exists(customer)
form = None
form = ProfileForm(instance=profile)
context=OrderProduct.fetch_customer_order_products(customer)
context['form']=form
if profile:
context['profile'] = profile
print(context)
return render(request, 'my-account.html',context)
def post(self, request):
customer = request.session.get('customer')
if customer:
profile = Profile.whether_customer_exists(customer)
if profile:
form = ProfileForm(request.POST or None, request.FILES or None,instance=profile)
if form.is_valid():
form.save()
else:
cust = Customer.objects.filter(id = customer).first()
form = ProfileForm(request.POST or None, request.FILES or None)
form1 = form.save(commit=False)
form1.customer = cust
form1.save()
form = ProfileForm(instance=profile)
context = {'form':form}
return render(request, 'my-account.html',context)
else:
return redirect('login')
实际上我试图做的是从 OrderProductmodel 中获取客户订购的与特定 Ordermodel 对象相关的产品及其各自的数量,我将订单对象提供给内部循环以将与该对象相关的产品显示为
{% for o in objects %}
{% for p in o %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{p.img.url}}</td>
<td>{{o.date}}</td>
<td>{{p.price}}</td>
{% if o.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{o.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{o.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
{% endfor %}
所以问题的解决方法是通过上下文将订单查询集对象获取到模板,模板内部使用循环迭代查询集并获取订单对象,然后在 templatetags 文件夹中创建自定义模板过滤器以获取产品通过将订单对象作为 cutstom 过滤器的参数与特定对象相关
比如
{%for o in objects %}
<h4>Order{{forloop.counter}}</h4>
<div class="table-responsive">
<table class="table table-bordered">
<thead class="thead-dark">
<tr>
<th>Sno</th>
<th>image</th>
<th>Name</th>
<th>price</th>
<th>Quantity</th>
<th>product total</th>
<th>DateTime</th>
<th>Order Status</th>
</tr>
</thead>
<tbody>
{% for p in o|get_object_related_products:request.session.customer %}
<tr>
<td>{{forloop.counter}}</td>
<td>
<div class="img">
<a href="#"><img src="{{p.img.url}}" alt="Image" height="50px" width="50px"></a>
</div>
</td>
<td>{{p.name}}</td>
<td>{{p.price}}</td>
<td>{{o|get_product_quantity:p}}</td>
<td>{{o|get_order_total:p}}</td>
<td>{{o.date}}</td>
{% if o.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{o.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{o.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
非常感谢任何考虑过的人...
我正在尝试从订单模型中获取订单记录并将其作为上下文传递到模板中 但在模板中,当 我在循环 中使用循环时会出现问题,例如
{% for o in objects %}
{% for p in o %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{p.img.url}}</td>
<td>{{o.date}}</td>
<td>{{p.price}}</td>
{% if o.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{o.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{o.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
{% endfor %}
我正在获取与特定订单对象相关的产品,并作为该特定订单对象的上下文传递 比如
context=OrderProduct.fetch_customer_order_products(customer)
OrderProduct.py 型号
from django.db.models.deletion import DO_NOTHING
from django.shortcuts import get_object_or_404
from django.db.models import Case, When
from django.db import models
from django.db.models.fields.related import ForeignKey
from .order import Order
from .products import Products
from .customer import Customer
class OrderProduct(models.Model):
order = models.ForeignKey(Order, on_delete=models.CASCADE)
product = models.ForeignKey(Products, on_delete=models.DO_NOTHING)
customer = models.ForeignKey(Customer, on_delete=DO_NOTHING, default="")
quantity = models.IntegerField()
def __str__(self):
return self.product.name
@staticmethod
def fetch_customer_order_products(cust):
obj = Order.objects.filter(customer=cust)
dict = {}
context={}
for o in obj:
l = []
id = o.id
prods = list(Order.objects.filter(id=id).values('products'))
for a in range(0,len(prods)):
l.append(prods[a]['products'])
dict[o] = l
prods = list(Products.objects.filter(id__in=l)) # to be passed as context
context[o]=prods
context['objects'] = obj
return context
order.py 型号
from django.db import models
from django.db.models.enums import Choices
from django.db.models.fields.related import ManyToManyField
from .customer import Customer
from .products import Products
from .payment_method import Payment_method
from datetime import datetime
Order_status_choices = (
('created', 'Created'),
('approved', 'Approved'),
('paid','Paid'),
('packaged','Packaged'),
('shipped','Shipped'),
('completed','Completed'),
)
class Order(models.Model):
name = models.CharField(max_length=20, default="")
products = models.ManyToManyField(Products)
customer = models.ForeignKey(Customer, on_delete=models.DO_NOTHING)
address = models.CharField(max_length=100, default='')
order_status = models.CharField(max_length=20, choices = Order_status_choices, default='created')
shipping_address = models.CharField(max_length=100, default='')
phno = models.BigIntegerField(default=00000000000)
email = models.EmailField(default="")
date = models.DateTimeField(default=datetime.now,blank=True)
price = models.IntegerField(default=0)
payment_method = models.ForeignKey(Payment_method, on_delete=models.DO_NOTHING, null=True)
name_additional = models.CharField(max_length=20, null=True,blank=True)
phno_additional = models.BigIntegerField(null=True, blank=True)
def __str__(self):
return self.name
@staticmethod
def get_order_by_customer_id(customer):
return Order.objects.filter(customer=customer)
myaccount.html 文件
{% extends 'base.html' %}
{% load static %}
{% load cart %}
{% block content %}
<!-- Breadcrumb Start -->
<div class="breadcrumb-wrap">
<div class="container-fluid">
<ul class="breadcrumb">
<li class="breadcrumb-item"><a href="#">Home</a></li>
<li class="breadcrumb-item"><a href="#">Products</a></li>
<li class="breadcrumb-item active">My Account</li>
</ul>
</div>
</div>
<!-- Breadcrumb End -->
<!-- My Account Start -->
<div class="my-account">
<div class="container-fluid">
<div class="row">
<div class="col-md-3">
<div class="nav flex-column nav-pills" role="tablist" aria-orientation="vertical">
<a class="nav-link active" id="dashboard-nav" data-toggle="pill" href="#dashboard-tab" role="tab"><i class="fa fa-tachometer-alt"></i>Dashboard</a>
<a class="nav-link" id="orders-nav" data-toggle="pill" href="#orders-tab" role="tab"><i class="fa fa-shopping-bag"></i>Orders</a>
<a class="nav-link" id="payment-nav" data-toggle="pill" href="#payment-tab" role="tab"><i class="fa fa-credit-card"></i>Payment Method</a>
<a class="nav-link" id="address-nav" data-toggle="pill" href="#address-tab" role="tab"><i class="fa fa-map-marker-alt"></i>address</a>
<a class="nav-link" id="account-nav" data-toggle="pill" href="#account-tab" role="tab"><i class="fa fa-user"></i>Account Details</a>
<a class="nav-link" href="index.html"><i class="fa fa-sign-out-alt"></i>Logout</a>
</div>
</div>
<div class="col-md-9">
<div class="tab-content">
<div class="tab-pane fade show active" id="dashboard-tab" role="tabpanel" aria-labelledby="dashboard-nav">
<h4>Dashboard</h4>
<p>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In condimentum quam ac mi viverra dictum. In efficitur ipsum diam, at dignissim lorem tempor in. Vivamus tempor hendrerit finibus. Nulla tristique viverra nisl, sit amet bibendum ante suscipit non. Praesent in faucibus tellus, sed gravida lacus. Vivamus eu diam eros. Aliquam et sapien eget arcu rhoncus scelerisque.
</p>
</div>
<div class="tab-pane fade" id="orders-tab" role="tabpanel" aria-labelledby="orders-nav">
<div class="table-responsive">
<table class="table table-bordered">
<thead class="thead-dark">
<tr>
<th>Sno</th>
<th>image</th>
<th>DateTime</th>
<th>price</th>
<th>Order Status</th>
</tr>
</thead>
<tbody>
{% for o in objects %}
{% for p in o %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{p.img.url}}</td>
<td>{{o.date}}</td>
<td>{{p.price}}</td>
{% if order.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{order.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{order.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
{% endfor %}
</tbody>
</table>
</div>
</div>
<div class="tab-pane fade" id="payment-tab" role="tabpanel" aria-labelledby="payment-nav">
<h4>Payment Method</h4>
<p>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In condimentum quam ac mi viverra dictum. In efficitur ipsum diam, at dignissim lorem tempor in. Vivamus tempor hendrerit finibus. Nulla tristique viverra nisl, sit amet bibendum ante suscipit non. Praesent in faucibus tellus, sed gravida lacus. Vivamus eu diam eros. Aliquam et sapien eget arcu rhoncus scelerisque.
</p>
</div>
<div class="tab-pane fade" id="address-tab" role="tabpanel" aria-labelledby="address-nav">
<h4>Address</h4>
<div class="row">
<div class="col-md-6">
<h5>Payment Address</h5>
<p>123 Payment Street, Los Angeles, CA</p>
<p>Mobile: 012-345-6789</p>
<button class="btn">Edit Address</button>
</div>
<div class="col-md-6">
<h5>Shipping Address</h5>
<p>123 Shipping Street, Los Angeles, CA</p>
<p>Mobile: 012-345-6789</p>
<button class="btn">Edit Address</button>
</div>
</div>
</div>
<div class="tab-pane fade" id="account-tab" role="tabpanel" aria-labelledby="account-nav">
<h4>Account Details</h4>
<div class="row">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="profile-container">
{% if profile.img %}
<img width="50" height="70" id="profileImage" src="{{profile.img.url}}" />
{% else %}
<img width="50" height="70" id="profileImage" src="https://p1.pxfuel.com/preview/423/292/62/girl-studio-female-woman-profile-black-and-white.jpg" />
{% endif %}
</div><br><br><br><br><br><br>
<form action="/my-account" method="post" enctype="multipart/form-data">
{% csrf_token %}
{{form.as_p}}
{% if request.session.customer|check_customer_profile %}
<div class="col-md-12">
<button type="submit" class="btn">update profile</button>
<br><br>
</div>
{% else %}
<div class="col-md-12">
<button type="submit" class="btn">Create profile</button>
<br><br>
</div>
{% endif %}
</form>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- My Account End -->
{% endblock %}
myaccount.py
from django.utils.decorators import method_decorator
from ..middlewares.authorization import auth_middleware
from store.models.customer import Customer
from django.views import View
from django.shortcuts import render,redirect
from ..models.order import Order
from ..models.orderproduct import OrderProduct
from ..models.profile import Profile
from ..forms.ProfileForm import ProfileForm
class MyAccount(View):
@method_decorator(auth_middleware)
def get(self, request):
customer = request.session.get('customer')
if customer:
profile = Profile.whether_customer_exists(customer)
form = None
form = ProfileForm(instance=profile)
context=OrderProduct.fetch_customer_order_products(customer)
context['form']=form
if profile:
context['profile'] = profile
print(context)
return render(request, 'my-account.html',context)
def post(self, request):
customer = request.session.get('customer')
if customer:
profile = Profile.whether_customer_exists(customer)
if profile:
form = ProfileForm(request.POST or None, request.FILES or None,instance=profile)
if form.is_valid():
form.save()
else:
cust = Customer.objects.filter(id = customer).first()
form = ProfileForm(request.POST or None, request.FILES or None)
form1 = form.save(commit=False)
form1.customer = cust
form1.save()
form = ProfileForm(instance=profile)
context = {'form':form}
return render(request, 'my-account.html',context)
else:
return redirect('login')
实际上我试图做的是从 OrderProductmodel 中获取客户订购的与特定 Ordermodel 对象相关的产品及其各自的数量,我将订单对象提供给内部循环以将与该对象相关的产品显示为
{% for o in objects %}
{% for p in o %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{p.img.url}}</td>
<td>{{o.date}}</td>
<td>{{p.price}}</td>
{% if o.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{o.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{o.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
{% endfor %}
所以问题的解决方法是通过上下文将订单查询集对象获取到模板,模板内部使用循环迭代查询集并获取订单对象,然后在 templatetags 文件夹中创建自定义模板过滤器以获取产品通过将订单对象作为 cutstom 过滤器的参数与特定对象相关 比如
{%for o in objects %}
<h4>Order{{forloop.counter}}</h4>
<div class="table-responsive">
<table class="table table-bordered">
<thead class="thead-dark">
<tr>
<th>Sno</th>
<th>image</th>
<th>Name</th>
<th>price</th>
<th>Quantity</th>
<th>product total</th>
<th>DateTime</th>
<th>Order Status</th>
</tr>
</thead>
<tbody>
{% for p in o|get_object_related_products:request.session.customer %}
<tr>
<td>{{forloop.counter}}</td>
<td>
<div class="img">
<a href="#"><img src="{{p.img.url}}" alt="Image" height="50px" width="50px"></a>
</div>
</td>
<td>{{p.name}}</td>
<td>{{p.price}}</td>
<td>{{o|get_product_quantity:p}}</td>
<td>{{o|get_order_total:p}}</td>
<td>{{o.date}}</td>
{% if o.order_status == 'completed' %}
<td><small style="background-color:green;"><span class="badge badge-success">{{o.order_status}}</span></small></td>
{% else %}
<td><small style="background-color:rgb(231, 211, 26);"><span class="badge badge-warning">{{o.order_status}}</span></small></td>
{% endif %}
</tr>
{% endfor %}
非常感谢任何考虑过的人...