Bug: fix(dashboard_metadata): Fix prod intent emails



Currently prod intent emails are not going to biz email. Email are working on custom integ, integ main pod and custom sandbox pod with some code changes. Need to check if sandbox main pod is also able to send emails.
diff --git a/config/config.example.toml b/config/config.example.toml
index be0532622bb..a6af984b01f 100644
--- a/config/config.example.toml
+++ b/config/config.example.toml
@@ -375,10 +375,12 @@ wildcard_origin = false                 # If true, allows any origin to make req
 
 # EmailClient configuration. Only applicable when the `email` feature flag is enabled.
 [email]
-sender_email = "example@example.com" # Sender email
-aws_region = ""                      # AWS region used by AWS SES
-allowed_unverified_days = 1          # Number of days the api calls ( with jwt token ) can be made without verifying the email
-active_email_client = "SES"          # The currently active email client
+sender_email = "example@example.com"                 # Sender email
+aws_region = ""                                      # AWS region used by AWS SES
+allowed_unverified_days = 1                          # Number of days the api calls ( with jwt token ) can be made without verifying the email
+active_email_client = "SES"                          # The currently active email client
+recon_recipient_email = "recon@example.com"          # Recipient email for recon request email
+prod_intent_recipient_email = "business@example.com" # Recipient email for prod intent email
 
 # Configuration for aws ses, applicable when the active email client is SES
 [email.aws_ses]
@@ -745,4 +747,4 @@ delete_token_url= ""          # base url to delete token from token service
 check_token_status_url= ""    # base url to check token status from token service
 
 [network_tokenization_supported_connectors]
-connector_list = "cybersource" # Supported connectors for network tokenization
\ No newline at end of file
+connector_list = "cybersource" # Supported connectors for network tokenization
diff --git a/config/deployments/env_specific.toml b/config/deployments/env_specific.toml
index 9bbf137d2ce..62350376271 100644
--- a/config/deployments/env_specific.toml
+++ b/config/deployments/env_specific.toml
@@ -60,6 +60,8 @@ sender_email = "example@example.com" # Sender email
 aws_region = ""                      # AWS region used by AWS SES
 allowed_unverified_days = 1          # Number of days the api calls ( with jwt token ) can be made without verifying the email
 active_email_client = "SES"          # The currently active email client
+recon_recipient_email = "recon@example.com"          # Recipient email for recon request email
+prod_intent_recipient_email = "business@example.com" # Recipient email for prod intent email
 
 # Configuration for aws ses, applicable when the active email client is SES
 [email.aws_ses]
