I have a model form that is basically a job ticket. The save method in the view is set to send an email notification on save. The model has a couple of fields that inherit from a parent UserProfile model:
class RemoteRequest(models.Model):
create_date = models.DateTimeField(auto_now_add=True)
requested_by = models.ForeignKey(UserProfile)
client = models.CharField(max_length=50, choices=CLIENT_CHOICES)
job_number = models.CharField(max_length=8, unique=False, blank=False, null=False)
cell_number = models.CharField(max_length=4, unique=False, blank=True, null=True)
job_name = models.CharField(max_length=200, unique=False, blank=True, null=True)
print_request = models.ManyToManyField(PrintRequest, unique=False, blank=True, null=True)
interactive_request = models.ManyToManyField(InteractiveRequest, unique=False, blank=True, null=True)
due_date = models.DateTimeField(auto_now_add=False)
job_notes = models.TextField(max_length=500, unique=False, blank=True, null=True)
asset_location = models.CharField(max_length=300, unique=False, blank=True, null=True)
asset_upload = models.FileField(upload_to=request_file_name, blank=True, null=True, max_length=300)
pdf_upload = models.FileField(upload_to=request_file_name, blank=True, null=True, max_length=300)
*notify_internal = models.ManyToManyField(UserProfile, related_name='+', unique=False, blank=True, null=True)*
notify_external = models.ManyToManyField(FreelanceProfile, unique=False, blank=True, null=True)
completed_by = models.ForeignKey(UserProfile, related_name='+', blank=True, null=True)
complete_date = models.DateTimeField(auto_now_add=False, blank=True)
asset_return = models.FileField(upload_to=return_file_name, blank=True, null=True, max_length=300)
pdf_return = models.FileField(upload_to=return_file_name, blank=True, null=True, max_length=300)
return_notes = models.TextField(max_length=500, unique=False, blank=True, null=True)
def __unicode__ (self):
return u'%s %s %s %s %s' % (self.client, self.job_number, '-', self.cell_number, self.job_name)
the UserProfile model has an email field. This is what I'm trying to pass to the recipient list in the view:
def remote_request(request):
if request.method=='POST':
form = RemoteRequestForm(request.POST)
if form.is_valid():
name = form.cleaned_data['job_name']
subject = form.cleaned_data['job_name']
message = form.cleaned_data['job_notes']
sender = form.cleaned_data['requested_by']
recipients = [form.cleaned_data['**notify_internal.userprofile.email**']]
from django.core.mail import send_mail
send_mail(subject, message, sender, recipients)
remoterq = form.save(commit=False)
remoterq.save()
form.save_m2m()
return render(request, 'remote_tmps/remoterequest.html', {'form': form,
})
else:
form = RemoteRequestForm()
return render(request, 'remote_tmps/remoterequest.html', {'form': form,})
Unfortunately "notify_internal.userprofile.email" throws a key error and I'm at a loss as to how to properly pass these email recipients.
What makes you think passing a string with python dot notation would do something special in the dictionary lookup?
You're saving your object, so just pull the recipients after you save, after save m2m().
recipients = [user.email for user in remoterq.notify_internal.all()]
Look at the ManyToManyField docs to see how to get data. There's a QuerySet interface exposed in the field attribute.
Related
I have a create view (Loan_assetCreateView(generic.CreateView)) where I save if an asset is going to be loaned and when it will be returened in a model called Loan_asset(models.Model). Then I have the asset in a diffrent model Asset(model.Model). I would like to once I have saved my data in my Loan_assetCreateView(generic.CreateView) that is set the value in Asset.is_loaned to True. How can I do that?
My models.py:
class Asset(models.Model):
# Relationships
room = models.ForeignKey("asset_app.Room", on_delete=models.SET_NULL, blank=True, null=True)
model_hardware = models.ForeignKey("asset_app.Model_hardware", on_delete=models.SET_NULL, blank=True, null=True)
# Fields
name = models.CharField(max_length=30)
serial = models.CharField(max_length=30, unique=True, blank=True, null=True, default=None)
mac_address = models.CharField(max_length=30, null=True, blank=True)
purchased_date = models.DateField(null=True, blank=True)
may_be_loaned = models.BooleanField(default=False, blank=True, null=True)
is_loaned = models.BooleanField(default=False, blank=True, null=True)
missing = models.BooleanField(default=False, blank=True, null=True)
notes = HTMLField(default="")
ip = models.CharField(max_length=90, null=True, blank=True)
created = models.DateTimeField(auto_now_add=True, editable=False)
last_updated = models.DateTimeField(auto_now=True, editable=False)
class Loan_asset(models.Model):
# Relationships
asset = models.ForeignKey("asset_app.Asset", on_delete=models.SET_NULL, blank=True, null=True)
loaner_type = models.ForeignKey("asset_app.Loaner_type", on_delete=models.SET_NULL, blank=True, null=True)
location = models.ForeignKey("asset_app.Locations", on_delete=models.SET_NULL, blank=True, null=True)
# Fields
loaner_name = models.CharField(max_length=60)
loaner_address = models.TextField(max_length=100, null=True, blank=True)
loaner_telephone_number = models.CharField(max_length=30)
loaner_email = models.EmailField()
loaner_quicklink = models.URLField(null=True, blank=True)
loan_date = models.DateField()
return_date = models.DateField()
notes = HTMLField(default="")
returned = models.BooleanField(default=False, blank=True, null=True)
created = models.DateTimeField(auto_now_add=True, editable=False)
last_updated = models.DateTimeField(auto_now=True, editable=False)
class Meta:
pass
def __str__(self):
return str(self.loaner_name)
def get_absolute_url(self):
return reverse("asset_app_loan_asset_detail", args=(self.pk,))
def get_update_url(self):
return reverse("asset_app_loan_asset_update", args=(self.pk,))
my urls.py
`path("asset_app/loan_asset/create/", views.Loan_assetCreateView.as_view(), name="asset_app_loan_asset_create")`,
my views.py
class Loan_assetCreateView(generic.CreateView):
model = models.Loan_asset
form_class = forms.Loan_assetForm
Here are some options:
override form_valid method that's being called in post method implementation, so that after form will be validated (model instance saved), you'll be able to set the flag through foreign key/by creating Asset instance:
...
def form_valid(self, form):
self.object = form.save()
if self.object.asset:
self.object.asset.is_loaned = True
else:
self.object.asset = Asset.objects.create(is_loaned=True)
return HttpResponseRedirect(self.get_success_url())
use Django signals:
#receiver(post_save, sender=Loan_asset)
def create_transaction(sender, instance, created, **kwargs):
if created:
Asset.objects.create(is_loaned=True)
You can override the post method in your Loan_assetCreateView.
class Loan_assetCreateView(generic.CreateView):
model = models.Loan_asset
form_class = forms.Loan_assetForm
def post(request, *args, **kwargs):
response = super().post(request, *args. **kwargs)
# Do your thing
return response
so I am building a pet blog project where my scenario is - my users will be able to post multiple images and audios if they want while doing so , am facing several problems -
while trying to post through POSTMAN . I am getting an error saying create() got multiple values for keyword argument 'hnid' ..
while querying using UUID , it is throwing , a String naming "HNUsers object (e3ec1a43-ebc4-47b9-bf2f-55967af8ea71)" where I just wanted UUID(e3ec1a43-ebc4-47b9-bf2f-55967af8ea71) but came with extra HNUsers object
Here is my Profile model
class HNUsers(models.Model):
USERTYPE = (
(u'RU', u'REGULAR USER'),
(u'HN', u'HN'),
)
GENDER = (
(u'M', u'Male'),
(u'F', u'Female'),
(u'O', u'Other'),
)
ip_address = models.CharField("IP Address" , max_length=100, blank=True, null=True)
full_name = models.CharField("Full Name", max_length=100, null=True, blank=True)
username = models.CharField("Username", max_length=100, null=True, blank=True)
email = models.EmailField("Email", blank=True, null=True)
user_type = models.CharField("User Type", max_length=2, choices=USERTYPE, null=True, blank=True, default=USERTYPE[0][0])
mobile_number = models.CharField("Mobile Number", max_length=20, blank=True, null=True)
date_of_birth = models.DateField("Date of Birth", auto_now_add=False, blank=False, null=True)
gender = models.CharField("Gender", max_length=1, choices=GENDER, blank=True, null=True, )
registration_date = models.DateTimeField("Registration Date", auto_now_add=True, null=True, blank=True)
city = models.CharField("City", max_length=50, blank=True, null=True)
country = models.CharField("Country", max_length=50, blank=True, null=True)
profile_img = models.ImageField("Profile Image", blank=True, null=True)
first_img = models.FileField("First Image", blank=True, null=True)
first_img_url = models.CharField("First Image Url", blank=True, null=True, max_length=500)
profile_img_url = models.CharField("Profile Image Url", blank=True, null=True, max_length=500)
hnid = models.UUIDField("HNID", default=uuid.uuid4, unique=True, primary_key=True, editable=False)
my imagepost model
class ImagePost(models.Model):
hnid = models.ForeignKey("profiles.HNUsers", on_delete=models.DO_NOTHING)
file = models.FileField("Image", blank=True, null=True)
timestamp = models.DateTimeField("Timestamp", blank=True, null=True, auto_now_add=True)
text = models.TextField("Description text", blank=True)
class Meta:
verbose_name_plural = "Image Posts"
serializer for image post
class MultiMediaSerializer(serializers.ModelSerializer):
file = serializers.ListField(child=serializers.FileField(max_length=100, allow_empty_file=False, use_url=True))
def create(self, validated_data):
request = self.context.get('request')
# print(validated_data)
files = validated_data.pop('file')
print(files)
user = HNUsers.objects.get(pk=request.data['hnid'])
print("hnid ", user)
# print("hnid ", entry)
for img in files:
print(img)
photo = ImagePost.objects.create(file=img, hnid=user, **validated_data)
return photo
class Meta:
model = ImagePost
fields = ('hnid', 'file',)
Views.py file for the above is -
#api_view(['POST'])
#permission_classes((permissions.AllowAny,))
#parser_classes([MultiPartParser, FormParser])
def posting_api(request):
if request.method == 'POST':
data = request.data
print(data)
serializer = MultiMediaSerializer(data=data, context={'request': request})
if serializer.is_valid():
serializer.save()
print("image object saved")
return Response(serializer.data, status=status.HTTP_201_CREATED)
Sorry I am new to this
Remove hnid=user from the create statement since the validated_data does have the hnid field already
photo = ImagePost.objects.create(file=img, **validated_data)
I am making a app for one kindergarten in my city. I have kids model and payment model.
For updating kid I am using class based view generic UpdateView and for creating a payment i am using form and function view. I have not problems with payment form when I am using a different template but when I try to put it on the same template, payment form is not showing up and it's not working. Is it possible to have payment form on same template as UpdateView class ? I am using UpdateView class as profile page and I would like to have payment form on the same page. Please help. Thanks
models:
class Kids(models.Model):
name = models.CharField(max_length=100, blank=True, null=True)
city_birthday = models.CharField(max_length=100, blank=True, null=True)
custom_id = models.CharField(max_length=100 ,blank=True, null=True)
gender = models.CharField(max_length=100, choices=gender_choices, null=True, blank=True)
address = models.CharField(max_length=250, null=True, blank=True)
contact_phone = models.CharField(max_length=100, blank=True, null=True)
family_size = models.IntegerField(null=True, blank=True)
living_with = models.CharField(max_length=100, choices=living_choices, null=True, blank=True)
number_of_preschool_kids_in_family = models.IntegerField(null=True, blank=True)
kid_already_been_in_kindergarten = models.CharField(max_length=100, choices=preschool_choices,
null=True, blank=True ,default=False)
father_name = models.CharField(max_length=100, blank=True, null=True)
father_education_level = models.CharField(max_length=200, blank=True, null=True)
father_company = models.CharField(max_length=200, blank=True, null=True)
mother_name = models.CharField(max_length=100, blank=True, null=True)
mother_education_level = models.CharField(max_length=200, blank=True, null=True)
mother_company = models.CharField(max_length=200, blank=True, null=True)
parent_notes = models.CharField(max_length=500, blank=True, null=True)
program_choice = models.CharField(max_length=100, choices=kindergarten_program_choice, null=True,
blank=True)
def __str__(self):
return self.name
class Meta:
ordering = ['name']
class Payment(models.Model):
user = models.ForeignKey(Kids, on_delete=models.CASCADE, blank=True, null=True)
bank_paper_id = models.IntegerField(null=True, blank=True)
payment_date = models.CharField(max_length=100, null=True, blank=True)
paid = models.FloatField(null=True, blank=True)
need_to_pay = models.FloatField(null=True, blank=True)
notes = models.CharField(max_length=500, blank=True, null=True)
def __str__(self):
return self.user.name
views:
class UpdateKidView(UpdateView):
model = Kids
fields = '__all__'
template_name = 'vrtic/update_kid.html'
success_url = reverse_lazy('vrtic:kids')
def create_payment(request, pk):
kid = Kids.objects.get(id=pk)
payment_form = PaymentForm()
if request.method == 'POST':
payment_form = PaymentForm(request.POST)
if payment_form.is_valid():
payment = payment_form.save(commit=False)
payment.user = kid
payment_form.save()
return redirect('vrtic:kids')
context = {
'payment_form': payment_form,
'kid': kid
}
return render(request, 'vrtic/update_kid.html', context)
form:
class PaymentForm(forms.ModelForm):
class Meta:
model = Payment
fields = '__all__'
class UpdateKidView(UpdateView):
model = Kids
form_class = KidsForm
second_form_class = PaymentForm
template_name = 'vrtic/update_kid.html'
success_url = reverse_lazy('vrtic:kids')
def get_context_data(self, **kwargs):
context = super(UpdateKidView, self).get_context_data(**kwargs)
context['form'] = self.form_class(instance=self.get_object())
context['second_form'] = self.second_form_class()
return context
def post(self, request, **kwargs):
kids_form = self.form_class(request.POST, request.FILES, instance=self.get_object())
if kids_form.is_valid():
kid = kids_form.save()
payment_form = self.second_form_class(request.POST)
...
Not the happiest solution, but u got the idea, if need more help contact me to explain on Serbian, not sure how are the rules here for languages : )
I have a template which displays a master detail form represented by a formset object. That part is working fine. I have a second detail model which is read-only that I would like to display on the same template as the master-detail form.
My view:
def order_edit(request, pk):
order = get_object_or_404(Orders, pk=pk)
if request.method == "POST":
form = OrderForm(request.POST, instance=order)
if form.is_valid():
order = form.save(commit=False)
lineitem_formset = LineFormSet(request.POST, instance=order)
if lineitem_formset.is_valid():
order.save()
lineitem_formset.save()
#order.date_ordered = timezone.now()
#order.save()
return redirect('order_list')
else:
form = OrderForm(instance=order)
#lineitem_formset = LineFormSet(instance=Orders()) This was wrong. It was calling a new instance of Orders which was blank
lineitem_formset = LineFormSet(instance=order)
modification_formset = ModificationFormSet(instance=order)
return render(request, "orders/order_edit.html", {"form": form, "lineitem_formset": lineitem_formset,"modification_formset": modification_formset })
I have read a number of posts on this topic but cannot seem to make sense of rendering the third model on my template. Here are my models.
class LineitemInfo(models.Model):
order = models.ForeignKey('Orders')
line_item_num = models.CharField(max_length=20)
item_description = models.CharField(max_length=1020, blank=True, null=True)
quantity = models.FloatField(blank=True, null=True)
unit = models.CharField(max_length=20, blank=True, null=True)
unit_price = models.FloatField(blank=True, null=True)
line_account_code = models.CharField(max_length=260, blank=True, null=True)
options = models.CharField(max_length=30, blank=True, null=True)
option_num = models.CharField(max_length=8, blank=True, null=True)
class Meta:
unique_together = (('order', 'line_item_num'),)
class Orders(models.Model):
pr_num = models.CharField(max_length=80, blank=True, null=True)
po_num = models.CharField(max_length=56, blank=True, null=True)
task_order_num = models.CharField(max_length=40, blank=True, null=True)
credit_card_id = models.CharField(max_length=40, blank=True, null=True)
date_ordered = models.DateField(blank=True, null=True)
vendor_name = models.CharField(max_length=200, blank=True, null=True)
order_description = models.CharField(max_length=400, blank=True, null=True)
predicted_order_total = models.DecimalField(max_digits=20, decimal_places=2, blank=True, null=True)
requestor = models.CharField(max_length=120, blank=True, null=True)
class Modifications(models.Model):
order = models.ForeignKey('Orders', editable=False)
mod_num = models.CharField(max_length=40, blank=True, null=True, editable=False)
mod_date = models.DateField(blank=True, null=True, editable=False)
mod_amount = models.IntegerField(blank=True, null=True, editable=False)
mod_description = models.CharField(max_length=400, blank=True, null=True, editable=False)
mod_performenddate = models.DateField(blank=True, null=True, editable=False)
optionyear = models.IntegerField(blank=True, null=True, editable=False)
class Meta:
unique_together = (('order', 'mod_num'),)
It is the third model that I am trying to render on the template. The first two are rendered as part of a formset. TIA.
Am learning Django and I used ForeignKey to link my models.
icontains work in field that are not ForeignKeys.
I want to filter the Items in my model to show me only fields that match the queryset.
But queryset raised: Related Field got invalid lookup: icontains
Please help. Below is My model and View
My Model
class Category(models.Model):
category = models.CharField(max_length=200, default='', blank=True, null=True)
def __unicode__(self):
return self.category
class StoreItems(models.Model):
item_name = models.CharField(max_length=200, default='', blank=True, null=True)
def __unicode__(self):
return self.item_name
class Supplier(models.Model):
supplier_name = models.CharField(max_length=200, default='', blank=True, null=True)
def __unicode__(self):
return self.supplier_name
class Unit(models.Model):
unit = models.CharField(max_length=200, default='', blank=True, null=True)
def __unicode__(self):
return self.unit
class Store(models.Model):
category = models.ForeignKey(Category, blank=True, null=True)
item_name = models.ForeignKey(StoreItems, blank=True, null=True)
quantity = models.IntegerField(default='', blank=True, null=False)
receive_amount = models.IntegerField(blank=True, null=True)
receive_by = models.CharField(max_length=120, default='', blank=True, null=False)
issue_amount = models.IntegerField(blank=True, null=True)
issue_by = models.CharField(max_length=120, default='', blank=True, null=True)
issue_to = models.CharField(max_length=120, default='', blank=True, null=True)
supplier_name = models.ForeignKey(Supplier, blank=True, null=True)
created_by = models.CharField(max_length=15, default='', blank=True, null=True)
unit = models.ForeignKey(Unit, blank=True, null=True)
reorder_level = models.IntegerField(default='0', blank=True, null=False)
export_to_CSV = models.BooleanField(default=False)
last_updated = models.DateTimeField(auto_now_add=False, auto_now=True)
My View
def store_list(request):
label = 'STORE'
title = 'Select the item you want to filter'
heading = 'SEARCH ITEMS'
if request.user.is_authenticated():
form = StoreSearchForm(request.POST or None)
context = {
"title": title,
"form": form,
"heading": heading,
}
if request.method == 'POST':
queryset = Store.objects.all().order_by('item_name').filter(category__icontains=form['category'].value(), item_name__icontains=form['item_name'].value())
context = {
"queryset": queryset,
"form": form,
}
return render(request, "store.html", context)
Yep, you can't directly use icontains on a foreign key but ...
Store.objects.all().order_by('item_name'
).filter(category__category__icontains=form['category'].value(), item_name__icontains=form['item_name'].value())
Your category model contains a field also called category. That can be accessed as category__category which means you can use a query such as the one given above.