@ikas/storefront 4.0.0-alpha.43 → 4.0.0-alpha.44
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.
- package/package.json +11 -11
- package/src/components/checkout/components/address-form/model.ts +1 -0
- package/src/components/checkout/components/button/style.module.scss +2 -2
- package/src/components/checkout/components/cart-summary/cart-item/index.tsx +11 -26
- package/src/components/checkout/components/cart-summary/cart-item/style.module.scss +53 -13
- package/src/components/checkout/components/cart-summary/index.tsx +23 -16
- package/src/components/checkout/components/cart-summary/style.module.scss +48 -3
- package/src/components/checkout/components/customer-addresses/index.tsx +1 -0
- package/src/components/checkout/components/customer-addresses/model.ts +16 -8
- package/src/components/checkout/components/error/index.tsx +1 -1
- package/src/components/checkout/components/error/unknown-error/index.tsx +4 -2
- package/src/components/checkout/index.tsx +14 -7
- package/src/components/checkout/model.ts +126 -37
- package/src/components/checkout/steps/step-info/index.tsx +9 -3
- package/src/components/checkout/steps/step-payment/billing-address/index.tsx +1 -1
- package/src/components/checkout/steps/step-payment/index.tsx +5 -1
- package/src/components/checkout/steps/step-success/index.tsx +5 -3
- package/src/components/page-editor/ThemeComponentEditor.tsx +4 -0
- package/src/models/data/country/index.ts +4 -0
- package/src/models/data/country/location-translations/index.ts +15 -0
- package/src/models/data/order/line-item/base-unit/index.ts +22 -0
- package/src/models/data/order/line-item/base-unit/unit-type/index.ts +14 -0
- package/src/models/data/order/line-item/index.ts +42 -5
- package/src/models/data/order/line-item/variant/index.ts +8 -0
- package/src/models/data/order/line-item/variant/price/index.ts +2 -0
- package/src/models/data/order/line-item/variant/unit/index.ts +17 -0
- package/src/models/data/product/attribute-value/index.ts +40 -0
- package/src/models/data/product/base-unit/index.ts +19 -0
- package/src/models/data/product/index.ts +5 -0
- package/src/models/data/product/variant/index.ts +3 -0
- package/src/models/data/product/variant/unit/index.ts +17 -0
- package/src/models/data/raffle/index.ts +2 -2
- package/src/models/data/storefront/routing/index.tsx +4 -0
- package/src/models/data/category/init.ts +0 -33
|
@@ -20,6 +20,7 @@ import {
|
|
|
20
20
|
IkasTransactionStatus,
|
|
21
21
|
IkasCampaignOfferTargetPageType,
|
|
22
22
|
IkasCampaignOfferProduct,
|
|
23
|
+
IkasOrderShippingMethod,
|
|
23
24
|
} from "../../models";
|
|
24
25
|
import { IkasOrderAddress } from "../../models/data/order/address";
|
|
25
26
|
import {
|
|
@@ -174,6 +175,11 @@ export default class CheckoutViewModel {
|
|
|
174
175
|
} else {
|
|
175
176
|
return this.changeStep(CheckoutStep.INFO);
|
|
176
177
|
}
|
|
178
|
+
} else if (
|
|
179
|
+
this.step === CheckoutStep.SUCCESS &&
|
|
180
|
+
!this.canProceedToPayment
|
|
181
|
+
) {
|
|
182
|
+
return this.changeStep(CheckoutStep.INFO);
|
|
177
183
|
} else if (
|
|
178
184
|
![
|
|
179
185
|
CheckoutStep.INFO,
|
|
@@ -250,15 +256,6 @@ export default class CheckoutViewModel {
|
|
|
250
256
|
}
|
|
251
257
|
}
|
|
252
258
|
|
|
253
|
-
if (this.step === CheckoutStep.PAYMENT) {
|
|
254
|
-
if (this.isInStoreDelivery) {
|
|
255
|
-
this.checkout.billingAddress = new IkasOrderAddress();
|
|
256
|
-
if (this.checkoutSettings) {
|
|
257
|
-
this.checkout.billingAddress.checkoutSettings = this.checkoutSettings;
|
|
258
|
-
}
|
|
259
|
-
}
|
|
260
|
-
}
|
|
261
|
-
|
|
262
259
|
if (this.step !== CheckoutStep.SUCCESS) {
|
|
263
260
|
if (this.checkout.isComplete) {
|
|
264
261
|
return this.changeStep(CheckoutStep.SUCCESS);
|
|
@@ -369,7 +366,9 @@ export default class CheckoutViewModel {
|
|
|
369
366
|
|
|
370
367
|
get canProceedToShipping() {
|
|
371
368
|
return (
|
|
372
|
-
this.
|
|
369
|
+
(this.isDigitalOnly
|
|
370
|
+
? this.checkout.billingAddress?.isValid
|
|
371
|
+
: this.checkout.shippingAddress?.isValid) &&
|
|
373
372
|
this.checkout.hasValidCustomerEmail &&
|
|
374
373
|
this.error?.type !== ErrorType.NO_SHIPPING_ERROR
|
|
375
374
|
);
|
|
@@ -435,6 +434,12 @@ export default class CheckoutViewModel {
|
|
|
435
434
|
);
|
|
436
435
|
}
|
|
437
436
|
|
|
437
|
+
get isDigitalOnly() {
|
|
438
|
+
return (
|
|
439
|
+
this.checkout.shippingMethod === IkasOrderShippingMethod.DIGITAL_DELIVERY
|
|
440
|
+
);
|
|
441
|
+
}
|
|
442
|
+
|
|
438
443
|
// VALIDATIONS END
|
|
439
444
|
|
|
440
445
|
saveCart = async () => {
|
|
@@ -445,12 +450,17 @@ export default class CheckoutViewModel {
|
|
|
445
450
|
}
|
|
446
451
|
|
|
447
452
|
if (
|
|
448
|
-
this.step === CheckoutStep.INFO ||
|
|
449
|
-
|
|
453
|
+
(this.step === CheckoutStep.INFO ||
|
|
454
|
+
this.step === CheckoutStep.SHIPPING) &&
|
|
455
|
+
!this.isDigitalOnly
|
|
450
456
|
) {
|
|
451
457
|
input.billingAddress = null;
|
|
452
458
|
}
|
|
453
459
|
|
|
460
|
+
if (this.isDigitalOnly) {
|
|
461
|
+
input.shippingAddress = null;
|
|
462
|
+
}
|
|
463
|
+
|
|
454
464
|
const response = await CartStoreAPI.saveCart({ input });
|
|
455
465
|
|
|
456
466
|
if (response?.graphQLErrors && response.graphQLErrors.length) {
|
|
@@ -463,6 +473,7 @@ export default class CheckoutViewModel {
|
|
|
463
473
|
} else {
|
|
464
474
|
throw {
|
|
465
475
|
type: ErrorType.API_ERROR,
|
|
476
|
+
data: response.firstErrorMessage,
|
|
466
477
|
};
|
|
467
478
|
}
|
|
468
479
|
}
|
|
@@ -517,6 +528,7 @@ export default class CheckoutViewModel {
|
|
|
517
528
|
if (!checkStocksResponse.isSuccess) {
|
|
518
529
|
throw {
|
|
519
530
|
type: ErrorType.API_ERROR,
|
|
531
|
+
data: checkStocksResponse.firstErrorMessage,
|
|
520
532
|
};
|
|
521
533
|
}
|
|
522
534
|
|
|
@@ -562,6 +574,7 @@ export default class CheckoutViewModel {
|
|
|
562
574
|
if (!response.isSuccess || !response.data?.length) {
|
|
563
575
|
this.error = {
|
|
564
576
|
type: ErrorType.API_ERROR,
|
|
577
|
+
data: response.firstErrorMessage,
|
|
565
578
|
};
|
|
566
579
|
return;
|
|
567
580
|
}
|
|
@@ -615,7 +628,7 @@ export default class CheckoutViewModel {
|
|
|
615
628
|
try {
|
|
616
629
|
await this.checkStocks();
|
|
617
630
|
} catch (err) {
|
|
618
|
-
if (err.type) {
|
|
631
|
+
if (typeof err.type !== undefined) {
|
|
619
632
|
this.error = err;
|
|
620
633
|
} else {
|
|
621
634
|
console.log(err);
|
|
@@ -639,6 +652,7 @@ export default class CheckoutViewModel {
|
|
|
639
652
|
) {
|
|
640
653
|
this.error = {
|
|
641
654
|
type: ErrorType.API_ERROR,
|
|
655
|
+
data: paymentGatewaysResponse.firstErrorMessage,
|
|
642
656
|
};
|
|
643
657
|
return;
|
|
644
658
|
}
|
|
@@ -711,18 +725,29 @@ export default class CheckoutViewModel {
|
|
|
711
725
|
this.checkout.customer = new IkasOrderCustomer(
|
|
712
726
|
this.store.customerStore.customer as any
|
|
713
727
|
);
|
|
714
|
-
} else
|
|
715
|
-
this.checkout.customer = new IkasOrderCustomer(
|
|
728
|
+
} else {
|
|
729
|
+
this.checkout.customer = new IkasOrderCustomer(
|
|
730
|
+
this.checkout.customer || {}
|
|
731
|
+
);
|
|
732
|
+
}
|
|
716
733
|
};
|
|
717
734
|
|
|
718
735
|
createShippingAddress = () => {
|
|
736
|
+
if (this.isDigitalOnly) return;
|
|
737
|
+
|
|
719
738
|
if (!this.checkout.shippingAddress) {
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
739
|
+
if (!!this.store.customerStore.customer) {
|
|
740
|
+
const customerAddresses = this.store.customerStore.customer.addresses;
|
|
741
|
+
this.onSelectedShippingAddressIdChange(
|
|
742
|
+
customerAddresses?.length ? customerAddresses[0].id! : "-1"
|
|
743
|
+
);
|
|
744
|
+
} else {
|
|
745
|
+
this.onSelectedShippingAddressIdChange("-1");
|
|
746
|
+
}
|
|
724
747
|
} else {
|
|
725
|
-
this.
|
|
748
|
+
this.checkout.shippingAddress = new IkasOrderAddress(
|
|
749
|
+
_cloneDeep(this.checkout.shippingAddress) || {}
|
|
750
|
+
);
|
|
726
751
|
this.checkout.shippingAddress.checkoutSettings = this.checkoutSettings;
|
|
727
752
|
}
|
|
728
753
|
};
|
|
@@ -733,26 +758,21 @@ export default class CheckoutViewModel {
|
|
|
733
758
|
USE_DIFFERENT_ADDRESS_KEY
|
|
734
759
|
);
|
|
735
760
|
|
|
736
|
-
if (this.
|
|
737
|
-
if (this.
|
|
738
|
-
this.
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
this.checkout.billingAddress =
|
|
742
|
-
this.checkout.billingAddress || new IkasOrderAddress();
|
|
743
|
-
} else {
|
|
744
|
-
if (this.isInStoreDelivery || this.checkout.billingAddress) {
|
|
745
|
-
this.checkout.billingAddress = new IkasOrderAddress(
|
|
746
|
-
_cloneDeep(this.checkout.billingAddress) || {}
|
|
761
|
+
if (!this.checkout.billingAddress) {
|
|
762
|
+
if (!!this.store.customerStore.customer) {
|
|
763
|
+
const customerAddresses = this.store.customerStore.customer.addresses;
|
|
764
|
+
this.onSelectedBillingAddressIdChange(
|
|
765
|
+
customerAddresses?.length ? customerAddresses[0].id! : "-1"
|
|
747
766
|
);
|
|
748
767
|
} else {
|
|
749
|
-
this.
|
|
750
|
-
_cloneDeep(this.checkout.shippingAddress) || {}
|
|
751
|
-
);
|
|
768
|
+
this.onSelectedBillingAddressIdChange("-1");
|
|
752
769
|
}
|
|
770
|
+
} else {
|
|
771
|
+
this.checkout.billingAddress = new IkasOrderAddress(
|
|
772
|
+
_cloneDeep(this.checkout.billingAddress) || {}
|
|
773
|
+
);
|
|
774
|
+
this.checkout.billingAddress.checkoutSettings = this.checkoutSettings;
|
|
753
775
|
}
|
|
754
|
-
|
|
755
|
-
this.checkout.billingAddress.checkoutSettings = this.checkoutSettings;
|
|
756
776
|
}
|
|
757
777
|
};
|
|
758
778
|
|
|
@@ -1048,6 +1068,34 @@ export default class CheckoutViewModel {
|
|
|
1048
1068
|
} else {
|
|
1049
1069
|
this.changeStep(CheckoutStep.PAYMENT);
|
|
1050
1070
|
}
|
|
1071
|
+
} catch (err) {
|
|
1072
|
+
if (typeof err.type !== undefined) {
|
|
1073
|
+
this.error = err;
|
|
1074
|
+
} else {
|
|
1075
|
+
console.log(err);
|
|
1076
|
+
this.error = {
|
|
1077
|
+
type: ErrorType.UNKNOWN,
|
|
1078
|
+
};
|
|
1079
|
+
}
|
|
1080
|
+
this.isStepLoading = false;
|
|
1081
|
+
}
|
|
1082
|
+
};
|
|
1083
|
+
|
|
1084
|
+
onProceedToDigitalOnlyPaymentClick = async () => {
|
|
1085
|
+
if (!this.canProceedToPayment) {
|
|
1086
|
+
this.isErrorsVisible = true;
|
|
1087
|
+
return;
|
|
1088
|
+
}
|
|
1089
|
+
|
|
1090
|
+
this.isErrorsVisible = false;
|
|
1091
|
+
|
|
1092
|
+
try {
|
|
1093
|
+
this.isStepLoading = true;
|
|
1094
|
+
|
|
1095
|
+
await this.checkStocks();
|
|
1096
|
+
await this.saveCart();
|
|
1097
|
+
|
|
1098
|
+
this.changeStep(CheckoutStep.PAYMENT);
|
|
1051
1099
|
} catch (err) {
|
|
1052
1100
|
if (err.type) {
|
|
1053
1101
|
this.error = err;
|
|
@@ -1076,7 +1124,7 @@ export default class CheckoutViewModel {
|
|
|
1076
1124
|
this.error = undefined;
|
|
1077
1125
|
this.changeStep(CheckoutStep.PAYMENT);
|
|
1078
1126
|
} catch (err) {
|
|
1079
|
-
if (err.type) {
|
|
1127
|
+
if (typeof err.type !== undefined) {
|
|
1080
1128
|
this.error = err;
|
|
1081
1129
|
} else {
|
|
1082
1130
|
console.log(err);
|
|
@@ -1118,6 +1166,46 @@ export default class CheckoutViewModel {
|
|
|
1118
1166
|
return;
|
|
1119
1167
|
}
|
|
1120
1168
|
|
|
1169
|
+
await this.createSaleTransaction();
|
|
1170
|
+
} catch (err) {
|
|
1171
|
+
if (typeof err.type !== undefined) {
|
|
1172
|
+
this.error = err;
|
|
1173
|
+
} else {
|
|
1174
|
+
this.error = {
|
|
1175
|
+
type: ErrorType.UNKNOWN,
|
|
1176
|
+
};
|
|
1177
|
+
}
|
|
1178
|
+
this.isStepLoading = false;
|
|
1179
|
+
}
|
|
1180
|
+
};
|
|
1181
|
+
|
|
1182
|
+
onCompleteDigitalOnlyPaymentClick = async () => {
|
|
1183
|
+
if (
|
|
1184
|
+
!this.canProceedToPayment ||
|
|
1185
|
+
(this.checkoutSettings.showTermsAndConditionsCheckbox &&
|
|
1186
|
+
!this.isTermsAndConditionsChecked)
|
|
1187
|
+
) {
|
|
1188
|
+
this.isErrorsVisible = true;
|
|
1189
|
+
return;
|
|
1190
|
+
}
|
|
1191
|
+
|
|
1192
|
+
try {
|
|
1193
|
+
this.isErrorsVisible = false;
|
|
1194
|
+
this.isStepLoading = true;
|
|
1195
|
+
|
|
1196
|
+
await this.checkStocks();
|
|
1197
|
+
await this.saveCart();
|
|
1198
|
+
|
|
1199
|
+
if (this.isCustomFlowStripe) {
|
|
1200
|
+
const stripeFromBtn = document.querySelector("#stripe-form-btn");
|
|
1201
|
+
if (stripeFromBtn) {
|
|
1202
|
+
//@ts-ignore
|
|
1203
|
+
stripeFromBtn.click();
|
|
1204
|
+
}
|
|
1205
|
+
|
|
1206
|
+
return;
|
|
1207
|
+
}
|
|
1208
|
+
|
|
1121
1209
|
await this.createSaleTransaction();
|
|
1122
1210
|
} catch (err) {
|
|
1123
1211
|
if (err.type) {
|
|
@@ -1207,6 +1295,7 @@ export default class CheckoutViewModel {
|
|
|
1207
1295
|
process.env.NEXT_PUBLIC_BASE_URL + response.data.returnSlug;
|
|
1208
1296
|
} else {
|
|
1209
1297
|
throw {
|
|
1298
|
+
data: response.firstErrorMessage,
|
|
1210
1299
|
type: ErrorType.UNKNOWN,
|
|
1211
1300
|
};
|
|
1212
1301
|
}
|
|
@@ -31,7 +31,9 @@ const CheckoutStepInfo: React.FC<Props> = ({ vm }) => {
|
|
|
31
31
|
);
|
|
32
32
|
|
|
33
33
|
const customerAddressesViewModel = React.useMemo(() => {
|
|
34
|
-
return
|
|
34
|
+
return vm.isDigitalOnly
|
|
35
|
+
? new CustomerAddressesViewModel(vm, "billing")
|
|
36
|
+
: new CustomerAddressesViewModel(vm, "shipping");
|
|
35
37
|
}, [vm]);
|
|
36
38
|
|
|
37
39
|
return (
|
|
@@ -70,12 +72,16 @@ const CheckoutStepInfo: React.FC<Props> = ({ vm }) => {
|
|
|
70
72
|
marginTop: vm.store.customerStore.customer ? "0px" : "32px",
|
|
71
73
|
}}
|
|
72
74
|
text={
|
|
73
|
-
vm.deliveryMethod === "address"
|
|
75
|
+
vm.deliveryMethod === "address" && !vm.isDigitalOnly
|
|
74
76
|
? t("checkout-page:actions.continueWithShipping")
|
|
75
77
|
: t("checkout-page:actions.continueWithPayment")
|
|
76
78
|
}
|
|
77
79
|
isLoading={vm.isStepLoading}
|
|
78
|
-
onClick={
|
|
80
|
+
onClick={
|
|
81
|
+
vm.isDigitalOnly
|
|
82
|
+
? vm.onProceedToDigitalOnlyPaymentClick
|
|
83
|
+
: vm.onProceedToShippingClick
|
|
84
|
+
}
|
|
79
85
|
/>
|
|
80
86
|
)}
|
|
81
87
|
</div>
|
|
@@ -31,7 +31,7 @@ export const BillingAddress: React.FC<Props> = observer(({ vm }) => {
|
|
|
31
31
|
marginBottom: vm.useDifferentAddress ? "24px" : "0px",
|
|
32
32
|
}}
|
|
33
33
|
>
|
|
34
|
-
{vm.deliveryMethod === "address" && (
|
|
34
|
+
{vm.deliveryMethod === "address" && !vm.isDigitalOnly && (
|
|
35
35
|
<Checkbox
|
|
36
36
|
value={!vm.useDifferentAddress}
|
|
37
37
|
hasError={vm.isErrorsVisible && !vm.isTermsAndConditionsChecked}
|
|
@@ -93,7 +93,11 @@ export const CheckoutStepPayment: React.FC<Props> = observer(({ vm }) => {
|
|
|
93
93
|
}}
|
|
94
94
|
text={t("checkout-page:actions.completeOrder")}
|
|
95
95
|
isLoading={vm.isStepLoading}
|
|
96
|
-
onClick={
|
|
96
|
+
onClick={
|
|
97
|
+
vm.isDigitalOnly
|
|
98
|
+
? vm.onCompleteDigitalOnlyPaymentClick
|
|
99
|
+
: vm.onCompletePaymentClick
|
|
100
|
+
}
|
|
97
101
|
/>
|
|
98
102
|
|
|
99
103
|
{!!t("checkout-page:securePaymentTooltip") && (
|
|
@@ -246,9 +246,11 @@ export const StepSuccess: React.FC<Props> = observer(({ vm }) => {
|
|
|
246
246
|
<ExpandableSection title={t("checkout-page:paymentSummary")}>
|
|
247
247
|
{paymentInfoGrid}
|
|
248
248
|
</ExpandableSection>
|
|
249
|
-
|
|
250
|
-
{
|
|
251
|
-
|
|
249
|
+
{!vm.isDigitalOnly && (
|
|
250
|
+
<ExpandableSection title={t("checkout-page:shippingSummary")}>
|
|
251
|
+
{contactInfoGrid}
|
|
252
|
+
</ExpandableSection>
|
|
253
|
+
)}
|
|
252
254
|
|
|
253
255
|
<div className={styles.Actions}>
|
|
254
256
|
<div className={styles.HelpText}>
|
|
@@ -96,6 +96,8 @@ export class ThemeEditorComponent extends React.Component<Props> {
|
|
|
96
96
|
statusUpdatedAt: null,
|
|
97
97
|
stockLocationId: null,
|
|
98
98
|
taxValue: null,
|
|
99
|
+
unitPrice: null,
|
|
100
|
+
finalUnitPrice: null,
|
|
99
101
|
variant: {
|
|
100
102
|
barcodeList: null,
|
|
101
103
|
brand: null,
|
|
@@ -112,6 +114,8 @@ export class ThemeEditorComponent extends React.Component<Props> {
|
|
|
112
114
|
type: null,
|
|
113
115
|
weight: null,
|
|
114
116
|
variantValues: [],
|
|
117
|
+
baseUnit: null,
|
|
118
|
+
unit: null,
|
|
115
119
|
},
|
|
116
120
|
orderedAt: 0,
|
|
117
121
|
}),
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { IkasBaseModel } from "../base";
|
|
2
|
+
import { IkasLocationTranslations } from "./location-translations";
|
|
2
3
|
import { IkasCountry as ICountry } from "@ikas/storefront-models";
|
|
3
4
|
import { makeObservable, observable } from "mobx";
|
|
4
5
|
|
|
@@ -9,6 +10,7 @@ export class IkasCountry extends IkasBaseModel implements ICountry {
|
|
|
9
10
|
emojiString: string | null = null;
|
|
10
11
|
iso2: string | null = null;
|
|
11
12
|
iso3: string | null = null;
|
|
13
|
+
locationTranslations?: IkasLocationTranslations | null = null;
|
|
12
14
|
name: string;
|
|
13
15
|
native: string | null = null;
|
|
14
16
|
phoneCode: string | null = null;
|
|
@@ -23,6 +25,7 @@ export class IkasCountry extends IkasBaseModel implements ICountry {
|
|
|
23
25
|
this.emojiString = data.emojiString || null;
|
|
24
26
|
this.iso2 = data.iso2 || null;
|
|
25
27
|
this.iso3 = data.iso3 || null;
|
|
28
|
+
this.locationTranslations = data.locationTranslations || null;
|
|
26
29
|
this.name = data.name || "";
|
|
27
30
|
this.native = data.native || null;
|
|
28
31
|
this.phoneCode = data.phoneCode || null;
|
|
@@ -36,6 +39,7 @@ export class IkasCountry extends IkasBaseModel implements ICountry {
|
|
|
36
39
|
emojiString: observable,
|
|
37
40
|
iso2: observable,
|
|
38
41
|
iso3: observable,
|
|
42
|
+
locationTranslations: observable,
|
|
39
43
|
name: observable,
|
|
40
44
|
native: observable,
|
|
41
45
|
phoneCode: observable,
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { IkasLocationTranslations as ILocationTranslations } from "@ikas/storefront-models";
|
|
2
|
+
import { makeAutoObservable } from "mobx";
|
|
3
|
+
|
|
4
|
+
export class IkasLocationTranslations implements ILocationTranslations {
|
|
5
|
+
de: string | null;
|
|
6
|
+
en: string;
|
|
7
|
+
tr: string;
|
|
8
|
+
|
|
9
|
+
constructor(data: ILocationTranslations) {
|
|
10
|
+
this.de = data.de || null;
|
|
11
|
+
this.en = data.en || "";
|
|
12
|
+
this.tr = data.tr || "";
|
|
13
|
+
makeAutoObservable(this);
|
|
14
|
+
}
|
|
15
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import {
|
|
2
|
+
IkasProductUnitType,
|
|
3
|
+
IkasOrderLineBaseUnit as IOrderLineBaseUnit,
|
|
4
|
+
} from "@ikas/storefront-models";
|
|
5
|
+
import { makeAutoObservable } from "mobx";
|
|
6
|
+
import { IkasOrderLineVariantUnitType } from "./unit-type";
|
|
7
|
+
|
|
8
|
+
export class IkasOrderLineBaseUnit implements IOrderLineBaseUnit {
|
|
9
|
+
baseAmount: number;
|
|
10
|
+
type: IkasProductUnitType;
|
|
11
|
+
unit: IkasOrderLineVariantUnitType | null;
|
|
12
|
+
|
|
13
|
+
constructor(data: IOrderLineBaseUnit) {
|
|
14
|
+
this.baseAmount = data.baseAmount;
|
|
15
|
+
this.type = data.type;
|
|
16
|
+
this.unit = data.unit ? new IkasOrderLineVariantUnitType(data.unit) : null;
|
|
17
|
+
|
|
18
|
+
makeAutoObservable(this);
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
export { IkasProductUnitType };
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { IkasOrderLineVariantUnitType as IOrderLineVariantUnitType } from "@ikas/storefront-models";
|
|
2
|
+
import { makeAutoObservable } from "mobx";
|
|
3
|
+
|
|
4
|
+
export class IkasOrderLineVariantUnitType implements IOrderLineVariantUnitType {
|
|
5
|
+
id: string;
|
|
6
|
+
name: string;
|
|
7
|
+
|
|
8
|
+
constructor(data: IOrderLineVariantUnitType) {
|
|
9
|
+
this.id = data.id;
|
|
10
|
+
this.name = data.name;
|
|
11
|
+
|
|
12
|
+
makeAutoObservable(this);
|
|
13
|
+
}
|
|
14
|
+
}
|
|
@@ -20,6 +20,7 @@ export class IkasOrderLineItem extends IkasBaseModel implements IOrderLineItem {
|
|
|
20
20
|
discount: IkasOrderLineDiscount | null = null;
|
|
21
21
|
discountPrice: number | null = null;
|
|
22
22
|
finalPrice: number | null = null;
|
|
23
|
+
finalUnitPrice: number | null;
|
|
23
24
|
options: IkasOrderLineItemOption[] | null = null;
|
|
24
25
|
originalOrderLineItemId: string | null = null;
|
|
25
26
|
price: number;
|
|
@@ -28,6 +29,7 @@ export class IkasOrderLineItem extends IkasBaseModel implements IOrderLineItem {
|
|
|
28
29
|
statusUpdatedAt: number | null = null;
|
|
29
30
|
stockLocationId: string | null = null;
|
|
30
31
|
taxValue: number | null = null;
|
|
32
|
+
unitPrice: number | null;
|
|
31
33
|
variant: IkasOrderLineVariant;
|
|
32
34
|
orderedAt: number;
|
|
33
35
|
|
|
@@ -42,14 +44,19 @@ export class IkasOrderLineItem extends IkasBaseModel implements IOrderLineItem {
|
|
|
42
44
|
this.discount = data.discount
|
|
43
45
|
? new IkasOrderLineDiscount(data.discount)
|
|
44
46
|
: null;
|
|
45
|
-
this.discountPrice = data.discountPrice
|
|
46
|
-
this.finalPrice = data.finalPrice
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
(
|
|
47
|
+
this.discountPrice = data.discountPrice ?? null;
|
|
48
|
+
this.finalPrice = data.finalPrice ?? null;
|
|
49
|
+
this.finalUnitPrice = data.finalUnitPrice ?? null;
|
|
50
|
+
this.options =
|
|
51
|
+
data.options?.map((o) => new IkasOrderLineItemOption(o)) || null;
|
|
52
|
+
this.originalOrderLineItemId = data.originalOrderLineItemId || null;
|
|
50
53
|
this.price = data.price;
|
|
51
54
|
this.quantity = data.quantity;
|
|
52
55
|
this.status = data.status;
|
|
56
|
+
this.statusUpdatedAt = data.statusUpdatedAt;
|
|
57
|
+
this.stockLocationId = data.stockLocationId;
|
|
58
|
+
this.taxValue = data.taxValue;
|
|
59
|
+
this.unitPrice = data.unitPrice ?? null;
|
|
53
60
|
this.variant = new IkasOrderLineVariant(data.variant);
|
|
54
61
|
this.orderedAt = data.orderedAt;
|
|
55
62
|
|
|
@@ -61,6 +68,7 @@ export class IkasOrderLineItem extends IkasBaseModel implements IOrderLineItem {
|
|
|
61
68
|
discount: observable,
|
|
62
69
|
discountPrice: observable,
|
|
63
70
|
finalPrice: observable,
|
|
71
|
+
finalUnitPrice: observable,
|
|
64
72
|
options: observable,
|
|
65
73
|
originalOrderLineItemId: observable,
|
|
66
74
|
price: observable,
|
|
@@ -69,6 +77,7 @@ export class IkasOrderLineItem extends IkasBaseModel implements IOrderLineItem {
|
|
|
69
77
|
statusUpdatedAt: observable,
|
|
70
78
|
stockLocationId: observable,
|
|
71
79
|
taxValue: observable,
|
|
80
|
+
unitPrice: observable,
|
|
72
81
|
variant: observable,
|
|
73
82
|
orderedAt: observable,
|
|
74
83
|
//@ts-ignore
|
|
@@ -79,6 +88,8 @@ export class IkasOrderLineItem extends IkasBaseModel implements IOrderLineItem {
|
|
|
79
88
|
overridenPriceWithQuantity: computed,
|
|
80
89
|
formattedOverridenPriceWithQuantity: computed,
|
|
81
90
|
formattedFinalPrice: computed,
|
|
91
|
+
formattedUnitPrice: computed,
|
|
92
|
+
formattedFinalUnitPrice: computed,
|
|
82
93
|
formattedDiscountPrice: computed,
|
|
83
94
|
finalPriceWithQuantity: computed,
|
|
84
95
|
formattedFinalPriceWithQuantity: computed,
|
|
@@ -120,6 +131,32 @@ export class IkasOrderLineItem extends IkasBaseModel implements IOrderLineItem {
|
|
|
120
131
|
);
|
|
121
132
|
}
|
|
122
133
|
|
|
134
|
+
get formattedUnitPrice() {
|
|
135
|
+
return formatCurrency(
|
|
136
|
+
this.unitPrice || 0,
|
|
137
|
+
this.currencyCode || "",
|
|
138
|
+
this.currencySymbol || ""
|
|
139
|
+
);
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
get formattedFinalUnitPrice() {
|
|
143
|
+
return formatCurrency(
|
|
144
|
+
this.finalUnitPrice || 0,
|
|
145
|
+
this.currencyCode || "",
|
|
146
|
+
this.currencySymbol || ""
|
|
147
|
+
);
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
get unitPriceText() {
|
|
151
|
+
if (this.finalUnitPrice === null) return;
|
|
152
|
+
|
|
153
|
+
return `${formatCurrency(
|
|
154
|
+
this.finalUnitPrice,
|
|
155
|
+
this.currencyCode || "",
|
|
156
|
+
this.currencySymbol || ""
|
|
157
|
+
)} / ${this.variant.baseUnit?.unit?.name || this.variant.baseUnit?.type}`;
|
|
158
|
+
}
|
|
159
|
+
|
|
123
160
|
get formattedDiscountPrice() {
|
|
124
161
|
return formatCurrency(
|
|
125
162
|
this.discountPrice || 0,
|
|
@@ -6,9 +6,12 @@ import { IkasOrderLineVariantBrand } from "./brand";
|
|
|
6
6
|
import { IkasOrderLineVariantCategory } from "./category";
|
|
7
7
|
import { IkasOrderLineVariantPrice } from "./price";
|
|
8
8
|
import { makeAutoObservable } from "mobx";
|
|
9
|
+
import { IkasOrderLineVariantUnit } from "./unit";
|
|
10
|
+
import { IkasOrderLineBaseUnit } from "../base-unit";
|
|
9
11
|
|
|
10
12
|
export class IkasOrderLineVariant implements IOrderLineVariant {
|
|
11
13
|
barcodeList: string[] | null = null;
|
|
14
|
+
baseUnit: IkasOrderLineBaseUnit | null;
|
|
12
15
|
brand: IkasOrderLineVariantBrand | null = null;
|
|
13
16
|
categories: IkasOrderLineVariantCategory[] | null = null;
|
|
14
17
|
id: string | null = null;
|
|
@@ -21,6 +24,7 @@ export class IkasOrderLineVariant implements IOrderLineVariant {
|
|
|
21
24
|
tagIds: string[] | null = null;
|
|
22
25
|
taxValue: number | null = null;
|
|
23
26
|
type: number | null = null;
|
|
27
|
+
unit: IkasOrderLineVariantUnit | null;
|
|
24
28
|
weight: number | null = null;
|
|
25
29
|
variantValues: IkasOrderLineVariantVariantValue[] | null = null;
|
|
26
30
|
|
|
@@ -29,6 +33,9 @@ export class IkasOrderLineVariant implements IOrderLineVariant {
|
|
|
29
33
|
|
|
30
34
|
constructor(data: IOrderLineVariant) {
|
|
31
35
|
this.barcodeList = data.barcodeList || null;
|
|
36
|
+
this.baseUnit = data.baseUnit
|
|
37
|
+
? new IkasOrderLineBaseUnit(data.baseUnit)
|
|
38
|
+
: null;
|
|
32
39
|
this.brand = data.brand ? new IkasOrderLineVariantBrand(data.brand) : null;
|
|
33
40
|
this.categories =
|
|
34
41
|
data.categories?.map((c) => new IkasOrderLineVariantCategory(c)) || null;
|
|
@@ -43,6 +50,7 @@ export class IkasOrderLineVariant implements IOrderLineVariant {
|
|
|
43
50
|
this.tagIds = data.tagIds || null;
|
|
44
51
|
this.taxValue = data.taxValue || null;
|
|
45
52
|
this.type = data.type || null;
|
|
53
|
+
this.unit = data.unit ? new IkasOrderLineVariantUnit(data.unit) : null;
|
|
46
54
|
this.weight = data.weight || null;
|
|
47
55
|
this.variantValues =
|
|
48
56
|
data.variantValues?.map(
|
|
@@ -7,6 +7,7 @@ export class IkasOrderLineVariantPrice implements IOrderLineVariantPrice {
|
|
|
7
7
|
discountPrice: number | null = null;
|
|
8
8
|
priceListId: string | null = null;
|
|
9
9
|
sellPrice: number;
|
|
10
|
+
unitPrice: number | null;
|
|
10
11
|
|
|
11
12
|
constructor(data: IOrderLineVariantPrice) {
|
|
12
13
|
this.buyPrice = data.buyPrice || null;
|
|
@@ -14,6 +15,7 @@ export class IkasOrderLineVariantPrice implements IOrderLineVariantPrice {
|
|
|
14
15
|
this.discountPrice = data.discountPrice || null;
|
|
15
16
|
this.priceListId = data.priceListId || null;
|
|
16
17
|
this.sellPrice = data.sellPrice;
|
|
18
|
+
this.unitPrice = data.unitPrice;
|
|
17
19
|
|
|
18
20
|
makeAutoObservable(this);
|
|
19
21
|
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import {
|
|
2
|
+
IkasProductUnitType,
|
|
3
|
+
IkasOrderLineVariantUnit as IOrderLineVariantUnit,
|
|
4
|
+
} from "@ikas/storefront-models";
|
|
5
|
+
import { makeAutoObservable } from "mobx";
|
|
6
|
+
|
|
7
|
+
export class IkasOrderLineVariantUnit implements IOrderLineVariantUnit {
|
|
8
|
+
amount: number;
|
|
9
|
+
type: IkasProductUnitType;
|
|
10
|
+
|
|
11
|
+
constructor(data: IOrderLineVariantUnit) {
|
|
12
|
+
this.amount = data.amount;
|
|
13
|
+
this.type = data.type;
|
|
14
|
+
|
|
15
|
+
makeAutoObservable(this);
|
|
16
|
+
}
|
|
17
|
+
}
|
|
@@ -5,9 +5,11 @@ import {
|
|
|
5
5
|
IkasProductAttributeValue as IProductAttributeValue,
|
|
6
6
|
IkasAttributeTableCellValue as IAttributeTableCellValue,
|
|
7
7
|
IkasProductAttributeMap as IProductAttributeMap,
|
|
8
|
+
IkasProductAttributeType,
|
|
8
9
|
} from "@ikas/storefront-models";
|
|
9
10
|
import { makeAutoObservable } from "mobx";
|
|
10
11
|
import { IkasProductAttributeValueFunctions } from "@ikas/storefront-model-functions";
|
|
12
|
+
import ProductStore from "../../../../store/product";
|
|
11
13
|
|
|
12
14
|
export class IkasProductAttributeValue implements IProductAttributeValue {
|
|
13
15
|
imageIds: string[] | null = null;
|
|
@@ -40,6 +42,44 @@ export class IkasProductAttributeValue implements IProductAttributeValue {
|
|
|
40
42
|
get tableValue() {
|
|
41
43
|
return IkasProductAttributeValueFunctions.getTableValue(this.value);
|
|
42
44
|
}
|
|
45
|
+
|
|
46
|
+
get productIds() {
|
|
47
|
+
if (
|
|
48
|
+
this.productAttribute?.type !== IkasProductAttributeType.PRODUCT ||
|
|
49
|
+
!this.value
|
|
50
|
+
) {
|
|
51
|
+
return [];
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
try {
|
|
55
|
+
return JSON.parse(this.value) as string[];
|
|
56
|
+
} catch (err) {
|
|
57
|
+
console.error(err);
|
|
58
|
+
return [];
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
async getProducts() {
|
|
63
|
+
if (
|
|
64
|
+
this.productAttribute?.type !== IkasProductAttributeType.PRODUCT ||
|
|
65
|
+
!this.value
|
|
66
|
+
) {
|
|
67
|
+
return [];
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
try {
|
|
71
|
+
const response = await ProductStore.searchProducts({
|
|
72
|
+
input: {
|
|
73
|
+
productIdList: this.productIds,
|
|
74
|
+
},
|
|
75
|
+
});
|
|
76
|
+
|
|
77
|
+
return response.data?.data || [];
|
|
78
|
+
} catch (err) {
|
|
79
|
+
console.error(err);
|
|
80
|
+
return [];
|
|
81
|
+
}
|
|
82
|
+
}
|
|
43
83
|
}
|
|
44
84
|
|
|
45
85
|
export class IkasAttributeTableCellValue implements IAttributeTableCellValue {
|