import os

FIBS = [1,1,2,3,5,8,13,21,34,55,89,144,233,377,610]

class HDGLPool:
    """Global shared vector pool."""
    def __init__(self):
        self.vectors = []

    def add_vector(self, value):
        self.vectors.append(value)
        return len(self.vectors)-1  # index

    def get_vector(self, index):
        return self.vectors[index]

# Encode a file using shared pool
def encode_file(file_path, pool, chunk_size=256):
    vectors_indices = []
    with open(file_path, "rb") as f:
        data = f.read()
    for i in range(0, len(data), chunk_size):
        chunk = data[i:i+chunk_size]
        vec_int = int.from_bytes(chunk, "big")
        fib_delta = FIBS[(i // chunk_size) % len(FIBS)]
        vec_int += fib_delta
        # Check if identical vector already exists
        if vec_int in pool.vectors:
            idx = pool.vectors.index(vec_int)
        else:
            idx = pool.add_vector(vec_int)
        vectors_indices.append(idx)
    return vectors_indices

# Generate covenant for multiple files
def generate_multi_file_covenant(files, pool):
    lines = ["<YOUR_PUBLIC_KEY> OP_CHECKSIGVERIFY"]
    for file_path in files:
        file_vecs = encode_file(file_path, pool)
        for idx in file_vecs:
            v = pool.get_vector(idx)
            lines.append(f"{v} {v} {v} OP_WITHINVERIFY")
    lines.append("OP_CHECKTEMPLATEVERIFY")
    return "\n".join(lines)

# Decode a file from shared pool
def decode_file(vectors_indices, pool, chunk_size=256, output_path="out.bin"):
    bytes_out = bytearray()
    for i, idx in enumerate(vectors_indices):
        vec_int = pool.get_vector(idx)
        fib_delta = FIBS[i % len(FIBS)]
        vec_int -= fib_delta
        chunk_bytes = vec_int.to_bytes(chunk_size, "big")
        bytes_out.extend(chunk_bytes)
    bytes_out = bytes_out.rstrip(b'\x00')
    with open(output_path, "wb") as f:
        f.write(bytes_out)
