Django2 How can i make some conditions in my Class based View - python

please i have an issue , i want to check the difference between two dates from my form, then allows to create the object using my class based_View if the date is bigger than an other attribute, if not render it to an other page without inserting nothing in the database.here is my
# view
class AddVacation(LoginRequiredMixin, CreateView):
form_class = VacationCreateForm
template_name = 'vacation.html'
login_url = 'login'
def form_valid(self, form):
instance = form.save(commit=False)
instance.employee = self.request.user
return super(AddVacation, self).form_valid(form)
# form:
class VacationCreateForm(forms.ModelForm):
class Meta:
model = VacationModel
fields = [
'type',
'startDate',
'enddate',
]

class VacationCreateForm(forms.ModelForm):
class Meta:
model = VacationModel
fields = [
'type',
'startDate',
'enddate',
]
def clean(self):
start_date = self.cleaned_data['start_date']
end_date = self.cleaned_data['end_date']
from dateutils import parse
start_date = parse(start_date)
end_date = parse(end_date)
# make your calculations
raise forms.ValidationError("message.")
class AddVacation(LoginRequiredMixin, CreateView):
form_class = VacationCreateForm
template_name = 'vavcation.html'
login_url = 'login'
def post(self, request, *args, **kwargs):
"""
Handles POST requests, instantiating a form instance with the passed
POST variables and then checked for validity.
"""
form = self.get_form()
if form.is_valid():
return self.form_valid(form)
else:
redirect(to_ur_another_view)
I'm not solving your specific problem I just deliver the idea or what can you do to jump over your problem

I found this solution to check the delay ! i was thinking class basedView are always the best
def create_vacation(request):
form = VacationCreateForm(request.POST or None)
error_message = ""
if form.is_valid():
dateD = request.POST.get("Startdate")
dateF = request.POST.get("Enddate")
fmt = '%Y-%m-%d'
dS = datetime.strptime(str(dateS), fmt)
dE = datetime.strptime(str(dateE), fmt)
dateDiff = (dE - dS).days
q = Employee.objects.get(id__iexact=request.user.id)
if dateDiff < q.VacationDays:
instance = form.save(commit=False)
instance.employee = request.user
instance.save()
else:
error_message = "Impossible check Your demand"
context = {
"form": form,
"error_message": error_message,
}
return render(request, 'vacation.html', context)

Related

Django - NOT NULL constraint failed

