Bug: [ENHANCEMENT] Payment link enhancements



Payment link flows to be updated, below is a list of enhancements -

**UI**
- Check the existing UI on Windows based browsers, and ensure it's rendered as expected

**Flows**
- In case `skip_status_screen` is true, re-opening the payment link on a terminal status should redirect to end URL (current behavior is to display the status screen)
- In case a payment link was opened in any state other than `requires_payment_method`, handle the state correctly
    - for `requires_customer_action`, payment link should resume the journey where the user abandoned it


diff --git a/api-reference-v2/openapi_spec.json b/api-reference-v2/openapi_spec.json
index cd8b8458364..4ca9f57efb3 100644
--- a/api-reference-v2/openapi_spec.json
+++ b/api-reference-v2/openapi_spec.json
@@ -12587,6 +12587,14 @@
                 "type": "string",
                 "description": "The url for Qr code given by the connector"
               },
+              "display_text": {
+                "type": "string",
+                "nullable": true
+              },
+              "border_color": {
+                "type": "string",
+                "nullable": true
+              },
               "type": {
                 "type": "string",
                 "enum": [
@@ -13983,6 +13991,28 @@
             "type": "string",
             "description": "Custom background colour for the payment link",
             "nullable": true
+          },
+          "sdk_ui_rules": {
+            "type": "object",
+            "description": "SDK configuration rules",
+            "additionalProperties": {
+              "type": "object",
+              "additionalProperties": {
+                "type": "string"
+              }
+            },
+            "nullable": true
+          },
+          "payment_link_ui_rules": {
+            "type": "object",
+            "description": "Payment link configuration rules",
+            "additionalProperties": {
+              "type": "object",
+              "additionalProperties": {
+                "type": "string"
+              }
+            },
+            "nullable": true
           }
         }
       },
@@ -14098,6 +14128,28 @@
             "type": "string",
             "description": "Custom background colour for the payment link",
             "nullable": true
+          },
+          "sdk_ui_rules": {
+            "type": "object",
+            "description": "SDK configuration rules",
+            "additionalProperties": {
+              "type": "object",
+              "additionalProperties": {
+                "type": "string"
+              }
+            },
+            "nullable": true
+          },
+          "payment_link_ui_rules": {
+            "type": "object",
+            "description": "Payment link configuration rules",
+            "additionalProperties": {
+              "type": "object",
+              "additionalProperties": {
+                "type": "string"
+              }
+            },
+            "nullable": true
           }
         }
       },
@@ -15301,13 +15353,29 @@
             "description": "The return url to which the user should be redirected to",
             "nullable": true
           },
-          "associated_payment": {
+          "next_action": {
             "allOf": [
               {
-                "$ref": "#/components/schemas/PaymentsResponse"
+                "$ref": "#/components/schemas/NextActionData"
               }
             ],
             "nullable": true
+          },
+          "authentication_details": {
+            "allOf": [
+              {
+                "$ref": "#/components/schemas/AuthenticationDetails"
+              }
+            ],
+            "nullable": true
+          },
+          "associated_payment_methods": {
+            "type": "array",
+            "items": {
+              "$ref": "#/components/schemas/id_type.GlobalPaymentMethodId"
+            },
+            "description": "The payment method that was created using this payment method session",
+            "nullable": true
           }
         }
       },
@@ -15542,60 +15610,6 @@
         },
         "additionalProperties": false
       },
