using CashLineERP.Contracts.Privacy;

namespace CashLineERP.Application.Privacy;

public sealed class PrivacyGovernanceService : IPrivacyGovernanceService
{
    public PrivacyGovernanceResponse GetGovernance(string? subjectTypeCode = null)
    {
        var normalizedSubjectTypeCode = NormalizeOptionalCode(subjectTypeCode);
        var notices = Notices
            .Where(notice => normalizedSubjectTypeCode is null
                || string.Equals(notice.SubjectTypeCode, normalizedSubjectTypeCode, StringComparison.OrdinalIgnoreCase))
            .ToArray();
        var purposes = ConsentPurposes
            .Where(purpose => normalizedSubjectTypeCode is null
                || string.Equals(purpose.AppliesTo, "BOTH", StringComparison.OrdinalIgnoreCase)
                || string.Equals(purpose.AppliesTo, normalizedSubjectTypeCode, StringComparison.OrdinalIgnoreCase))
            .ToArray();

        return new PrivacyGovernanceResponse(
            notices,
            purposes,
            DataClassificationRules,
            MaskingRules,
            ThirdPartySharingRules,
            ReadinessControls);
    }

    private static readonly PrivacyNoticeResponse[] Notices =
    [
        new(
            "SUPPLIER",
            "SUPPLIER_PRIVACY_NOTICE",
            "2026.04-MVP",
            "AR-EN",
            "Supplier Portal Privacy Notice",
            "Explains how CashLine uses supplier onboarding, KYC, documents, order, invoice, settlement, notification, and finance-request data for platform operation and controlled third-party processing.",
            true),
        new(
            "CUSTOMER",
            "CUSTOMER_PRIVACY_NOTICE",
            "2026.04-MVP",
            "AR-EN",
            "Customer Portal Privacy Notice",
            "Explains how CashLine uses customer onboarding, KYC, documents, orders, payments, statements, notifications, and finance-request data for platform operation and controlled third-party processing.",
            true)
    ];

    private static readonly ConsentPurposeResponse[] ConsentPurposes =
    [
        new("ONBOARDING_KYC", "Onboarding and KYC processing", "BOTH", true, false, false),
        new("DOCUMENT_STORAGE", "Compliance document storage and lifecycle control", "BOTH", true, true, false),
        new("NOTIFICATIONS", "Operational notifications and status updates", "BOTH", true, true, false),
        new("FINANCE_APPLICATION", "Islamic Finance application and eligibility review", "BOTH", false, true, true),
        new("LENDER_HANDOFF", "Case-based lender sharing after finance request", "BOTH", false, true, true),
        new("TAX_AND_ETA", "Tax, e-invoicing, e-receipt, and authority processing where applicable", "BOTH", false, false, true),
        new("PAYMENT_GATEWAY", "Payment provider processing for collections, refunds, and settlement", "BOTH", false, false, true),
    ];

    private static readonly DataClassificationRuleResponse[] DataClassificationRules =
    [
        new("PARTY_MASTER", "Party master data", "Company profile, contacts, CR, tax card references", "Need-to-know by portal, party, and role", "Keep while relationship is active; archive per legal/accounting rules", true, true),
        new("KYC_COMPLIANCE", "KYC and compliance documents", "National ID, UBO, signatories, tax cards, compliance files", "Compliance-limited vault access", "Retain per compliance and legal requirements", true, true),
        new("PROCUREMENT_COMMERCIAL", "Procurement and commercial data", "RFQs, quotations, bid comparisons, POs, price lists", "Role-based commercial access only", "Operational retention plus controlled archive", false, true),
        new("FINANCE_CASE", "Finance application case file", "Requested amount, purpose, schedules, supporting evidence, lender status", "Finance-case team and approved lender case API only", "Retain through lifecycle plus regulatory obligations", true, true),
        new("PAYMENT_SETTLEMENT", "Payment and settlement data", "Bank details, gateway references, receipts, AP/AR settlements", "Finance-authorized access with masking in reports", "Tax/accounting retention applies", true, true),
        new("AUDIT_CONSENT", "Audit and consent evidence", "Views, exports, shares, approvals, consent, revocation, admin actions", "Security, audit, privacy owner, and privileged governance only", "Retain for governance, dispute, and incident needs", true, false),
        new("INTEGRATION_EVENTS", "Integration event data", "ETA callbacks, payment callbacks, lender handoff logs, outbox/inbox events", "Integration service and operational support access", "Retain for reconciliation and incident traceability", true, true),
    ];

