Merge pull request #582 from dod-ccpo/clin-decimals
Accept decimals in CLIN fields
This commit is contained in:
commit
0e8264cbe1
@ -1,5 +1,7 @@
|
||||
from sqlalchemy.orm.exc import NoResultFound
|
||||
|
||||
from flask import current_app as app
|
||||
|
||||
from atst.database import db
|
||||
from atst.models.task_order import TaskOrder
|
||||
from atst.models.permissions import Permissions
|
||||
@ -50,6 +52,8 @@ class TaskOrders(object):
|
||||
],
|
||||
}
|
||||
|
||||
UNCLASSIFIED_FUNDING = ["performance_length", "csp_estimate", "clin_01", "clin_03"]
|
||||
|
||||
@classmethod
|
||||
def get(cls, user, task_order_id):
|
||||
try:
|
||||
@ -90,7 +94,7 @@ class TaskOrders(object):
|
||||
|
||||
@classmethod
|
||||
def is_section_complete(cls, task_order, section):
|
||||
if section in TaskOrders.SECTIONS:
|
||||
if section in TaskOrders.sections():
|
||||
for attr in TaskOrders.SECTIONS[section]:
|
||||
if getattr(task_order, attr) is None:
|
||||
return False
|
||||
@ -108,6 +112,13 @@ class TaskOrders(object):
|
||||
|
||||
return True
|
||||
|
||||
@classmethod
|
||||
def sections(cls):
|
||||
section_list = TaskOrders.SECTIONS
|
||||
if not app.config.get("CLASSIFIED"):
|
||||
section_list["funding"] = TaskOrders.UNCLASSIFIED_FUNDING
|
||||
return section_list
|
||||
|
||||
OFFICERS = [
|
||||
"contracting_officer",
|
||||
"contracting_officer_representative",
|
||||
|
@ -1,6 +1,6 @@
|
||||
from wtforms.fields import (
|
||||
BooleanField,
|
||||
IntegerField,
|
||||
DecimalField,
|
||||
RadioField,
|
||||
SelectField,
|
||||
SelectMultipleField,
|
||||
@ -10,7 +10,7 @@ from wtforms.fields import (
|
||||
)
|
||||
from wtforms.fields.html5 import DateField, TelField
|
||||
from wtforms.widgets import ListWidget, CheckboxInput
|
||||
from wtforms.validators import Length
|
||||
from wtforms.validators import Length, InputRequired
|
||||
from flask_wtf.file import FileAllowed
|
||||
|
||||
from atst.forms.validators import IsNumber, PhoneNumber, RequiredIf
|
||||
@ -97,20 +97,41 @@ class FundingForm(CacheableForm):
|
||||
],
|
||||
render_kw={"accept": ".pdf,.png,application/pdf,image/png"},
|
||||
)
|
||||
clin_01 = IntegerField(translate("forms.task_order.clin_01_label"))
|
||||
clin_02 = IntegerField(translate("forms.task_order.clin_02_label"))
|
||||
clin_03 = IntegerField(translate("forms.task_order.clin_03_label"))
|
||||
clin_04 = IntegerField(translate("forms.task_order.clin_04_label"))
|
||||
clin_01 = DecimalField(
|
||||
translate("forms.task_order.clin_01_label"),
|
||||
validators=[
|
||||
InputRequired(message=(translate("forms.task_order.clin_validation_error")))
|
||||
],
|
||||
)
|
||||
clin_02 = DecimalField(
|
||||
translate("forms.task_order.clin_02_label"),
|
||||
validators=[
|
||||
InputRequired(message=(translate("forms.task_order.clin_validation_error")))
|
||||
],
|
||||
)
|
||||
clin_03 = DecimalField(
|
||||
translate("forms.task_order.clin_03_label"),
|
||||
validators=[
|
||||
InputRequired(message=(translate("forms.task_order.clin_validation_error")))
|
||||
],
|
||||
)
|
||||
clin_04 = DecimalField(
|
||||
translate("forms.task_order.clin_04_label"),
|
||||
validators=[
|
||||
InputRequired(message=(translate("forms.task_order.clin_validation_error")))
|
||||
],
|
||||
)
|
||||
|
||||
|
||||
class UnclassifiedFundingForm(FundingForm):
|
||||
clin_02 = IntegerField(translate("forms.task_order.unclassified_clin_02_label"))
|
||||
clin_04 = IntegerField(translate("forms.task_order.unclassified_clin_04_label"))
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
super().__init__(*args, **kwargs)
|
||||
self.clin_02.data = "0"
|
||||
self.clin_04.data = "0"
|
||||
clin_02 = StringField(
|
||||
translate("forms.task_order.unclassified_clin_02_label"),
|
||||
filters=[lambda x: x or None],
|
||||
)
|
||||
clin_04 = StringField(
|
||||
translate("forms.task_order.unclassified_clin_04_label"),
|
||||
filters=[lambda x: x or None],
|
||||
)
|
||||
|
||||
|
||||
class OversightForm(CacheableForm):
|
||||
|
@ -128,7 +128,12 @@ class UpdateTaskOrderWorkflow(ShowTaskOrderWorkflow):
|
||||
self.portfolio_id = portfolio_id
|
||||
self._task_order = None
|
||||
self._section = TASK_ORDER_SECTIONS[screen - 1]
|
||||
self._form = self._section["form"](self.form_data)
|
||||
form_type = (
|
||||
"unclassified_form"
|
||||
if "unclassified_form" in self._section and not app.config.get("CLASSIFIED")
|
||||
else "form"
|
||||
)
|
||||
self._form = self._section[form_type](self.form_data)
|
||||
|
||||
@property
|
||||
def form(self):
|
||||
@ -277,7 +282,6 @@ def update(screen, task_order_id=None, portfolio_id=None):
|
||||
workflow = UpdateTaskOrderWorkflow(
|
||||
g.current_user, form_data, screen, task_order_id, portfolio_id
|
||||
)
|
||||
|
||||
if workflow.validate():
|
||||
workflow.update()
|
||||
return redirect(
|
||||
|
@ -48,22 +48,21 @@ export default {
|
||||
totalBudget: function() {
|
||||
return [this.clin_01, this.clin_02, this.clin_03, this.clin_04].reduce(
|
||||
function(acc, curr) {
|
||||
curr = !curr ? 0 : parseInt(curr)
|
||||
curr = !curr ? 0 : parseFloat(curr)
|
||||
return acc + curr
|
||||
},
|
||||
0
|
||||
)
|
||||
},
|
||||
totalBudgetStr: function() {
|
||||
return this.formatDollars(this.totalBudget)
|
||||
return this.totalBudget.toLocaleString('us-US', {
|
||||
style: 'currency',
|
||||
currency: 'USD',
|
||||
})
|
||||
},
|
||||
},
|
||||
|
||||
methods: {
|
||||
formatDollars: function(intValue) {
|
||||
const mask = createNumberMask({ prefix: '$', allowDecimal: true })
|
||||
return conformToMask(intValue.toString(), mask).conformedValue
|
||||
},
|
||||
showUploadInput: function() {
|
||||
this.showUpload = true
|
||||
},
|
||||
|
@ -119,7 +119,7 @@ def test_task_order_form_shows_errors(client, user_session):
|
||||
|
||||
body = response.data.decode()
|
||||
assert "There were some errors" in body
|
||||
assert "Not a valid integer" in body
|
||||
assert "Not a valid decimal" in body
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
|
@ -222,6 +222,7 @@ forms:
|
||||
clin_02_label: 'CLIN 02: Classified'
|
||||
clin_03_label: 'CLIN 03: Unclassified'
|
||||
clin_04_label: 'CLIN 04: Classified'
|
||||
clin_validation_error: Please enter a dollar amount
|
||||
unclassified_clin_02_label: 'CLIN 02: Classified (available soon)'
|
||||
unclassified_clin_04_label: 'CLIN 04: Classified (available soon)'
|
||||
oversight_first_name_label: First Name
|
||||
|
Loading…
x
Reference in New Issue
Block a user