-      "PaymentMethodsSessionResponse": {
-        "type": "object",
-        "required": [
-          "id",
-          "customer_id",
-          "expires_at",
-          "client_secret"
-        ],
-        "properties": {
-          "id": {
-            "type": "string",
-            "example": "12345_pms_01926c58bc6e77c09e809964e72af8c8"
-          },
-          "customer_id": {
-            "type": "string",
-            "description": "The customer id for which the payment methods session is to be created",
-            "example": "12345_cus_01926c58bc6e77c09e809964e72af8c8"
-          },
-          "billing": {
-            "allOf": [
-              {
-                "$ref": "#/components/schemas/Address"
-              }
-            ],
-            "nullable": true
-          },
-          "psp_tokenization": {
-            "allOf": [
-              {
-                "$ref": "#/components/schemas/PspTokenization"
-              }
-            ],
-            "nullable": true
-          },
-          "network_tokenization": {
-            "allOf": [
-              {
-                "$ref": "#/components/schemas/NetworkTokenization"
-              }
-            ],
-            "nullable": true
-          },
-          "expires_at": {
-            "type": "string",
-            "format": "date-time",
-            "description": "The iso timestamp when the session will expire\nTrying to retrieve the session or any operations on the session after this time will result in an error",
-            "example": "2023-01-18T11:04:09.922Z"
-          },
-          "client_secret": {
-            "type": "string",
-            "description": "Client Secret"
-          }
-        }
-      },
       "PaymentMethodsSessionUpdateRequest": {
         "type": "object",
         "properties": {
diff --git a/crates/api_models/src/admin.rs b/crates/api_models/src/admin.rs
index 5d31ea70994..d5a4d89910b 100644
--- a/crates/api_models/src/admin.rs
+++ b/crates/api_models/src/admin.rs
@@ -2810,6 +2810,10 @@ pub struct PaymentLinkConfigRequest {
     pub payment_button_text_colour: Option<String>,
     /// Custom background colour for the payment link
     pub background_colour: Option<String>,
+    /// SDK configuration rules
+    pub sdk_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
+    /// Payment link configuration rules
+    pub payment_link_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
 }
 
 #[derive(Clone, Debug, serde::Deserialize, serde::Serialize, PartialEq, ToSchema)]
@@ -2891,6 +2895,10 @@ pub struct PaymentLinkConfig {
     pub payment_button_text_colour: Option<String>,
     /// Custom background colour for the payment link
     pub background_colour: Option<String>,
+    /// SDK configuration rules
+    pub sdk_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
+    /// Payment link configuration rules
+    pub payment_link_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
 }
 
 #[derive(Debug, Clone, serde::Serialize, serde::Deserialize, PartialEq, Eq)]
diff --git a/crates/api_models/src/payments.rs b/crates/api_models/src/payments.rs
index 12da310ac61..813408da0ea 100644
--- a/crates/api_models/src/payments.rs
+++ b/crates/api_models/src/payments.rs
@@ -7831,6 +7831,8 @@ pub struct PaymentLinkDetails {
     pub payment_button_colour: Option<String>,
     pub payment_button_text_colour: Option<String>,
     pub background_colour: Option<String>,
+    pub sdk_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
+    pub payment_link_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
 }
 
 #[derive(Debug, serde::Serialize, Clone)]
@@ -7846,6 +7848,8 @@ pub struct SecurePaymentLinkDetails {
     pub payment_button_colour: Option<String>,
     pub payment_button_text_colour: Option<String>,
     pub background_colour: Option<String>,
+    pub sdk_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
+    pub payment_link_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
 }
 
 #[derive(Debug, serde::Serialize)]
diff --git a/crates/diesel_models/src/business_profile.rs b/crates/diesel_models/src/business_profile.rs
index 744193bf51e..44f32c6eb4b 100644
--- a/crates/diesel_models/src/business_profile.rs
+++ b/crates/diesel_models/src/business_profile.rs
@@ -644,6 +644,8 @@ pub struct PaymentLinkConfigRequest {
     pub skip_status_screen: Option<bool>,
     pub payment_button_text_colour: Option<String>,
     pub background_colour: Option<String>,
+    pub sdk_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
+    pub payment_link_ui_rules: Option<HashMap<String, HashMap<String, String>>>,
 }
 
 #[derive(Clone, Debug, serde::Deserialize, serde::Serialize, PartialEq)]
diff --git a/crates/diesel_models/src/payment_intent.rs b/crates/diesel_models/src/payment_intent.rs
index a2b3c406a2a..8845a92ba6a 100644
--- a/crates/diesel_models/src/payment_intent.rs
+++ b/crates/diesel_models/src/payment_intent.rs
@@ -187,6 +187,12 @@ pub struct PaymentLinkConfigRequestForPayments {
     pub payment_button_text_colour: Option<String>,
     /// Custom background colour for the payment link
     pub background_colour: Option<String>,
+    /// SDK configuration rules
+    pub sdk_ui_rules:
+        Option<std::collections::HashMap<String, std::collections::HashMap<String, String>>>,
+    /// Payment link configuration rules
+    pub payment_link_ui_rules:
+        Option<std::collections::HashMap<String, std::collections::HashMap<String, String>>>,
 }
 
 common_utils::impl_to_sql_from_sql_json!(PaymentLinkConfigRequestForPayments);
diff --git a/crates/hyperswitch_domain_models/src/lib.rs b/crates/hyperswitch_domain_models/src/lib.rs
index c97753a6dc0..2d2a4413afc 100644
--- a/crates/hyperswitch_domain_models/src/lib.rs
+++ b/crates/hyperswitch_domain_models/src/lib.rs
@@ -412,6 +412,8 @@ impl ApiModelToDieselModelConvertor<api_models::admin::PaymentLinkConfigRequest>
             skip_status_screen: item.skip_status_screen,
             background_colour: item.background_colour,
             payment_button_text_colour: item.payment_button_text_colour,
+            sdk_ui_rules: item.sdk_ui_rules,
+            payment_link_ui_rules: item.payment_link_ui_rules,
         }
     }
     fn convert_back(self) -> api_models::admin::PaymentLinkConfigRequest {
@@ -433,6 +435,8 @@ impl ApiModelToDieselModelConvertor<api_models::admin::PaymentLinkConfigRequest>
             skip_status_screen,
             background_colour,
             payment_button_text_colour,
+            sdk_ui_rules,
+            payment_link_ui_rules,
         } = self;
         api_models::admin::PaymentLinkConfigRequest {
             theme,
@@ -458,6 +462,8 @@ impl ApiModelToDieselModelConvertor<api_models::admin::PaymentLinkConfigRequest>
             skip_status_screen,
             background_colour,
             payment_button_text_colour,
+            sdk_ui_rules,
+            payment_link_ui_rules,
         }
     }
 }