@@ -300,9 +302,6 @@ public = { name = "hyperswitch", base_url = "http://localhost:8080", schema = "p
 [user_auth_methods]
 encryption_key = "user_auth_table_encryption_key" # Encryption key used for encrypting data in user_authentication_methods table
 
-[recipient_emails]
-recon = "recon@example.com"
-
 [network_tokenization_service] # Network Tokenization Service Configuration
 generate_token_url= ""        # base url to generate token
 fetch_token_url= ""           # base url to fetch token
@@ -311,4 +310,4 @@ public_key= ""                # public key to encrypt data for token service
 private_key= ""               # private key to decrypt  response payload from token service
 key_id= ""                    # key id to encrypt data for token service
 delete_token_url= ""          # base url to delete token from token service
-check_token_status_url= ""    # base url to check token status from token service
\ No newline at end of file
+check_token_status_url= ""    # base url to check token status from token service
diff --git a/config/development.toml b/config/development.toml
index f9f1ebc1202..43130cb78f2 100644
--- a/config/development.toml
+++ b/config/development.toml
@@ -301,6 +301,8 @@ sender_email = "example@example.com"
 aws_region = ""
 allowed_unverified_days = 1
 active_email_client = "SES"
+recon_recipient_email = "recon@example.com"
+prod_intent_recipient_email = "business@example.com"
 
 [email.aws_ses]
 email_role_arn = ""
@@ -732,11 +734,8 @@ encryption_key = "A8EF32E029BC3342E54BF2E172A4D7AA43E8EF9D2C3A624A9F04E2EF79DC69
 [locker_based_open_banking_connectors]
 connector_list = ""
 
-[recipient_emails]
-recon = "recon@example.com"
-
 [network_tokenization_supported_card_networks]
 card_networks = "Visa, AmericanExpress, Mastercard"
 
 [network_tokenization_supported_connectors]
-connector_list = "cybersource"
\ No newline at end of file
+connector_list = "cybersource"
diff --git a/config/docker_compose.toml b/config/docker_compose.toml
index 698800f082d..379f491a4f6 100644
--- a/config/docker_compose.toml
+++ b/config/docker_compose.toml
@@ -591,9 +591,6 @@ ach = { country = "US", currency = "USD" }
 [locker_based_open_banking_connectors]
 connector_list = ""
 
-[recipient_emails]
-recon = "recon@example.com"
-
 [network_tokenization_supported_card_networks]
 card_networks = "Visa, AmericanExpress, Mastercard"
 
@@ -609,3 +606,17 @@ check_token_status_url= ""
 
 [network_tokenization_supported_connectors]
 connector_list = "cybersource"
+
+# EmailClient configuration. Only applicable when the `email` feature flag is enabled.
+[email]
+sender_email = "example@example.com"                 # Sender email
+aws_region = ""                                      # AWS region used by AWS SES
+allowed_unverified_days = 1                          # Number of days the api calls ( with jwt token ) can be made without verifying the email
+active_email_client = "SES"                          # The currently active email client
+recon_recipient_email = "recon@example.com"          # Recipient email for recon request email
+prod_intent_recipient_email = "business@example.com" # Recipient email for prod intent email
+
+# Configuration for aws ses, applicable when the active email client is SES
+[email.aws_ses]
+email_role_arn = ""        # The amazon resource name ( arn ) of the role which has permission to send emails
+sts_role_session_name = "" # An identifier for the assumed role session, used to uniquely identify a session.
diff --git a/crates/external_services/src/email.rs b/crates/external_services/src/email.rs
index fc577a012c3..5751de95c12 100644
--- a/crates/external_services/src/email.rs
+++ b/crates/external_services/src/email.rs
@@ -137,6 +137,12 @@ pub struct EmailSettings {
 
     /// The active email client to use
     pub active_email_client: AvailableEmailClients,
+
+    /// Recipient email for recon emails
+    pub recon_recipient_email: pii::Email,
+
+    /// Recipient email for recon emails
+    pub prod_intent_recipient_email: pii::Email,
 }
 
 /// Errors that could occur from EmailClient.
diff --git a/crates/router/src/configs/secrets_transformers.rs b/crates/router/src/configs/secrets_transformers.rs
index 604dce5047c..8c893b88319 100644
--- a/crates/router/src/configs/secrets_transformers.rs
+++ b/crates/router/src/configs/secrets_transformers.rs
@@ -498,7 +498,6 @@ pub(crate) async fn fetch_raw_secrets(
         decision: conf.decision,
         locker_based_open_banking_connectors: conf.locker_based_open_banking_connectors,
         grpc_client: conf.grpc_client,
-        recipient_emails: conf.recipient_emails,
         network_tokenization_supported_card_networks: conf
             .network_tokenization_supported_card_networks,
         network_tokenization_service,
diff --git a/crates/router/src/configs/settings.rs b/crates/router/src/configs/settings.rs
index 7d6dfd26eae..675b8c44e2a 100644
--- a/crates/router/src/configs/settings.rs
+++ b/crates/router/src/configs/settings.rs
@@ -6,7 +6,7 @@ use std::{
 #[cfg(feature = "olap")]
 use analytics::{opensearch::OpenSearchConfig, ReportConfig};
 use api_models::{enums, payment_methods::RequiredFieldInfo};
-use common_utils::{ext_traits::ConfigExt, pii::Email};
+use common_utils::ext_traits::ConfigExt;
 use config::{Environment, File};
 use error_stack::ResultExt;
 #[cfg(feature = "email")]
@@ -122,7 +122,6 @@ pub struct Settings<S: SecretState> {
     pub decision: Option<DecisionConfig>,
     pub locker_based_open_banking_connectors: LockerBasedRecipientConnectorList,
     pub grpc_client: GrpcClientSettings,
-    pub recipient_emails: RecipientMails,
     pub network_tokenization_supported_card_networks: NetworkTokenizationSupportedCardNetworks,
     pub network_tokenization_service: Option<SecretStateContainer<NetworkTokenizationService, S>>,
     pub network_tokenization_supported_connectors: NetworkTokenizationSupportedConnectors,
@@ -941,11 +940,6 @@ pub struct ServerTls {
     pub certificate: PathBuf,
 }
 
-#[derive(Debug, Deserialize, Clone, Default)]
-pub struct RecipientMails {
-    pub recon: Email,
-}
-
 fn deserialize_hashmap_inner<K, V>(
     value: HashMap<String, String>,
 ) -> Result<HashMap<K, HashSet<V>>, String>
diff --git a/crates/router/src/consts/user.rs b/crates/router/src/consts/user.rs
index 1a2b2ef60a4..6ac2b08e6bb 100644
--- a/crates/router/src/consts/user.rs
+++ b/crates/router/src/consts/user.rs
@@ -5,7 +5,6 @@ pub const MAX_NAME_LENGTH: usize = 70;
 /// The max length of company name and merchant should be same
 /// because we are deriving the merchant name from company name
 pub const MAX_COMPANY_NAME_LENGTH: usize = MAX_ALLOWED_MERCHANT_NAME_LENGTH;
-pub const BUSINESS_EMAIL: &str = "neeraj.kumar@juspay.in";
 
 pub const RECOVERY_CODES_COUNT: usize = 8;
 pub const RECOVERY_CODE_LENGTH: usize = 8; // This is without counting the hyphen in between
diff --git a/crates/router/src/core/recon.rs b/crates/router/src/core/recon.rs
index fa9944ee8ee..55ec8cea7a9 100644
--- a/crates/router/src/core/recon.rs
+++ b/crates/router/src/core/recon.rs
@@ -34,7 +34,7 @@ pub async fn send_recon_request(
             .change_context(errors::ApiErrorResponse::InternalServerError)
             .attach_printable("Failed to convert recipient's email to UserEmail")?,
         recipient_email: domain::UserEmail::from_pii_email(
-            state.conf.recipient_emails.recon.clone(),
+            state.conf.email.recon_recipient_email.clone(),
         )
         .change_context(errors::ApiErrorResponse::InternalServerError)
         .attach_printable("Failed to convert recipient's email to UserEmail")?,
diff --git a/crates/router/src/core/user/dashboard_metadata.rs b/crates/router/src/core/user/dashboard_metadata.rs
index 47639fed717..32ad135a7d6 100644
--- a/crates/router/src/core/user/dashboard_metadata.rs
+++ b/crates/router/src/core/user/dashboard_metadata.rs
@@ -484,7 +484,7 @@ async fn insert_metadata(
                             state.conf.proxy.https_url.as_ref(),
                         )
                         .await;
-                    logger::info!(?send_email_result);
+                    logger::info!(prod_intent_email=?send_email_result);
                 }
             }
 
diff --git a/crates/router/src/services/email/types.rs b/crates/router/src/services/email/types.rs
index 35bc9f06d9a..1c4ce79ac8c 100644
--- a/crates/router/src/services/email/types.rs
+++ b/crates/router/src/services/email/types.rs
@@ -413,9 +413,9 @@ pub struct BizEmailProd {
 impl BizEmailProd {
     pub fn new(state: &SessionState, data: ProdIntent) -> UserResult<Self> {
         Ok(Self {
-            recipient_email: (domain::UserEmail::new(
-                consts::user::BUSINESS_EMAIL.to_string().into(),
-            ))?,
+            recipient_email: domain::UserEmail::from_pii_email(
+                state.conf.email.prod_intent_recipient_email.clone(),
+            )?,
             settings: state.conf.clone(),
             subject: "New Prod Intent",
             user_name: data.poc_name.unwrap_or_default().into(),
diff --git a/crates/router/src/utils/user/dashboard_metadata.rs b/crates/router/src/utils/user/dashboard_metadata.rs
index 5814f64f759..3abdfdd3abe 100644
--- a/crates/router/src/utils/user/dashboard_metadata.rs
+++ b/crates/router/src/utils/user/dashboard_metadata.rs
@@ -1,4 +1,4 @@
-use std::{net::IpAddr, str::FromStr};
+use std::{net::IpAddr, ops::Not, str::FromStr};
 
 use actix_web::http::header::HeaderMap;
 use api_models::user::dashboard_metadata::{
@@ -11,6 +11,7 @@ use diesel_models::{
 };
 use error_stack::{report, ResultExt};
 use masking::Secret;
+use router_env::logger;
 
 use crate::{
     core::errors::{UserErrors, UserResult},
@@ -284,8 +285,16 @@ fn not_contains_string(value: &Option<String>, value_to_be_checked: &str) -> boo
 }
 
 pub fn is_prod_email_required(data: &ProdIntent, user_email: String) -> bool {
-    not_contains_string(&data.poc_email, "juspay")
-        && not_contains_string(&data.business_website, "juspay")
-        && not_contains_string(&data.business_website, "hyperswitch")
-        && not_contains_string(&Some(user_email), "juspay")
+    let poc_email_check = not_contains_string(&data.poc_email, "juspay");
+    let business_website_check = not_contains_string(&data.business_website, "juspay")
+        && not_contains_string(&data.business_website, "hyperswitch");
+    let user_email_check = not_contains_string(&Some(user_email), "juspay");
+
+    if (poc_email_check && business_website_check && user_email_check).not() {
+        logger::info!(prod_intent_email = poc_email_check);
+        logger::info!(prod_intent_email = business_website_check);
+        logger::info!(prod_intent_email = user_email_check);
+    }
+
+    poc_email_check && business_website_check && user_email_check
 }
diff --git a/loadtest/config/development.toml b/loadtest/config/development.toml
index ed15e8893bd..82a21f9fc9c 100644
--- a/loadtest/config/development.toml
+++ b/loadtest/config/development.toml
@@ -368,5 +368,15 @@ global_tenant = { schema = "public", redis_key_prefix = "" }
 [multitenancy.tenants]
 public = { name = "hyperswitch", base_url = "http://localhost:8080", schema = "public", redis_key_prefix = "", clickhouse_database = "default"}
 
-[recipient_emails]
-recon = "recon@example.com"
+[email]
+sender_email = "example@example.com"
+aws_region = ""
+allowed_unverified_days = 1
+active_email_client = "SES"
+recon_recipient_email = "recon@example.com"
+prod_intent_recipient_email = "business@example.com"
+
+[email.aws_ses]
+email_role_arn = ""
+sts_role_session_name = ""
+

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

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

## Description
<!-- Describe your changes in detail -->
- This PR add recipient emails for recon and prod_intent under email config.

### Additional Changes

- [ ] This PR modifies the API contract
- [ ] This PR modifies the database schema
- [x] 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`
-->
`config/config.example.toml`
`config/deployments/env_specific.toml`
`config/development.toml`
`config/docker_compose.toml`
`loadtest/config/development.toml`

## Motivation and Context
<!--
Why is this change required? What problem does it solve?
If it fixes an open issue, please link to the issue here.

If you don't have an issue, we'd recommend starting with one first so the PR
can focus on the implementation (unless it is an obvious bug or documentation fix
that will have little conversation).
-->
Closes #5963.

## How did you test it?
<!--
Did you write an integration/unit/API test to verify the code changes?
Or did you test this change manually (provide relevant screenshots)?
-->
```
curl --location 'http://localhost:8080/user/data' \
--header 'Content-Type: application/json' \
--header 'Authorization: ••••••' \
--data '
{
    "ProdIntent": {
        "is_completed": true,
        "legal_business_name": "test",
        "business_label": "test",
        "business_location": "US",
        "display_name": "test",
        "poc_email": "test",
        "business_type": "test",
        "business_identifier": "test",
        "business_website": "test",
        "poc_name": "test",
        "poc_contact": "test",
        "comments": "test"
    }
} 
'
```
The above API should send prod intent email to configured prod intent email.

## 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
