Я использую встроенные наборы форм Django с представлениями на основе классов и четкими формами.В настоящее время в моем проекте есть требование, согласно которому пользователь может отправить запрос на новую концепцию обучения, а любой пользователь в приложении может предоставить комментарии и поделиться своим мнением о концепции исследования.Когда пользователь вводит свои комментарии и отправляет форму, я хочу автоматически сохранить пользователя, вошедшего в систему, в поле пользователя.
Например, пользователь А создал новую концепцию исследования и предоставил комментарий (пожалуйста,утвердить мой запрос) при создании нового запроса.Затем для приведенного выше комментария пользователь А должен быть сохранен.
Позже приходит пользователь Б, редактирует этот запрос и комментирует «Запрос выглядит хорошо для меня» и обновляет форму.Теперь пользователь B должен быть автоматически сохранен для этого комментария.
Это новое требование для проекта.Я пробовал различные решения, доступные для переполнения стека, но мне пока не удалось.Вы можете проверить в моем коде то, что я сейчас пытаюсь достичь.
Пожалуйста, найдите мой код ниже:
models.py:
class StudyRequestConcept(models.Model):
CHOICES = (
('Yes', 'Yes'),
('No', 'No'),
)
REQUEST_STATUS = (
('Pending', 'Pending'),
('Approved', 'Approved'),
('Denied', 'Denied'),
)
APPROVER_CHOICES = (
('Amey Kelekar', 'Amey Kelekar'),
)
requestor_name = models.CharField(max_length=240, blank=False, null=False)
project = models.CharField(max_length=240, blank=False, null=False)
date_of_request = models.DateField(blank=False, null=False)
brief_summary = models.CharField(max_length=4000, blank=False, null=False)
scientific_question = models.CharField(max_length=2000, blank=False, null=False)
strategic_fit = models.CharField(max_length=2000, blank=False, null=False)
collaborators = models.CharField(max_length=1000, blank=False, null=False)
risk_assessment = models.CharField(max_length=2000, blank=False, null=False)
devices = models.CharField(max_length=1000, blank=False, null=False)
statistics = models.CharField(max_length=2000, blank=False, null=False)
personnel = models.CharField(max_length=1000, blank=False, null=False)
sample_size = models.PositiveIntegerField(blank=False, null=False, default=0)
population = models.CharField(max_length=2000, blank=False, null=False)
dmti_study_start_date = models.DateField(blank=False, null=False)
duration = models.PositiveIntegerField(blank=False, null=False, default=0)
decision_date = models.DateField(blank=False, null=False)
deliverables = models.CharField(max_length=4000, blank=False, null=False)
logistics_flag = models.CharField(max_length=3, choices=CHOICES, default='No')
status = models.CharField(max_length=20, choices=REQUEST_STATUS, default='Pending')
approver_date = models.DateField(blank=True, null=True)
approver_name = models.CharField(max_length=240, choices=APPROVER_CHOICES, blank=True, null=True)
user = models.ForeignKey(User, on_delete=models.CASCADE)
def __str__(self):
return str(self.id)
def get_absolute_url(self):
return reverse('update_StudyRequestConcept', kwargs={'pk': self.pk})
def get_commentsStudyRequestConcept(self):
return ','.join([str(i) for i in self.commentsStudyRequestConcept.all().values_list('id', flat=True)])
class CommentsStudyRequestConcept(models.Model):
"""
A Class for Study Request Concept Comments.
"""
comments = models.CharField('Comment', max_length=2000, blank=True, null=True)
commented_on = models.DateTimeField(default=timezone.now)
user = models.ForeignKey(User, on_delete=models.CASCADE)
studyRequestConcept = models.ForeignKey(StudyRequestConcept, related_name='commentsStudyRequestConcept', on_delete=models.CASCADE)
def __str__(self):
return str(self.id)
forms.py:
class StudyRequestConceptForm(forms.ModelForm):
requestor_name = forms.CharField(label=mark_safe('<b>Name of Requestor</b>'))
project = forms.CharField(label=mark_safe('<b>On behalf of which project or platform</b> <br/> <i>(What is the portfolio project / asset team / RU which will benefit from this study? At what development stage is it?)</i>'))
date_of_request = forms.DateField(label=mark_safe('<b>Date of Request</b>'),
input_formats=['%Y-%m-%d'],
widget=XDSoftDateTimePickerInput()
)
brief_summary = forms.CharField(label=mark_safe('<b>Brief Summary of Project</b>'))
scientific_question = forms.CharField(label=mark_safe('<b>Scientific Question</b> <br/><i>(What is the question you would like answered? What is the challenge we are trying to address?)</i>'))
strategic_fit = forms.CharField(label=mark_safe('<b>Strategic Fit / Impact Statement </b><br/><i>(What is the rationale for this study? What is the potential value to Pfizer? What asset team would it support, and have you secured endorsement from that asset team?)</i>'))
collaborators = forms.CharField(label=mark_safe('<b>Potential Collaborators (Internal & External)</b> <br/><i>(Who are the key collaborators required to execute the study?)</i>'))
risk_assessment = forms.CharField(label=mark_safe('<b>Risk Assessment</b> <br/> <i>(What are the risks you foresee? If so, what is your proposed mitigation plan?)</i>'))
devices = forms.CharField(label=mark_safe('<b>Devices / imaging modality</b> <br/> <i>(What device(s) will be deployed, if known)</i>'))
statistics = forms.CharField(label=mark_safe('<b>Statistics</b> <br/><i>(Have you consulted with a statistician? If so, with whom?)</i>'))
personnel = forms.CharField(label=mark_safe('<b>Anticipated personnel needs</b> <br/> <i>(Technician(s), Data Manager(s), CTS, etc.)</i>'))
sample_size = forms.IntegerField(label=mark_safe('<b>Anticipated sample size</b>'), min_value=0, max_value=2147483647)
population = forms.CharField(label=mark_safe('<b>Anticipated study population, or animal model</b><br/><i> (Pfizer internal, healthy, specific disease population…)</i>'))
dmti_study_start_date = forms.DateField(label=mark_safe('<b>Anticipated DMTI study start date</b>'),
input_formats=['%Y-%m-%d'],
widget=XDSoftDateTimePickerInput()
)
duration = forms.IntegerField(label=mark_safe('<b>Estimated study duration (months)</b>'), min_value=0, max_value=2147483647)
decision_date = forms.DateField(label=mark_safe('<b>Anticipated Asset Team study start date (or asset decision date)</b><br/><i> (For decision making to inform internal phased study design</i>'),
input_formats=['%Y-%m-%d'],
widget=XDSoftDateTimePickerInput()
)
deliverables = forms.CharField(label=mark_safe('<b>Expected deliverables</b><br/><i> (Device selection & validation, algorithm developed to qualify…)</i>'))
source = forms.CharField(max_length=50, widget=forms.HiddenInput(), required=False)
def clean(self):
requestor_name = self.cleaned_data.get('requestor_name')
project = self.cleaned_data.get('project')
date_of_request = self.cleaned_data.get('date_of_request')
brief_summary = self.cleaned_data.get('brief_summary')
scientific_question = self.cleaned_data.get('scientific_question')
strategic_fit = self.cleaned_data.get('strategic_fit')
collaborators = self.cleaned_data.get('collaborators')
risk_assessment = self.cleaned_data.get('risk_assessment')
devices = self.cleaned_data.get('devices')
statistics = self.cleaned_data.get('statistics')
personnel = self.cleaned_data.get('personnel')
sample_size = self.cleaned_data.get('sample_size')
population = self.cleaned_data.get('population')
dmti_study_start_date = self.cleaned_data.get('dmti_study_start_date')
duration = self.cleaned_data.get('duration')
decision_date = self.cleaned_data.get('decision_date')
deliverables = self.cleaned_data.get('deliverables')
if (dmti_study_start_date not in EMPTY_VALUES) and (dmti_study_start_date < datetime.date.today()):
self._errors['dmti_study_start_date'] = self.error_class([
'The date cannot be in the past.'])
if (dmti_study_start_date not in EMPTY_VALUES) and (decision_date not in EMPTY_VALUES) and (decision_date < dmti_study_start_date):
self._errors['decision_date'] = self.error_class([
'The date cannot be earlier Anticipated DMTI study start date.'])
return self.cleaned_data
class Meta:
model = StudyRequestConcept
exclude = ('user', 'logistics_flag', 'status','approver_date','approver_name')
class CommentsStudyRequestConceptForm(forms.ModelForm):
comments = forms.CharField(label='Comments',
widget=forms.TextInput(attrs={
'class': 'form-control',
}))
def clean(self):
comments = self.cleaned_data.get('comments')
class Meta:
model = CommentsStudyRequestConcept
exclude = ('commented_on', 'user')
CommentsStudyRequestConceptFormset = inlineformset_factory(StudyRequestConcept, CommentsStudyRequestConcept, form=CommentsStudyRequestConceptForm, extra=1)
views.py:
class StudyRequestConceptCreate(CreateView):
model = StudyRequestConcept
form_class = StudyRequestConceptForm
class StudyRequestConceptFormsetCreate(CreateView):
model = StudyRequestConcept
template_name = 'createStudyRequestConcept.html'
form_class = StudyRequestConceptForm
success_url = reverse_lazy('create_StudyRequestConcept')
def get_context_data(self, **kwargs):
data = super(StudyRequestConceptFormsetCreate, self).get_context_data(**kwargs)
if self.request.POST:
data['comment'] = CommentsStudyRequestConceptFormset(self.request.POST, prefix='comments')
else:
data['comment'] = CommentsStudyRequestConceptFormset(prefix='comments')
return data
def form_valid(self, form):
context = self.get_context_data()
comment = context['comment']
with transaction.atomic():
if comment.is_valid():
self.object = form.save(commit=False)
self.object.user = self.request.user
self.object = form.save()
comment.instance = self.object
commentinstance = comment.save(commit=False)
commentinstance.user = self.request.user
commentinstance.save()
messages.success(self.request, StudyRequestConcept.__name__ +' Form ID: '+ str(self.object.id) + ' was submitted successfully')
return super(StudyRequestConceptFormsetCreate, self).form_valid(form)
else:
return self.render_to_response(self.get_context_data(form=form))
class StudyRequestConceptUpdate(UpdateView):
model = StudyRequestConcept
form_class = StudyRequestConceptEditForm
template_name = 'updateStudyRequestConcept.html'
success_url = '/'
class StudyRequestConceptFormsetUpdate(UpdateView):
model = StudyRequestConcept
form_class = StudyRequestConceptEditForm
template_name = 'updateStudyRequestConcept.html'
success_url = reverse_lazy('edit_StudyRequestConcept')
def get_context_data(self, **kwargs):
data = super(StudyRequestConceptFormsetUpdate, self).get_context_data(**kwargs)
if self.request.POST:
data['comment'] = CommentsStudyRequestConceptFormset(self.request.POST, prefix='comments', instance=self.object)
else:
data['comment'] = CommentsStudyRequestConceptFormset(prefix='comments', instance=self.object)
return data
def form_valid(self, form):
context = self.get_context_data()
comment = context['comment']
with transaction.atomic():
self.object = form.save()
if comment.is_valid():
comment.instance = self.object
commentinstance = comment.save(commit=False)
commentinstance.user = self.request.user
commentinstance.save()
messages.success(self.request, (StudyRequestConcept.__name__) +' Form ID: '+ str(self.object.id) + ' was updated successfully')
return super(StudyRequestConceptFormsetUpdate, self).form_valid(form)
Поскольку для поля 'commented_on' по умолчанию используется timezone.now, оно автоматически сохраняет его в таблице.Но это не тот случай с пользователем.
Я получаю ошибку:
IntegrityError в / 1 / updateStudyRequestConcept / RequestPortal_commentsstudyrequestconcept.user_id не может быть NULL
AnyПомощь или совет будут оценены!Я буду более чем рад предоставить любой дополнительный код или необходимую информацию.Заранее благодарим за поддержку и помощь.
С уважением,
Амей Келекар