I'm currently working on a Django app that will parse the contents of an uploaded log file to the associated database in my Django project. I've managed to get it all running as expected except it won't associate my uploaded data with the model's ForeignKey. I can assign null=True which resolves the integrity error but then of course, it doesn't assign any of the uploaded data to that ForeignKey. Here's the code:
models.py
class Case(models.Model):
case_ref = models.CharField(max_length=8)
oic = models.CharField(max_length=50)
subject = models.CharField(max_length=100)
submitted_date = models.DateTimeField(default=datetime.now, blank=True)
def get_absolute_url(self):
return reverse('case_list', kwargs={'pk': self.pk})
def __str__(self):
return self.case_ref + " " + self.subject
class TeamviewerLogs(models.Model):
case = models.ForeignKey(Case, on_delete=models.DO_NOTHING)
teamviewer_id = models.IntegerField()
teamviewer_name = models.TextField()
connection_start = models.TextField()
connection_end = models.TextField()
local_user = models.TextField()
connection_type = models.TextField()
unique_id = models.TextField()
def get_absolute_url(self):
return reverse('case_list', kwargs={'pk': self.pk})
def __str__(self):
return str(self.teamviewer_id) + " - " + str(self.teamviewer_id)
forms.py
class UploadLog(forms.ModelForm):
file = forms.FileField()
class Meta:
model = TeamviewerLogs
fields = [
'file'
]
views.py
def add_logs(request, pk):
case = get_object_or_404(Case, pk=pk)
if request.method == 'POST':
form = UploadLog(request.POST, request.FILES)
if form.is_valid():
teamviewer = form.save(commit=False)
teamviewer.case = case
log_file = request.FILES['file']
log_file = filter(None, (line.rstrip() for line in log_file))
for lines in log_file:
split = lines.decode('utf-8').split('\t')
teamviewer_id = split[0]
teamviewer_name = split[1]
connection_start = split[2]
connection_end = split[3]
local_user = split[4]
connection_type = split[5]
unique_id = split[6]
teamviewer = TeamviewerLogs(teamviewer_id=teamviewer_id, teamviewer_name=teamviewer_name,
connection_start=connection_start, connection_end=connection_end,
local_user=local_user, connection_type=connection_type, unique_id=unique_id)
teamviewer.save()
return redirect('tv_log_details', pk=case.pk)
form.save()
else:
form = UploadLog()
return render(request, 'teamviewer/add_logs.html', {'form': form})
But when I click to upload the file I'm hit with:
When it tries to execute teamviewer.save().
I've been trying to resolve this issue for hours and have tried so many different variations of answers from Stackoverflow or previous code I've used that has worked for different models but I've hit a brick wall...hard!
Any help anyone can offer would be greatly appreciated.
Ok, so here's an example of the concept I've suggested in the comments.
I've got a view which passes some data to the a form;
class ListingDetailView(DetailView):
""" Listing detail page """
model = Listing
template_name = 'listing.html'
def get_form_kwargs(self):
"""Return the kwargs for the form"""
kwargs = {}
initial = {
'listing': self.object,
}
kwargs['initial'] = initial
return kwargs
def get_form(self):
form = ApplicationSignupForm(
**self.get_form_kwargs()
)
return form
def get_context_data(self, **kwargs):
""" Add our form to the context """
context = super().get_context_data(**kwargs)
context['form'] = self.get_form()
return context
The form then makes use of that initial data and sets the field it relates to as hidden. I don't validate this data, but I'll try to show how you might do that;
class ApplicationSignupForm(forms.ModelForm):
class Meta:
""" Setup the form """
fields = (
'listing',
...
)
model = Application
widgets = {
'listing': forms.HiddenInput()
}
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
initial_data = kwargs['initial']
self.listing = initial_data.get('listing')
def clean(self):
"""
Custom form cleaning
"""
cleaned_data = super().clean()
listing = cleaned_data.get('listing')
if listing != self.listing:
self.add_error('listing', "You can't modify this value")
return cleaned_data

Unable to override post method of Django UpdateView

I have a update view in django project. I need to override the post method because I am using multiple modelform.
views.py:
class EmployeeUpdateView(LoginRequiredMixin, UpdateView):
"""
Update a created a employee
"""
login_url = '/authentication/login/'
template_name = 'employee/employee_update_form.html'
form_class = EmployeeAddModelForm
work_form_class = WorkExperienceForm
education_form_class = EducationForm
queryset = Employee.objects.all()
#success_url = reverse_lazy('employee:employee-list')
def get(self, request, *args, **kwargs):
id_ = self.kwargs.get("id")
employee_id = Employee.objects.get(id=id_)
work_info = WorkExperience.objects.get(employee=employee_id)
education_info = Education.objects.get(employee=employee_id)
return render(request, self.template_name, {
'form': self.form_class(instance=employee_id),
'work_form': self.work_form_class(instance=work_info),
'education_form': self.education_form_class(instance=education_info)
}
)
def post(self, request, *args, **kwargs):
form = self.form_class(request.POST)
work_form = self.work_form_class(request.POST, prefix='work_form')
education_form = self.education_form_class(request.POST, prefix='education_form')
# Check form validation
if form.is_valid() and work_form.is_valid() and education_form.is_valid():
instance = form.save()
work = work_form.save(commit=False)
education = education_form.save(commit=False)
work.employee = instance
education.employee = instance
work.update()
education.update()
return redirect('employee:employee-list')
return render(request, self.template_name, {
'form': form,
'work_form': work_form,
'education_form': education_form
}
)
When I press update button of my form, error is giving showwing "This field already exist". It means when i update the form is post data as a new form not as a update form.
Where is error in my post method?

how to work with Multiple forms in django Detailview

