From 6122d9d200b934969ee8643e598754d724a786a4 Mon Sep 17 00:00:00 2001 From: Sanskar Atrey Date: Fri, 25 Oct 2024 12:56:20 +0530 Subject: [PATCH 01/19] fix: card cvc bug fix (#748) --- .../cypress/e2e/cvc-checks-e2e-test.cy.ts | 84 +++++++++++++++++++ cypress-tests/cypress/support/utils.ts | 2 + src/CardUtils.res | 4 + src/Payment.res | 3 +- 4 files changed, 92 insertions(+), 1 deletion(-) create mode 100644 cypress-tests/cypress/e2e/cvc-checks-e2e-test.cy.ts diff --git a/cypress-tests/cypress/e2e/cvc-checks-e2e-test.cy.ts b/cypress-tests/cypress/e2e/cvc-checks-e2e-test.cy.ts new file mode 100644 index 000000000..883aaa5bf --- /dev/null +++ b/cypress-tests/cypress/e2e/cvc-checks-e2e-test.cy.ts @@ -0,0 +1,84 @@ +import * as testIds from "../../../src/Utilities/TestUtils.bs"; +import { getClientURL, amexTestCard, visaTestCard, createPaymentBody } from "../support/utils"; + +describe("Card CVC Checks", () => { + let getIframeBody: () => Cypress.Chainable>; + const publishableKey = Cypress.env('HYPERSWITCH_PUBLISHABLE_KEY') + const secretKey = Cypress.env('HYPERSWITCH_SECRET_KEY') + let iframeSelector = + "#orca-payment-element-iframeRef-orca-elements-payment-element-payment-element"; + + + beforeEach(() => { + getIframeBody = () => cy.iframe(iframeSelector); + cy.createPaymentIntent(secretKey, createPaymentBody).then(() => { + cy.getGlobalState("clientSecret").then((clientSecret) => { + + cy.visit(getClientURL(clientSecret, publishableKey)); + }); + + }) + }); + + + + + it("title rendered correctly", () => { + cy.contains("Hyperswitch Unified Checkout").should("be.visible"); + }); + + it("orca-payment-element iframe loaded", () => { + cy.get( + "#orca-payment-element-iframeRef-orca-elements-payment-element-payment-element" + ) + .should("be.visible") + .its("0.contentDocument") + .its("body"); + }); + + + it('user can enter 4 digit cvc in card form', () => { + getIframeBody().find(`[data-testid=${testIds.addNewCardIcon}]`).click() + getIframeBody().find(`[data-testid=${testIds.cardNoInputTestId}]`).type(amexTestCard) + getIframeBody().find(`[data-testid=${testIds.expiryInputTestId}]`).type("0444") + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).type("1234").then(() => { + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).should('have.value', '1234'); + }) + + + }) + it('user can enter 3 digit cvc on saved payment methods screen', () => { + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).type('123').then(() => { + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).should('have.value', '123'); + }) + + }) + + it('user can enter 3 digit cvc in card form', () => { + getIframeBody().find(`[data-testid=${testIds.addNewCardIcon}]`).click() + getIframeBody().find(`[data-testid=${testIds.cardNoInputTestId}]`).type(visaTestCard) + getIframeBody().find(`[data-testid=${testIds.expiryInputTestId}]`).type("0444") + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).type("123").then(() => { + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).should('have.value', '123'); + }) + }) + + it('user can enter 4 digit cvc on saved payment methods screen', () => { + cy.wait(2000) + getIframeBody() + .contains('div', '4 digit cvc test card') + .should('exist') + .trigger('click') + cy.wait(1000) + + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).type("1234").then(() => { + getIframeBody().find(`[data-testid=${testIds.cardCVVInputTestId}]`).should('have.value', '1234'); + }) + + }) + +}) + + + + diff --git a/cypress-tests/cypress/support/utils.ts b/cypress-tests/cypress/support/utils.ts index 08a516365..4d6ca4c02 100644 --- a/cypress-tests/cypress/support/utils.ts +++ b/cypress-tests/cypress/support/utils.ts @@ -116,3 +116,5 @@ export const confirmBody = { export const stripeTestCard = "4000000000003220"; export const adyenTestCard = "4917610000000000"; export const bluesnapTestCard = "4000000000001091"; +export const amexTestCard = "378282246310005" +export const visaTestCard = "4242424242424242"; diff --git a/src/CardUtils.res b/src/CardUtils.res index 02a4bd55f..9341d889d 100644 --- a/src/CardUtils.res +++ b/src/CardUtils.res @@ -671,3 +671,7 @@ let getEligibleCoBadgedCardSchemes = (~matchedCardSchemes, ~enabledCardSchemes) enabledCardSchemes->Array.includes(ele->String.toLowerCase) }) } + +let getCardBrandFromStates = (cardBrand, cardScheme, showFields) => { + !showFields ? cardScheme : cardBrand +} diff --git a/src/Payment.res b/src/Payment.res index 9aa7ba63b..f549921df 100644 --- a/src/Payment.res +++ b/src/Payment.res @@ -18,7 +18,6 @@ let make = (~paymentMode, ~integrateError, ~logger) => { let isManualRetryEnabled = Recoil.useRecoilValueFromAtom(isManualRetryEnabled) let paymentToken = Recoil.useRecoilValueFromAtom(paymentTokenAtom) let paymentMethodListValue = Recoil.useRecoilValueFromAtom(PaymentUtils.paymentMethodListValue) - let {iframeId} = keys let (cardNumber, setCardNumber) = React.useState(_ => "") @@ -56,6 +55,8 @@ let make = (~paymentMode, ~integrateError, ~logger) => { let (cardBrand, setCardBrand) = React.useState(_ => !showFields && isNotBancontact ? cardScheme : cardBrand ) + + let cardBrand = CardUtils.getCardBrandFromStates(cardBrand, cardScheme, showFields) let supportedCardBrands = React.useMemo(() => { paymentMethodListValue->PaymentUtils.getSupportedCardBrands }, [paymentMethodListValue]) From 627980d55a18a8ebe15ba65cc7cb2a1ccde068d0 Mon Sep 17 00:00:00 2001 From: semantic-release-bot Date: Fri, 25 Oct 2024 07:28:14 +0000 Subject: [PATCH 02/19] chore(release): 0.96.1 [skip ci] ## [0.96.1](https://github.com/juspay/hyperswitch-web/compare/v0.96.0...v0.96.1) (2024-10-25) ### Bug Fixes * card cvc bug fix ([#748](https://github.com/juspay/hyperswitch-web/issues/748)) ([6122d9d](https://github.com/juspay/hyperswitch-web/commit/6122d9d200b934969ee8643e598754d724a786a4)) --- CHANGELOG.md | 7 +++++++ package-lock.json | 4 ++-- package.json | 2 +- 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4e7bf7ee4..1519bc3d9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,10 @@ +## [0.96.1](https://github.com/juspay/hyperswitch-web/compare/v0.96.0...v0.96.1) (2024-10-25) + + +### Bug Fixes + +* card cvc bug fix ([#748](https://github.com/juspay/hyperswitch-web/issues/748)) ([6122d9d](https://github.com/juspay/hyperswitch-web/commit/6122d9d200b934969ee8643e598754d724a786a4)) + # [0.96.0](https://github.com/juspay/hyperswitch-web/compare/v0.95.3...v0.96.0) (2024-10-23) diff --git a/package-lock.json b/package-lock.json index 7b8ec0ad0..b2ec9bb59 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "orca-payment-page", - "version": "0.96.0", + "version": "0.96.1", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "orca-payment-page", - "version": "0.96.0", + "version": "0.96.1", "hasInstallScript": true, "dependencies": { "@glennsl/rescript-fetch": "^0.2.0", diff --git a/package.json b/package.json index cd23cd0c7..4ceafaf2a 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "orca-payment-page", - "version": "0.96.0", + "version": "0.96.1", "main": "index.js", "private": true, "dependencies": { From 6059f13fa147d4087872576fe05852b939323f33 Mon Sep 17 00:00:00 2001 From: Pritish Budhiraja Date: Mon, 28 Oct 2024 13:10:25 +0530 Subject: [PATCH 03/19] refactor: disable logging in integration environment (#753) --- package.json | 25 ++++++++++++------------- webpack.common.js | 4 ++-- 2 files changed, 14 insertions(+), 15 deletions(-) diff --git a/package.json b/package.json index 4ceafaf2a..57ab68d49 100644 --- a/package.json +++ b/package.json @@ -16,23 +16,22 @@ "webpack-merge": "^5.9.0" }, "scripts": { - "build:dev": "cross-env sdkEnv=sandbox webpack --config webpack.dev.js", - "build:dev-integ": "cross-env sdkEnv=integ webpack --config webpack.dev.js", - "start": "cross-env sdkEnv=local webpack serve --config webpack.dev.js", - "build:prod": "cross-env sdkEnv=prod webpack --config webpack.common.js", "build": "webpack --config webpack.common.js", - "build:sandbox": "cross-env sdkEnv=sandbox webpack --config webpack.common.js", - "build:integ": "cross-env sdkEnv=integ webpack --config webpack.common.js", - "test": "cd cypress-tests && npm run cypress:run", + "build:integ": "cross-env sdkEnv=integ enableLogging=false webpack --config webpack.common.js", + "build:playground": "npm run setup:playground && npm run build", + "build:prod": "cross-env sdkEnv=prod enableLogging=true webpack --config webpack.common.js", + "build:sandbox": "cross-env sdkEnv=sandbox enableLogging=true webpack --config webpack.common.js", + "deploy-to-s3": "node ./scripts/pushToS3.js", + "postinstall": "cd Hyperswitch-React-Demo-App && npm i", + "prepare": "husky install", "re:build": "rescript", "re:clean": "rescript clean", - "re:start": "rescript -w", "re:format": "rescript format -all", - "start:playground": "npm run postinstall && cd Hyperswitch-React-Demo-App && node promptScript.js && npm run start", - "build:playground": "npm run postinstall && cd Hyperswitch-React-Demo-App && node promptScript.js && npm run build", - "prepare": "husky install", - "deploy-to-s3": "node ./scripts/pushToS3.js", - "postinstall": "cd Hyperswitch-React-Demo-App && npm i", + "re:start": "rescript -w", + "setup:playground": "npm run postinstall && cd Hyperswitch-React-Demo-App && node promptScript.js", + "start": "cross-env sdkEnv=local enableLogging=false webpack serve --config webpack.dev.js", + "start:playground": "npm run setup:playground && npm run start", + "test": "cd cypress-tests && npm run cypress:run", "test:hooks": "npx eslint src/" }, "eslintConfig": { diff --git a/webpack.common.js b/webpack.common.js index 981f2a979..4357ab075 100644 --- a/webpack.common.js +++ b/webpack.common.js @@ -14,6 +14,7 @@ const getEnvVariable = (variable, defaultValue) => process.env[variable] ?? defaultValue; const sdkEnv = getEnvVariable("sdkEnv", "local"); +const enableLogging = getEnvVariable("enableLogging", "false") === "true"; const envSdkUrl = getEnvVariable("ENV_SDK_URL", ""); const envBackendUrl = getEnvVariable("ENV_BACKEND_URL", ""); const envLoggingUrl = getEnvVariable("ENV_LOGGING_URL", ""); @@ -60,7 +61,6 @@ const confirmEndPoint = const logEndpoint = envLoggingUrl || `https://${logDomain}.hyperswitch.io/logs/sdk`; -const enableLogging = true; const loggingLevel = "DEBUG"; const maxLogsPushedPerEventName = 100; @@ -84,7 +84,7 @@ module.exports = (publicPath = "auto") => { logEndpoint: JSON.stringify(logEndpoint), sentryDSN: JSON.stringify(process.env.SENTRY_DSN), sentryScriptUrl: JSON.stringify(process.env.SENTRY_SCRIPT_URL), - enableLogging: JSON.stringify(enableLogging), + enableLogging: enableLogging, loggingLevel: JSON.stringify(loggingLevel), maxLogsPushedPerEventName: JSON.stringify(maxLogsPushedPerEventName), }), From bc4e296bae2e3d7c94bb4c47c0a779cd510aa6b0 Mon Sep 17 00:00:00 2001 From: semantic-release-bot Date: Mon, 28 Oct 2024 07:42:15 +0000 Subject: [PATCH 04/19] chore(release): 0.96.2 [skip ci] ## [0.96.2](https://github.com/juspay/hyperswitch-web/compare/v0.96.1...v0.96.2) (2024-10-28) --- CHANGELOG.md | 2 ++ package-lock.json | 4 ++-- package.json | 2 +- 3 files changed, 5 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 1519bc3d9..c66c3a707 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,5 @@ +## [0.96.2](https://github.com/juspay/hyperswitch-web/compare/v0.96.1...v0.96.2) (2024-10-28) + ## [0.96.1](https://github.com/juspay/hyperswitch-web/compare/v0.96.0...v0.96.1) (2024-10-25) diff --git a/package-lock.json b/package-lock.json index b2ec9bb59..cfcead004 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "orca-payment-page", - "version": "0.96.1", + "version": "0.96.2", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "orca-payment-page", - "version": "0.96.1", + "version": "0.96.2", "hasInstallScript": true, "dependencies": { "@glennsl/rescript-fetch": "^0.2.0", diff --git a/package.json b/package.json index 57ab68d49..6615f765d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "orca-payment-page", - "version": "0.96.1", + "version": "0.96.2", "main": "index.js", "private": true, "dependencies": { From 40ef7a5578b3a687c9b596a27818f4533758f136 Mon Sep 17 00:00:00 2001 From: aritro2002 Date: Tue, 29 Oct 2024 12:30:32 +0530 Subject: [PATCH 05/19] fix: remove blue border in firefox (#746) Co-authored-by: Pritish Budhiraja --- src/Index.res | 1 + src/index.css | 23 ++++++++--------------- 2 files changed, 9 insertions(+), 15 deletions(-) diff --git a/src/Index.res b/src/Index.res index 34fb585d3..52691270d 100644 --- a/src/Index.res +++ b/src/Index.res @@ -1,4 +1,5 @@ %%raw(`require("tailwindcss/tailwind.css")`) +%%raw("import './index.css'") Sentry.initiateSentry(~dsn=GlobalVars.sentryDSN) diff --git a/src/index.css b/src/index.css index 651ed53e7..a6f7ec31d 100644 --- a/src/index.css +++ b/src/index.css @@ -1,16 +1,9 @@ -@tailwind base; -@tailwind components; -@tailwind utilities; -body { - margin: 0; - font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', 'Oxygen', - 'Ubuntu', 'Cantarell', 'Fira Sans', 'Droid Sans', 'Helvetica Neue', - sans-serif; - -webkit-font-smoothing: antialiased; - -moz-osx-font-smoothing: grayscale; -} - -code { - font-family: source-code-pro, Menlo, Monaco, Consolas, 'Courier New', - monospace; +/* Remove focus outline in Firefox */ +@-moz-document url-prefix() { + *:focus, + *:focus-visible, + *:focus-within, + *:active { + outline: transparent !important; + } } From 7c1584b06bdcfc7ece35d11ab0f1249109852635 Mon Sep 17 00:00:00 2001 From: semantic-release-bot Date: Tue, 29 Oct 2024 07:02:19 +0000 Subject: [PATCH 06/19] chore(release): 0.96.3 [skip ci] ## [0.96.3](https://github.com/juspay/hyperswitch-web/compare/v0.96.2...v0.96.3) (2024-10-29) ### Bug Fixes * remove blue border in firefox ([#746](https://github.com/juspay/hyperswitch-web/issues/746)) ([40ef7a5](https://github.com/juspay/hyperswitch-web/commit/40ef7a5578b3a687c9b596a27818f4533758f136)) --- CHANGELOG.md | 7 +++++++ package-lock.json | 4 ++-- package.json | 2 +- 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c66c3a707..6598502e7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,10 @@ +## [0.96.3](https://github.com/juspay/hyperswitch-web/compare/v0.96.2...v0.96.3) (2024-10-29) + + +### Bug Fixes + +* remove blue border in firefox ([#746](https://github.com/juspay/hyperswitch-web/issues/746)) ([40ef7a5](https://github.com/juspay/hyperswitch-web/commit/40ef7a5578b3a687c9b596a27818f4533758f136)) + ## [0.96.2](https://github.com/juspay/hyperswitch-web/compare/v0.96.1...v0.96.2) (2024-10-28) ## [0.96.1](https://github.com/juspay/hyperswitch-web/compare/v0.96.0...v0.96.1) (2024-10-25) diff --git a/package-lock.json b/package-lock.json index cfcead004..fe440a524 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "orca-payment-page", - "version": "0.96.2", + "version": "0.96.3", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "orca-payment-page", - "version": "0.96.2", + "version": "0.96.3", "hasInstallScript": true, "dependencies": { "@glennsl/rescript-fetch": "^0.2.0", diff --git a/package.json b/package.json index 6615f765d..ae6bb03ba 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "orca-payment-page", - "version": "0.96.2", + "version": "0.96.3", "main": "index.js", "private": true, "dependencies": { From 0039fbe65ec7ff958d637d00c58aed710fed5b1f Mon Sep 17 00:00:00 2001 From: Sagnik Mitra <83326850+ImSagnik007@users.noreply.github.com> Date: Tue, 29 Oct 2024 12:43:43 +0530 Subject: [PATCH 07/19] feat: tax calculation in google pay (#750) Co-authored-by: Pritish Budhiraja Co-authored-by: Shiva Nandan --- src/Components/SavedMethods.res | 1 + src/Payments/GPay.res | 1 + src/Types/GooglePayType.res | 2 + src/Utilities/GooglePayHelpers.res | 21 ++++- src/orca-loader/Elements.res | 123 +++++++++++++++++++++++------ 5 files changed, 120 insertions(+), 28 deletions(-) diff --git a/src/Components/SavedMethods.res b/src/Components/SavedMethods.res index ae2dbdf1f..2516e9ca5 100644 --- a/src/Components/SavedMethods.res +++ b/src/Components/SavedMethods.res @@ -141,6 +141,7 @@ let make = ( GooglePayHelpers.handleGooglePayClicked( ~sessionObj=optToken, ~componentName, + ~paymentMethodListValue, ~iframeId, ~readOnly, ) diff --git a/src/Payments/GPay.res b/src/Payments/GPay.res index d9e0c69d1..26ba4e176 100644 --- a/src/Payments/GPay.res +++ b/src/Payments/GPay.res @@ -127,6 +127,7 @@ let make = ( GooglePayHelpers.handleGooglePayClicked( ~sessionObj, ~componentName, + ~paymentMethodListValue, ~iframeId, ~readOnly=options.readOnly, ) diff --git a/src/Types/GooglePayType.res b/src/Types/GooglePayType.res index a2d99aaf6..acbbf276e 100644 --- a/src/Types/GooglePayType.res +++ b/src/Types/GooglePayType.res @@ -14,6 +14,7 @@ type paymentDataRequest = { mutable shippingAddressRequired: bool, mutable emailRequired: bool, mutable shippingAddressParameters: JSON.t, + mutable callbackIntents: array, } @val @scope("Object") external assign2: (JSON.t, JSON.t) => paymentDataRequest = "assign" type element = { @@ -180,6 +181,7 @@ let getPaymentDataFromSession = (~sessionObj, ~componentName) => { paymentDataRequest.shippingAddressRequired = gpayobj.shippingAddressRequired paymentDataRequest.shippingAddressParameters = gpayobj.shippingAddressParameters->transformKeys(CamelCase) + paymentDataRequest.callbackIntents = ["SHIPPING_ADDRESS"->JSON.Encode.string] } paymentDataRequest diff --git a/src/Utilities/GooglePayHelpers.res b/src/Utilities/GooglePayHelpers.res index 04b9c9ef6..a8007b69a 100644 --- a/src/Utilities/GooglePayHelpers.res +++ b/src/Utilities/GooglePayHelpers.res @@ -151,7 +151,13 @@ let useHandleGooglePayResponse = ( }, (paymentMethodTypes, stateJson, isManualRetryEnabled, requiredFieldsBody, isWallet)) } -let handleGooglePayClicked = (~sessionObj, ~componentName, ~iframeId, ~readOnly) => { +let handleGooglePayClicked = ( + ~sessionObj, + ~componentName, + ~iframeId, + ~readOnly, + ~paymentMethodListValue: PaymentMethodsRecord.paymentMethodList, +) => { let paymentDataRequest = GooglePayType.getPaymentDataFromSession(~sessionObj, ~componentName) messageParentWindow([ ("fullscreen", true->JSON.Encode.bool), @@ -162,6 +168,10 @@ let handleGooglePayClicked = (~sessionObj, ~componentName, ~iframeId, ~readOnly) messageParentWindow([ ("GpayClicked", true->JSON.Encode.bool), ("GpayPaymentDataRequest", paymentDataRequest->Identity.anyTypeToJson), + ( + "IsTaxCalculationEnabled", + paymentMethodListValue.is_tax_calculation_enabled->JSON.Encode.bool, + ), ]) } } @@ -169,6 +179,7 @@ let handleGooglePayClicked = (~sessionObj, ~componentName, ~iframeId, ~readOnly) let useSubmitCallback = (~isWallet, ~sessionObj, ~componentName) => { let areRequiredFieldsValid = Recoil.useRecoilValueFromAtom(RecoilAtoms.areRequiredFieldsValid) let areRequiredFieldsEmpty = Recoil.useRecoilValueFromAtom(RecoilAtoms.areRequiredFieldsEmpty) + let paymentMethodListValue = Recoil.useRecoilValueFromAtom(PaymentUtils.paymentMethodListValue) let options = Recoil.useRecoilValueFromAtom(RecoilAtoms.optionAtom) let {localeString} = Recoil.useRecoilValueFromAtom(RecoilAtoms.configAtom) let {iframeId} = Recoil.useRecoilValueFromAtom(RecoilAtoms.keys) @@ -178,7 +189,13 @@ let useSubmitCallback = (~isWallet, ~sessionObj, ~componentName) => { let json = ev.data->safeParse let confirm = json->getDictFromJson->ConfirmType.itemToObjMapper if confirm.doSubmit && areRequiredFieldsValid && !areRequiredFieldsEmpty { - handleGooglePayClicked(~sessionObj, ~componentName, ~iframeId, ~readOnly=options.readOnly) + handleGooglePayClicked( + ~sessionObj, + ~componentName, + ~paymentMethodListValue, + ~iframeId, + ~readOnly=options.readOnly, + ) } else if areRequiredFieldsEmpty { postFailedSubmitResponse( ~errortype="validation_error", diff --git a/src/orca-loader/Elements.res b/src/orca-loader/Elements.res index a664a8750..d6aa0b596 100644 --- a/src/orca-loader/Elements.res +++ b/src/orca-loader/Elements.res @@ -915,35 +915,106 @@ let make = ( ) try { - let gPayClient = GooglePayType.google( - { - "environment": publishableKey->String.startsWith("pk_prd_") - ? "PRODUCTION" - : "TEST", - }->Identity.anyTypeToJson, - ) - - gPayClient.isReadyToPay(payRequest) - ->then(res => { - let dict = res->getDictFromJson - let isReadyToPay = getBool(dict, "result", false) - let msg = [("isReadyToPay", isReadyToPay->JSON.Encode.bool)]->Dict.fromArray - mountedIframeRef->Window.iframePostMessage(msg) - resolve() - }) - ->catch(err => { - logger.setLogInfo( - ~value=err->Identity.anyTypeToJson->JSON.stringify, - ~eventName=GOOGLE_PAY_FLOW, - ~paymentMethod="GOOGLE_PAY", - ~logType=DEBUG, - ) - resolve() - }) - ->ignore + let transactionInfo = gpayobj.transaction_info->getDictFromJson let handleGooglePayMessages = (event: Types.event) => { let evJson = event.data->anyTypeToJson + let isTaxCalculationEnabled = + evJson + ->getOptionalJsonFromJson("IsTaxCalculationEnabled") + ->Option.flatMap(JSON.Decode.bool) + ->Option.getOr(false) + + let onPaymentDataChanged = intermediatePaymentData => { + let shippingAddress = + intermediatePaymentData + ->getDictFromJson + ->getDictFromDict("shippingAddress") + ->billingContactItemToObjMapper + let newShippingAddress = + [ + ("state", shippingAddress.administrativeArea->JSON.Encode.string), + ("country", shippingAddress.countryCode->JSON.Encode.string), + ("zip", shippingAddress.postalCode->JSON.Encode.string), + ]->getJsonFromArrayOfJson + + let paymentMethodType = "google_pay"->JSON.Encode.string + + if isTaxCalculationEnabled { + TaxCalculation.calculateTax( + ~shippingAddress=[ + ("address", newShippingAddress), + ]->getJsonFromArrayOfJson, + ~logger, + ~publishableKey, + ~clientSecret, + ~paymentMethodType, + )->then(resp => { + switch resp->TaxCalculation.taxResponseToObjMapper { + | Some(taxCalculationResponse) => { + let updatePaymentRequest = + [ + ( + "newTransactionInfo", + [ + ( + "countryCode", + shippingAddress.countryCode->JSON.Encode.string, + ), + ( + "currencyCode", + transactionInfo + ->getString("currency_code", "") + ->JSON.Encode.string, + ), + ("totalPriceStatus", "FINAL"->JSON.Encode.string), + ( + "totalPrice", + taxCalculationResponse.net_amount + ->minorUnitToString + ->JSON.Encode.string, + ), + ]->getJsonFromArrayOfJson, + ), + ]->getJsonFromArrayOfJson + updatePaymentRequest->resolve + } + | None => JSON.Encode.null->resolve + } + }) + } else { + JSON.Encode.null->resolve + } + } + let gPayClient = GooglePayType.google( + { + "environment": publishableKey->String.startsWith("pk_prd_") + ? "PRODUCTION" + : "TEST", + "paymentDataCallbacks": { + "onPaymentDataChanged": onPaymentDataChanged, + }, + }->Identity.anyTypeToJson, + ) + + gPayClient.isReadyToPay(payRequest) + ->then(res => { + let dict = res->getDictFromJson + let isReadyToPay = getBool(dict, "result", false) + let msg = [("isReadyToPay", isReadyToPay->JSON.Encode.bool)]->Dict.fromArray + mountedIframeRef->Window.iframePostMessage(msg) + resolve() + }) + ->catch(err => { + logger.setLogInfo( + ~value=err->Identity.anyTypeToJson->JSON.stringify, + ~eventName=GOOGLE_PAY_FLOW, + ~paymentMethod="GOOGLE_PAY", + ~logType=DEBUG, + ) + resolve() + }) + ->ignore let gpayClicked = evJson ->getOptionalJsonFromJson("GpayClicked") From dd789930210966e0828a40c5b0f745a7dbfa1049 Mon Sep 17 00:00:00 2001 From: semantic-release-bot Date: Tue, 29 Oct 2024 07:15:44 +0000 Subject: [PATCH 08/19] chore(release): 0.97.0 [skip ci] # [0.97.0](https://github.com/juspay/hyperswitch-web/compare/v0.96.3...v0.97.0) (2024-10-29) ### Features * tax calculation in google pay ([#750](https://github.com/juspay/hyperswitch-web/issues/750)) ([0039fbe](https://github.com/juspay/hyperswitch-web/commit/0039fbe65ec7ff958d637d00c58aed710fed5b1f)) --- CHANGELOG.md | 7 +++++++ package-lock.json | 4 ++-- package.json | 2 +- 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6598502e7..962929a15 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,10 @@ +# [0.97.0](https://github.com/juspay/hyperswitch-web/compare/v0.96.3...v0.97.0) (2024-10-29) + + +### Features + +* tax calculation in google pay ([#750](https://github.com/juspay/hyperswitch-web/issues/750)) ([0039fbe](https://github.com/juspay/hyperswitch-web/commit/0039fbe65ec7ff958d637d00c58aed710fed5b1f)) + ## [0.96.3](https://github.com/juspay/hyperswitch-web/compare/v0.96.2...v0.96.3) (2024-10-29) diff --git a/package-lock.json b/package-lock.json index fe440a524..ff68b0145 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "orca-payment-page", - "version": "0.96.3", + "version": "0.97.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "orca-payment-page", - "version": "0.96.3", + "version": "0.97.0", "hasInstallScript": true, "dependencies": { "@glennsl/rescript-fetch": "^0.2.0", diff --git a/package.json b/package.json index ae6bb03ba..b65050649 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "orca-payment-page", - "version": "0.96.3", + "version": "0.97.0", "main": "index.js", "private": true, "dependencies": { From 63f536ef22dc0304b01d703a232ce99819743608 Mon Sep 17 00:00:00 2001 From: Pritish Budhiraja Date: Tue, 29 Oct 2024 13:58:14 +0530 Subject: [PATCH 09/19] feat: added dynamic fields for SEPA (#624) --- src/App.res | 32 ++ src/CardTheme.res | 4 +- src/CardUtils.res | 2 +- src/Components/AddBankAccount.res | 7 +- src/Components/DynamicFields.res | 37 +++ src/Components/PayNowButton.res | 17 +- src/LoaderController.res | 10 +- src/LocaleStrings/ArabicLocale.res | 1 + src/LocaleStrings/CatalanLocale.res | 1 + src/LocaleStrings/ChineseLocale.res | 1 + src/LocaleStrings/DeutschLocale.res | 1 + src/LocaleStrings/DutchLocale.res | 1 + src/LocaleStrings/EnglishGBLocale.res | 1 + src/LocaleStrings/EnglishLocale.res | 1 + src/LocaleStrings/FrenchBelgiumLocale.res | 1 + src/LocaleStrings/FrenchLocale.res | 1 + src/LocaleStrings/HebrewLocale.res | 1 + src/LocaleStrings/ItalianLocale.res | 1 + src/LocaleStrings/JapaneseLocale.res | 1 + src/LocaleStrings/LocaleStringTypes.res | 1 + src/LocaleStrings/PolishLocale.res | 1 + src/LocaleStrings/PortugueseLocale.res | 1 + src/LocaleStrings/RussianLocale.res | 1 + src/LocaleStrings/SpanishLocale.res | 1 + src/LocaleStrings/SwedishLocale.res | 1 + src/Payments/ACHBankDebit.res | 2 +- src/Payments/BankDebitModal.res | 344 ++++++++++++---------- src/Payments/BecsBankDebit.res | 2 +- src/Payments/PaymentMethodsRecord.res | 5 + src/Payments/PaymentMethodsWrapper.res | 9 +- src/Payments/SepaBankDebit.res | 93 +++--- src/Types/ACHTypes.res | 1 + src/Utilities/DynamicFieldsUtils.res | 74 +++-- src/Utilities/PaymentBody.res | 45 +-- src/Utilities/RecoilAtoms.res | 1 + src/Utilities/Utils.res | 2 + src/orca-loader/LoaderPaymentElement.res | 4 + 37 files changed, 415 insertions(+), 294 deletions(-) diff --git a/src/App.res b/src/App.res index 020d9cd9a..eec095614 100644 --- a/src/App.res +++ b/src/App.res @@ -16,6 +16,38 @@ let make = () => { None }, [logger]) + React.useEffect0(() => { + let handleMetaDataPostMessage = (ev: Window.event) => { + let json = ev.data->Utils.safeParse + let dict = json->Utils.getDictFromJson + + if dict->Dict.get("metadata")->Option.isSome { + let metadata = dict->Utils.getJsonObjectFromDict("metadata") + let config = metadata->Utils.getDictFromJson->Dict.get("config") + + switch config { + | Some(config) => { + let config = CardTheme.itemToObjMapper( + config->Utils.getDictFromJson, + DefaultTheme.default, + DefaultTheme.defaultRules, + logger, + ) + + CardUtils.generateFontsLink(config.fonts) + let dict = config.appearance.rules->Utils.getDictFromJson + if dict->Dict.toArray->Array.length > 0 { + Utils.generateStyleSheet("", dict, "mystyle") + } + } + | None => () + } + } + } + Window.addEventListener("message", handleMetaDataPostMessage) + Some(() => Window.removeEventListener("message", handleMetaDataPostMessage)) + }) + let renderFullscreen = switch paymentMode { | "paymentMethodCollect" => diff --git a/src/CardTheme.res b/src/CardTheme.res index 28aa2a226..c5cd8eb1d 100644 --- a/src/CardTheme.res +++ b/src/CardTheme.res @@ -3,7 +3,7 @@ open Utils open ErrorUtils let getTheme = (val, logger) => { - switch val { + switch val->String.toLowerCase { | "default" => Default | "brutal" => Brutal | "midnight" => Midnight @@ -360,7 +360,7 @@ let getAppearance = ( variables: getVariables("variables", json, default, logger), rules: mergeJsons(rulesJson, getJsonObjectFromDict(json, "rules")), innerLayout: getWarningString(json, "innerLayout", "spaced", ~logger)->getInnerLayout, - labels: switch getWarningString(json, "labels", "above", ~logger) { + labels: switch getWarningString(json, "labels", "above", ~logger)->String.toLowerCase { | "above" => Above | "floating" => Floating | "none" => Never diff --git a/src/CardUtils.res b/src/CardUtils.res index 9341d889d..e917851b9 100644 --- a/src/CardUtils.res +++ b/src/CardUtils.res @@ -424,7 +424,7 @@ let cvcNumberInRange = (val, cardBrand) => { }) cvcLengthInRange } -let genreateFontsLink = (fonts: array) => { +let generateFontsLink = (fonts: array) => { if fonts->Array.length > 0 { fonts ->Array.map(item => diff --git a/src/Components/AddBankAccount.res b/src/Components/AddBankAccount.res index b89e379a2..d49f5787e 100644 --- a/src/Components/AddBankAccount.res +++ b/src/Components/AddBankAccount.res @@ -6,7 +6,7 @@ module ToolTip = { let {themeObj} = Recoil.useRecoilValueFromAtom(configAtom)