"""Base provider interface."""
from abc import ABC, abstractmethod
from dataclasses import dataclass
from typing import Any, Optional
import time


@dataclass
class OracleData:
    """Data structure for oracle updates."""
    provider: str
    key: str  # e.g., "sentiment:twitter", "price:ETH/USD"
    value: Any  # The actual data
    confidence: float  # 0.0 to 1.0
    timestamp: int  # Unix timestamp
    metadata: Optional[dict] = None

    def to_dict(self) -> dict:
        return {
            "provider": self.provider,
            "key": self.key,
            "value": self.value,
            "confidence": self.confidence,
            "timestamp": self.timestamp,
            "metadata": self.metadata or {},
        }

    def encode_for_chain(self) -> bytes:
        """Encode data for on-chain storage."""
        import json
        return json.dumps(self.to_dict()).encode()


class BaseProvider(ABC):
    """Abstract base class for oracle data providers."""

    name: str = "base"

    @abstractmethod
    async def fetch(self, key: str, **kwargs) -> OracleData:
        """Fetch data from the provider.

        Args:
            key: The data key to fetch (e.g., "ETH/USD", "twitter:nanopy")
            **kwargs: Provider-specific arguments

        Returns:
            OracleData with the fetched value
        """
        pass

    @abstractmethod
    async def validate(self, data: OracleData) -> bool:
        """Validate the fetched data.

        Args:
            data: The data to validate

        Returns:
            True if valid, False otherwise
        """
        pass

    def create_data(
        self,
        key: str,
        value: Any,
        confidence: float = 1.0,
        metadata: Optional[dict] = None,
    ) -> OracleData:
        """Helper to create OracleData."""
        return OracleData(
            provider=self.name,
            key=key,
            value=value,
            confidence=confidence,
            timestamp=int(time.time()),
            metadata=metadata,
        )