    private static readonly SensitiveFieldMaskingRuleResponse[] MaskingRules =
    [
        new("NATIONAL_ID", "National ID / government ID", "Show last 4 characters only", "Visible unmasked only to compliance-authorized roles"),
        new("BANK_ACCOUNT", "Bank account / IBAN / wallet reference", "Show bank name and last 4 characters only", "Visible unmasked only to finance-authorized roles"),
        new("PHONE", "Mobile and telephone numbers", "Mask middle digits", "Visible unmasked to assigned operations and relationship owners"),
        new("EMAIL", "Email address", "Mask local-part after first two characters", "Visible unmasked to assigned operations and notification services"),
        new("TAX_ID", "Tax registration ID", "Show last 4 characters in non-tax reports", "Visible unmasked to tax/finance-authorized roles"),
        new("DOCUMENT_REFERENCE", "Stored document reference", "Show document type and status, not storage path", "Visible unmasked only through document service authorization"),
    ];

    private static readonly ThirdPartySharingRuleResponse[] ThirdPartySharingRules =
    [
        new("LENDER", "PRE_SCREENING", "Share anonymized or banded indicators only", "No identifiable data before explicit finance request and consent"),
        new("LENDER", "APPLICATION_SUBMITTED", "Share only case-required identifiable fields and documents", "Consent, purpose, case ID, expiry, and audit event required"),
        new("LENDER", "SERVICING_RENEWAL", "Share only agreed performance and covenant indicators", "No raw ERP history or unrestricted export"),
        new("ETA", "TAX_PROCESSING", "Share statutory tax/e-invoicing payloads only", "Gateway isolation, HTTPS, idempotency, callback audit"),
        new("PAYMENT_PROVIDER", "PAYMENT_EXECUTION", "Share payment execution data only", "Gateway adapter, callback validation, settlement reconciliation"),
        new("SCORING_PROVIDER", "FUTURE_CREDIT_SCORING", "Share only approved scoring inputs", "Consent, model version, explainability, and audit trail required"),
    ];

    private static readonly PrivacyReadinessControlResponse[] ReadinessControls =
    [
        new("PRIV-NOTICE", "Versioned privacy notices", "Supplier and customer notices available before onboarding", "Public privacy API and onboarding acceptance record", "IMPLEMENTED_BASELINE"),
        new("PRIV-CONSENT", "Purpose-based consent", "Consent purposes defined for onboarding, finance, notifications, integrations, and third-party sharing", "Consent capture must be linked to party/case/version during transaction implementation", "CONTROL_DEFINED"),
        new("PRIV-MASKING", "Sensitive-field masking", "Mask IDs, bank details, phone, email, tax IDs, and document paths in non-privileged views", "API serializers, reporting exports, and UI views", "CONTROL_DEFINED"),
        new("PRIV-SHARING", "Third-party sharing limits", "Case-based sharing only; no raw ERP or unrestricted lender access", "Integration adapters, lender APIs, ETA/payment adapters", "CONTROL_DEFINED"),
        new("PRIV-EXPORT-AUDIT", "Export auditability", "Report exports must record actor, filter, format, and reason where applicable", "AuditEvent records", "IMPLEMENTED_BASELINE"),
        new("PRIV-RETENTION", "Retention and legal hold", "Retention rules defined per data class", "Archive/purge jobs and legal hold flags", "ROADMAP_CONTROL"),
        new("PRIV-INCIDENT", "Incident and breach workflow", "Incident owner and investigation data pack defined", "Security runbook and audit reports", "ROADMAP_CONTROL"),
    ];

    private static string? NormalizeOptionalCode(string? value) =>
        string.IsNullOrWhiteSpace(value) ? null : value.Trim().ToUpperInvariant();
}