I have a comment section in django blog and there are two forms one is for comment another is for reply to the comment but the comment form is working fine and reply form doesn't work! i was trying to do but getting error... IntegrityError at /page/9/
FOREIGN KEY constraint failed...
appreciate to your help :)
Thank you.
views.py
class PostDetailView(DetailView):
model = Post
template_name = "post_detail.html"
context_object_name = 'post'
form = CommentForm()
def get_object(self):
obj = super().get_object()
if self.request.user.is_authenticated:
PostView.objects.get_or_create(
user=self.request.user,
post=obj
)
return obj
def get_context_data(self, **kwargs):
category_count = get_category_count()
most_recent = Post.objects.order_by('-timestamp')[:3]
context = super().get_context_data(**kwargs)
context['most_recent'] = most_recent
context['page_request_var'] = "page"
context['category_count'] = category_count
context['form'] = self.form
return context
def post(self, request, *args, **kwargs):
form = CommentForm(request.POST)
form = ReplyForm(request.POST)# how to work with this form like above from
if form.is_valid():
post = self.get_object()
form.instance.user = request.user
form.instance.post = post
form.save()
return redirect(reverse("post-detail", kwargs={
'pk': post.pk
}))
models.py
class Reply(models.Model):
user = models.ForeignKey(User, on_delete=models.CASCADE)
timestamp = models.DateTimeField(auto_now_add=True)
content = models.TextField()
comment = models.ForeignKey('Comment', related_name='replies',default=False, null=True,
on_delete=models.CASCADE)
def __str__(self):
return self.content
class Comment(models.Model):
user = models.ForeignKey(User, on_delete=models.CASCADE)
timestamp = models.DateTimeField(auto_now_add=True)
content = models.TextField()
post = models.ForeignKey('Post', related_name='comments', default=False,
on_delete=models.CASCADE)
def __str__(self):
return self.content
You might find it easier if you did not struggle with trying to persuade a Class-based view to do what it was not intended to do, and instead used a plain old Function-based view.
Here is a two-form view. The code has been refactored into what I regard as a better pattern, to validate both forms and redisplay if anything is wrong at the top, and then you just do the actual work to create and save the objects at the bottom.
def receive_uncoated( request): #Function based view
# let's put form instantiation in one place not two, and reverse the usual test. This
# makes for a much nicer layout with actions not sandwiched by "boilerplate"
# note any([ ]) forces invocation of both .is_valid() methods
# so errors in second form get shown even in presence of errors in first
args = [request.POST, ] if request.method == "POST" else []
batchform = CreateUncWaferBatchForm( *args )
po_form = CreateUncWaferPOForm( *args, prefix='po')
if request.method != "POST" or any(
[ not batchform.is_valid(), not po_form.is_valid() ]):
return render(request, 'wafers/receive_uncoated.html', # can get this out of the way at the top
{'batchform': batchform,
'po_form': po_form,
})
#POST, everything is valid, do the work
# create and save some objects based on the validated forms ...
return redirect( 'wafers:ok' )

Django form with dynamic queryset ModelMultipleChoiceField

I'm trying to pass a queryset to a forms ModelMultipleChoiceField as an initial value. I want to send a filtered queryset as all the choices and an initial selection. It seems to fail is_valid. Can anyone tell me what I'm doing wrong?
forms.py
class sendListForm(forms.Form):
recipients = forms.ModelMultipleChoiceField(queryset = CustomUser.objects.all())
title = forms.CharField(max_length=100,required=True)
description = forms.CharField(max_length=500,required=False,widget=forms.Textarea(attrs={'cols': 20, 'rows': 4}))
extraInfo = forms.CharField(max_length=500,required=False, help_text='Add a message to send',widget=forms.Textarea(attrs={"rows":4, "cols":20}),label='Extra Message')
startDate = forms.DateField(required=False,widget=forms.HiddenInput())
startTime = forms.TimeField(required=False,widget=forms.HiddenInput())
endDate = forms.DateField(required=False,widget=forms.HiddenInput())
endTime = forms.TimeField(required=False,widget=forms.HiddenInput())
yearName = forms.CharField(widget=forms.HiddenInput())
def __init__(self, *args, **kwargs):
recipients = kwargs.pop('recipients')
super(sendListForm, self).__init__(*args, **kwargs)
self.fields['recipients'] = forms.ModelMultipleChoiceField(queryset=recipients)
views.py
def eventSendList(request, modelPk=None):
event = get_object_or_404(Event, pk=modelPk)
if request.method == 'POST':
form = sendListForm(request.POST,recipients=CustomUser.objects.all())
if form.is_valid():
print('valid')
baseInfo = {
'recipients':recipients,
'title':event.title,
'description':event.description,
'startDate':event.startDate,
'startTime':event.startTime,
'endDate':event.endDate,
'endTime':event.endTime,
'yearName':event.yearName.name,
}
classParents = CustomUser.objects.all()
form = sendListForm(initial=baseInfo,recipients=classParents)
return render(request, 'page/sendListForm.html',{'form':form})
It never gets past the if form.is_valid():... in the view.
you can easily find your form errors by printing the form.errors field.

