I am doing CRUD using serializers and foreign key as tasked,the problem is that when I am trying to delete a data,an error which is completely unexpected has come.
this error should not be coming as I am not missing the id in the below functions and html code
NOTE : I am doing soft delete hence the parameter 'isactive' is there
delete function
def delete(request,id):
deleteclothes = Products.objects.all(id=id)
delclothes = {}
delclothes['isactive']=False
form = POLLSerializer(deleteclothes,data=delclothes)
if form.is_valid():
print("error of form when valid:",form.errors)
form.save()
return redirect('polls:show')
else:
print("error of form when not valid:",form.errors)
return redirect('polls:show')
html code of product_list
<td>
<a href="/delete/{{result.id}}/" onclick="return confirm('Are You Sure you want to delete?')">
<button class="btn btn-danger">
Delete
</button>
</a>
</td>
models
class Products(models.Model):
categories = models.ForeignKey(Categories,on_delete=models.CASCADE)
sub_categories = models.ForeignKey(SUBCategories,on_delete=models.CASCADE)
color = models.ForeignKey(Colors,on_delete=models.CASCADE)
size = models.ForeignKey(Size,on_delete=models.CASCADE)
# image = models.ImageField(upload_to = 'media/',width_field=None,height_field=None,null=True)
title = models.CharField(max_length=50)
price = models.CharField(max_length=10)
sku_number = models.CharField(max_length=10)
product_details = models.CharField(max_length=300)
quantity = models.IntegerField(default=0)
isactive = models.BooleanField(default=True)
where am I going wrong in the code?
You can't do deleteclothes = Products.objects.all(id=id), whether you retrieve all Products by doing :
deleteclothes = Products.objects.all()
Or you retrieve the one with the id you want (which is what you need here) with :
deleteclothes = Products.objects.get(id=id)
Related
I have this table.
class MyTable(BaseModel):
key = m.CharField(max_length=20,null=False,unique=True)
pre_json = m.JSONField(blank=True, null=True)
post_json = m.JSONField(blank=True, null=True)
And I use this model through ListView/UpdateView
list view is here.
class MyTableListView(LoginRequiredMixin, ListSearchView):
model = MyTable
form_class = MyTableForm
template_name = 'mytable_list.html'
class MyTableForm(forms.ModelForm):
key = forms.CharField(required=True)
pre_json = forms.JSONField
post_json = forms.JSONField
class Meta:
model = sm.ScenarioWorker
fields = ["key","key","pre_json","post_json"]
in list html template
{{obj.pre_json}}
in edit html template
{% render_field form.pre_json class="form-control" %}
Upper one shows None in template
Lower one shows null in textarea as placeholder.
Why this two are shown? or can I erase these?
I want to stop this.
I'm at a total loss as to why I get this error. When I run similar code in the python shell I never get this error but when I try to do this through the web browser I get this error. Any idea why this happens? FYI, I'm a total beginner.
Models:
from django.contrib.auth.models import User
class Hull (models.Model):
hull = models.CharField(max_length = 33, )
def __str__(self):
return self.hull
class Hull_Spec(models.Model):
ship = models.ForeignKey(Hull, on_delete=models.CASCADE)
speed = models.FloatField()
depth = models.FloatField()
remarks = models.CharField(max_length =300)
def __str__(self):
return self.remarks
views
def new_ship (response):
x = Hull
x.objects.create(hull = response.POST.get('ship'))
Z = Hull(hull = response.POST.get('ship'))
Z.hull_spec_set.create(speed = response.POST.get('speed'), depth = response.POST.get('depth'), remarks = response.POST.get('remarks')).save()
return HttpResponse('Success')
html user interface
<div>
<form action = '/new_ship/' method = 'POST'>
{% csrf_token %}
<table>
<col>
<tr>
<td><input type = 'text' name = 'ship'>Hull</input></td>
<td><input type = 'text' name = 'speed'>Speed</input></td>
</tr>
<tr>
<td><input type = 'text' name = 'depth'>Depth</input></td>
<td><input type = 'text' name = 'remarks'>Remarks</input></td>
</tr>
<tr>
<td><input type="submit" value="Submit Fields" id = 'button_1'></td>
</tr>
</col>
</table>
</form>
</div>
Your instannce of Hull (Z) has not been saved to the database (with .save() ). This is the cause of the error.
You need to first create your Hull instance (instances are normally lower (snake) case):
hull = Hull.objects.create(hull = response.POST.get('ship'))
Then you can use that to create a Hull_Spec instance:
hull_spec = Hull_spec.objects.create(
hull=hull,
speed = response.POST.get('speed'),
depth = response.POST.get('depth'),
remarks = response.POST.get('remarks')
)
So your view would become:
def new_ship (response):
hull = Hull.objects.create(hull = response.POST.get('ship'))
hull_spec = Hull_spec.objects.create(
hull=hull,
speed = response.POST.get('speed'),
depth = response.POST.get('depth'),
remarks = response.POST.get('remarks')
)
return HttpResponse('Success')
Note also, it would be convention to name your model HullSpec not Hull_Spec.
In general the two ways of saving a model instance to the db would be:
hull = Hull(hull="something") # creates the instance
hull.save() # saves it to the database
# or
hull = Hull.objects.create(hull="something") # does it all in one go
Say I have three models, a Professor model, a Course model, and a Review model. The user is allowed to make a Review, which reviews a Professor that teaches a certain Course.
I'm thinking of how to model the many to many relationship of Professor and Course, and how to reference that relationship in Review. My idea so far is to use models.ManyToMany to link Professor and Course.
Models.py (Prof)
class Prof(models.Model):
first_name = models.CharField(max_length = 20, unique = False)
last_name = models.CharField(max_length = 20, unique = False)
def __str__ (self):
return self.first_name + " " + self.last_name
class Course(models.Model):
name = models.CharField(max_length = 20, unique = True)
prof = models.ManyToManyField(Prof)
def __str__ (self):
return self.name
Models.py (Review)
class Review(models.Model):
message = models.TextField(max_length = 4000)
created_at = models.DateTimeField(auto_now_add = True)
updated_at = models.DateTimeField(null = True)
rating = models.IntegerField(
default = 5,
validators = [MaxValueValidator(5), MinValueValidator(0)]
)
prof = models.ForeignKey(Prof, related_name = 'reviews')
course = models.ForeignKey(Course, related_name = 'reviews')
user = models.ForeignKey(User, related_name = 'reviews')
def __str__ (self):
return self.message
forms.py
class ReviewForm(ModelForm):
rating = CharField(widget=TextInput(attrs={'type': 'number','value': 5, 'min': 0, 'max': 5}))
class Meta:
model = Review
fields = ['message', 'rating', 'prof', 'course', 'user']
This is my code so far for displaying the form
<h1>New Review</h1>
<form method="POST">
{% csrf_token %}
<p>{{ review_form.message }}</p>
<p>{{ review_form.rating }}</p>
<p>{{ review_form.prof }}</p>
<!-- The prof chosen's courses should be shown here -->
<button type="submit">Save</button>
</form>
Right now, forms.py shows all the objects under Course, and i'm not sure how to instead show the courses of a professor. Is it possible to filter the form after a prof is chosen from the drop down, to display the courses he/she teacher?
It sounds like you're going about this the right way. You haven't mentioned your urls.py structure yet, or views.py but the most straightforward way to do this is to display the courses by professor, taking the professor's id (or slug-field) in as a parameter - either in the URL (v straightforward) or as the output from a form on a previous page (and reload the template with a professor parameter) or in Ajax, depending on your appetite for shiny-new-things.
In your view, when you call the form, you can then do, along the lines from this answer -
form.courses.queryset = Course.objects.filter(professor__in=[professor.id,])
Note that I've put filtered on a list here, which only has one item - it does give you scope to expand, or to use a queryset for more complicated functions later.
Tweak as appropriate if you're using class-based views. :)
I am trying to make a click event with Django Tables2 so that whenever someone clicks on a delete link in a row it will create a dialogue box for confirmation before deleting the row. Here is my code:
models.py
class Schedules(models.Model):
course_name = models.CharField(max_length=128, choices=COURSE_NAME_CHOICES, default='a-plus')
location = models.CharField(max_length=128, choices=LOCATION_CHOICES, default='south_plainfield')
room = models.CharField(max_length=128, choices=ROOM_CHOICES, default='A')
start_date = models.DateField(auto_now=False, auto_now_add=False, default=datetime.date.today)
start_time = models.CharField(max_length=128, choices=START_TIME_CHOICES, default='eight-thirty am')
end_time = models.CharField(max_length=128, choices=END_TIME_CHOICES, default='eight-thirty am')
instructor = models.CharField(max_length=128, choices=INSTRUCTOR_CHOICES, default='adewale')
total_hours = models.CharField(max_length=128, choices=TOTAL_HOURS_CHOICES, default='six')
hours_per_class = models.CharField(max_length=128, choices=HOURS_PER_CLASS_CHOICES, default='four_and_half')
frequency = models.CharField(max_length=128)
status = models.CharField(max_length=128, choices=STATUS_CHOICES)
interval = models.CharField(max_length=128, choices=INTERVAL_CHOICES, default='1 day')
initiated_by = models.CharField(max_length=128, null=True)
schedule_id = models.IntegerField(default=0)
tables.py
class ScheduleListTable(tables.Table):
change = tables.TemplateColumn('Update / Cancel / Event / '
'<a href="/schedule/delete_schedule/{{ record.id }}"
onclick="return confirm("Are you sure you want to delete this?")">Delete</a>',
verbose_name=u'Change', )
class Meta:
model = Schedules
fields = ('id', 'course_name', 'start_date', 'start_time', 'hours_per_class', 'instructor', 'change',)
attrs = {"class": "paleblue"}
views.py
def schedule_List(request):
context_dict = {}
schedule_list = Schedules.objects.order_by('start_date')
table = ScheduleListTable(schedule_list)
context_dict['table'] = table
return render(request, "schedule/schedule_list.html", context_dict)
schedule_list.html
<div id="schedule_list_table">
{% if table %}
{% render_table table %}
{% endif %}
</div>
For some reason, I can't make the onclick event that makes the confirmation dialogue box appear, and it just goes straight to deleting. I assume that it's written incorrectly in tables.py, but I don't know how to write it correctly in that case. Or do I need to do something else?
Have a look at the rendered html, for example using your browsers inspect context menu option. I think you could see there that there is a problem with the double quotes you use.
The onclick-attribute is enclosed by double quotes, but the message passed as argument to confirm() is also enclosed by double quotes. This results in your browser interpreting the attribute as `onclick="return confirm(" and ignores the gibberish it cannot understand which is your message.
You can fix that by using single quotes to enclose the message argument to confirm(), either by escaping them in the syntax you used (\'), or by using triple quotes like this:
template_code = '''
Update / Cancel / Event /
<a href="/schedule/delete_schedule/{{ record.id }}"
onclick="return confirm('Are you sure you want to delete this?')">Delete</a>'''
I tried to get data from ManyToManyField but found not luck. Will you please help me?
Here is My Song App Models.
class Artist(models.Model):
name = models.CharField(max_length=100)
slug = models.SlugField(unique = True,max_length=100,help_text="Suggested value automatically generated from name. Must be unique.")
class Album(models.Model):
name = models.CharField(max_length=100)
slug = models.SlugField(unique = True,max_length=100,help_text="Suggested value automatically generated from name. Must be unique.")
path = models.CharField(max_length=100,null=True, blank=True)
language = models.ForeignKey(Category)
albumid = models.CharField(max_length=100)
class Song(models.Model):
title = models.CharField(max_length=100)
artist = models.ManyToManyField(Artist)
music = models.ForeignKey(Music)
album = models.ForeignKey(Album)
Here is my view. I want to print Artist with titles. Titles are working fine. but not Artist
def movie_details(request,slug):
movies = get_object_or_404(Movie,slug=slug)
# calculating wikipedia directory structer for images
#image_name = movies.image
name = movies.title
album_name = Album.objects.get(name__exact=name)
album_id = album_name.id
song_list = Song.objects.filter(album=album_id)
#image_path = generateWikiImage(image_name)
#
return render_to_response('base_movies.html',locals(),
context_instance=RequestContext(request)
)
I tried in template like this. {{song_list.artist}} and getting message like this <django.db.models.fields.related.ManyRelatedManager object at 0x024CBED0>
thanks
ManyRelatedManager is the object that handles the ManyToMany relation there. To get the list of objects that you're looking for, you need to use its all() method.
In this case, you'd use {{song_list.artist.all}}, which will give you a QuerySet that you can then iterate over in your template.
ManyToManyField holds queryset, so you can't just output it in template. You should iterate over it.
Like this (song is some Song instance)
<ul>
{% for artist in song.artist.all %}
<li>{{ artist.name }}</li>
{% endfor %}
</ul>