thm-p3-configurator 0.0.202 → 0.0.204
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -47,6 +47,7 @@ var _helpers__ = require("../../__helpers__");
|
|
|
47
47
|
var _product = require("../../__helpers__/product");
|
|
48
48
|
var _ui = require("../../__helpers__/ui");
|
|
49
49
|
var _useIsTmg = require("../../__hooks__/useIsTmg");
|
|
50
|
+
var _AddressLookupService = _interopRequireDefault(require("../../__services__/AddressLookupService"));
|
|
50
51
|
var _LicensePlateValidator = _interopRequireDefault(require("../../__services__/LicensePlateValidator"));
|
|
51
52
|
var _LocalStorageWorker = require("../../__services__/LocalStorageWorker");
|
|
52
53
|
var _InternalAppointmentSuccessModal = _interopRequireDefault(require("./InternalAppointmentSuccessModal"));
|
|
@@ -124,6 +125,7 @@ function _toPrimitive(t, r) {
|
|
|
124
125
|
return ("string" === r ? String : Number)(t);
|
|
125
126
|
}
|
|
126
127
|
const licensePlateValidator = new _LicensePlateValidator.default();
|
|
128
|
+
const addressLookupService = new _AddressLookupService.default();
|
|
127
129
|
const internalAppointmentFormSchema = (0, _yup.object)({
|
|
128
130
|
ownershipType: (0, _yup.string)().required(_constants__.FORM_ERROR_MESSAGES.required),
|
|
129
131
|
leaseNumber: (0, _yup.string)().nullable(),
|
|
@@ -174,6 +176,8 @@ const InternalAppointmentForm = _ref => {
|
|
|
174
176
|
const [refreshKey, setRefreshKey] = (0, _react.useState)(Date.now());
|
|
175
177
|
const [companySearchTerm, setCompanySearchTerm] = (0, _react.useState)('');
|
|
176
178
|
const [isCompanyInputFocused, setIsCompanyInputFocused] = (0, _react.useState)(false);
|
|
179
|
+
const [addressLookupLoading, setAddressLookupLoading] = (0, _react.useState)(false);
|
|
180
|
+
const [addressLookupTimeoutId, setAddressLookupTimeoutId] = (0, _react.useState)(null);
|
|
177
181
|
const {
|
|
178
182
|
customerAgreed,
|
|
179
183
|
customer,
|
|
@@ -557,6 +561,62 @@ const InternalAppointmentForm = _ref => {
|
|
|
557
561
|
label: marketingChannels === null || marketingChannels === void 0 || (_marketingChannels$fi = marketingChannels.find(marketingC => (marketingC === null || marketingC === void 0 ? void 0 : marketingC.entityId) === (channel === null || channel === void 0 ? void 0 : channel.channelId))) === null || _marketingChannels$fi === void 0 ? void 0 : _marketingChannels$fi.title,
|
|
558
562
|
value: marketingChannels === null || marketingChannels === void 0 ? void 0 : marketingChannels.find(marketingC => (marketingC === null || marketingC === void 0 ? void 0 : marketingC.entityId) === (channel === null || channel === void 0 ? void 0 : channel.channelId))
|
|
559
563
|
} : null;
|
|
564
|
+
|
|
565
|
+
/**
|
|
566
|
+
* @description Debounced address lookup function
|
|
567
|
+
*/
|
|
568
|
+
const performAddressLookup = async (postcode, houseNumber) => {
|
|
569
|
+
if (!postcode || !houseNumber) return;
|
|
570
|
+
try {
|
|
571
|
+
setAddressLookupLoading(true);
|
|
572
|
+
const addressInfo = await addressLookupService.lookup(postcode, houseNumber);
|
|
573
|
+
if (addressInfo && addressInfo.street && addressInfo.city) {
|
|
574
|
+
// Auto-fill street and city fields
|
|
575
|
+
dispatch({
|
|
576
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_STREET_NAME,
|
|
577
|
+
payload: {
|
|
578
|
+
streetName: addressInfo.street
|
|
579
|
+
}
|
|
580
|
+
});
|
|
581
|
+
dispatch({
|
|
582
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_CITY,
|
|
583
|
+
payload: {
|
|
584
|
+
city: addressInfo.city
|
|
585
|
+
}
|
|
586
|
+
});
|
|
587
|
+
}
|
|
588
|
+
} catch (error) {
|
|
589
|
+
console.error('Address lookup failed:', error);
|
|
590
|
+
} finally {
|
|
591
|
+
setAddressLookupLoading(false);
|
|
592
|
+
}
|
|
593
|
+
};
|
|
594
|
+
|
|
595
|
+
/**
|
|
596
|
+
* @description Handles address lookup with debouncing
|
|
597
|
+
*/
|
|
598
|
+
const handleAddressLookup = (postcode, houseNumber) => {
|
|
599
|
+
// Clear existing timeout
|
|
600
|
+
if (addressLookupTimeoutId) {
|
|
601
|
+
clearTimeout(addressLookupTimeoutId);
|
|
602
|
+
}
|
|
603
|
+
|
|
604
|
+
// Set new timeout for debounced lookup
|
|
605
|
+
const newTimeoutId = setTimeout(() => {
|
|
606
|
+
performAddressLookup(postcode, houseNumber);
|
|
607
|
+
}, 800); // 800ms delay
|
|
608
|
+
|
|
609
|
+
setAddressLookupTimeoutId(newTimeoutId);
|
|
610
|
+
};
|
|
611
|
+
|
|
612
|
+
// Cleanup timeout on unmount
|
|
613
|
+
(0, _react.useEffect)(() => {
|
|
614
|
+
return () => {
|
|
615
|
+
if (addressLookupTimeoutId) {
|
|
616
|
+
clearTimeout(addressLookupTimeoutId);
|
|
617
|
+
}
|
|
618
|
+
};
|
|
619
|
+
}, [addressLookupTimeoutId]);
|
|
560
620
|
return /*#__PURE__*/_react.default.createElement("div", {
|
|
561
621
|
className: (0, _helpers__.withStyle)('row gx-5 mt-3 mt-lg-5')
|
|
562
622
|
}, /*#__PURE__*/_react.default.createElement("div", {
|
|
@@ -619,7 +679,136 @@ const InternalAppointmentForm = _ref => {
|
|
|
619
679
|
options: Object.values(_constants__.VEHICLE_OWNERSHIP_TYPE),
|
|
620
680
|
isRequired: true,
|
|
621
681
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['ownershipType']
|
|
622
|
-
})
|
|
682
|
+
}), (vehicle === null || vehicle === void 0 ? void 0 : vehicle.ownershipType) === _constants__.VEHICLE_OWNERSHIP_TYPE.Leasemaatschappij && /*#__PURE__*/_react.default.createElement("div", {
|
|
683
|
+
className: (0, _helpers__.withStyle)('company-search-container position-relative mt-2 mb-2')
|
|
684
|
+
}, /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
685
|
+
placeholder: "Zoek leasemaatschappijen...",
|
|
686
|
+
value: customer.companyName,
|
|
687
|
+
name: "companyName",
|
|
688
|
+
onChange: value => {
|
|
689
|
+
dispatch({
|
|
690
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_COMPANY_NAME,
|
|
691
|
+
payload: {
|
|
692
|
+
companyName: value
|
|
693
|
+
}
|
|
694
|
+
});
|
|
695
|
+
|
|
696
|
+
// Also update search term if value is different
|
|
697
|
+
if (value !== companySearchTerm) {
|
|
698
|
+
setCompanySearchTerm(value);
|
|
699
|
+
setIsCompanyInputFocused(true);
|
|
700
|
+
}
|
|
701
|
+
},
|
|
702
|
+
onFocus: () => {
|
|
703
|
+
setIsCompanyInputFocused(true);
|
|
704
|
+
},
|
|
705
|
+
onBlur: () => {
|
|
706
|
+
setTimeout(() => {
|
|
707
|
+
setIsCompanyInputFocused(false);
|
|
708
|
+
}, 300); // Increased delay for better chance of click completion
|
|
709
|
+
},
|
|
710
|
+
isRequired: false,
|
|
711
|
+
form: "quotation",
|
|
712
|
+
label: "Leasemaatschappij:",
|
|
713
|
+
errorMessage: errors === null || errors === void 0 ? void 0 : errors['companyName']
|
|
714
|
+
}), isCompanyInputFocused && companySearchTerm && companySearchTerm.length >= 3 && branchesByType && branchesByType.length > 0 && /*#__PURE__*/_react.default.createElement("div", {
|
|
715
|
+
className: (0, _helpers__.withStyle)('dropdown-results position-absolute w-100 border rounded bg-white shadow'),
|
|
716
|
+
style: {
|
|
717
|
+
maxHeight: '200px',
|
|
718
|
+
overflowY: 'auto',
|
|
719
|
+
zIndex: 1050,
|
|
720
|
+
top: '100%',
|
|
721
|
+
left: 0,
|
|
722
|
+
right: 0
|
|
723
|
+
},
|
|
724
|
+
onMouseDown: e => {
|
|
725
|
+
e.preventDefault();
|
|
726
|
+
}
|
|
727
|
+
}, isLoadingBranchesByType && /*#__PURE__*/_react.default.createElement("div", {
|
|
728
|
+
className: (0, _helpers__.withStyle)('p-2 text-center')
|
|
729
|
+
}, /*#__PURE__*/_react.default.createElement("span", null, "Zoeken...")), branchesByType.map(branch => /*#__PURE__*/_react.default.createElement("div", {
|
|
730
|
+
key: branch.entityId,
|
|
731
|
+
className: (0, _helpers__.withStyle)('dropdown-item p-2 border-bottom'),
|
|
732
|
+
style: {
|
|
733
|
+
cursor: 'pointer'
|
|
734
|
+
},
|
|
735
|
+
onMouseDown: e => {
|
|
736
|
+
e.preventDefault();
|
|
737
|
+
dispatch({
|
|
738
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_COMPANY_NAME,
|
|
739
|
+
payload: {
|
|
740
|
+
companyName: branch.name
|
|
741
|
+
}
|
|
742
|
+
});
|
|
743
|
+
if (branch.postalCode) {
|
|
744
|
+
dispatch({
|
|
745
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_ZIP_CODE,
|
|
746
|
+
payload: {
|
|
747
|
+
zipCode: branch.postalCode
|
|
748
|
+
}
|
|
749
|
+
});
|
|
750
|
+
}
|
|
751
|
+
if (branch.street) {
|
|
752
|
+
dispatch({
|
|
753
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_STREET_NAME,
|
|
754
|
+
payload: {
|
|
755
|
+
streetName: branch.street
|
|
756
|
+
}
|
|
757
|
+
});
|
|
758
|
+
}
|
|
759
|
+
if (branch.city) {
|
|
760
|
+
dispatch({
|
|
761
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_CITY,
|
|
762
|
+
payload: {
|
|
763
|
+
city: branch.city
|
|
764
|
+
}
|
|
765
|
+
});
|
|
766
|
+
}
|
|
767
|
+
if (branch.street2) {
|
|
768
|
+
dispatch({
|
|
769
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_HOUSE_NUMBER,
|
|
770
|
+
payload: {
|
|
771
|
+
houseNumber: branch.street2
|
|
772
|
+
}
|
|
773
|
+
});
|
|
774
|
+
}
|
|
775
|
+
if (branch.vatNumber) {
|
|
776
|
+
dispatch({
|
|
777
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_VAT_NUMBER,
|
|
778
|
+
payload: {
|
|
779
|
+
vatNumber: branch.vatNumber
|
|
780
|
+
}
|
|
781
|
+
});
|
|
782
|
+
}
|
|
783
|
+
if (branch.kvkNumber) {
|
|
784
|
+
dispatch({
|
|
785
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_KVK_NUMBER,
|
|
786
|
+
payload: {
|
|
787
|
+
kvkNumber: branch.kvkNumber
|
|
788
|
+
}
|
|
789
|
+
});
|
|
790
|
+
}
|
|
791
|
+
if (branch.huisnummerToevoeging) {
|
|
792
|
+
dispatch({
|
|
793
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_HOUSE_NUMBER_ADDITION,
|
|
794
|
+
payload: {
|
|
795
|
+
houseNumberAddition: branch.huisnummerToevoeging
|
|
796
|
+
}
|
|
797
|
+
});
|
|
798
|
+
}
|
|
799
|
+
if (branch.country && branch.country.entityId) {
|
|
800
|
+
dispatch({
|
|
801
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_COUNTRY_ID,
|
|
802
|
+
payload: {
|
|
803
|
+
countryId: branch.country.entityId
|
|
804
|
+
}
|
|
805
|
+
});
|
|
806
|
+
setRefreshKey(Date.now());
|
|
807
|
+
}
|
|
808
|
+
setCompanySearchTerm('');
|
|
809
|
+
setIsCompanyInputFocused(false);
|
|
810
|
+
}
|
|
811
|
+
}, branch.name))))), /*#__PURE__*/_react.default.createElement("h5", {
|
|
623
812
|
className: (0, _helpers__.withStyle)('my-2')
|
|
624
813
|
}, "Persoonlijke gegevens"), /*#__PURE__*/_react.default.createElement("div", {
|
|
625
814
|
className: (0, _helpers__.withStyle)('col-12 col-md-6 mb-2')
|
|
@@ -756,140 +945,7 @@ const InternalAppointmentForm = _ref => {
|
|
|
756
945
|
form: "appointment",
|
|
757
946
|
label: "E-mailadres:",
|
|
758
947
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['email']
|
|
759
|
-
}), /*#__PURE__*/_react.default.createElement(
|
|
760
|
-
className: (0, _helpers__.withStyle)('company-search-container position-relative mt-2 mb-2')
|
|
761
|
-
}, /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
762
|
-
placeholder: "Zoek leasemaatschappijen...",
|
|
763
|
-
value: customer.companyName,
|
|
764
|
-
name: "companyName",
|
|
765
|
-
onChange: value => {
|
|
766
|
-
// Update company name in state
|
|
767
|
-
dispatch({
|
|
768
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_COMPANY_NAME,
|
|
769
|
-
payload: {
|
|
770
|
-
companyName: value
|
|
771
|
-
}
|
|
772
|
-
});
|
|
773
|
-
|
|
774
|
-
// Also update search term if value is different
|
|
775
|
-
if (value !== companySearchTerm) {
|
|
776
|
-
console.log('value', value);
|
|
777
|
-
setCompanySearchTerm(value);
|
|
778
|
-
// Force focused state when typing
|
|
779
|
-
setIsCompanyInputFocused(true);
|
|
780
|
-
}
|
|
781
|
-
},
|
|
782
|
-
onFocus: () => {
|
|
783
|
-
setIsCompanyInputFocused(true);
|
|
784
|
-
},
|
|
785
|
-
onBlur: () => {
|
|
786
|
-
// Delay hiding the dropdown to allow click events to complete
|
|
787
|
-
setTimeout(() => {
|
|
788
|
-
setIsCompanyInputFocused(false);
|
|
789
|
-
}, 300); // Increased delay for better chance of click completion
|
|
790
|
-
},
|
|
791
|
-
isRequired: false,
|
|
792
|
-
form: "quotation",
|
|
793
|
-
label: "Leasemaatschappij:",
|
|
794
|
-
errorMessage: errors === null || errors === void 0 ? void 0 : errors['companyName']
|
|
795
|
-
}), isCompanyInputFocused && companySearchTerm && companySearchTerm.length >= 3 && branchesByType && branchesByType.length > 0 && /*#__PURE__*/_react.default.createElement("div", {
|
|
796
|
-
className: (0, _helpers__.withStyle)('dropdown-results position-absolute w-100 border rounded bg-white shadow'),
|
|
797
|
-
style: {
|
|
798
|
-
maxHeight: '200px',
|
|
799
|
-
overflowY: 'auto',
|
|
800
|
-
zIndex: 1050,
|
|
801
|
-
top: '100%',
|
|
802
|
-
left: 0,
|
|
803
|
-
right: 0
|
|
804
|
-
},
|
|
805
|
-
onMouseDown: e => {
|
|
806
|
-
e.preventDefault();
|
|
807
|
-
}
|
|
808
|
-
}, isLoadingBranchesByType && /*#__PURE__*/_react.default.createElement("div", {
|
|
809
|
-
className: (0, _helpers__.withStyle)('p-2 text-center')
|
|
810
|
-
}, /*#__PURE__*/_react.default.createElement("span", null, "Zoeken...")), branchesByType.map(branch => /*#__PURE__*/_react.default.createElement("div", {
|
|
811
|
-
key: branch.entityId,
|
|
812
|
-
className: (0, _helpers__.withStyle)('dropdown-item p-2 border-bottom'),
|
|
813
|
-
style: {
|
|
814
|
-
cursor: 'pointer'
|
|
815
|
-
},
|
|
816
|
-
onMouseDown: e => {
|
|
817
|
-
e.preventDefault();
|
|
818
|
-
dispatch({
|
|
819
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_COMPANY_NAME,
|
|
820
|
-
payload: {
|
|
821
|
-
companyName: branch.name
|
|
822
|
-
}
|
|
823
|
-
});
|
|
824
|
-
if (branch.postalCode) {
|
|
825
|
-
dispatch({
|
|
826
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_ZIP_CODE,
|
|
827
|
-
payload: {
|
|
828
|
-
zipCode: branch.postalCode
|
|
829
|
-
}
|
|
830
|
-
});
|
|
831
|
-
}
|
|
832
|
-
if (branch.street) {
|
|
833
|
-
dispatch({
|
|
834
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_STREET_NAME,
|
|
835
|
-
payload: {
|
|
836
|
-
streetName: branch.street
|
|
837
|
-
}
|
|
838
|
-
});
|
|
839
|
-
}
|
|
840
|
-
if (branch.city) {
|
|
841
|
-
dispatch({
|
|
842
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_CITY,
|
|
843
|
-
payload: {
|
|
844
|
-
city: branch.city
|
|
845
|
-
}
|
|
846
|
-
});
|
|
847
|
-
}
|
|
848
|
-
if (branch.street2) {
|
|
849
|
-
dispatch({
|
|
850
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_HOUSE_NUMBER,
|
|
851
|
-
payload: {
|
|
852
|
-
houseNumber: branch.street2
|
|
853
|
-
}
|
|
854
|
-
});
|
|
855
|
-
}
|
|
856
|
-
if (branch.vatNumber) {
|
|
857
|
-
dispatch({
|
|
858
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_VAT_NUMBER,
|
|
859
|
-
payload: {
|
|
860
|
-
vatNumber: branch.vatNumber
|
|
861
|
-
}
|
|
862
|
-
});
|
|
863
|
-
}
|
|
864
|
-
if (branch.kvkNumber) {
|
|
865
|
-
dispatch({
|
|
866
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_KVK_NUMBER,
|
|
867
|
-
payload: {
|
|
868
|
-
kvkNumber: branch.kvkNumber
|
|
869
|
-
}
|
|
870
|
-
});
|
|
871
|
-
}
|
|
872
|
-
if (branch.huisnummerToevoeging) {
|
|
873
|
-
dispatch({
|
|
874
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_HOUSE_NUMBER_ADDITION,
|
|
875
|
-
payload: {
|
|
876
|
-
houseNumberAddition: branch.huisnummerToevoeging
|
|
877
|
-
}
|
|
878
|
-
});
|
|
879
|
-
}
|
|
880
|
-
if (branch.country && branch.country.entityId) {
|
|
881
|
-
dispatch({
|
|
882
|
-
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_COUNTRY_ID,
|
|
883
|
-
payload: {
|
|
884
|
-
countryId: branch.country.entityId
|
|
885
|
-
}
|
|
886
|
-
});
|
|
887
|
-
setRefreshKey(Date.now());
|
|
888
|
-
}
|
|
889
|
-
setCompanySearchTerm('');
|
|
890
|
-
setIsCompanyInputFocused(false);
|
|
891
|
-
}
|
|
892
|
-
}, branch.name)))), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
948
|
+
}), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
893
949
|
placeholder: "",
|
|
894
950
|
value: customer.phoneNumber,
|
|
895
951
|
name: "phoneNumber",
|
|
@@ -1133,12 +1189,18 @@ const InternalAppointmentForm = _ref => {
|
|
|
1133
1189
|
placeholder: "",
|
|
1134
1190
|
value: customer.zipCode,
|
|
1135
1191
|
name: "zipCode",
|
|
1136
|
-
onChange: value =>
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1192
|
+
onChange: value => {
|
|
1193
|
+
dispatch({
|
|
1194
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_ZIP_CODE,
|
|
1195
|
+
payload: {
|
|
1196
|
+
zipCode: value
|
|
1197
|
+
}
|
|
1198
|
+
});
|
|
1199
|
+
// Trigger address lookup if house number is also available
|
|
1200
|
+
if (customer.houseNumber) {
|
|
1201
|
+
handleAddressLookup(value, customer.houseNumber);
|
|
1140
1202
|
}
|
|
1141
|
-
}
|
|
1203
|
+
},
|
|
1142
1204
|
key: "zipCode-".concat(refreshKey),
|
|
1143
1205
|
isRequired: true,
|
|
1144
1206
|
label: "Postcode:",
|
|
@@ -1147,12 +1209,18 @@ const InternalAppointmentForm = _ref => {
|
|
|
1147
1209
|
placeholder: "",
|
|
1148
1210
|
value: customer.houseNumber,
|
|
1149
1211
|
name: "houseNumber",
|
|
1150
|
-
onChange: value =>
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1212
|
+
onChange: value => {
|
|
1213
|
+
dispatch({
|
|
1214
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_HOUSE_NUMBER,
|
|
1215
|
+
payload: {
|
|
1216
|
+
houseNumber: value
|
|
1217
|
+
}
|
|
1218
|
+
});
|
|
1219
|
+
// Trigger address lookup if postcode is also available
|
|
1220
|
+
if (customer.zipCode) {
|
|
1221
|
+
handleAddressLookup(customer.zipCode, value);
|
|
1154
1222
|
}
|
|
1155
|
-
}
|
|
1223
|
+
},
|
|
1156
1224
|
key: "houseNumber-".concat(refreshKey),
|
|
1157
1225
|
isRequired: true,
|
|
1158
1226
|
label: "Huisnummer:",
|
|
@@ -1172,7 +1240,7 @@ const InternalAppointmentForm = _ref => {
|
|
|
1172
1240
|
label: "Huisnummer toevoeging:",
|
|
1173
1241
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['houseNumberAddition']
|
|
1174
1242
|
}), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
1175
|
-
placeholder:
|
|
1243
|
+
placeholder: addressLookupLoading ? 'Adres wordt opgezocht...' : '',
|
|
1176
1244
|
value: customer.streetName,
|
|
1177
1245
|
name: "streetName",
|
|
1178
1246
|
onChange: value => dispatch({
|
|
@@ -1183,10 +1251,10 @@ const InternalAppointmentForm = _ref => {
|
|
|
1183
1251
|
}),
|
|
1184
1252
|
key: "streetName-".concat(refreshKey),
|
|
1185
1253
|
isRequired: true,
|
|
1186
|
-
label: "Straat:",
|
|
1254
|
+
label: "Straat:".concat(addressLookupLoading ? ' (wordt opgezocht...)' : ''),
|
|
1187
1255
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['streetName']
|
|
1188
1256
|
}), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
1189
|
-
placeholder:
|
|
1257
|
+
placeholder: addressLookupLoading ? 'Stad wordt opgezocht...' : '',
|
|
1190
1258
|
value: customer.city,
|
|
1191
1259
|
name: "city",
|
|
1192
1260
|
onChange: value => dispatch({
|
|
@@ -1197,7 +1265,7 @@ const InternalAppointmentForm = _ref => {
|
|
|
1197
1265
|
}),
|
|
1198
1266
|
key: "city-".concat(refreshKey),
|
|
1199
1267
|
isRequired: true,
|
|
1200
|
-
label: "Stad:",
|
|
1268
|
+
label: "Stad:".concat(addressLookupLoading ? ' (wordt opgezocht...)' : ''),
|
|
1201
1269
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['city']
|
|
1202
1270
|
}), /*#__PURE__*/_react.default.createElement(_DropdownInput.default, {
|
|
1203
1271
|
key: "country-business-".concat((customer === null || customer === void 0 ? void 0 : customer.countryId) || 'default'),
|
|
@@ -1225,12 +1293,18 @@ const InternalAppointmentForm = _ref => {
|
|
|
1225
1293
|
placeholder: "",
|
|
1226
1294
|
value: customer.zipCode,
|
|
1227
1295
|
name: "zipCode",
|
|
1228
|
-
onChange: value =>
|
|
1229
|
-
|
|
1230
|
-
|
|
1231
|
-
|
|
1296
|
+
onChange: value => {
|
|
1297
|
+
dispatch({
|
|
1298
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_ZIP_CODE,
|
|
1299
|
+
payload: {
|
|
1300
|
+
zipCode: value
|
|
1301
|
+
}
|
|
1302
|
+
});
|
|
1303
|
+
// Trigger address lookup if house number is also available
|
|
1304
|
+
if (customer.houseNumber) {
|
|
1305
|
+
handleAddressLookup(value, customer.houseNumber);
|
|
1232
1306
|
}
|
|
1233
|
-
}
|
|
1307
|
+
},
|
|
1234
1308
|
key: "zipCode-".concat(refreshKey),
|
|
1235
1309
|
isRequired: true,
|
|
1236
1310
|
label: "Postcode:",
|
|
@@ -1239,12 +1313,18 @@ const InternalAppointmentForm = _ref => {
|
|
|
1239
1313
|
placeholder: "",
|
|
1240
1314
|
value: customer.houseNumber,
|
|
1241
1315
|
name: "houseNumber",
|
|
1242
|
-
onChange: value =>
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
|
|
1316
|
+
onChange: value => {
|
|
1317
|
+
dispatch({
|
|
1318
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_HOUSE_NUMBER,
|
|
1319
|
+
payload: {
|
|
1320
|
+
houseNumber: value
|
|
1321
|
+
}
|
|
1322
|
+
});
|
|
1323
|
+
// Trigger address lookup if postcode is also available
|
|
1324
|
+
if (customer.zipCode) {
|
|
1325
|
+
handleAddressLookup(customer.zipCode, value);
|
|
1246
1326
|
}
|
|
1247
|
-
}
|
|
1327
|
+
},
|
|
1248
1328
|
key: "houseNumber-".concat(refreshKey),
|
|
1249
1329
|
isRequired: true,
|
|
1250
1330
|
label: "Huisnummer:",
|
|
@@ -1264,7 +1344,7 @@ const InternalAppointmentForm = _ref => {
|
|
|
1264
1344
|
label: "Huisnummer toevoeging:",
|
|
1265
1345
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['houseNumberAddition']
|
|
1266
1346
|
}), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
1267
|
-
placeholder:
|
|
1347
|
+
placeholder: addressLookupLoading ? 'Adres wordt opgezocht...' : '',
|
|
1268
1348
|
value: customer.streetName,
|
|
1269
1349
|
name: "streetName",
|
|
1270
1350
|
onChange: value => dispatch({
|
|
@@ -1275,10 +1355,10 @@ const InternalAppointmentForm = _ref => {
|
|
|
1275
1355
|
}),
|
|
1276
1356
|
key: "streetName-".concat(refreshKey),
|
|
1277
1357
|
isRequired: true,
|
|
1278
|
-
label: "Straat:",
|
|
1358
|
+
label: "Straat:".concat(addressLookupLoading ? ' (wordt opgezocht...)' : ''),
|
|
1279
1359
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['streetName']
|
|
1280
1360
|
}), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
1281
|
-
placeholder:
|
|
1361
|
+
placeholder: addressLookupLoading ? 'Stad wordt opgezocht...' : '',
|
|
1282
1362
|
value: customer.city,
|
|
1283
1363
|
name: "city",
|
|
1284
1364
|
onChange: value => dispatch({
|
|
@@ -1289,7 +1369,7 @@ const InternalAppointmentForm = _ref => {
|
|
|
1289
1369
|
}),
|
|
1290
1370
|
key: "city-".concat(refreshKey),
|
|
1291
1371
|
isRequired: true,
|
|
1292
|
-
label: "Stad:",
|
|
1372
|
+
label: "Stad:".concat(addressLookupLoading ? ' (wordt opgezocht...)' : ''),
|
|
1293
1373
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['city']
|
|
1294
1374
|
}), /*#__PURE__*/_react.default.createElement(_DropdownInput.default, {
|
|
1295
1375
|
key: "country-lease-".concat((customer === null || customer === void 0 ? void 0 : customer.countryId) || 'default'),
|
|
@@ -1331,12 +1411,18 @@ const InternalAppointmentForm = _ref => {
|
|
|
1331
1411
|
placeholder: "",
|
|
1332
1412
|
value: customer.zipCode,
|
|
1333
1413
|
name: "zipCode",
|
|
1334
|
-
onChange: value =>
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1414
|
+
onChange: value => {
|
|
1415
|
+
dispatch({
|
|
1416
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_ZIP_CODE,
|
|
1417
|
+
payload: {
|
|
1418
|
+
zipCode: value
|
|
1419
|
+
}
|
|
1420
|
+
});
|
|
1421
|
+
// Trigger address lookup if house number is also available
|
|
1422
|
+
if (customer.houseNumber) {
|
|
1423
|
+
handleAddressLookup(value, customer.houseNumber);
|
|
1338
1424
|
}
|
|
1339
|
-
}
|
|
1425
|
+
},
|
|
1340
1426
|
key: "zipCode-".concat(refreshKey),
|
|
1341
1427
|
isRequired: true,
|
|
1342
1428
|
label: "Postcode:",
|
|
@@ -1345,12 +1431,18 @@ const InternalAppointmentForm = _ref => {
|
|
|
1345
1431
|
placeholder: "",
|
|
1346
1432
|
value: customer.houseNumber,
|
|
1347
1433
|
name: "houseNumber",
|
|
1348
|
-
onChange: value =>
|
|
1349
|
-
|
|
1350
|
-
|
|
1351
|
-
|
|
1434
|
+
onChange: value => {
|
|
1435
|
+
dispatch({
|
|
1436
|
+
type: _OrderSessionContext.orderSessionActions.SET_CUSTOMER_HOUSE_NUMBER,
|
|
1437
|
+
payload: {
|
|
1438
|
+
houseNumber: value
|
|
1439
|
+
}
|
|
1440
|
+
});
|
|
1441
|
+
// Trigger address lookup if postcode is also available
|
|
1442
|
+
if (customer.zipCode) {
|
|
1443
|
+
handleAddressLookup(customer.zipCode, value);
|
|
1352
1444
|
}
|
|
1353
|
-
}
|
|
1445
|
+
},
|
|
1354
1446
|
key: "houseNumber-".concat(refreshKey),
|
|
1355
1447
|
isRequired: true,
|
|
1356
1448
|
label: "Huisnummer:",
|
|
@@ -1370,7 +1462,7 @@ const InternalAppointmentForm = _ref => {
|
|
|
1370
1462
|
label: "Huisnummer toevoeging:",
|
|
1371
1463
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['houseNumberAddition']
|
|
1372
1464
|
}), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
1373
|
-
placeholder:
|
|
1465
|
+
placeholder: addressLookupLoading ? 'Adres wordt opgezocht...' : '',
|
|
1374
1466
|
value: customer.streetName,
|
|
1375
1467
|
name: "streetName",
|
|
1376
1468
|
onChange: value => dispatch({
|
|
@@ -1381,10 +1473,10 @@ const InternalAppointmentForm = _ref => {
|
|
|
1381
1473
|
}),
|
|
1382
1474
|
key: "streetName-".concat(refreshKey),
|
|
1383
1475
|
isRequired: true,
|
|
1384
|
-
label: "Straat:",
|
|
1476
|
+
label: "Straat:".concat(addressLookupLoading ? ' (wordt opgezocht...)' : ''),
|
|
1385
1477
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['streetName']
|
|
1386
1478
|
}), /*#__PURE__*/_react.default.createElement(_TextInput.default, {
|
|
1387
|
-
placeholder:
|
|
1479
|
+
placeholder: addressLookupLoading ? 'Stad wordt opgezocht...' : '',
|
|
1388
1480
|
value: customer.city,
|
|
1389
1481
|
name: "city",
|
|
1390
1482
|
onChange: value => dispatch({
|
|
@@ -1395,7 +1487,7 @@ const InternalAppointmentForm = _ref => {
|
|
|
1395
1487
|
}),
|
|
1396
1488
|
key: "city-".concat(refreshKey),
|
|
1397
1489
|
isRequired: true,
|
|
1398
|
-
label: "Stad:",
|
|
1490
|
+
label: "Stad:".concat(addressLookupLoading ? ' (wordt opgezocht...)' : ''),
|
|
1399
1491
|
errorMessage: errors === null || errors === void 0 ? void 0 : errors['city']
|
|
1400
1492
|
}), /*#__PURE__*/_react.default.createElement(_DropdownInput.default, {
|
|
1401
1493
|
key: "country-personal-".concat((customer === null || customer === void 0 ? void 0 : customer.countryId) || 'default'),
|
|
@@ -0,0 +1,192 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
require("core-js/modules/es.parse-int.js");
|
|
4
|
+
require("core-js/modules/es.promise.js");
|
|
5
|
+
require("core-js/modules/es.regexp.exec.js");
|
|
6
|
+
require("core-js/modules/es.regexp.test.js");
|
|
7
|
+
require("core-js/modules/es.string.replace.js");
|
|
8
|
+
require("core-js/modules/web.dom-collections.iterator.js");
|
|
9
|
+
Object.defineProperty(exports, "__esModule", {
|
|
10
|
+
value: true
|
|
11
|
+
});
|
|
12
|
+
exports.default = void 0;
|
|
13
|
+
require("core-js/modules/es.parse-int.js");
|
|
14
|
+
require("core-js/modules/es.promise.js");
|
|
15
|
+
require("core-js/modules/es.regexp.exec.js");
|
|
16
|
+
require("core-js/modules/es.regexp.test.js");
|
|
17
|
+
require("core-js/modules/es.string.replace.js");
|
|
18
|
+
require("core-js/modules/web.dom-collections.iterator.js");
|
|
19
|
+
class AddressLookupService {
|
|
20
|
+
constructor() {
|
|
21
|
+
this.cache = new Map();
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
/**
|
|
25
|
+
* @description Validates Dutch postcode format
|
|
26
|
+
* @param {string} postcode - The postcode to validate
|
|
27
|
+
* @returns {boolean} - True if valid Dutch postcode format
|
|
28
|
+
*/
|
|
29
|
+
isValidPostcode(postcode) {
|
|
30
|
+
if (!postcode || typeof postcode !== 'string') return false;
|
|
31
|
+
const cleanPostcode = postcode.replace(/\s/g, '').toUpperCase();
|
|
32
|
+
const dutchPostcodeRegex = /^[1-9][0-9]{3}[A-Z]{2}$/;
|
|
33
|
+
return dutchPostcodeRegex.test(cleanPostcode);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* @description Validates house number
|
|
38
|
+
* @param {string|number} houseNumber - The house number to validate
|
|
39
|
+
* @returns {boolean} - True if valid house number
|
|
40
|
+
*/
|
|
41
|
+
isValidHouseNumber(houseNumber) {
|
|
42
|
+
if (!houseNumber) return false;
|
|
43
|
+
const num = typeof houseNumber === 'string' ? parseInt(houseNumber, 10) : houseNumber;
|
|
44
|
+
return !isNaN(num) && num > 0 && num <= 99999;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/**
|
|
48
|
+
* @description Creates a cache key for the lookup
|
|
49
|
+
* @param {string} postcode - The postcode
|
|
50
|
+
* @param {string|number} houseNumber - The house number
|
|
51
|
+
* @returns {string} - Cache key
|
|
52
|
+
*/
|
|
53
|
+
getCacheKey(postcode, houseNumber) {
|
|
54
|
+
const cleanPostcode = postcode.replace(/\s/g, '').toUpperCase();
|
|
55
|
+
return "".concat(cleanPostcode, "-").concat(houseNumber);
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* @description Lookup using PDOK BAG API (free Dutch government service)
|
|
60
|
+
* @param {string} postcode - The Dutch postcode
|
|
61
|
+
* @param {string|number} houseNumber - The house number
|
|
62
|
+
* @returns {Promise<{street: string, city: string} | null>} - Address information or null if not found
|
|
63
|
+
*/
|
|
64
|
+
async lookupAddressPDOK(postcode, houseNumber) {
|
|
65
|
+
try {
|
|
66
|
+
if (!this.isValidPostcode(postcode) || !this.isValidHouseNumber(houseNumber)) {
|
|
67
|
+
return null;
|
|
68
|
+
}
|
|
69
|
+
const cacheKey = this.getCacheKey(postcode, houseNumber);
|
|
70
|
+
if (this.cache.has(cacheKey)) {
|
|
71
|
+
return this.cache.get(cacheKey);
|
|
72
|
+
}
|
|
73
|
+
const cleanPostcode = postcode.replace(/\s/g, '').toUpperCase();
|
|
74
|
+
const url = "https://api.pdok.nl/bzk/locatieserver/search/v3_1/suggest?q=".concat(cleanPostcode, " ").concat(houseNumber, "&fl=weergavenaam,straatnaam,woonplaatsnaam,postcode,huisnummer&rows=1");
|
|
75
|
+
const response = await fetch(url, {
|
|
76
|
+
method: 'GET',
|
|
77
|
+
headers: {
|
|
78
|
+
Accept: 'application/json'
|
|
79
|
+
}
|
|
80
|
+
});
|
|
81
|
+
if (!response.ok) {
|
|
82
|
+
console.warn('PDOK lookup failed:', response.status);
|
|
83
|
+
return null;
|
|
84
|
+
}
|
|
85
|
+
const data = await response.json();
|
|
86
|
+
let addressInfo = null;
|
|
87
|
+
if (data && data.response && data.response.docs && data.response.docs.length > 0) {
|
|
88
|
+
const doc = data.response.docs[0];
|
|
89
|
+
if (doc.postcode === cleanPostcode && String(doc.huisnummer) === String(houseNumber)) {
|
|
90
|
+
addressInfo = {
|
|
91
|
+
street: doc.straatnaam,
|
|
92
|
+
city: doc.woonplaatsnaam
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
this.cache.set(cacheKey, addressInfo);
|
|
97
|
+
return addressInfo;
|
|
98
|
+
} catch (error) {
|
|
99
|
+
console.error('PDOK address lookup error:', error);
|
|
100
|
+
return null;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
/**
|
|
105
|
+
* @description Mock lookup for development/demo (returns mock data for common postcodes)
|
|
106
|
+
* @param {string} postcode - The Dutch postcode
|
|
107
|
+
* @param {string|number} houseNumber - The house number
|
|
108
|
+
* @returns {Promise<{street: string, city: string} | null>} - Address information or null if not found
|
|
109
|
+
*/
|
|
110
|
+
async lookupAddressMock(postcode, houseNumber) {
|
|
111
|
+
const cleanPostcode = postcode.replace(/\s/g, '').toUpperCase();
|
|
112
|
+
const mockData = {
|
|
113
|
+
'1012JS': {
|
|
114
|
+
street: 'Dam',
|
|
115
|
+
city: 'Amsterdam'
|
|
116
|
+
},
|
|
117
|
+
'2511CS': {
|
|
118
|
+
street: 'Binnenhof',
|
|
119
|
+
city: 'Den Haag'
|
|
120
|
+
},
|
|
121
|
+
'3011AD': {
|
|
122
|
+
street: 'Coolsingel',
|
|
123
|
+
city: 'Rotterdam'
|
|
124
|
+
},
|
|
125
|
+
'3512JE': {
|
|
126
|
+
street: 'Oudegracht',
|
|
127
|
+
city: 'Utrecht'
|
|
128
|
+
},
|
|
129
|
+
'9712CP': {
|
|
130
|
+
street: 'Grote Markt',
|
|
131
|
+
city: 'Groningen'
|
|
132
|
+
},
|
|
133
|
+
'5611AG': {
|
|
134
|
+
street: 'Stratumseind',
|
|
135
|
+
city: 'Eindhoven'
|
|
136
|
+
},
|
|
137
|
+
'6511LN': {
|
|
138
|
+
street: 'Grote Markt',
|
|
139
|
+
city: 'Nijmegen'
|
|
140
|
+
},
|
|
141
|
+
'4811CE': {
|
|
142
|
+
street: 'Grote Markt',
|
|
143
|
+
city: 'Breda'
|
|
144
|
+
}
|
|
145
|
+
};
|
|
146
|
+
await new Promise(resolve => setTimeout(resolve, 500));
|
|
147
|
+
const addressInfo = mockData[cleanPostcode] || null;
|
|
148
|
+
if (addressInfo) {
|
|
149
|
+
console.log("Mock address lookup for ".concat(cleanPostcode, ": ").concat(addressInfo.street, ", ").concat(addressInfo.city));
|
|
150
|
+
}
|
|
151
|
+
return addressInfo;
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
/**
|
|
155
|
+
* @description Main lookup method that tries PDOK API first, then fallback to mock data
|
|
156
|
+
* @param {string} postcode - The Dutch postcode
|
|
157
|
+
* @param {string|number} houseNumber - The house number
|
|
158
|
+
* @returns {Promise<{street: string, city: string} | null>} - Address information or null if not found
|
|
159
|
+
*/
|
|
160
|
+
async lookup(postcode, houseNumber) {
|
|
161
|
+
if (!this.isValidPostcode(postcode) || !this.isValidHouseNumber(houseNumber)) {
|
|
162
|
+
return null;
|
|
163
|
+
}
|
|
164
|
+
const cacheKey = this.getCacheKey(postcode, houseNumber);
|
|
165
|
+
if (this.cache.has(cacheKey)) {
|
|
166
|
+
return this.cache.get(cacheKey);
|
|
167
|
+
}
|
|
168
|
+
let result = null;
|
|
169
|
+
try {
|
|
170
|
+
result = await this.lookupAddressPDOK(postcode, houseNumber);
|
|
171
|
+
if (result) {
|
|
172
|
+
return result;
|
|
173
|
+
}
|
|
174
|
+
} catch (error) {
|
|
175
|
+
console.warn('PDOK lookup failed, using mock data...');
|
|
176
|
+
}
|
|
177
|
+
try {
|
|
178
|
+
result = await this.lookupAddressMock(postcode, houseNumber);
|
|
179
|
+
} catch (error) {
|
|
180
|
+
console.warn('Mock lookup failed');
|
|
181
|
+
}
|
|
182
|
+
return result;
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
/**
|
|
186
|
+
* @description Clears the cache
|
|
187
|
+
*/
|
|
188
|
+
clearCache() {
|
|
189
|
+
this.cache.clear();
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
var _default = exports.default = AddressLookupService;
|