Skip to content

Report

hypha.apply.projects.forms.report

ReportEditForm

ReportEditForm(*args, user=None, initial=None, **kwargs)

Bases: StreamBaseForm, ModelForm

Source code in hypha/apply/projects/forms/report.py
def __init__(self, *args, user=None, initial=None, **kwargs):
    if initial is None:
        initial = {}
    # Need to populate form_fields, right?
    # No: The form_fields got populated from the view which instantiated this Form.
    # Yes: they don't seem to be here.
    # No: this is not where the magic happens.
    # self.form_fields = kwargs.pop("form_fields", {})
    # Need to populate form_data, right? Yes. No. IDK. Appears no.
    # self.form_data = kwargs.pop("form_data", {})
    # OK, both yes and no. If there is an existing value it will come via "initial", so if present there, use them.
    # if initial["form_fields"] is not None:
    #     self.form_fields = initial["form_fields"]
    # if initial["form_data"] is not None:
    #     self.form_data = initial["form_data"]
    # But this should not be needed because super().__init__ will already take these initial values and use them.
    super().__init__(*args, initial=initial, **kwargs)
    self.user = user

user instance-attribute

user = user

Meta

model class-attribute instance-attribute
model = Report
fields class-attribute instance-attribute
fields = []

swap_fields_for_display

swap_fields_for_display(func)
Source code in hypha/apply/stream_forms/forms.py
def swap_fields_for_display(func):
    def wrapped(self, *args, **kwargs):
        # Replaces the form fields with the display fields
        # should only add new streamblocks and wont affect validation
        fields = self.fields.copy()
        self.fields = self.display
        yield from func(self, *args, **kwargs)
        self.fields = fields

    return wrapped

hidden_fields

hidden_fields()
Source code in hypha/apply/stream_forms/forms.py
def hidden_fields(self):
    # No hidden fields are returned by default because of MixedFieldMetaclass
    return [self[f] for f in self.fields.keys() if self[f].is_hidden]

delete_temporary_files

delete_temporary_files()

Overridden method of django_file_form's FileFormMixin, to handle multiple forms on the same page.

Source code in hypha/apply/stream_forms/forms.py
def delete_temporary_files(self):
    """
    Overridden method of django_file_form's FileFormMixin, to handle multiple forms on the same page.
    """
    form_id = self.data.getlist(self.add_prefix("form_id"))

    if not form_id:
        return

    form_id = form_id[0]
    for field_name, field in self.fields.items():
        if hasattr(field, "delete_file_data"):
            prefixed_field_name = self.add_prefix(field_name)
            field.delete_file_data(prefixed_field_name, form_id)

clean

clean()
Source code in hypha/apply/projects/forms/report.py
def clean(self):
    cleaned_data = super().clean()
    cleaned_data["form_data"] = {
        key: value
        for key, value in cleaned_data.items()
        if key not in self._meta.fields
    }
    return cleaned_data

save

save(commit=True, form_fields=dict)
Source code in hypha/apply/projects/forms/report.py
@transaction.atomic
def save(self, commit=True, form_fields=dict):
    is_draft = "save" in self.data
    version = ReportVersion.objects.create(
        report=self.instance,
        form_fields=form_fields,
        # Save a ReportVersion first then edit/update the form_data below.
        form_data={},
        submitted=timezone.now(),
        draft=is_draft,
        author=self.user,
    )
    # We need to save the fields first, not attempt to save form_data on first save, then update the form_data next.
    # Otherwise, we don't get access to the generator method "question_field_ids" which we use to prevent temp file
    # fields from getting into the saved form_data.
    # Inspired by ProjectForm.save and ProjectSOWForm.save but enhanced to support multi-answer fields.
    version.form_data = {
        field: self.cleaned_data["form_data"][field]
        for field in self.cleaned_data["form_data"]
        # Where do we get question_field_ids? On the version, but only when it exists, thus the create-then-update.
        # The split-on-underscore supports the use of multi-answer fields such as MultiInputCharFieldBlock.
        if field.split("_")[0] in version.question_field_ids
    }

    # In case there are stream form file fields, process those here.
    version.process_file_data(self.cleaned_data["form_data"])
    # Because ReportVersion is a separate entity from Project, super().save will not save ReportVersion: save here.
    version.save()

    if is_draft:
        self.instance.draft = version
    else:
        # If this is the first submission of the report we track that as the
        # submitted date of the report
        if not self.instance.submitted:
            self.instance.submitted = version.submitted
        self.instance.current = version
        self.instance.draft = None

    instance = super().save(commit)
    return instance

ReportFrequencyForm

ReportFrequencyForm(*args, **kwargs)

Bases: ModelForm

Source code in hypha/apply/projects/forms/report.py
def __init__(self, *args, **kwargs):
    super().__init__(*args, **kwargs)
    self.fields["occurrence"].required = False
    self.fields["frequency"].required = False

start class-attribute instance-attribute

start = DateField(label='Report on:', required=False)

Meta

model class-attribute instance-attribute
model = ReportConfig
fields class-attribute instance-attribute
fields = ('start', 'occurrence', 'frequency', 'does_not_repeat')
labels class-attribute instance-attribute
labels = {'occurrence': '', 'frequency': ''}