#!/usr/bin/env python3
"""
Скрипт верификации розыгрыша — Рандомайзер.ру
Использование: python3 verify.py --draw <DRAW_ID>
               python3 verify.py --file data.json
"""

import hmac
import hashlib
import json
import sys
import argparse
import urllib.request


def draw_winners(seed_hex: str, participant_hashes: list, k: int) -> list:
    seed = bytes.fromhex(seed_hex)
    ids  = sorted(participant_hashes)
    n    = len(ids)

    p_hash = hashlib.sha256(
        json.dumps(ids, separators=(',', ':')).encode()
    ).digest()

    indices  = list(range(n))
    save_idx = [0] * k
    save_val = [0] * k
    save_end = [0] * k
    winners  = []

    for r in range(k):
        active = n - r
        h      = hmac.new(seed, p_hash + r.to_bytes(4, 'big'), hashlib.sha256).digest()
        idx    = int.from_bytes(h, 'big') % active

        winners.append(ids[indices[idx]])

        save_idx[r] = idx
        save_val[r] = indices[idx]
        save_end[r] = indices[active - 1]
        indices[idx] = indices[active - 1]

    return winners


def verify(draw_id: str = None, file_path: str = None) -> bool:
    if file_path:
        with open(file_path, 'r') as f:
            data = json.load(f)
    else:
        url = f"https://randomizer.ru/api/draw/{draw_id}/public"
        try:
            with urllib.request.urlopen(url, timeout=10) as r:
                data = json.loads(r.read())
        except Exception as e:
            print(f"Ошибка загрузки данных: {e}")
            print(f"Скачайте JSON вручную: https://randomizer.ru/draw/{draw_id}/data.json")
            print("Затем запустите: python3 verify.py --file data.json")
            return False

    seed = data.get('seed')
    if not seed:
        print("Ошибка: seed ещё не раскрыт (розыгрыш не завершён).")
        return False

    print("=" * 56)
    print(f"  Розыгрыш: {data['draw_id']}")
    print(f"  Участников: {data['eligible_count']}")
    print(f"  Победителей: {data['winners_count']}")
    print("=" * 56)

    # 1. Проверяем commitment
    commitment = hashlib.sha256(bytes.fromhex(seed)).hexdigest()
    ok1 = commitment == data['seed_commitment']
    print(f"\n{'✓' if ok1 else '✗'} Проверка seed_commitment")
    if not ok1:
        print(f"  Получено:  {commitment}")
        print(f"  Ожидалось: {data['seed_commitment']}")
        print("  ОШИБКА: seed не соответствует опубликованному commitment!")
        return False
    print(f"  SHA-256(seed) = {commitment[:32]}... ✓")

    # 2. Пересчитываем победителей
    print(f"\n{'─' * 56}")
    print("  Пересчёт победителей:")
    winners = draw_winners(seed, data['participant_hashes'], data['winners_count'])
    announced = data.get('winner_hashes', [])

    all_ok = True
    for i, w in enumerate(winners):
        match = i < len(announced) and w == announced[i]
        if not match:
            all_ok = False
        print(f"  {'✓' if match else '✗'} Место {i+1}: {w[:32]}...")

    print(f"\n{'─' * 56}")
    if all_ok:
        print("  ✓ Верификация прошла успешно")
        print("  Победители совпадают с объявленными.")
    else:
        print("  ✗ Верификация не прошла")
        print("  Пересчитанные победители не совпадают с объявленными!")
    print("=" * 56)

    return all_ok


if __name__ == '__main__':
    parser = argparse.ArgumentParser(
        description='Верификация розыгрыша Рандомайзер.ру',
        formatter_class=argparse.RawDescriptionHelpFormatter,
        epilog="""
Примеры:
  python3 verify.py --draw abc123
  python3 verify.py --file data.json
        """
    )
    parser.add_argument('--draw', help='ID розыгрыша (загружает данные с сайта)')
    parser.add_argument('--file', help='Локальный JSON файл с данными розыгрыша')
    args = parser.parse_args()

    if not args.draw and not args.file:
        parser.print_help()
        sys.exit(1)

    success = verify(draw_id=args.draw, file_path=args.file)
    sys.exit(0 if success else 1)
