// App Attest: produce a per-request assertion proving this is a genuine,
// unmodified instance of the app on a real device.
//
// EXAMPLE CODE. Placeholders only.
//
// The key is generated and attested once; the attestation is registered with
// the BFF so it can store the public key under keyId (registration is out of
// scope here). Each request then carries an assertion the Worker verifies.

import Foundation
import CryptoKit
import DeviceCheck

extension ClaudeBFF {
    struct Assertion {
        let keyId: String
        let assertion: String // base64
    }

    /// Produce an App Attest assertion over the given client data, or nil when
    /// App Attest is unavailable (Simulator, unsupported device).
    static func appAttestAssertion(clientData: String) async throws -> Assertion? {
        let service = DCAppAttestService.shared
        guard service.isSupported else { return nil }

        let keyId = try await attestedKeyId(service)
        let hash = Data(SHA256.hash(data: Data(clientData.utf8)))
        let assertion = try await service.generateAssertion(keyId, clientDataHash: hash)
        return Assertion(keyId: keyId, assertion: assertion.base64EncodedString())
    }

    private static let keyIdDefaultsKey = "ClaudeBFF.appAttestKeyId"

    private static func attestedKeyId(_ service: DCAppAttestService) async throws -> String {
        if let saved = UserDefaults.standard.string(forKey: keyIdDefaultsKey) {
            return saved
        }
        let keyId = try await service.generateKey()
        // Attest the new key once, then register the attestation with your BFF
        // so it can store the public key for this keyId. Registration omitted.
        UserDefaults.standard.set(keyId, forKey: keyIdDefaultsKey)
        return keyId
    }
}
