-- =====================================================================================
-- Admin 商品模块 - 商品统计概况 RPC
-- 位置：docs/sql/30_rpc/product/
-- 对象类型：RPC 函数（SECURITY DEFINER）
-- 版本：v1
-- 依赖：ml_products, ml_orders, ml_browse_history, ak_users
-- =====================================================================================

CREATE OR REPLACE FUNCTION public.rpc_admin_product_stats(
    p_start_time TIMESTAMP WITH TIME ZONE,
    p_end_time TIMESTAMP WITH TIME ZONE
)
RETURNS JSONB
SECURITY DEFINER
SET search_path = public
LANGUAGE plpgsql
AS $$
DECLARE
    v_stats JSONB;
BEGIN
    -- 1. 权限检查
    IF NOT EXISTS (
        SELECT 1 FROM public.ak_users 
        WHERE id = auth.uid() AND role IN ('admin', 'analytics')
    ) THEN
        RAISE EXCEPTION 'Permission denied';
    END IF;

    -- 2. 统计核心指标
    -- 商品浏览量 (PV), 访客数 (UV), 支付件数, 支付金额, 退款件数, 退款金额
    WITH stats AS (
        SELECT
            (SELECT COALESCE(SUM(browse_duration), 0) FROM public.ml_browse_history WHERE created_at BETWEEN p_start_time AND p_end_time) as total_views,
            (SELECT COUNT(DISTINCT user_id) FROM public.ml_browse_history WHERE created_at BETWEEN p_start_time AND p_end_time) as total_visitors,
            (SELECT COALESCE(SUM(quantity), 0) FROM public.ml_order_items oi JOIN public.ml_orders o ON oi.order_id = o.id 
             WHERE o.created_at BETWEEN p_start_time AND p_end_time AND o.order_status NOT IN (1, 5)) as pay_count,
            (SELECT COALESCE(SUM(paid_amount), 0) FROM public.ml_orders 
             WHERE created_at BETWEEN p_start_time AND p_end_time AND order_status NOT IN (1, 5)) as pay_amount,
            (SELECT COUNT(*) FROM public.ml_orders WHERE created_at BETWEEN p_start_time AND p_end_time AND order_status = 7) as refund_count,
            (SELECT COALESCE(SUM(total_amount), 0) FROM public.ml_orders WHERE created_at BETWEEN p_start_time AND p_end_time AND order_status = 7) as refund_amount
    )
    SELECT jsonb_build_object(
        'views', total_views,
        'visitors', total_visitors,
        'pay_count', pay_count,
        'pay_amount', pay_amount,
        'refund_count', refund_count,
        'refund_amount', refund_amount
    ) INTO v_stats FROM stats;

    RETURN v_stats; 
END;
$$;

-- =====================================================================================
-- Admin 商品模块 - 商品排行 RPC
-- =====================================================================================
CREATE OR REPLACE FUNCTION public.rpc_admin_product_ranking(
    p_start_time TIMESTAMP WITH TIME ZONE,
    p_end_time TIMESTAMP WITH TIME ZONE,
    p_sort_by TEXT DEFAULT 'sales', -- views, sales, amount
    p_limit INTEGER DEFAULT 10
)
RETURNS JSONB
SECURITY DEFINER
SET search_path = public
LANGUAGE plpgsql
AS $$
DECLARE
    v_items JSONB;
BEGIN
    -- 1. 权限检查
    IF NOT EXISTS (
        SELECT 1 FROM public.ak_users 
        WHERE id = auth.uid() AND role IN ('admin', 'analytics')
    ) THEN
        RAISE EXCEPTION 'Permission denied';
    END IF;

    -- 2. 获取排行数据
    SELECT jsonb_agg(t) INTO v_items
    FROM (
        SELECT 
            p.id,
            p.name,
            p.main_image_url as image,
            COALESCE(p.view_count, 0) as views,
            (SELECT COUNT(DISTINCT user_id) FROM public.ml_browse_history bh WHERE bh.product_id = p.id AND bh.created_at BETWEEN p_start_time AND p_end_time) as visitors,
            (SELECT COALESCE(SUM(quantity), 0) FROM public.ml_shopping_cart sc WHERE sc.product_id = p.id AND sc.created_at BETWEEN p_start_time AND p_end_time) as cart_count,
            (SELECT COUNT(DISTINCT o.id) FROM public.ml_orders o JOIN public.ml_order_items oi ON o.id = oi.order_id 
             WHERE oi.product_id = p.id AND o.created_at BETWEEN p_start_time AND p_end_time) as order_count,
            (SELECT COALESCE(SUM(oi.quantity), 0) FROM public.ml_order_items oi JOIN public.ml_orders o ON oi.order_id = o.id 
             WHERE oi.product_id = p.id AND o.created_at BETWEEN p_start_time AND p_end_time AND o.order_status NOT IN (1, 5)) as pay_count,
            (SELECT COALESCE(SUM(oi.total_amount), 0) FROM public.ml_order_items oi JOIN public.ml_orders o ON oi.order_id = o.id 
             WHERE oi.product_id = p.id AND o.created_at BETWEEN p_start_time AND p_end_time AND o.order_status NOT IN (1, 5)) as pay_amount,
            (SELECT COUNT(*) FROM public.ml_user_favorites f WHERE f.target_id = p.id AND f.target_type = 1 AND f.created_at BETWEEN p_start_time AND p_end_time) as fav_count
        FROM public.ml_products p
        WHERE p.status != 4
        ORDER BY 
            CASE 
                WHEN p_sort_by = 'views' THEN COALESCE(p.view_count, 0)
                WHEN p_sort_by = 'sales' THEN (
                    SELECT COALESCE(SUM(oi.quantity), 0) FROM public.ml_order_items oi JOIN public.ml_orders o ON oi.order_id = o.id 
                    WHERE oi.product_id = p.id AND o.created_at BETWEEN p_start_time AND p_end_time AND o.order_status NOT IN (1, 5)
                )
                WHEN p_sort_by = 'amount' THEN (
                    SELECT COALESCE(SUM(oi.total_amount), 0) FROM public.ml_order_items oi JOIN public.ml_orders o ON oi.order_id = o.id 
                    WHERE oi.product_id = p.id AND o.created_at BETWEEN p_start_time AND p_end_time AND o.order_status NOT IN (1, 5)
                )
                ELSE COALESCE(p.view_count, 0)
            END DESC
        LIMIT p_limit
    ) t;

    RETURN COALESCE(v_items, '[]'::jsonb);
END;
$$;
