I have a view that I want to be able to add an event to a project. There are 2 models, one for the Project
and one for Event
.
Project Model
class Project(models.Model):
project_name = models.CharField(max_length=50, blank=False, unique=True)
project_website = models.URLField(max_length=50, blank=True)
project_description = models.TextField(blank=True)
ckeditor_classic = models.TextField(blank=True)
project_category = models.CharField(max_length=15, blank=True)
project_type = models.CharField(max_length=10, blank=True)
project_platform = models.CharField(max_length=25, blank=True)
project_marketcap = models.IntegerField(blank=True, null=True)
project_stage = models.CharField(max_length=25, blank=True)
project_blockchain = models.CharField(max_length=25, blank=True)
project_investors = models.ManyToManyField(Investor, blank=True)
project_developers = models.ManyToManyField(Developer, blank=True)
def __str__(self):
return str(self.project_name)
Event Model
class Event(models.Model):
project = models.ForeignKey(Project, to_field='project_name', on_delete=models.CASCADE)
event_name = models.CharField(max_length=100)
event_date = models.DateTimeField(blank=True)
event_url = models.URLField(max_length=100, blank=True)
def __str__(self):
return str(self.event_name)
The event has a ForeignKey
to the Project.
when I go to the project page for a specific project, I then click a button to enable me to create an event.
The Project Name is pre-populated using this URL
path('apps/add_event/<int:project_id>', view=AddEvent, name="add_event"),
This creates a simple form that i can then assign a name and date for the event, but when i POST
(Submit) the data doesn't get added to the database.
I do get a POST
in the logs
[25/Nov/2021 21:37:11] "POST /apps/add_event/3 HTTP/1.1" 302 0
I can't work out why the data is not being updated in the database?
Form.PY
class addEventForm(forms.ModelForm):
def __init__(self, *args, **kwargs):
super(addEventForm, self).__init__(*args, **kwargs)
class Meta:
model = Event
fields = '__all__'
View.py
@login_required
def AddEvent(request,project_id):
project = Project.objects.get(pk=project_id)
form = addEventForm(request.POST or None, instance=project)
if form.is_valid():
form.save()
return redirect('http://127.0.0.1:8000/')
return render(request, 'pages/add_event.html', {'project': project, "form": form})
I'm wondering if its this line form = addEventForm(request.POST or None, instance=project)
should the instance be instance=event
I added in event = Event.objects.all()
and changed the instance=event
but it throws an error:
AttributeError at /apps/add_event/4
'QuerySet' object has no attribute '_meta'
So I am at a bit of a loss. Any ideas?
CodePudding user response:
You can not make project
the instance: your form works on an Event
. By using instance=project
you let the form edit attributes that belong to the event
like event_name
, but these will not be saved to the database, since a Project
has no column event_name
.
The view thus should take request.POST
as data, and we set the .project
of the Event
wrapped in the form with:
from django.shortcuts import get_object_or_404
@login_required
def AddEvent(request,project_id):
project = get_object_or_404(Project, pk=project_id)
if request.method == 'POST':
form = addEventForm(request.POST)
if form.is_valid():
form.instance.project = project
form.save()
return redirect('http://127.0.0.1:8000/')
else:
form = addEventForm()
return render(request, 'pages/add_event.html', {'project': project, "form": form})