diff --git a/CHANGELOG.md b/CHANGELOG.md
index 727e4f2a7..f9e63c62f 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -12,6 +12,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- BPay handling to NSW GovPay provider
- `formsAppService.getFormSubmissionMetaList()`
+### Changed
+
+- required logic for `lookupButton` form element
+
## [10.1.2] - 2026-05-07
### Added
diff --git a/package-lock.json b/package-lock.json
index 6f1e5580c..3a831783a 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -5067,7 +5067,7 @@
},
"node_modules/@oneblink/types": {
"version": "1.0.0",
- "resolved": "git+ssh://git@github.com/oneblink/types.git#044689f0b15d094ebbf48dd8b6bafa25f4d7f8d0",
+ "resolved": "git+ssh://git@github.com/oneblink/types.git#010587c817b2fc3bfe9b64b47684148de5e925cb",
"dev": true,
"license": "GPL-3.0-only",
"dependencies": {
diff --git a/src/components/renderer/LookupButton.tsx b/src/components/renderer/LookupButton.tsx
index 4a3513667..23d0d84cc 100644
--- a/src/components/renderer/LookupButton.tsx
+++ b/src/components/renderer/LookupButton.tsx
@@ -12,6 +12,7 @@ type Props = {
hasMarginTop?: boolean
isInputButton?: boolean
lookupButtonConfig?: EnvironmentTypes.ButtonConfiguration
+ overrideRequiredMessage: string | undefined
}
function LookupButton({
@@ -20,6 +21,7 @@ function LookupButton({
hasMarginTop,
isInputButton,
lookupButtonConfig,
+ overrideRequiredMessage,
}: Props) {
const { isLookup, onLookup, isDisabled, isLoading, allowLookupOnEmptyValue } =
useLookupNotification(value)
@@ -51,7 +53,10 @@ function LookupButton({
(!isEmptyValue &&
!!validationMessage &&
validationMessage !==
- generateLookupValidationMessage(lookupButtonConfig))
+ generateLookupValidationMessage(
+ lookupButtonConfig,
+ overrideRequiredMessage,
+ ))
}
>
{isInputButton && }
diff --git a/src/form-elements/FormElementABN.tsx b/src/form-elements/FormElementABN.tsx
index e271ddb70..420c1b81e 100644
--- a/src/form-elements/FormElementABN.tsx
+++ b/src/form-elements/FormElementABN.tsx
@@ -120,7 +120,8 @@ function FormElementABN({
})
if (result.ABRPayloadSearchResults.response.exception) {
throw new Error(
- result.ABRPayloadSearchResults.response.exception.exceptionDescription,
+ result.ABRPayloadSearchResults.response.exception
+ .exceptionDescription,
)
}
@@ -269,6 +270,7 @@ function FormElementABN({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
{value && (
diff --git a/src/form-elements/FormElementBSB.tsx b/src/form-elements/FormElementBSB.tsx
index 311ba95a8..e92d17dff 100644
--- a/src/form-elements/FormElementBSB.tsx
+++ b/src/form-elements/FormElementBSB.tsx
@@ -170,7 +170,7 @@ function FormElementBSB({
onChange(element, {
value: undefined,
})
- setText("")
+ setText('')
}
setIsDirty()
}}
@@ -198,6 +198,7 @@ function FormElementBSB({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
{bsbRecord && (
diff --git a/src/form-elements/FormElementBarcodeScanner.tsx b/src/form-elements/FormElementBarcodeScanner.tsx
index 30ba773ef..e7737353a 100644
--- a/src/form-elements/FormElementBarcodeScanner.tsx
+++ b/src/form-elements/FormElementBarcodeScanner.tsx
@@ -164,6 +164,7 @@ function FormElementBarcodeScanner({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
diff --git a/src/form-elements/FormElementCheckBoxes.tsx b/src/form-elements/FormElementCheckBoxes.tsx
index d74807ec5..0bb72c15a 100644
--- a/src/form-elements/FormElementCheckBoxes.tsx
+++ b/src/form-elements/FormElementCheckBoxes.tsx
@@ -213,6 +213,7 @@ function FormElementCheckboxes({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
diff --git a/src/form-elements/FormElementDate.tsx b/src/form-elements/FormElementDate.tsx
index 0bf5e9235..5298b74c9 100644
--- a/src/form-elements/FormElementDate.tsx
+++ b/src/form-elements/FormElementDate.tsx
@@ -133,6 +133,7 @@ function FormElementDate({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
diff --git a/src/form-elements/FormElementDateTime.tsx b/src/form-elements/FormElementDateTime.tsx
index d27a06806..5fd3f0197 100644
--- a/src/form-elements/FormElementDateTime.tsx
+++ b/src/form-elements/FormElementDateTime.tsx
@@ -124,6 +124,7 @@ function FormElementDateTime({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
diff --git a/src/form-elements/FormElementEmail.tsx b/src/form-elements/FormElementEmail.tsx
index 9e3e99bca..66852d43b 100644
--- a/src/form-elements/FormElementEmail.tsx
+++ b/src/form-elements/FormElementEmail.tsx
@@ -83,6 +83,7 @@ function FormElementEmail({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
diff --git a/src/form-elements/FormElementLookupButton.tsx b/src/form-elements/FormElementLookupButton.tsx
index d300a255a..30c8bc5d3 100644
--- a/src/form-elements/FormElementLookupButton.tsx
+++ b/src/form-elements/FormElementLookupButton.tsx
@@ -52,6 +52,7 @@ function FormElementLookupButton({
element,
onChange,
onLookup,
+ validationMessage,
...validationMessageProps
}: Props & {
onChange: FormElementValueChangeHandler
@@ -111,14 +112,16 @@ function FormElementLookupButton({
className="ob-lookup-button"
id={id}
element={element}
- required={false}
+ required={!!element.required}
>
diff --git a/src/form-elements/FormElementNumber.tsx b/src/form-elements/FormElementNumber.tsx
index eaee4bb71..6043970f5 100644
--- a/src/form-elements/FormElementNumber.tsx
+++ b/src/form-elements/FormElementNumber.tsx
@@ -118,6 +118,7 @@ function FormElementNumber({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
) : isPageVisible ? (
diff --git a/src/form-elements/FormElementSelect.tsx b/src/form-elements/FormElementSelect.tsx
index 516eb38f7..a53497650 100644
--- a/src/form-elements/FormElementSelect.tsx
+++ b/src/form-elements/FormElementSelect.tsx
@@ -150,6 +150,7 @@ function FormElementSelect({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
)}
diff --git a/src/form-elements/FormElementTelephone.tsx b/src/form-elements/FormElementTelephone.tsx
index 13d91d505..05a62f9f8 100644
--- a/src/form-elements/FormElementTelephone.tsx
+++ b/src/form-elements/FormElementTelephone.tsx
@@ -84,6 +84,7 @@ function FormElementTelephone({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
diff --git a/src/form-elements/FormElementText.tsx b/src/form-elements/FormElementText.tsx
index 0da5ed431..176fa16f3 100644
--- a/src/form-elements/FormElementText.tsx
+++ b/src/form-elements/FormElementText.tsx
@@ -80,6 +80,7 @@ function FormElementText({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
{(isDisplayingValidationMessage || !!element.maxLength) && (
diff --git a/src/form-elements/FormElementTextarea.tsx b/src/form-elements/FormElementTextarea.tsx
index c59698c44..823f33302 100644
--- a/src/form-elements/FormElementTextarea.tsx
+++ b/src/form-elements/FormElementTextarea.tsx
@@ -119,6 +119,7 @@ function FormElementTextarea({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
)}
diff --git a/src/form-elements/FormElementTime.tsx b/src/form-elements/FormElementTime.tsx
index fd6f54e9c..3012c98f2 100644
--- a/src/form-elements/FormElementTime.tsx
+++ b/src/form-elements/FormElementTime.tsx
@@ -109,6 +109,7 @@ function FormElementTime({
value={value}
validationMessage={validationMessage}
lookupButtonConfig={element.lookupButton}
+ overrideRequiredMessage={undefined}
/>
diff --git a/src/services/form-validation/determineLookupButtonIsRequired.ts b/src/services/form-validation/determineLookupButtonIsRequired.ts
deleted file mode 100644
index d3e460d6d..000000000
--- a/src/services/form-validation/determineLookupButtonIsRequired.ts
+++ /dev/null
@@ -1,71 +0,0 @@
-import { FormTypes, SubmissionTypes } from '@oneblink/types'
-
-export function determineLookupButtonIsRequired(
- elementDependencies: FormTypes.LookupButtonFormElement['elementDependencies'],
- elements: FormTypes.FormElement[],
- submissions: Array,
-): boolean {
- for (const elementDependency of elementDependencies) {
- const formElement = elements.find(
- (formElement) => formElement.id === elementDependency.elementId,
- )
- if (formElement && 'required' in formElement && formElement.required) {
- return true
- }
-
- switch (elementDependency.type) {
- case 'REPEATABLE_SET_FORM_ELEMENT': {
- if (formElement?.type === 'repeatableSet') {
- const entries = submissions.reduce<
- Array
- >((memo, submission) => {
- const subEntries = submission?.[formElement.name]
- if (Array.isArray(subEntries) && subEntries.length) {
- memo.push(...subEntries)
- }
- return memo
- }, [])
- if (Array.isArray(entries) && entries.length) {
- const hasNestedRequiredFormElements =
- determineLookupButtonIsRequired(
- [elementDependency.elementDependency],
- formElement.elements,
- entries,
- )
- if (hasNestedRequiredFormElements) {
- return true
- }
- }
- }
- break
- }
- case 'FORM_FORM_ELEMENT': {
- if (
- formElement?.type === 'form' &&
- Array.isArray(formElement.elements)
- ) {
- const hasNestedRequiredFormElements = determineLookupButtonIsRequired(
- [elementDependency.elementDependency],
- formElement.elements,
- submissions.reduce<
- Array
- >((memo, submission) => {
- const subEntry = submission?.[formElement.name]
- if (subEntry) {
- memo.push(
- subEntry as SubmissionTypes.S3SubmissionData['submission'],
- )
- }
- return memo
- }, []),
- )
- if (hasNestedRequiredFormElements) {
- return true
- }
- }
- break
- }
- }
- }
- return false
-}
diff --git a/src/services/form-validation/extensions.ts b/src/services/form-validation/extensions.ts
index 2b87249e0..6bc2709a1 100644
--- a/src/services/form-validation/extensions.ts
+++ b/src/services/form-validation/extensions.ts
@@ -16,7 +16,10 @@ const validationExtensions = {
executedLookups,
formElement,
}: {
- formElement: FormTypes.LookupFormElement & FormTypes.FormElementRequired
+ formElement: FormTypes.LookupFormElement &
+ FormTypes.FormElementRequired & {
+ type: FormTypes.FormElement['type']
+ }
executedLookups: ExecutedLookups
}): string[] {
if (!formElement.isDataLookup && !formElement.isElementLookup) {
@@ -24,7 +27,7 @@ const validationExtensions = {
}
// Lookups must only be executed on required form elements
- if (formElement && !formElement.required) {
+ if (!formElement.required) {
return []
}
@@ -33,7 +36,14 @@ const validationExtensions = {
return []
}
- return [generateLookupValidationMessage(formElement.lookupButton)]
+ return [
+ generateLookupValidationMessage(
+ formElement.lookupButton,
+ formElement.type === 'lookupButton'
+ ? formElement.requiredMessage
+ : undefined,
+ ),
+ ]
},
presence(
diff --git a/src/services/form-validation/validateSubmission.ts b/src/services/form-validation/validateSubmission.ts
index 6c7fa2312..0e36c4022 100644
--- a/src/services/form-validation/validateSubmission.ts
+++ b/src/services/form-validation/validateSubmission.ts
@@ -21,7 +21,6 @@ import { parseDateValue } from '../generate-default-data'
import { localisationService } from '../../apps'
import { ArcGISWebMapElementValue } from '@oneblink/types/typescript/arcgis'
import { generateConfirmationFormElementName } from '../dynamic-elements'
-import { determineLookupButtonIsRequired } from './determineLookupButtonIsRequired'
import { Value as FormElementComplianceValue } from '../../form-elements/FormElementCompliance'
import {
defaultAutoSnapshotButtonLabel,
@@ -752,14 +751,7 @@ export default function validateSubmission({
}
case 'lookupButton': {
const errorMessages = validationExtensions.lookups({
- formElement: {
- ...formElement,
- required: determineLookupButtonIsRequired(
- formElement.elementDependencies,
- elements,
- submission ? [submission] : [],
- ),
- },
+ formElement,
executedLookups,
})
if (errorMessages.length) {
diff --git a/src/services/form-validation/validators.ts b/src/services/form-validation/validators.ts
index d7f6b1b20..33edf65e2 100644
--- a/src/services/form-validation/validators.ts
+++ b/src/services/form-validation/validators.ts
@@ -157,9 +157,14 @@ export function validateAttachments(
}
export const generateLookupValidationMessage = (
- lookupButtonConfig?: EnvironmentTypes.ButtonConfiguration,
+ lookupButtonConfig: EnvironmentTypes.ButtonConfiguration | undefined,
+ overrideMessage: string | undefined,
) => {
- return lookupButtonConfig && lookupButtonConfig.label
- ? `${lookupButtonConfig.label} is required`
- : 'Lookup is required'
+ if (overrideMessage) {
+ return overrideMessage
+ }
+ if (lookupButtonConfig && lookupButtonConfig.label) {
+ return `${lookupButtonConfig.label} is required`
+ }
+ return 'Lookup is required'
}