Files
kebuu.com/altcha_utils.py
2026-01-19 20:12:50 -05:00

84 lines
2.4 KiB
Python

import hashlib
import hmac
import secrets
import base64
import json
import time
class AltchaChallenge:
"""Self-hosted Altcha challenge generator and verifier."""
def __init__(self, hmac_key=None):
self.hmac_key = hmac_key or secrets.token_hex(32)
def create_challenge(self, max_number=100000):
"""Generate a new Altcha challenge."""
salt = secrets.token_hex(12)
secret_number = secrets.randbelow(max_number) + 1
# Create the challenge string that needs to be solved
challenge_data = f"{salt}{secret_number}"
challenge = hashlib.sha256(challenge_data.encode()).hexdigest()
# Create signature for verification
signature = hmac.new(
self.hmac_key.encode(),
challenge.encode(),
hashlib.sha256
).hexdigest()
return {
"algorithm": "SHA-256",
"challenge": challenge,
"maxnumber": max_number,
"salt": salt,
"signature": signature
}
def verify_solution(self, payload):
"""Verify an Altcha solution payload."""
try:
# Decode base64 payload
decoded = base64.b64decode(payload).decode('utf-8')
data = json.loads(decoded)
algorithm = data.get('algorithm', '')
challenge = data.get('challenge', '')
number = data.get('number', 0)
salt = data.get('salt', '')
signature = data.get('signature', '')
# Verify algorithm
if algorithm.upper() != 'SHA-256':
return False
# Verify signature
expected_signature = hmac.new(
self.hmac_key.encode(),
challenge.encode(),
hashlib.sha256
).hexdigest()
if not hmac.compare_digest(signature, expected_signature):
return False
# Verify the solution
challenge_data = f"{salt}{number}"
computed_challenge = hashlib.sha256(challenge_data.encode()).hexdigest()
return hmac.compare_digest(computed_challenge, challenge)
except Exception:
return False
_altcha_instances = {}
def get_altcha(hmac_key):
"""Get or create an Altcha instance for the given HMAC key."""
if hmac_key not in _altcha_instances:
_altcha_instances[hmac_key] = AltchaChallenge(hmac_key)
return _altcha_instances[hmac_key]