Unable to Update InlineFormset in Django with CBV

class PreChildrenView(CreateView):
model = PreDealDetails2
template_name = 'cam_app/children_form.html'
fields = '__all__'
success_url = reverse_lazy('forms_app:deal-entering')
session_initial = 'children_'
def get_initial(self,**kwargs):
initial = super(PreChildrenView, self).get_initial(**kwargs)
initial['deal_id'] = self.request.session['deal_id']
return initial
def get_context_data(self, **kwargs):
data = super(PreChildrenView, self).get_context_data(**kwargs)
if self.request.POST:
data['childrens'] = ChildrenFormSet(self.request.POST)
print('post')
else:
print('get')
data['childrens'] = ChildrenFormSet()
data['childrens'].extra = 5
data['info'] = 'Children Details'
return data
def form_valid(self, form):
print('wwwww')
context = self.get_context_data()
childrens = context['childrens']
if form.is_valid():
pass
if childrens.is_valid():
count = 0
self.object = form.save()
childrens.instance = self.object
childrens.save()
self.request.session[self.session_initial + 'children_count'] = count
self.request.session['valid_children'] = True
messages.success(self.request, 'Successfully filled Children Details')
return self.render_to_response(self.get_context_data(form=form))
else:
return super(PreChildrenView, self).form_invalid(form)
class UpdatePreChildrenView(UpdateView):
model = PreDealDetails2
template_name = 'cam_app/children_form.html'
fields = '__all__'
success_url = reverse_lazy('forms_app:deal-entering')
session_initial = 'children_'
def get_object(self, queryset=None):
return PreDealDetails2(deal_id = self.request.session['deal_id'])
def get_context_data(self, **kwargs):
data = super(UpdatePreChildrenView, self).get_context_data(**kwargs)
if self.request.POST:
a = PreDealDetails2.objects.get(deal_id = self.request.session['deal_id'])
data['childrens'] = ChildrenFormSet(self.request.POST)
print('post')
else:
print('get')
data['childrens'] = ChildrenFormSet(instance=self.object)
data['childrens'].extra = 5
data['info'] = 'Children Details'
return data
def form_valid(self, form):
print('update valid')
context = self.get_context_data()
childrens = context['childrens']
if form.is_valid():
print('wejri')
self.object =form.save()
if childrens.is_valid():
childrens.instance = self.object
childrens.save()
count = 0
self.request.session[self.session_initial + 'children_count'] = count
self.request.session['valid_children'] = True
messages.success(self.request, 'Successfully filled Children Details')
return self.render_to_response(self.get_context_data(form=form))
else:
return super(UpdatePreChildrenView, self).form_invalid(form)
else:
print('sfeief')
class PreChildrenRedirectView(RedirectView):
def get_redirect_url(self):
flag = 0
try:
PreDealDetails2.objects.get(deal_id=self.request.session['deal_id'])
flag = 1
except:
pass
if flag == 1:
return reverse("cam_app:update-prechildren-view")
else:
return reverse("cam_app:create-prechildren-view")
I am using above code to enter details to form and later update form.
CreateView is working fine and saving data.
UpdateView is displaying data. When i try to save updateview it is showing following error :-
Code Flow :-
First PreChildrenRedirectView is called. It checks if data already exist or not. If it does then Updateview is called and if it doesnot exist then Createview is called.
I am not using slug. Instead i am using get_object in Updateview. Let me know what is causing problem or how to solve the error.
Update
I have changed the forms.py to remove the error in child. But Deal Id is still showing error. I am also attaching the forms.py below
class ChildrenForm(forms.ModelForm):
class Meta:
model = PreChildrenDetails
fields = '__all__'
def __init__(self, *args, **kwargs):
super(ChildrenForm, self).__init__(*args, **kwargs)
self.fields['deal_id'].widget.attrs['readonly'] = True
self.helper = FormHelper(self)
self.helper.form_show_labels = False
def clean(self):
print('wow')
pass
ChildrenFormSet = inlineformset_factory(PreDealDetails2,PreChildrenDetails, form=ChildrenForm, fields = '__all__', extra=1)
Below is screenshot of error after updating

Categories