import json
import time
from collections import defaultdict


class Order:
    """A customer order with product, pricing, and shipping info."""

    def __init__(
        self,
        id,
        customer,
        product,
        category,
        quantity,
        price,
        shipping_address,
        metadata,
    ):
        self.id = id
        self.customer = customer
        self.product = product
        self.category = category
        self.quantity = quantity
        self.price = price
        self.shipping_address = shipping_address
        self.metadata = metadata
        self.validated = False
        self.final_price = 0.0


def parse_orders(raw_data):
    """Parse raw dicts into Order objects."""
    orders = []
    for item in raw_data:
        orders.append(
            Order(
                id=item["id"],
                customer=item["customer"],
                product=item["product"],
                category=item["category"],
                quantity=item["quantity"],
                price=item["price"],
                shipping_address=item["shipping_address"],
                metadata=item.get("metadata", {}),
            )
        )
    return orders


def validate_orders(orders):
    """Validate orders and attach audit context for compliance review."""
    valid = []
    for order in orders:
        checks = {
            "price": order.price > 0,
            "quantity": 0 < order.quantity <= 10000,
            "address": bool(order.shipping_address),
        }
        # Audit context — kept on the order for downstream compliance checks
        order._audit = {
            "order_repr": (
                f"Order(id={order.id}, customer={order.customer!r}, "
                f"product={order.product!r}, qty={order.quantity}, "
                f"price={order.price}, addr={order.shipping_address!r}, "
                f"meta={order.metadata!r})"
            ),
            "checks": checks,
            "ts": time.time(),
        }
        if all(checks.values()):
            order.validated = True
            valid.append(order)
    return valid


def compute_pricing(orders):
    """Apply category-based discount pricing."""
    for order in orders:
        discount_pct = 5 if order.quantity >= 10 else 0
        subtotal = round(order.price * order.quantity, 2)
        order.final_price = round(subtotal * (1 - discount_pct / 100), 2)

        # Pricing receipt — stored for invoice generation
        order._receipt = (
            f"Receipt #{order.id}: {order.product} x{order.quantity} "
            f"@ ${order.price} = ${subtotal}"
            f"{f' - {discount_pct}% bulk discount' if discount_pct else ''}"
            f" -> ${order.final_price} [{order.category}]"
        )
    return orders


def build_fulfillment_plan(orders):
    """Generate fulfillment plan with shipping labels for each order."""
    plan = []
    for order in orders:
        label = (
            f"{'=' * 50}\n"
            f"SHIPMENT #{order.id:06d}\n"
            f"Customer: {order.customer}\n"
            f"Ship To:  {order.shipping_address}\n"
            f"Product:  {order.product} x{order.quantity}\n"
            f"Subtotal: ${order.price * order.quantity:.2f}\n"
            f"Total:    ${order.final_price}\n"
            f"Priority: {'EXPRESS' if order.final_price > 500 else 'STANDARD'}\n"
            f"Details:  {json.dumps(order.metadata)}\n"
            f"{'=' * 50}\n"
        )
        plan.append(
            {
                "order_id": order.id,
                "label": label,
                "warehouse": f"WH-{abs(hash(order.shipping_address)) % 5}",
                "priority": "EXPRESS"
                if order.final_price > 500
                else "STANDARD",
            }
        )
    return plan


def generate_summary(orders):
    """Produce per-category summary statistics."""
    by_cat = defaultdict(list)
    for order in orders:
        by_cat[order.category].append(order)

    summary = {}
    for cat, cat_orders in by_cat.items():
        summary[cat] = {
            "count": len(cat_orders),
            "total_revenue": round(sum(o.final_price for o in cat_orders), 2),
            "avg_quantity": round(
                sum(o.quantity for o in cat_orders) / len(cat_orders), 1
            ),
        }
    return summary


def process_orders(raw_data):
    """Main entry point — full order processing pipeline."""
    orders = parse_orders(raw_data)
    valid = validate_orders(orders)
    priced = compute_pricing(valid)
    plan = build_fulfillment_plan(priced)
    summary = generate_summary(priced)
    return {"summary": summary, "plan_size": len(plan)}