diff --git a/crates/router/src/core/payment_link.rs b/crates/router/src/core/payment_link.rs
index e62d9946416..292f582df9a 100644
--- a/crates/router/src/core/payment_link.rs
+++ b/crates/router/src/core/payment_link.rs
@@ -135,6 +135,8 @@ pub async fn form_payment_link_data(
                 skip_status_screen: None,
                 background_colour: None,
                 payment_button_text_colour: None,
+                sdk_ui_rules: None,
+                payment_link_ui_rules: None,
             }
         };
 
@@ -286,6 +288,8 @@ pub async fn form_payment_link_data(
         skip_status_screen: payment_link_config.skip_status_screen,
         background_colour: payment_link_config.background_colour.clone(),
         payment_button_text_colour: payment_link_config.payment_button_text_colour.clone(),
+        sdk_ui_rules: payment_link_config.sdk_ui_rules.clone(),
+        payment_link_ui_rules: payment_link_config.payment_link_ui_rules.clone(),
     };
 
     Ok((
@@ -342,6 +346,8 @@ pub async fn initiate_secure_payment_link_flow(
                 skip_status_screen: payment_link_config.skip_status_screen,
                 background_colour: payment_link_config.background_colour,
                 payment_button_text_colour: payment_link_config.payment_button_text_colour,
+                sdk_ui_rules: payment_link_config.sdk_ui_rules,
+                payment_link_ui_rules: payment_link_config.payment_link_ui_rules,
             };
             let js_script = format!(
                 "window.__PAYMENT_DETAILS = {}",
@@ -653,6 +659,8 @@ pub fn get_payment_link_config_based_on_priority(
         skip_status_screen,
         background_colour,
         payment_button_text_colour,
+        sdk_ui_rules,
+        payment_link_ui_rules,
     ) = get_payment_link_config_value!(
         payment_create_link_config,
         business_theme_configs,
@@ -664,7 +672,9 @@ pub fn get_payment_link_config_based_on_priority(
         (payment_button_colour),
         (skip_status_screen),
         (background_colour),
-        (payment_button_text_colour)
+        (payment_button_text_colour),
+        (sdk_ui_rules),
+        (payment_link_ui_rules),
     );
 
     let payment_link_config =
@@ -690,6 +700,8 @@ pub fn get_payment_link_config_based_on_priority(
             payment_button_colour,
             background_colour,
             payment_button_text_colour,
+            sdk_ui_rules,
+            payment_link_ui_rules,
         };
 
     Ok((payment_link_config, domain_name))
@@ -798,6 +810,8 @@ pub async fn get_payment_link_status(
             skip_status_screen: None,
             background_colour: None,
             payment_button_text_colour: None,
+            sdk_ui_rules: None,
+            payment_link_ui_rules: None,
         }
     };
 
diff --git a/crates/router/src/core/payment_link/payment_link_initiate/payment_link.js b/crates/router/src/core/payment_link/payment_link_initiate/payment_link.js
index 811ae799d0f..5b8267c57a9 100644
--- a/crates/router/src/core/payment_link/payment_link_initiate/payment_link.js
+++ b/crates/router/src/core/payment_link/payment_link_initiate/payment_link.js
@@ -231,8 +231,8 @@ function boot() {
     link.type = "image/x-icon";
     document.head.appendChild(link);
   }
-  // Render UI
 
+  // Render UI
   if (paymentDetails.display_sdk_only) {
     renderSDKHeader(paymentDetails);
     renderBranding(paymentDetails);
@@ -247,7 +247,6 @@ function boot() {
     renderSDKHeader(paymentDetails);
   }
 
-
   // Deal w loaders
   show("#sdk-spinner");
   hide("#page-spinner");
@@ -256,6 +255,12 @@ function boot() {
   // Add event listeners
   initializeEventListeners(paymentDetails);
 
+  // Update payment link styles
+  var paymentLinkUiRules = paymentDetails.payment_link_ui_rules;
+  if (paymentLinkUiRules !== null && typeof paymentLinkUiRules === "object" && Object.getPrototypeOf(paymentLinkUiRules) === Object.prototype) {
+    updatePaymentLinkUi(paymentLinkUiRules);
+  }
+
   // Initialize SDK
   // @ts-ignore
   if (window.Hyper) {
@@ -461,7 +466,7 @@ function handleSubmit(e) {
         window.top.location.href = url.toString();
       } else {
         redirectToStatus();
-    }
+      }
     })
     .catch(function (error) {
       console.error("Error confirming payment_intent", error);
@@ -801,7 +806,7 @@ function renderBranding(paymentDetails) {
  *    - Renders background image in the payment details section
  * @param {PaymentDetails} paymentDetails 
  */
-function renderBackgroundImage(paymentDetails)  {
+function renderBackgroundImage(paymentDetails) {
   var backgroundImage = paymentDetails.background_image;
   if (typeof backgroundImage === "object" && backgroundImage !== null) {
     var paymentDetailsNode = document.getElementById("hyper-checkout-details");
@@ -1104,3 +1109,24 @@ function renderSDKHeader(paymentDetails) {
     sdkHeaderNode.append(sdkHeaderItemNode);
   }
 }
+
+/**
+ * Trigger - post UI render
+ * Use - add CSS rules for the payment link
+ * @param {Object} paymentLinkUiRules
+ */
+function updatePaymentLinkUi(paymentLinkUiRules) {
+  Object.keys(paymentLinkUiRules).forEach(function (selector) {
+    try {
+      var node = document.querySelector(selector);
+      if (node instanceof HTMLElement) {
+        var styles = paymentLinkUiRules[selector];
+        Object.keys(styles).forEach(function (property) {
+          node.style[property] = styles[property];
+        });
+      }
+    } catch (error) {
+      console.error("Failed to apply styles to selector", selector, error);
+    }
+  })
+}
\ No newline at end of file
diff --git a/crates/router/src/core/payment_link/payment_link_initiate/payment_link_initiator.js b/crates/router/src/core/payment_link/payment_link_initiate/payment_link_initiator.js
index 6abe5f7d5b2..ca6a944baaa 100644
--- a/crates/router/src/core/payment_link/payment_link_initiate/payment_link_initiator.js
+++ b/crates/router/src/core/payment_link/payment_link_initiate/payment_link_initiator.js
@@ -10,7 +10,8 @@
 function initializeSDK() {
   // @ts-ignore
   var paymentDetails = window.__PAYMENT_DETAILS;
-  var client_secret = paymentDetails.client_secret;
+  var clientSecret = paymentDetails.client_secret;
+  var sdkUiRules = paymentDetails.sdk_ui_rules;
   var appearance = {
     variables: {
       colorPrimary: paymentDetails.theme || "rgb(0, 109, 249)",
@@ -24,6 +25,9 @@ function initializeSDK() {
       colorBackground: "rgb(255, 255, 255)",
     },
   };
+  if (sdkUiRules !== null && typeof sdkUiRules === "object" && Object.getPrototypeOf(sdkUiRules) === Object.prototype) {
+    appearance.rules = sdkUiRules;
+  }
   // @ts-ignore
   hyper = window.Hyper(pub_key, {
     isPreloadEnabled: false,
@@ -37,12 +41,12 @@ function initializeSDK() {
   // @ts-ignore
   widgets = hyper.widgets({
     appearance: appearance,
-    clientSecret: client_secret,
+    clientSecret: clientSecret,
     locale: paymentDetails.locale,
   });
   var type =
     paymentDetails.sdk_layout === "spaced_accordion" ||
-    paymentDetails.sdk_layout === "accordion"
+      paymentDetails.sdk_layout === "accordion"
       ? "accordion"
       : paymentDetails.sdk_layout;
   var hideCardNicknameField = paymentDetails.hide_card_nickname_field;
diff --git a/crates/router/src/core/payment_link/payment_link_initiate/secure_payment_link_initiator.js b/crates/router/src/core/payment_link/payment_link_initiate/secure_payment_link_initiator.js
index a8a00e4de9d..9b5a144d29a 100644
--- a/crates/router/src/core/payment_link/payment_link_initiate/secure_payment_link_initiator.js
+++ b/crates/router/src/core/payment_link/payment_link_initiate/secure_payment_link_initiator.js
@@ -31,7 +31,8 @@ if (!isFramed) {
   function initializeSDK() {
     // @ts-ignore
     var paymentDetails = window.__PAYMENT_DETAILS;
-    var client_secret = paymentDetails.client_secret;
+    var clientSecret = paymentDetails.client_secret;
+    var sdkUiRules = paymentDetails.sdk_ui_rules;
     var appearance = {
       variables: {
         colorPrimary: paymentDetails.theme || "rgb(0, 109, 249)",
@@ -45,6 +46,9 @@ if (!isFramed) {
         colorBackground: "rgb(255, 255, 255)",
       },
     };
+    if (sdkUiRules !== null && typeof sdkUiRules === "object" && Object.getPrototypeOf(sdkUiRules) === Object.prototype) {
+      appearance.rules = sdkUiRules;
+    }
     // @ts-ignore
     hyper = window.Hyper(pub_key, {
       isPreloadEnabled: false,
@@ -58,12 +62,12 @@ if (!isFramed) {
     // @ts-ignore
     widgets = hyper.widgets({
       appearance: appearance,
-      clientSecret: client_secret,
+      clientSecret: clientSecret,
       locale: paymentDetails.locale,
     });
     var type =
       paymentDetails.sdk_layout === "spaced_accordion" ||
-      paymentDetails.sdk_layout === "accordion"
+        paymentDetails.sdk_layout === "accordion"
         ? "accordion"
         : paymentDetails.sdk_layout;
 
diff --git a/crates/router/src/core/payments/transformers.rs b/crates/router/src/core/payments/transformers.rs
index 12483aac8e2..eb0f246fdcb 100644
--- a/crates/router/src/core/payments/transformers.rs
+++ b/crates/router/src/core/payments/transformers.rs
@@ -4431,6 +4431,8 @@ impl ForeignFrom<api_models::admin::PaymentLinkConfigRequest>
             skip_status_screen: config.skip_status_screen,
             background_colour: config.background_colour,
             payment_button_text_colour: config.payment_button_text_colour,
+            sdk_ui_rules: config.sdk_ui_rules,
+            payment_link_ui_rules: config.payment_link_ui_rules,
         }
     }
 }
@@ -4499,6 +4501,8 @@ impl ForeignFrom<diesel_models::PaymentLinkConfigRequestForPayments>
             skip_status_screen: config.skip_status_screen,
             background_colour: config.background_colour,
             payment_button_text_colour: config.payment_button_text_colour,
+            sdk_ui_rules: config.sdk_ui_rules,
+            payment_link_ui_rules: config.payment_link_ui_rules,
         }
     }
 }
diff --git a/crates/router/src/routes/admin.rs b/crates/router/src/routes/admin.rs
index 9557aabbe81..a112be46188 100644
--- a/crates/router/src/routes/admin.rs
+++ b/crates/router/src/routes/admin.rs
@@ -456,7 +456,7 @@ pub async fn connector_retrieve(
     let id = path.into_inner();
     let payload = web::Json(admin::MerchantConnectorId { id: id.clone() }).into_inner();
 
-    api::server_wrap(
+    Box::pin(api::server_wrap(
         flow,
         state,
         &req,
@@ -477,7 +477,7 @@ pub async fn connector_retrieve(
             req.headers(),
         ),
         api_locking::LockAction::NotApplicable,
-    )
+    ))
     .await
 }
 
@@ -491,7 +491,7 @@ pub async fn connector_list(
     let flow = Flow::MerchantConnectorsList;
     let profile_id = path.into_inner();
 
-    api::server_wrap(
+    Box::pin(api::server_wrap(
         flow,
         state,
         &req,
@@ -507,7 +507,7 @@ pub async fn connector_list(
             req.headers(),
         ),
         api_locking::LockAction::NotApplicable,
-    )
+    ))
     .await
 }
 
diff --git a/crates/router/src/routes/ephemeral_key.rs b/crates/router/src/routes/ephemeral_key.rs
index 92b5d667daa..64b46eb2f55 100644
--- a/crates/router/src/routes/ephemeral_key.rs
+++ b/crates/router/src/routes/ephemeral_key.rs
@@ -64,7 +64,7 @@ pub async fn client_secret_create(
 ) -> HttpResponse {
     let flow = Flow::EphemeralKeyCreate;
     let payload = json_payload.into_inner();
-    api::server_wrap(
+    Box::pin(api::server_wrap(
         flow,
         state,
         &req,
@@ -80,7 +80,7 @@ pub async fn client_secret_create(
         },
         &auth::HeaderAuth(auth::ApiKeyAuth),
         api_locking::LockAction::NotApplicable,
-    )
+    ))
     .await
 }
 
@@ -93,7 +93,7 @@ pub async fn client_secret_delete(
 ) -> HttpResponse {
     let flow = Flow::EphemeralKeyDelete;
     let payload = path.into_inner();
-    api::server_wrap(
+    Box::pin(api::server_wrap(
         flow,
         state,
         &req,
@@ -101,6 +101,6 @@ pub async fn client_secret_delete(
         |state, _: auth::AuthenticationData, req, _| helpers::delete_client_secret(state, req),
         &auth::HeaderAuth(auth::ApiKeyAuth),
         api_locking::LockAction::NotApplicable,
-    )
+    ))
     .await
 }
diff --git a/crates/router/src/routes/verification.rs b/crates/router/src/routes/verification.rs
index d89f3c65cbe..31e7638b3ef 100644
--- a/crates/router/src/routes/verification.rs
+++ b/crates/router/src/routes/verification.rs
@@ -53,7 +53,7 @@ pub async fn retrieve_apple_pay_verified_domains(
     let merchant_id = &params.merchant_id;
     let mca_id = &params.merchant_connector_account_id;
 
-    api::server_wrap(
+    Box::pin(api::server_wrap(
         flow,
         state,
         &req,
@@ -73,6 +73,6 @@ pub async fn retrieve_apple_pay_verified_domains(
             req.headers(),
         ),
         api_locking::LockAction::NotApplicable,
-    )
+    ))
     .await
 }
diff --git a/crates/router/src/types/transformers.rs b/crates/router/src/types/transformers.rs
index 514ddbbbb50..2b563f5644b 100644
--- a/crates/router/src/types/transformers.rs
+++ b/crates/router/src/types/transformers.rs
@@ -2164,6 +2164,8 @@ impl ForeignFrom<api_models::admin::PaymentLinkConfigRequest>
             payment_button_colour: item.payment_button_colour,
             background_colour: item.background_colour,
             payment_button_text_colour: item.payment_button_text_colour,
+            sdk_ui_rules: item.sdk_ui_rules,
+            payment_link_ui_rules: item.payment_link_ui_rules,
         }
     }
 }
@@ -2192,6 +2194,8 @@ impl ForeignFrom<diesel_models::business_profile::PaymentLinkConfigRequest>
             payment_button_colour: item.payment_button_colour,
             background_colour: item.background_colour,
             payment_button_text_colour: item.payment_button_text_colour,
+            sdk_ui_rules: item.sdk_ui_rules,
+            payment_link_ui_rules: item.payment_link_ui_rules,
         }
     }
 }

## Type of Change
<!-- Put an `x` in the boxes that apply -->

- [ ] Bugfix
- [ ] New feature
- [x] Enhancement
- [ ] Refactoring
- [ ] Dependency updates
- [ ] Documentation
- [ ] CI/CD

## Description
This PR exposes customizations for payment links. Below configs are added -
- SDK UI rules - https://docs.hyperswitch.io/explore-hyperswitch/merchant-controls/integration-guide/web/customization#id-4.-rules
- Payment Link UI rules - similar to SDK UI rules, but for payment link template*

### Additional Changes

- [ ] This PR modifies the API contract
- [ ] This PR modifies the database schema
- [ ] This PR modifies application configuration/environment variables

<!--
Provide links to the files with corresponding changes.

Following are the paths where you can find config files:
1. `config`
2. `crates/router/src/configs`
3. `loadtest/config`
-->


## Motivation and Context
Gives granular control to the payment link consumer for designing their UI.

## How did you test it?
Tested locally.

<details>
    <summary>1. Add a payment link style ID</summary>

cURL

    curl --location --request POST 'http://localhost:8080/account/merchant_1741095653/business_profile/pro_dgzCAaE0KhqCTj6cY5a7' \
        --header 'Content-Type: application/json' \
        --header 'api-key: test_admin' \
        --data '{"payment_link_config":{"allowed_domains":["*"],"business_specific_configs":{"style1":{"enabled_saved_payment_method":true,"theme":"#E71D36","logo":"https://hyperswitch.io/favicon.ico","sdk_ui_rules":{".Label":{"fontWeight":"700 !important","fontSize":"13px !important","color":"#003264 !important","opacity":"1 !important"}},"payment_link_ui_rules":{"#submit":{"color":"#003264","fontWeight":"700","fontSize":"18px","padding":"25px 0","borderRadius":"20px","backgroundColor":"#ffc439"},"#hyper-checkout-sdk":{"backgroundColor":"#003264"}}}}}}'

Response

    {"merchant_id":"merchant_1741095653","profile_id":"pro_dgzCAaE0KhqCTj6cY5a7","profile_name":"IN_default","return_url":"https://google.com/success","enable_payment_response_hash":true,"payment_response_hash_key":"fVkaUtGhpJbDbwJ6bkDO1MX6yRgCNlJPSyaaMkOfe8izhPgWUGS8mdP8p95t5gqp","redirect_to_merchant_with_http_post":false,"webhook_details":{"webhook_version":"1.0.1","webhook_username":"random","webhook_password":"pass","webhook_url":"https://webhook.site/c5368f5d-882b-4d3a-b5be-f372294b6146","payment_created_enabled":true,"payment_succeeded_enabled":true,"payment_failed_enabled":true},"metadata":null,"routing_algorithm":null,"intent_fulfillment_time":900,"frm_routing_algorithm":null,"payout_routing_algorithm":null,"applepay_verified_domains":null,"session_expiry":900,"payment_link_config":{"domain_name":null,"theme":"#1A1A1A","logo":"https://hyperswitch.io/favicon.ico","seller_name":null,"sdk_layout":null,"display_sdk_only":null,"enabled_saved_payment_method":true,"hide_card_nickname_field":null,"show_card_form_by_default":null,"transaction_details":null,"background_image":null,"details_layout":null,"payment_button_text":"Proceed to Payment!","custom_message_for_card_terms":"Hello","payment_button_colour":null,"skip_status_screen":null,"payment_button_text_colour":null,"background_colour":null,"sdk_ui_rules":{".Label":{"fontWeight":"700 !important","fontSize":"13px !important","opacity":"1 !important","backgroundColor":"red !important","color":"#003264 !important"}},"payment_link_ui_rules":null,"business_specific_configs":{"style2":{"theme":"#1A1A1A","logo":"https://hyperswitch.io/favicon.ico","seller_name":null,"sdk_layout":null,"display_sdk_only":null,"enabled_saved_payment_method":true,"hide_card_nickname_field":null,"show_card_form_by_default":null,"transaction_details":null,"background_image":null,"details_layout":null,"payment_button_text":null,"custom_message_for_card_terms":null,"payment_button_colour":null,"skip_status_screen":null,"payment_button_text_colour":null,"background_colour":null,"sdk_ui_rules":null,"payment_link_ui_rules":null},"style1":{"theme":"#E71D36","logo":"https://hyperswitch.io/favicon.ico","seller_name":null,"sdk_layout":null,"display_sdk_only":null,"enabled_saved_payment_method":true,"hide_card_nickname_field":null,"show_card_form_by_default":null,"transaction_details":null,"background_image":null,"details_layout":null,"payment_button_text":null,"custom_message_for_card_terms":null,"payment_button_colour":null,"skip_status_screen":null,"payment_button_text_colour":null,"background_colour":null,"sdk_ui_rules":{".Label":{"color":"#003264 !important","opacity":"1 !important","fontWeight":"700 !important","fontSize":"13px !important"}},"payment_link_ui_rules":{"#submit":{"color":"#003264","fontSize":"18px","backgroundColor":"#ffc439","borderRadius":"20px","padding":"25px 0","fontWeight":"700"},"#hyper-checkout-sdk":{"backgroundColor":"#003264"}}}},"allowed_domains":["*"],"branding_visibility":null},"authentication_connector_details":null,"use_billing_as_payment_method_billing":true,"extended_card_info_config":null,"collect_shipping_details_from_wallet_connector":false,"collect_billing_details_from_wallet_connector":false,"always_collect_shipping_details_from_wallet_connector":false,"always_collect_billing_details_from_wallet_connector":false,"is_connector_agnostic_mit_enabled":true,"payout_link_config":null,"outgoing_webhook_custom_http_headers":null,"tax_connector_id":null,"is_tax_connector_enabled":false,"is_network_tokenization_enabled":true,"is_auto_retries_enabled":false,"max_auto_retries_enabled":null,"always_request_extended_authorization":null,"is_click_to_pay_enabled":true,"authentication_product_ids":null,"card_testing_guard_config":{"card_ip_blocking_status":"disabled","card_ip_blocking_threshold":3,"guest_user_card_blocking_status":"disabled","guest_user_card_blocking_threshold":10,"customer_id_blocking_status":"disabled","customer_id_blocking_threshold":5,"card_testing_guard_expiry":3600},"is_clear_pan_retries_enabled":false}

</details>

<details>
    <summary>2. Create a payment link</summary>

cURL

    curl --location --request POST 'http://localhost:8080/payments' \
        --header 'Content-Type: application/json' \
        --header 'Accept: application/json' \
        --header 'api-key: dev_R70SBQ7gQzMiqsCrbSGMBTEtsKbNkgc8sXo5yHgpEA0mvT8BktGLXrn9zPOxLwpf' \
        --data '{"customer_id":"cus_jJuzSZ5cVZ5mgBGGUNYs","profile_id":"pro_dgzCAaE0KhqCTj6cY5a7","customer_acceptance":{"acceptance_type":"online","accepted_at":"1963-05-03T04:07:52.723Z","online":{"ip_address":"127.0.0.1","user_agent":"amet irure esse"}},"amount":100,"currency":"EUR","payment_link":true,"setup_future_usage":"off_session","capture_method":"automatic","session_expiry":100000,"return_url":"https://example.com","payment_link_config_id":"style1"}'

Response

    {"payment_id":"pay_1QLObAU2blLbNSfehTJN","merchant_id":"merchant_1741095653","status":"requires_payment_method","amount":100,"net_amount":100,"shipping_cost":null,"amount_capturable":100,"amount_received":null,"connector":null,"client_secret":"pay_1QLObAU2blLbNSfehTJN_secret_oRqjfv36rG6plNEBHvvQ","created":"2025-03-04T22:10:37.490Z","currency":"EUR","customer_id":"cus_jJuzSZ5cVZ5mgBGGUNYs","customer":{"id":"cus_jJuzSZ5cVZ5mgBGGUNYs","name":"John Nether","email":null,"phone":"6168205362","phone_country_code":"+1"},"description":null,"refunds":null,"disputes":null,"mandate_id":null,"mandate_data":null,"setup_future_usage":"off_session","off_session":null,"capture_on":null,"capture_method":"automatic","payment_method":null,"payment_method_data":null,"payment_token":null,"shipping":null,"billing":null,"order_details":null,"email":null,"name":"John Nether","phone":"6168205362","return_url":"https://example.com/","authentication_type":null,"statement_descriptor_name":null,"statement_descriptor_suffix":null,"next_action":null,"cancellation_reason":null,"error_code":null,"error_message":null,"unified_code":null,"unified_message":null,"payment_experience":null,"payment_method_type":null,"connector_label":null,"business_country":null,"business_label":"default","business_sub_label":null,"allowed_payment_method_types":null,"ephemeral_key":{"customer_id":"cus_jJuzSZ5cVZ5mgBGGUNYs","created_at":1741126237,"expires":1741129837,"secret":"epk_5255cf68bc6947db9fcf59f285eeb37b"},"manual_retry_allowed":null,"connector_transaction_id":null,"frm_message":null,"metadata":null,"connector_metadata":null,"feature_metadata":null,"reference_id":null,"payment_link":{"link":"http://localhost:8080/payment_link/merchant_1741095653/pay_1QLObAU2blLbNSfehTJN?locale=en","secure_link":"http://localhost:8080/payment_link/s/merchant_1741095653/pay_1QLObAU2blLbNSfehTJN?locale=en","payment_link_id":"plink_Uve1VxVAdO7XJAkBQzMg"},"profile_id":"pro_dgzCAaE0KhqCTj6cY5a7","surcharge_details":null,"attempt_count":1,"merchant_decision":null,"merchant_connector_id":null,"incremental_authorization_allowed":null,"authorization_count":null,"incremental_authorizations":null,"external_authentication_details":null,"external_3ds_authentication_attempted":false,"expires_on":"2025-03-06T01:57:17.488Z","fingerprint":null,"browser_info":null,"payment_method_id":null,"payment_method_status":null,"updated":"2025-03-04T22:10:37.496Z","split_payments":null,"frm_metadata":null,"extended_authorization_applied":null,"capture_before":null,"merchant_order_reference_id":null,"order_tax_amount":null,"connector_mandate_id":null,"card_discovery":null}

<img width="646" alt="Screenshot 2025-03-05 at 3 41 38 AM" src="https://github.com/user-attachments/assets/5ceef6f4-e935-463d-904c-6855de2bd4a3" />


</details>


## Checklist
<!-- Put an `x` in the boxes that apply -->

- [x] I formatted the code `cargo +nightly fmt --all`
- [x] I addressed lints thrown by `cargo clippy`
- [x] I reviewed the submitted code
- [ ] I added unit tests for my changes where possible

### Note
**\* - EDIT 1**

