Skip to content

Commit

Permalink
Merge pull request #2286 from GSA-TTS/main
Browse files Browse the repository at this point in the history
  • Loading branch information
jadudm authored Sep 28, 2023
2 parents 34ec315 + 6da1652 commit af72f4a
Show file tree
Hide file tree
Showing 36 changed files with 346 additions and 65 deletions.
32 changes: 32 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-acceptance-criteria.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
---
name: "Snip: Acceptance Criteria"
about: Starting point for a story acceptance.
title: 'snip-acceptance-criteria'
labels: ''
assignees: ''
---

# Acceptance Criteria

We use [DRY](https://docs.behat.org/en/latest/user_guide/writing_scenarios.html#backgrounds) [behavior-driven development](https://en.wikipedia.org/wiki/Behavior-driven_development#Behavioral_specifications) wherever possible.

[comment]: # "ACs should be clearly demoable/verifiable whenever possible."
[comment]: # "Given: the initial context at the beginning of the scenario"
[comment]: # "when: the event that triggers the scenario"
[comment]: # "then: the expected outcome(s)"
[comment]: # "Repeat scenarios as needed, or repeat behaviors and lists within a scenario as needed."

[comment]: # "The scenario should be a short, plain language description."
[comment]: # "Feeling repetative? Apply the DRY (Don't Repeat Yourself) principle!"

### Scenario:

**Given**
**when**
...

[comment]: # "Each task should be a verifiable outcome"
```[tasklist]
### then...
- [ ] [a thing happens]
```
8 changes: 8 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-at-a-glance.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,11 @@
---
name: "Snip: At a glance"
about: Starting point for a story.
title: 'snip-at-a-glance'
labels: ''
assignees: ''
---

# At a glance

[comment]: # "Begin with a short summary so intent can be understood at a glance."
Expand Down
7 changes: 7 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-background.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,10 @@
---
name: "Snip: Background"
about: Starting point for the background on a ticket.
title: 'snip-background'
labels: ''
assignees: ''
---

# Background

Expand Down
8 changes: 8 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-content-signoff.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,11 @@
---
name: "Snip: Content signoff"
about: Starting point for a content signoff checklist.
title: 'snip-content-signoff'
labels: 'content'
assignees: ''
---

### Content signoff

[comment]: # "As each step is completed, assign the next team member to this ticket. At-mention (@-mention) them in a comment for visibility."
Expand Down
22 changes: 22 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-scenario.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
---
name: "Snip: Scenario"
about: Starting point for a scenario; sub-item to acceptance.
title: 'snip-scenario'
labels: ''
assignees: ''
---

[comment]: # "The scenario should be a short, plain language description."
[comment]: # "Feeling repetative? Apply the DRY (Don't Repeat Yourself) principle!"

### Scenario:

**Given**
**when**
...

[comment]: # "Each task should be a verifiable outcome"
```[tasklist]
### then...
- [ ] [a thing happens]
```
7 changes: 7 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-security-considerations.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,10 @@
---
name: "Snip: Security Considerations"
about: Starting point for security considerations on a piece of work.
title: 'snip-security-considerations'
labels: ''
assignees: ''
---

# Security Considerations

Expand Down
10 changes: 10 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-shepherd.md
Original file line number Diff line number Diff line change
@@ -1,9 +1,19 @@
---
name: "Snip: Shepherds"
about: Starting point for who will shepherd work.
title: 'snip-shepherds'
labels: ''
assignees: ''
---

### Shepherds

[comment]: # "@ mention shepherds as we move across the board."
[comment]: # "Add/remove as needed"

* Content shepherd:
* Design shepherd:
* Data shepherd:
* Infrastructure shepherd:
* Engineering shepherd:

9 changes: 9 additions & 0 deletions .github/ISSUE_TEMPLATE/snip-story-process.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,12 @@
---
name: "Snip: Process Checklist"
about: Starting point for a process checklist.
title: 'snip-process-checklist'
labels: ''
assignees: ''
---


<h3>Process Checklist</h3>
<p>How it moves across the board...</p>

Expand Down
7 changes: 5 additions & 2 deletions .github/workflows/pull-request-checks.yml
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ jobs:
dev-requirements: ${{ steps.filter.outputs.devrequirements }}
docker: ${{ steps.filter.outputs.docker }}
package: ${{ steps.filter.outputs.package }}
staticfiles: ${{ steps.filter.outputs.staticfiles }}
steps:
- uses: dorny/paths-filter@v2
id: filter
Expand All @@ -34,17 +35,19 @@ jobs:
- './backend/Dockerfile'
package:
- './backend/package.json'
staticfiles:
- './backend/static/**'
# Tests and Linting invoked on a Pull Request
testing-from-build:
needs: [check-for-changes]
if: ${{ needs.check-for-changes.outputs.requirements == 'true' || needs.check-for-changes.outputs.dev-requirements == 'true' || needs.check-for-changes.outputs.docker == 'true' || needs.check-for-changes.outputs.package == 'true' }}
if: ${{ needs.check-for-changes.outputs.requirements == 'true' || needs.check-for-changes.outputs.dev-requirements == 'true' || needs.check-for-changes.outputs.docker == 'true' || needs.check-for-changes.outputs.package == 'true' || needs.check-for-changes.outputs.staticfiles == 'true' }}
uses: ./.github/workflows/testing-from-build.yml
secrets: inherit

testing-from-ghcr:
needs: [check-for-changes]
if: ${{ needs.check-for-changes.outputs.requirements != 'true' && needs.check-for-changes.outputs.dev-requirements != 'true' && needs.check-for-changes.outputs.docker != 'true' && needs.check-for-changes.outputs.package != 'true' }}
if: ${{ needs.check-for-changes.outputs.requirements != 'true' && needs.check-for-changes.outputs.dev-requirements != 'true' && needs.check-for-changes.outputs.docker != 'true' && needs.check-for-changes.outputs.package != 'true' && needs.check-for-changes.outputs.staticfiles != 'true' }}
uses: ./.github/workflows/testing-from-ghcr.yml
secrets: inherit

Expand Down
1 change: 1 addition & 0 deletions backend/audit/fixtures/excel.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@
)
SECONDARY_AUDITORS_TEST_FILE = TESTFILES_DIR / "secondary-auditors-pass-01.json"
NOTES_TO_SEFA_TEST_FILE = TESTFILES_DIR / "notes-to-sefa-pass-01.json"
TRIBAL_ACCESS_TEST_FILE = TESTFILES_DIR / "tribal-access-pass-01.json"

