From 4d0f9573d724d426fc7f5393d454fcb25262cedb Mon Sep 17 00:00:00 2001 From: Shiva Nandan Date: Tue, 20 Aug 2024 17:35:09 +0530 Subject: [PATCH 1/3] refactor: refactor PreMountLoader --- src/Payments/PreMountLoader.res | 222 +++++++++++++------------------- 1 file changed, 93 insertions(+), 129 deletions(-) diff --git a/src/Payments/PreMountLoader.res b/src/Payments/PreMountLoader.res index 4e3abf9a7..0ef19f3ad 100644 --- a/src/Payments/PreMountLoader.res +++ b/src/Payments/PreMountLoader.res @@ -1,63 +1,53 @@ -@react.component -let make = ( - ~sessionId, - ~publishableKey, - ~clientSecret, - ~endpoint, - ~ephemeralKey, - ~hyperComponentName: Types.hyperComponentName, - ~merchantHostname, -) => { - open Utils - let (paymentMethodsResponseSent, setPaymentMethodsResponseSent) = React.useState(_ => false) - let ( - customerPaymentMethodsResponseSent, - setCustomerPaymentMethodsResponseSent, - ) = React.useState(_ => false) - let (savedPaymentMethodsResponseSent, setSavedPaymentMethodsResponseSent) = React.useState(_ => - false - ) - let (sessionTokensResponseSent, setSessionTokensResponseSent) = React.useState(_ => false) - let logger = OrcaLogger.make( - ~sessionId, - ~source=Loader, - ~merchantId=publishableKey, - ~clientSecret, - ) +let sendPromiseData = (promise, key) => { + open Promise + promise + ->then(res => resolve(res)) + ->catch(_err => resolve(JSON.Encode.null)) + ->thenResolve(response => { + Utils.messageParentWindow([("response", response), ("data", key->JSON.Encode.string)]) + }) + ->ignore +} - let ( - paymentMethodsResponse, - customerPaymentMethodsResponse, - sessionTokensResponse, - savedPaymentMethodsResponse, - ) = React.useMemo0(() => { - let paymentMethodsResponse = switch hyperComponentName { - | Elements => - PaymentHelpers.fetchPaymentMethodList( +let useMessageHandler = getPromisesAndMessageHandler => { + React.useEffect0(() => { + let (promises, messageHandler) = getPromisesAndMessageHandler() + + open Promise + Promise.all(promises) + ->thenResolve(_ => { + Utils.messageParentWindow([("preMountLoaderIframeUnMount", true->JSON.Encode.bool)]) + Window.removeEventListener("message", messageHandler) + }) + ->ignore + + Utils.messageParentWindow([("preMountLoaderIframeMountedCallback", true->JSON.Encode.bool)]) + Window.addEventListener("message", messageHandler) + Some(() => Window.removeEventListener("message", messageHandler)) + }) +} + +module PreMountLoaderForElements = { + @react.component + let make = (~logger, ~publishableKey, ~clientSecret, ~endpoint, ~merchantHostname) => { + useMessageHandler(() => { + let paymentMethodsPromise = PaymentHelpers.fetchPaymentMethodList( ~clientSecret, ~publishableKey, ~logger, ~switchToCustomPod=false, ~endpoint, ) - | _ => JSON.Encode.null->Promise.resolve - } - let customerPaymentMethodsResponse = switch hyperComponentName { - | Elements => - PaymentHelpers.fetchCustomerPaymentMethodList( + let customerPaymentMethodsPromise = PaymentHelpers.fetchCustomerPaymentMethodList( ~clientSecret, ~publishableKey, ~optLogger=Some(logger), ~switchToCustomPod=false, ~endpoint, ) - | _ => JSON.Encode.null->Promise.resolve - } - let sessionTokensResponse = switch hyperComponentName { - | Elements => - PaymentHelpers.fetchSessions( + let sessionTokensPromise = PaymentHelpers.fetchSessions( ~clientSecret, ~publishableKey, ~optLogger=Some(logger), @@ -65,101 +55,75 @@ let make = ( ~endpoint, ~merchantHostname, ) - | _ => JSON.Encode.null->Promise.resolve - } - let savedPaymentMethodsResponse = switch hyperComponentName { - | PaymentMethodsManagementElements => - PaymentHelpers.fetchSavedPaymentMethodList( + let messageHandler = (ev: Window.event) => { + let json = ev.data->Utils.safeParse + let dict = json->Utils.getDictFromJson + if dict->Dict.get("sendPaymentMethodsResponse")->Option.isSome { + paymentMethodsPromise->sendPromiseData("payment_methods") + } else if dict->Dict.get("sendCustomerPaymentMethodsResponse")->Option.isSome { + customerPaymentMethodsPromise->sendPromiseData("customer_payment_methods") + } else if dict->Dict.get("sendSessionTokensResponse")->Option.isSome { + sessionTokensPromise->sendPromiseData("session_tokens") + } + } + + let promises = [paymentMethodsPromise, customerPaymentMethodsPromise, sessionTokensPromise] + (promises, messageHandler) + }) + + React.null + } +} + +module PreMountLoaderForPMMElements = { + @react.component + let make = (~logger, ~endpoint, ~ephemeralKey) => { + useMessageHandler(() => { + let savedPaymentMethodsPromise = PaymentHelpers.fetchSavedPaymentMethodList( ~ephemeralKey, ~optLogger=Some(logger), ~switchToCustomPod=false, ~endpoint, ) - | _ => JSON.Encode.null->Promise.resolve - } - - ( - paymentMethodsResponse, - customerPaymentMethodsResponse, - sessionTokensResponse, - savedPaymentMethodsResponse, - ) - }) - let sendPromiseData = (promise, key) => { - open Promise - promise - ->then(res => { - messageParentWindow([("response", res), ("data", key->JSON.Encode.string)]) - switch key { - | "payment_methods" => setPaymentMethodsResponseSent(_ => true) - | "session_tokens" => setSessionTokensResponseSent(_ => true) - | "customer_payment_methods" => setCustomerPaymentMethodsResponseSent(_ => true) - | "saved_payment_methods" => setSavedPaymentMethodsResponseSent(_ => true) - | _ => () + let messageHandler = (ev: Window.event) => { + let json = ev.data->Utils.safeParse + let dict = json->Utils.getDictFromJson + if dict->Dict.get("sendSavedPaymentMethodsResponse")->Belt.Option.isSome { + savedPaymentMethodsPromise->sendPromiseData("saved_payment_methods") + } } - resolve() - }) - ->catch(_err => { - messageParentWindow([("response", JSON.Encode.null), ("data", key->JSON.Encode.string)]) - resolve() + + let promises = [savedPaymentMethodsPromise] + (promises, messageHandler) }) - ->ignore - } - let handle = (ev: Window.event) => { - let json = ev.data->safeParse - let dict = json->Utils.getDictFromJson - if dict->Dict.get("sendPaymentMethodsResponse")->Option.isSome { - paymentMethodsResponse->sendPromiseData("payment_methods") - } else if dict->Dict.get("sendCustomerPaymentMethodsResponse")->Option.isSome { - customerPaymentMethodsResponse->sendPromiseData("customer_payment_methods") - } else if dict->Dict.get("sendSessionTokensResponse")->Option.isSome { - sessionTokensResponse->sendPromiseData("session_tokens") - } else if dict->Dict.get("sendSavedPaymentMethodsResponse")->Belt.Option.isSome { - savedPaymentMethodsResponse->sendPromiseData("saved_payment_methods") - } + React.null } +} - React.useEffect0(() => { - Window.addEventListener("message", handle) - messageParentWindow([("preMountLoaderIframeMountedCallback", true->JSON.Encode.bool)]) - Some( - () => { - Window.removeEventListener("message", handle) - }, - ) - }) - - React.useEffect4(() => { - let handleUnmount = () => { - messageParentWindow([("preMountLoaderIframeUnMount", true->JSON.Encode.bool)]) - Window.removeEventListener("message", handle) - } - - switch hyperComponentName { - | Elements => - if ( - paymentMethodsResponseSent && - customerPaymentMethodsResponseSent && - sessionTokensResponseSent - ) { - handleUnmount() - } - | PaymentMethodsManagementElements => - if savedPaymentMethodsResponseSent { - handleUnmount() - } - } - - None - }, ( - paymentMethodsResponseSent, - customerPaymentMethodsResponseSent, - sessionTokensResponseSent, - savedPaymentMethodsResponseSent, - )) +@react.component +let make = ( + ~sessionId, + ~publishableKey, + ~clientSecret, + ~endpoint, + ~ephemeralKey, + ~hyperComponentName: Types.hyperComponentName, + ~merchantHostname, +) => { + let logger = OrcaLogger.make( + ~sessionId, + ~source=Loader, + ~merchantId=publishableKey, + ~clientSecret, + ) - React.null + switch hyperComponentName { + | Elements => + + | PaymentMethodsManagementElements => + + } } From ca298264b7e4680e28683524972b5d09c1bf5e16 Mon Sep 17 00:00:00 2001 From: Shiva Nandan Date: Mon, 26 Aug 2024 14:01:06 +0530 Subject: [PATCH 2/3] Apply suggestions from code review Co-authored-by: Pritish Budhiraja --- src/Payments/PreMountLoader.res | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Payments/PreMountLoader.res b/src/Payments/PreMountLoader.res index 0ef19f3ad..9c2489c8b 100644 --- a/src/Payments/PreMountLoader.res +++ b/src/Payments/PreMountLoader.res @@ -2,7 +2,7 @@ let sendPromiseData = (promise, key) => { open Promise promise ->then(res => resolve(res)) - ->catch(_err => resolve(JSON.Encode.null)) + ->catch(_ => resolve(JSON.Encode.null)) ->thenResolve(response => { Utils.messageParentWindow([("response", response), ("data", key->JSON.Encode.string)]) }) @@ -90,7 +90,7 @@ module PreMountLoaderForPMMElements = { let messageHandler = (ev: Window.event) => { let json = ev.data->Utils.safeParse let dict = json->Utils.getDictFromJson - if dict->Dict.get("sendSavedPaymentMethodsResponse")->Belt.Option.isSome { + if dict->Dict.get("sendSavedPaymentMethodsResponse")->Option.isSome { savedPaymentMethodsPromise->sendPromiseData("saved_payment_methods") } } From 2999f22f2624181a2e0e3dd8845bef5439bfd826 Mon Sep 17 00:00:00 2001 From: Pritish Budhiraja Date: Tue, 3 Sep 2024 11:20:44 +0530 Subject: [PATCH 3/3] chore: comments addressed --- src/Payments/PreMountLoader.res | 16 ++++++++-------- src/Utilities/Utils.res | 2 ++ 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/src/Payments/PreMountLoader.res b/src/Payments/PreMountLoader.res index 9c2489c8b..c1f680ea8 100644 --- a/src/Payments/PreMountLoader.res +++ b/src/Payments/PreMountLoader.res @@ -57,13 +57,13 @@ module PreMountLoaderForElements = { ) let messageHandler = (ev: Window.event) => { - let json = ev.data->Utils.safeParse - let dict = json->Utils.getDictFromJson - if dict->Dict.get("sendPaymentMethodsResponse")->Option.isSome { + open Utils + let dict = ev.data->safeParse->getDictFromJson + if dict->isKeyPresentInDict("sendPaymentMethodsResponse") { paymentMethodsPromise->sendPromiseData("payment_methods") - } else if dict->Dict.get("sendCustomerPaymentMethodsResponse")->Option.isSome { + } else if dict->isKeyPresentInDict("sendCustomerPaymentMethodsResponse") { customerPaymentMethodsPromise->sendPromiseData("customer_payment_methods") - } else if dict->Dict.get("sendSessionTokensResponse")->Option.isSome { + } else if dict->isKeyPresentInDict("sendSessionTokensResponse") { sessionTokensPromise->sendPromiseData("session_tokens") } } @@ -88,9 +88,9 @@ module PreMountLoaderForPMMElements = { ) let messageHandler = (ev: Window.event) => { - let json = ev.data->Utils.safeParse - let dict = json->Utils.getDictFromJson - if dict->Dict.get("sendSavedPaymentMethodsResponse")->Option.isSome { + open Utils + let dict = ev.data->safeParse->getDictFromJson + if dict->isKeyPresentInDict("sendSavedPaymentMethodsResponse") { savedPaymentMethodsPromise->sendPromiseData("saved_payment_methods") } } diff --git a/src/Utilities/Utils.res b/src/Utilities/Utils.res index deb9d3fa6..6aef9c586 100644 --- a/src/Utilities/Utils.res +++ b/src/Utilities/Utils.res @@ -1372,3 +1372,5 @@ let getFirstAndLastNameFromFullName = fullName => { (firstName, lastNameJson) } + +let isKeyPresentInDict = (dict, key) => dict->Dict.get(key)->Option.isSome