<?php
namespace EasyChat\Library\Commerce;

final class CommerceIdentityRepository
{
    private $db;
    private $prefix;
    private $secret;

    public function __construct($db, string $prefix, string $secret)
    {
        $this->db=$db; $this->prefix=$prefix; $this->secret=trim($secret);
    }

    public function find(int $customer_id,string $provider,string $scope,array $lookup=array()): array
    {
        if ($this->secret==='') return array();
        $q=$this->db->query("SELECT `external_customer_id`,`external_kind`,`evidence`,`confidence`,`email_hash`,`phone_hash` FROM `{$this->prefix}commerce_customer_identities` WHERE `customer_id`=".(int)$customer_id." AND `provider`='".$this->db->escape($provider)."' AND `scope_hash`='".$this->db->escape($this->hash($scope))."' LIMIT 1");
        if (!$q || empty($q->row)) return array();
        $matches=false;
        foreach((array)($lookup['emails']??array())as$email)$matches=$matches||hash_equals((string)$q->row['email_hash'],$this->hash(mb_strtolower(trim((string)$email),'UTF-8')));
        foreach((array)($lookup['phones']??array())as$phone)$matches=$matches||hash_equals((string)$q->row['phone_hash'],$this->hash(preg_replace('/\D+/','',(string)$phone)));
        if(!$matches)return array();
        return array('id'=>(string)$q->row['external_customer_id'],'kind'=>(string)$q->row['external_kind'],'evidence'=>(string)$q->row['evidence'],'confidence'=>(string)$q->row['confidence']);
    }

    public function save(int $customer_id,string $provider,string $scope,array $reference,array $lookup,string $confidence): void
    {
        if ($this->secret==='' || $customer_id<=0 || trim((string)($reference['id']??''))==='' || ($reference['kind']??'')==='guest_contact') return;
        $email=(string)($lookup['emails'][0]??''); $phone=(string)($lookup['phones'][0]??''); $now=date('Y-m-d H:i:s');
        $this->db->query("INSERT INTO `{$this->prefix}commerce_customer_identities` SET `customer_id`=".(int)$customer_id.",`provider`='".$this->db->escape($provider)."',`scope_hash`='".$this->db->escape($this->hash($scope))."',`external_customer_id`='".$this->db->escape((string)$reference['id'])."',`external_kind`='".$this->db->escape((string)$reference['kind'])."',`evidence`='".$this->db->escape((string)($reference['evidence']??''))."',`confidence`='".$this->db->escape($confidence)."',`email_hash`='".$this->db->escape($email!==''?$this->hash(mb_strtolower($email,'UTF-8')):'')."',`phone_hash`='".$this->db->escape($phone!==''?$this->hash(preg_replace('/\D+/','',$phone)):'')."',`verified_at`=".($confidence==='confirmed'?"'{$now}'":'NULL').",`last_seen_at`='{$now}',`date_added`='{$now}',`date_modified`='{$now}' ON DUPLICATE KEY UPDATE `external_customer_id`=VALUES(`external_customer_id`),`external_kind`=VALUES(`external_kind`),`evidence`=VALUES(`evidence`),`confidence`=VALUES(`confidence`),`email_hash`=VALUES(`email_hash`),`phone_hash`=VALUES(`phone_hash`),`verified_at`=COALESCE(VALUES(`verified_at`),`verified_at`),`last_seen_at`=VALUES(`last_seen_at`),`date_modified`=VALUES(`date_modified`)");
    }

    private function hash(string $value): string { return hash_hmac('sha256',$value,$this->secret); }
}