ADDITIONAL_UEIS_ENTRY_FIXTURES = (
settings.AUDIT_TEST_DATA_ENTRY_DIR / "additional-ueis-entries.json"
Expand Down
10 changes: 9 additions & 1 deletion backend/audit/intake_to_dissemination.py
Original file line number Diff line number Diff line change
Expand Up @@ -266,6 +266,7 @@ def load_general(self):
audit_information = self.single_audit_checklist.audit_information or {}
auditee_certification = self.single_audit_checklist.auditee_certification or {}
# auditor_certification = self.single_audit_checklist.auditor_certification or {}
tribal_data_consent = self.single_audit_checklist.tribal_data_consent or {}
cognizant_agency = self.single_audit_checklist.cognizant_agency or ""
oversight_agency = self.single_audit_checklist.oversight_agency or ""

Expand Down Expand Up @@ -321,6 +322,13 @@ def load_general(self):
addl = Util.bool_to_yes_no(general_information["multiple_ueis_covered"])
general_data["is_additional_ueis"] = addl

if general_information["user_provided_organization_type"] == "tribal":
is_public = tribal_data_consent[
"is_tribal_information_authorized_to_be_public"
]
else:
is_public = True

# Various values in audit_information need special handling
audit_data = {
"agencies_with_prior_findings": Util.json_array_to_str(
Expand Down Expand Up @@ -366,7 +374,7 @@ def load_general(self):
# is_duplicate_reports = Util.bool_to_yes_no(audit_information["is_aicpa_audit_guide_included"]), #FIXME This mapping does not seem correct
total_amount_expended=total_amount_expended,
type_audit_code="UG",
is_public=self.single_audit_checklist.is_public,
is_public=is_public,
data_source=self.single_audit_checklist.data_source,
**general_data,
**audit_data,
Expand Down
119 changes: 78 additions & 41 deletions backend/audit/test_intake_to_dissemination.py
Original file line number Diff line number Diff line change
Expand Up @@ -71,34 +71,58 @@ def _run_state_transition(self, sac):
# Increment the minute by 2
transition_date += timedelta(minutes=2)

return sac

def setUp(self):
self.user = baker.make(User)
def _create_sac(
self,
reference_number=None,
user_provided_organization_type=None,
cognizant_agency=None,
oversight_agency=None,
privacy_flag=None,
):
if reference_number:
findings_text_data = self._fake_findings_text(
reference_number=reference_number
)
else:
findings_text_data = self._fake_findings_text()

if user_provided_organization_type:
general_data = self._fake_general(
user_provided_organization_type=user_provided_organization_type
)
else:
general_data = self._fake_general()

sac = SingleAuditChecklist.objects.create(
submitted_by=self.user,
general_information=self._fake_general(),
general_information=general_data,
federal_awards=self._fake_federal_awards(),
findings_uniform_guidance=self._fake_findings_uniform_guidance(),
notes_to_sefa=self._fake_notes_to_sefa(),
findings_text=self._fake_findings_text(),
findings_text=findings_text_data,
corrective_action_plan=self._fake_corrective_action_plan(),
secondary_auditors=self._fake_secondary_auditors(),
additional_ueis=self._fake_additional_ueis(),
additional_eins=self._fake_additional_eins(),
audit_information=self._fake_audit_information(),
auditee_certification=self._fake_auditee_certification(),
cognizant_agency="42",
oversight_agency="42",
tribal_data_consent=self._fake_tribal_data_consent(privacy_flag),
cognizant_agency=cognizant_agency,
oversight_agency=oversight_agency,
)
sac = self._run_state_transition(sac)
return sac

def setUp(self):
self.user = baker.make(User)

sac = self._create_sac(cognizant_agency="42", oversight_agency="42")
self._run_state_transition(sac)
self.sac = sac
self.intake_to_dissemination = IntakeToDissemination(self.sac)
self.report_id = sac.report_id

@staticmethod
def _fake_general():
def _fake_general(user_provided_organization_type: str = "state"):
fake = Faker()
geninfofile = "general-information--test0001test--simple-pass.json"
geninfo = _load_json(AUDIT_JSON_FIXTURES / geninfofile)
Expand Down Expand Up @@ -136,7 +160,7 @@ def _fake_general():
"auditee_fiscal_period_end": "2023-06-01",
"ein_not_an_ssn_attestation": "true",
"auditee_fiscal_period_start": "2022-11-01",
"user_provided_organization_type": "state",
"user_provided_organization_type": user_provided_organization_type,
"auditor_ein_not_an_ssn_attestation": "true",
}

Expand Down Expand Up @@ -330,6 +354,19 @@ def _fake_audit_information():
}
return audit_information

@staticmethod
def _fake_tribal_data_consent(privacy_flag=None):
fake = Faker()

if privacy_flag is None:
privacy_flag = fake.boolean()

return {
"is_tribal_information_authorized_to_be_public": privacy_flag,
"tribal_authorization_certifying_official_name": fake.word(),
"tribal_authorization_certifying_official_title": fake.word(),
}

@staticmethod
def _fake_additional_ueis():
return {
Expand Down Expand Up @@ -397,6 +434,29 @@ def test_submitted_date(self):
self.assertEqual(general.submitted_date, date_in_american_samoa)
general.delete()

def _setup_and_test_privacy_flag(self, flag):
"""Common setup and test logic for tribal data privacy flag tests."""

sac = self._create_sac(
privacy_flag=flag,
user_provided_organization_type="tribal",
)
self._run_state_transition(sac)
self.intake_to_dissemination = IntakeToDissemination(sac)
self.intake_to_dissemination.load_all()
self.intake_to_dissemination.save_dissemination_objects()
general = General.objects.first()
self.assertEqual(general.entity_type, "tribal")
self.assertEqual(general.is_public, flag)

def test_tribal_data_is_public_when_authorized(self):
"""Test that tribal data privacy flag is enabled when user has authorized it to be public."""
self._setup_and_test_privacy_flag(True)

def test_tribal_data_is_private_when_not_authorized(self):
"""Test that tribal data privacy flag is disabled when user has not authorized it to be public."""
self._setup_and_test_privacy_flag(False)

def test_load_federal_award(self):
self.intake_to_dissemination.load_federal_award()
self.intake_to_dissemination.save_dissemination_objects()
Expand Down Expand Up @@ -489,47 +549,24 @@ def test_load_all(self):
len_general = len(General.objects.all())
len_captext = len(CapText.objects.all())

sac = SingleAuditChecklist.objects.create(
submitted_by=self.user,
general_information=self._fake_general(),
federal_awards=self._fake_federal_awards(),
findings_uniform_guidance=self._fake_findings_uniform_guidance(),
notes_to_sefa=self._fake_notes_to_sefa(),
findings_text=self._fake_findings_text(reference_number=2),
corrective_action_plan=self._fake_corrective_action_plan(),
secondary_auditors=self._fake_secondary_auditors(),
additional_ueis=self._fake_additional_ueis(),
additional_eins=self._fake_additional_eins(),
audit_information=self._fake_audit_information(),
auditee_certification=self._fake_auditee_certification(),
)
sac = self._run_state_transition(sac)
sac = self._create_sac(reference_number=2)
self._run_state_transition(sac)
self.sac = sac
self.intake_to_dissemination = IntakeToDissemination(self.sac)
self.intake_to_dissemination.load_all()
self.intake_to_dissemination.save_dissemination_objects()
self.report_id = sac.report_id
self.assertLess(len_general, len(General.objects.all()))
self.assertLess(len_captext, len(CapText.objects.all()))
general = General.objects.first()
self.assertNotEqual(general.entity_type, "tribal")
self.assertEqual(general.is_public, True)

def test_load_and_return_objects(self):
len_general = len(General.objects.all())
len_captext = len(CapText.objects.all())
sac = SingleAuditChecklist.objects.create(
submitted_by=self.user,
general_information=self._fake_general(),
federal_awards=self._fake_federal_awards(),
findings_uniform_guidance=self._fake_findings_uniform_guidance(),
notes_to_sefa=self._fake_notes_to_sefa(),
findings_text=self._fake_findings_text(reference_number=2),
corrective_action_plan=self._fake_corrective_action_plan(),
secondary_auditors=self._fake_secondary_auditors(),
additional_ueis=self._fake_additional_ueis(),
additional_eins=self._fake_additional_eins(),
audit_information=self._fake_audit_information(),
auditee_certification=self._fake_auditee_certification(),
)
sac = self._run_state_transition(sac)
sac = self._create_sac(reference_number=2)
self._run_state_transition(sac)
self.sac = sac
self.intake_to_dissemination = IntakeToDissemination(self.sac)
self.report_id = sac.report_id
Expand Down
Loading

0 comments on commit af72f4a

Please sign in to comment.