Merge pull request #374 from dod-ccpo/finver-refactor

financial verification routes refactor
This commit is contained in:
dandds 2018-10-12 11:19:05 -04:00 committed by GitHub
commit ffa317a3eb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 152 additions and 56 deletions

View File

@ -1,8 +1,10 @@
from sqlalchemy import exists, and_, exc, text from sqlalchemy import exists, and_, exc, text
from sqlalchemy.orm.exc import NoResultFound
from atst.database import db from atst.database import db
from atst.domain.common import Query from atst.domain.common import Query
from atst.models.request import Request from atst.models.request import Request
from atst.domain.exceptions import NotFoundError
class RequestsQuery(Query): class RequestsQuery(Query):

View File

@ -6,80 +6,129 @@ from atst.domain.requests import Requests
from atst.forms.financial import FinancialForm, ExtendedFinancialForm from atst.forms.financial import FinancialForm, ExtendedFinancialForm
def task_order_data(task_order): class FinancialVerification:
def __init__(self, request, extended=False, post_data=None):
self.request = request
self._extended = extended
self._post_data = post_data
self._form = None
self.reset()
def reset(self):
self._updateable = False
self._valid = False
self.workspace = None
if self._form:
self._form.reset()
@property
def is_extended(self):
return self._extended or self.is_pending_changes
@property
def is_pending_changes(self):
return self.request.is_pending_financial_verification_changes
@property
def _task_order_data(self):
if self.request.task_order:
task_order = self.request.task_order
data = task_order.to_dictionary() data = task_order.to_dictionary()
data["task_order_number"] = task_order.number data["task_order_number"] = task_order.number
data["funding_type"] = task_order.funding_type.value data["funding_type"] = task_order.funding_type.value
return data return data
else:
return {}
@property
def _form_data(self):
if self._post_data:
return self._post_data
else:
form_data = self.request.body.get("financial_verification", {})
form_data.update(self._task_order_data)
def is_extended(request): return form_data
return (
http_request.args.get("extended") @property
or request.is_pending_financial_verification_changes def form(self):
if not self._form:
if self.is_extended:
self._form = ExtendedFinancialForm(data=self._form_data)
else:
self._form = FinancialForm(data=self._form_data)
return self._form
def validate(self):
if self.form.validate():
self._updateable = True
self._valid = self.form.perform_extra_validation(
self.request.body.get("financial_verification")
)
else:
self._updateable = False
self._valid = False
return self._valid
@property
def pending(self):
return self.request.is_pending_ccpo_approval
def finalize(self):
if self._updateable:
self.request = Requests.update_financial_verification(
self.request.id, self.form.data
) )
if self._valid:
self.request = Requests.submit_financial_verification(self.request)
def financial_form(request, data): if self.request.is_financially_verified:
if is_extended(request): self.workspace = Requests.approve_and_create_workspace(self.request)
return ExtendedFinancialForm(data=data)
else:
return FinancialForm(data=data)
@requests_bp.route("/requests/verify/<string:request_id>", methods=["GET"]) @requests_bp.route("/requests/verify/<string:request_id>", methods=["GET"])
def financial_verification(request_id=None): def financial_verification(request_id):
request = Requests.get(g.current_user, request_id) request = Requests.get(g.current_user, request_id)
form_data = request.body.get("financial_verification") finver = FinancialVerification(request, extended=http_request.args.get("extended"))
if request.task_order:
form_data.update(task_order_data(request.task_order))
form = financial_form(request, form_data)
return render_template( return render_template(
"requests/financial_verification.html", "requests/financial_verification.html",
f=form, f=finver.form,
jedi_request=request, jedi_request=finver.request,
review_comment=request.review_comment, review_comment=finver.request.review_comment,
extended=is_extended(request), extended=finver.is_extended,
) )
@requests_bp.route("/requests/verify/<string:request_id>", methods=["POST"]) @requests_bp.route("/requests/verify/<string:request_id>", methods=["POST"])
def update_financial_verification(request_id): def update_financial_verification(request_id):
post_data = http_request.form request = Requests.get(g.current_user, request_id)
existing_request = Requests.get(g.current_user, request_id) finver = FinancialVerification(
form = financial_form(existing_request, post_data) request, extended=http_request.args.get("extended"), post_data=http_request.form
rerender_args = dict(
jedi_request=existing_request, f=form, extended=is_extended(existing_request)
) )
if form.validate(): finver.validate()
valid = form.perform_extra_validation(
existing_request.body.get("financial_verification") finver.finalize()
)
updated_request = Requests.update_financial_verification(request_id, form.data) if finver.workspace:
if valid:
submitted_request = Requests.submit_financial_verification(updated_request)
if submitted_request.is_financially_verified:
new_workspace = Requests.approve_and_create_workspace(submitted_request)
return redirect( return redirect(
url_for( url_for(
"workspaces.new_project", "workspaces.new_project",
workspace_id=new_workspace.id, workspace_id=finver.workspace.id,
newWorkspace=True, newWorkspace=True,
) )
) )
elif finver.pending:
return redirect(url_for("requests.requests_index", modal="pendingCCPOApproval"))
else: else:
return redirect( finver.reset()
url_for("requests.requests_index", modal="pendingCCPOApproval")
)
else:
form.reset()
return render_template( return render_template(
"requests/financial_verification.html", **rerender_args "requests/financial_verification.html",
jedi_request=finver.request,
f=finver.form,
extended=finver.is_extended,
) )
else:
form.reset()
return render_template("requests/financial_verification.html", **rerender_args)

View File

@ -4,6 +4,7 @@ from flask import url_for
from atst.eda_client import MockEDAClient from atst.eda_client import MockEDAClient
from atst.models.request_status_event import RequestStatus from atst.models.request_status_event import RequestStatus
from atst.routes.requests.financial_verification import FinancialVerification
from tests.mocks import MOCK_REQUEST, MOCK_USER from tests.mocks import MOCK_REQUEST, MOCK_USER
from tests.factories import ( from tests.factories import (
@ -172,3 +173,47 @@ def test_displays_ccpo_review_comment(user_session, client):
response = client.get("/requests/verify/{}".format(request.id)) response = client.get("/requests/verify/{}".format(request.id))
body = response.data.decode() body = response.data.decode()
assert review_comment in body assert review_comment in body
class TestFinancialVerification:
def _service_object(self, request=None, extended=False, post_data={}):
if not request:
self.request = RequestFactory.create()
else:
self.request = request
return FinancialVerification(
self.request, extended=extended, post_data=post_data
)
def test_is_extended(self):
finver_one = self._service_object()
assert not finver_one.is_extended
finver_two = self._service_object(
request=RequestFactory.create_with_status(
RequestStatus.CHANGES_REQUESTED_TO_FINVER
)
)
assert finver_two.is_extended
finver_three = self._service_object(extended=True)
assert finver_three.is_extended
def test_is_pending_changes(self):
finver_one = self._service_object()
assert not finver_one.is_pending_changes
finver_two = self._service_object(
request=RequestFactory.create_with_status(
RequestStatus.CHANGES_REQUESTED_TO_FINVER
)
)
assert finver_two.is_pending_changes
def test_pending(self):
finver_one = self._service_object()
assert not finver_one.pending
finver_two = self._service_object(
request=RequestFactory.create_with_status(
RequestStatus.PENDING_CCPO_APPROVAL
)
)
assert finver_two.pending