Просмотр исходного кода

Flag a labour line's missing description when it gets hours or a price, not when it is added (#491)

A new hourly line arrives with the workshop's rate and a new service line
with a quantity of one, and both counted as a started row. Every line was
marked as missing its description the moment it was added, so the red
border said nothing, and a ready line left untouched blocked the save with
"Every labour line needs a description". Now an hourly line counts once it
has hours and a service line once it has a price, so the line is marked as
soon as it needs the description and an untouched one is dropped on save
as the blank row always was.
Bernt Christian Egeland 1 день назад
Родитель
Сommit
00df115c3e

+ 18 - 4
src/__tests__/features/workorders/validate-service-form.test.ts

@@ -75,22 +75,36 @@ describe('what a work order must have before it saves', () => {
 
   it('leaves the blank row the editor keeps ready alone', () => {
     // Every list ends in an empty row waiting to be typed into. It is not a
-    // mistake, and it is dropped on save without a word.
+    // mistake, and it is dropped on save without a word. A new labour line
+    // comes with the workshop's rate already in it, and a new service line
+    // with a quantity of one: still nobody has said anything with them.
     expect(
       findServiceFormProblem({
         ...empty,
         partItems: [part(), part({ name: '', unitPrice: 0, quantity: 1 })],
-        laborItems: [labor(), labor({ description: '', hours: 0, rate: 0 })],
+        laborItems: [
+          labor(),
+          labor({ description: '', hours: 0, rate: 0 }),
+          labor({ description: '', hours: 0, rate: 800 }),
+          labor({ description: '', hours: 1, rate: 0, pricingType: 'service' }),
+        ],
       })
     ).toBeNull()
   })
 
-  it('refuses labour with hours or a rate but nothing said about it', () => {
+  it('refuses labour with hours, or a priced service, but nothing said about it', () => {
     expect(findServiceFormProblem({ ...empty, laborItems: [labor({ description: '' })] })).toBe(
       'laborDescription'
     )
+    // Hours with no rate yet are still time somebody recorded.
     expect(
-      findServiceFormProblem({ ...empty, laborItems: [labor({ description: '', hours: 0 })] })
+      findServiceFormProblem({ ...empty, laborItems: [labor({ description: '', rate: 0 })] })
+    ).toBe('laborDescription')
+    expect(
+      findServiceFormProblem({
+        ...empty,
+        laborItems: [labor({ description: '', hours: 1, rate: 450, pricingType: 'service' })],
+      })
     ).toBe('laborDescription')
   })
 

+ 10 - 2
src/features/vehicles/Lib/validateServiceForm.ts

@@ -19,7 +19,7 @@ export type ServiceFormProblem =
   | 'negative'
   /** A part priced or numbered but never named. */
   | 'partName'
-  /** Labour with hours or a rate but nothing said about it. */
+  /** Labour with hours, or a priced service, but nothing said about it. */
   | 'laborDescription'
   /** A cause, correction or confirmation written against no condition. */
   | 'concernCondition'
@@ -37,6 +37,8 @@ export interface ServiceFormLabor {
   description: string
   hours: number | string
   rate: number | string
+  /** Hourly when absent; a service or the shop fee is priced per unit. */
+  pricingType?: string | null
 }
 
 export interface ServiceFormConcern {
@@ -69,7 +71,13 @@ export function partRowHasContent(part: ServiceFormPart): boolean {
 }
 
 export function laborRowHasContent(labor: ServiceFormLabor): boolean {
-  return num(labor.hours) > 0 || num(labor.rate) > 0
+  // A new hourly line arrives with the workshop's rate and no hours, and a
+  // new service line with a quantity of one and no price. Counting those
+  // marked every line wrong the moment it was added, and a ready line left
+  // untouched blocked the save. Hours on an hourly line say it was meant, and
+  // a price on a line priced per unit.
+  if (labor.pricingType && labor.pricingType !== 'hourly') return num(labor.rate) > 0
+  return num(labor.hours) > 0
 }
 
 /**