-- =====================================================================================
-- 商城系统数据库迁移脚本 (PostgreSQL + Supabase)
-- 用途: 在现有数据库基础上添加商城相关表和功能
-- 说明: 复用 ak_users 表，新增 ml_ 前缀的商城表
-- 执行方式: 直接在数据库中执行此脚本
-- =====================================================================================

-- 检查必要的扩展
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
CREATE EXTENSION IF NOT EXISTS "pg_stat_statements";
CREATE EXTENSION IF NOT EXISTS "btree_gin";

-- =====================================================================================
-- 1. 创建商城用户扩展表
-- =====================================================================================

-- 商城用户档案表
CREATE TABLE IF NOT EXISTS public.ml_user_profiles (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID UNIQUE NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    user_type INTEGER DEFAULT 1 NOT NULL, -- 1:消费者 2:商家 3:配送员 4:客服 5:管理员
    status INTEGER DEFAULT 1 NOT NULL, -- 1:正常 2:冻结 3:注销 4:待审核
    real_name VARCHAR(100), -- 真实姓名
    id_card VARCHAR(32), -- 身份证号
    business_license VARCHAR(100), -- 营业执照号
    credit_score INTEGER DEFAULT 100, -- 信用分数 0-1000
    verification_status INTEGER DEFAULT 0, -- 认证状态 0:未认证 1:已认证 2:认证失败
    verification_data JSONB DEFAULT '{}', -- 认证相关数据
    preferences JSONB DEFAULT '{}', -- 用户偏好设置
    emergency_contact VARCHAR(200), -- 紧急联系人
    service_areas JSONB, -- 服务区域(配送员)
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_user_type CHECK (user_type IN (1,2,3,4,5)),
    CONSTRAINT chk_ml_user_status CHECK (status IN (1,2,3,4)),
    CONSTRAINT chk_ml_verification_status CHECK (verification_status IN (0,1,2)),
    CONSTRAINT chk_ml_credit_score CHECK (credit_score >= 0 AND credit_score <= 1000)
);

COMMENT ON TABLE public.ml_user_profiles IS '商城用户扩展信息表';

-- 用户地址表
CREATE TABLE IF NOT EXISTS public.ml_user_addresses (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    receiver_name VARCHAR(100) NOT NULL,
    receiver_phone VARCHAR(32) NOT NULL,
    province VARCHAR(100) NOT NULL,
    city VARCHAR(100) NOT NULL,
    district VARCHAR(100) NOT NULL,
    street VARCHAR(200),
    address_detail TEXT NOT NULL,
    postal_code VARCHAR(16),
    is_default BOOLEAN DEFAULT FALSE,
    label VARCHAR(50), -- home/office/school/other
    latitude DECIMAL(10,7),
    longitude DECIMAL(10,7),
    delivery_instructions TEXT,
    business_hours VARCHAR(100),
    status INTEGER DEFAULT 1, -- 1:正常 2:禁用
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_address_status CHECK (status IN (1,2))
);

COMMENT ON TABLE public.ml_user_addresses IS '用户地址表';

-- =====================================================================================
-- 2. 创建商品相关表
-- =====================================================================================

-- 商品分类表
CREATE TABLE IF NOT EXISTS public.ml_categories (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    cid SERIAL UNIQUE NOT NULL, -- SEO友好的自增ID
    parent_id UUID REFERENCES public.ml_categories(id),
    name VARCHAR(200) NOT NULL,
    slug VARCHAR(200) UNIQUE,
    description TEXT,
    icon_url TEXT,
    banner_url TEXT,
    sort_order INTEGER DEFAULT 0,
    level INTEGER DEFAULT 1,
    path TEXT[], -- 分类路径
    is_active BOOLEAN DEFAULT TRUE,
    seo_title VARCHAR(200),
    seo_description VARCHAR(500),
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);

COMMENT ON TABLE public.ml_categories IS '商品分类表';

-- 品牌表
CREATE TABLE IF NOT EXISTS public.ml_brands (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    cid SERIAL UNIQUE NOT NULL, -- SEO友好的自增ID
    name VARCHAR(200) NOT NULL,
    logo_url TEXT,
    description TEXT,
    website VARCHAR(500),
    is_active BOOLEAN DEFAULT TRUE,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);

COMMENT ON TABLE public.ml_brands IS '品牌表';

-- 商品表
CREATE TABLE IF NOT EXISTS public.ml_products (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    cid SERIAL UNIQUE NOT NULL, -- SEO友好的自增ID
    merchant_id UUID NOT NULL REFERENCES public.ak_users(id),
    category_id UUID NOT NULL REFERENCES public.ml_categories(id),
    brand_id UUID REFERENCES public.ml_brands(id),
    product_code VARCHAR(100) UNIQUE NOT NULL,
    name VARCHAR(500) NOT NULL,
    subtitle VARCHAR(1000),
    description TEXT,
    main_image_url TEXT,
    image_urls JSONB DEFAULT '[]',
    video_urls JSONB DEFAULT '[]',
    
    -- 价格信息
    base_price DECIMAL(12,2) NOT NULL CHECK (base_price >= 0),
    market_price DECIMAL(12,2),
    cost_price DECIMAL(12,2),
    
    -- 库存信息
    total_stock INTEGER DEFAULT 0 CHECK (total_stock >= 0),
    available_stock INTEGER DEFAULT 0 CHECK (available_stock >= 0),
    min_order_qty INTEGER DEFAULT 1 CHECK (min_order_qty > 0),
    max_order_qty INTEGER,
    
    -- 基础属性
    weight DECIMAL(10,3),
    dimensions JSONB, -- {length, width, height}
    
    -- 状态
    status INTEGER DEFAULT 1, -- 1:上架 2:下架 3:草稿 4:删除
    is_featured BOOLEAN DEFAULT FALSE,
    is_new BOOLEAN DEFAULT FALSE,
    is_hot BOOLEAN DEFAULT FALSE,
    
    -- 统计
    view_count INTEGER DEFAULT 0,
    sale_count INTEGER DEFAULT 0,
    favorite_count INTEGER DEFAULT 0,
    rating_avg DECIMAL(3,2) DEFAULT 0.00 CHECK (rating_avg >= 0 AND rating_avg <= 5),
    rating_count INTEGER DEFAULT 0,
    
    -- SEO
    seo_title VARCHAR(200),
    seo_description VARCHAR(500),
    seo_keywords TEXT[],
    slug VARCHAR(200) UNIQUE,
    
    -- 其他
    tags TEXT[],
    attributes JSONB DEFAULT '{}',
    
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    published_at TIMESTAMP WITH TIME ZONE,
    
    CONSTRAINT chk_ml_product_status CHECK (status IN (1,2,3,4))
);

COMMENT ON TABLE public.ml_products IS '商品表';

-- 商品SKU表
CREATE TABLE IF NOT EXISTS public.ml_product_skus (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    product_id UUID NOT NULL REFERENCES public.ml_products(id) ON DELETE CASCADE,
    sku_code VARCHAR(100) UNIQUE NOT NULL,
    specifications JSONB DEFAULT '{}', -- 规格组合
    price DECIMAL(12,2) NOT NULL CHECK (price >= 0),
    market_price DECIMAL(12,2),
    cost_price DECIMAL(12,2),
    stock INTEGER DEFAULT 0 CHECK (stock >= 0),
    warning_stock INTEGER DEFAULT 10, -- 库存预警
    image_url TEXT,
    weight DECIMAL(10,3),
    status INTEGER DEFAULT 1, -- 1:正常 2:禁用
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_sku_status CHECK (status IN (1,2))
);

COMMENT ON TABLE public.ml_product_skus IS '商品SKU表';

-- 商品规格表
CREATE TABLE IF NOT EXISTS public.ml_product_specs (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    product_id UUID NOT NULL REFERENCES public.ml_products(id) ON DELETE CASCADE,
    spec_name VARCHAR(100) NOT NULL, -- 规格名称：颜色、尺寸等
    spec_values JSONB NOT NULL DEFAULT '[]', -- 规格值数组
    sort_order INTEGER DEFAULT 0,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);

COMMENT ON TABLE public.ml_product_specs IS '商品规格表';

-- =====================================================================================
-- 3. 创建店铺相关表
-- =====================================================================================

-- 店铺信息表
CREATE TABLE IF NOT EXISTS public.ml_shops (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    cid SERIAL UNIQUE NOT NULL, -- SEO友好的自增ID
    merchant_id UUID UNIQUE NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    shop_name VARCHAR(200) NOT NULL,
    shop_logo TEXT,
    shop_banner TEXT,
    description TEXT,
    business_license VARCHAR(100),
    contact_name VARCHAR(100),
    contact_phone VARCHAR(32),
    contact_email VARCHAR(200),
    address JSONB, -- 店铺地址信息
    business_hours JSONB, -- 营业时间
    
    -- 状态
    status INTEGER DEFAULT 1, -- 1:正常 2:暂停 3:关闭
    
    -- 统计
    product_count INTEGER DEFAULT 0,
    order_count INTEGER DEFAULT 0,
    rating_avg DECIMAL(3,2) DEFAULT 0.00,
    rating_count INTEGER DEFAULT 0,
    
    -- 认证信息
    verified_at TIMESTAMP WITH TIME ZONE,
    
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_shop_status CHECK (status IN (1,2,3))
);

COMMENT ON TABLE public.ml_shops IS '店铺信息表';

-- =====================================================================================
-- 4. 创建订单相关表
-- =====================================================================================

-- 订单表
CREATE TABLE IF NOT EXISTS public.ml_orders (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    cid SERIAL UNIQUE NOT NULL, -- SEO友好的自增ID
    order_no VARCHAR(50) UNIQUE NOT NULL,
    user_id UUID NOT NULL REFERENCES public.ak_users(id),
    merchant_id UUID NOT NULL REFERENCES public.ak_users(id),
    
    -- 金额信息
    product_amount DECIMAL(12,2) NOT NULL DEFAULT 0, -- 商品金额
    discount_amount DECIMAL(12,2) DEFAULT 0, -- 优惠金额
    shipping_fee DECIMAL(12,2) DEFAULT 0, -- 运费
    total_amount DECIMAL(12,2) NOT NULL, -- 总金额
    paid_amount DECIMAL(12,2) DEFAULT 0, -- 已付金额
    
    -- 地址信息
    shipping_address JSONB NOT NULL, -- 收货地址
    
    -- 状态信息
    order_status INTEGER DEFAULT 1, -- 1:待付款 2:待发货 3:待收货 4:已完成 5:已取消 6:退款中 7:已退款
    payment_status INTEGER DEFAULT 1, -- 1:未付款 2:已付款 3:部分退款 4:全额退款
    shipping_status INTEGER DEFAULT 1, -- 1:未发货 2:已发货 3:运输中 4:已送达
    
    -- 时间信息
    paid_at TIMESTAMP WITH TIME ZONE,
    shipped_at TIMESTAMP WITH TIME ZONE,
    delivered_at TIMESTAMP WITH TIME ZONE,
    completed_at TIMESTAMP WITH TIME ZONE,
    
    -- 其他信息
    remark TEXT, -- 买家备注
    merchant_memo TEXT, -- 商家备注
    cancel_reason TEXT, -- 取消原因
    
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_order_status CHECK (order_status IN (1,2,3,4,5,6,7)),
    CONSTRAINT chk_ml_payment_status CHECK (payment_status IN (1,2,3,4)),
    CONSTRAINT chk_ml_shipping_status CHECK (shipping_status IN (1,2,3,4))
);

COMMENT ON TABLE public.ml_orders IS '订单表';

-- 订单商品表
CREATE TABLE IF NOT EXISTS public.ml_order_items (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    order_id UUID NOT NULL REFERENCES public.ml_orders(id) ON DELETE CASCADE,
    product_id UUID NOT NULL REFERENCES public.ml_products(id),
    sku_id UUID REFERENCES public.ml_product_skus(id),
    product_name VARCHAR(500) NOT NULL,
    sku_name VARCHAR(500),
    specifications JSONB DEFAULT '{}',
    image_url TEXT,
    price DECIMAL(12,2) NOT NULL,
    quantity INTEGER NOT NULL CHECK (quantity > 0),
    total_amount DECIMAL(12,2) NOT NULL,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);

COMMENT ON TABLE public.ml_order_items IS '订单商品表';

-- =====================================================================================
-- 5. 创建购物车和营销相关表
-- =====================================================================================

-- 购物车表
CREATE TABLE IF NOT EXISTS public.ml_shopping_cart (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    product_id UUID NOT NULL REFERENCES public.ml_products(id) ON DELETE CASCADE,
    sku_id UUID REFERENCES public.ml_product_skus(id) ON DELETE CASCADE,
    quantity INTEGER NOT NULL CHECK (quantity > 0),
    selected BOOLEAN DEFAULT TRUE,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    UNIQUE(user_id, product_id, sku_id)
);

COMMENT ON TABLE public.ml_shopping_cart IS '购物车表';

-- 优惠券模板表
CREATE TABLE IF NOT EXISTS public.ml_coupon_templates (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    cid SERIAL UNIQUE NOT NULL, -- SEO友好的自增ID
    merchant_id UUID REFERENCES public.ak_users(id), -- NULL表示平台券
    name VARCHAR(200) NOT NULL,
    description TEXT,
    coupon_type INTEGER NOT NULL, -- 1:满减券 2:折扣券 3:免运费券
    discount_type INTEGER NOT NULL, -- 1:固定金额 2:百分比
    discount_value DECIMAL(12,2) NOT NULL, -- 优惠值
    min_order_amount DECIMAL(12,2) DEFAULT 0, -- 最低订单金额
    max_discount_amount DECIMAL(12,2), -- 最大优惠金额
    total_quantity INTEGER, -- 总发放数量
    per_user_limit INTEGER DEFAULT 1, -- 每用户限领数量
    usage_limit INTEGER DEFAULT 1, -- 每张券使用次数限制
    
    -- 适用范围
    applicable_products JSONB DEFAULT '[]', -- 适用商品ID数组
    applicable_categories JSONB DEFAULT '[]', -- 适用分类ID数组
    
    -- 时间限制
    start_time TIMESTAMP WITH TIME ZONE NOT NULL,
    end_time TIMESTAMP WITH TIME ZONE NOT NULL,
    
    status INTEGER DEFAULT 1, -- 1:正常 2:暂停 3:已结束
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_coupon_type CHECK (coupon_type IN (1,2,3)),
    CONSTRAINT chk_ml_discount_type CHECK (discount_type IN (1,2)),
    CONSTRAINT chk_ml_coupon_status CHECK (status IN (1,2,3))
);

COMMENT ON TABLE public.ml_coupon_templates IS '优惠券模板表';

-- 用户优惠券表
CREATE TABLE IF NOT EXISTS public.ml_user_coupons (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    template_id UUID NOT NULL REFERENCES public.ml_coupon_templates(id),
    coupon_code VARCHAR(50) UNIQUE NOT NULL,
    status INTEGER DEFAULT 1, -- 1:未使用 2:已使用 3:已过期
    used_at TIMESTAMP WITH TIME ZONE,
    order_id UUID REFERENCES public.ml_orders(id),
    received_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    expire_at TIMESTAMP WITH TIME ZONE NOT NULL,
    
    CONSTRAINT chk_ml_user_coupon_status CHECK (status IN (1,2,3))
);

COMMENT ON TABLE public.ml_user_coupons IS '用户优惠券表';

-- =====================================================================================
-- 6. 创建配送和评价相关表
-- =====================================================================================

-- 配送员信息表
CREATE TABLE IF NOT EXISTS public.ml_delivery_drivers (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID UNIQUE NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    real_name VARCHAR(100) NOT NULL,
    id_card VARCHAR(32) NOT NULL,
    driver_license VARCHAR(50),
    vehicle_type INTEGER, -- 1:电动车 2:摩托车 3:汽车
    vehicle_number VARCHAR(20),
    service_areas JSONB DEFAULT '[]', -- 服务区域
    work_status INTEGER DEFAULT 1, -- 1:在线 2:忙碌 3:离线
    current_lat DECIMAL(10,7),
    current_lng DECIMAL(10,7),
    rating_avg DECIMAL(3,2) DEFAULT 0.00,
    rating_count INTEGER DEFAULT 0,
    order_count INTEGER DEFAULT 0,
    status INTEGER DEFAULT 1, -- 1:正常 2:暂停 3:离职
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_driver_vehicle_type CHECK (vehicle_type IN (1,2,3)),
    CONSTRAINT chk_ml_driver_work_status CHECK (work_status IN (1,2,3)),
    CONSTRAINT chk_ml_driver_status CHECK (status IN (1,2,3))
);

COMMENT ON TABLE public.ml_delivery_drivers IS '配送员信息表';

-- 配送任务表
CREATE TABLE IF NOT EXISTS public.ml_delivery_tasks (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    order_id UUID UNIQUE NOT NULL REFERENCES public.ml_orders(id),
    driver_id UUID REFERENCES public.ml_delivery_drivers(id),
    pickup_address JSONB NOT NULL, -- 取货地址
    delivery_address JSONB NOT NULL, -- 配送地址
    distance DECIMAL(8,2), -- 配送距离(km)
    estimated_time INTEGER, -- 预计配送时间(分钟)
    delivery_fee DECIMAL(10,2) NOT NULL DEFAULT 0,
    
    status INTEGER DEFAULT 1, -- 1:待接单 2:已接单 3:取货中 4:配送中 5:已送达 6:配送失败
    
    -- 时间记录
    assigned_at TIMESTAMP WITH TIME ZONE,
    picked_at TIMESTAMP WITH TIME ZONE,
    delivered_at TIMESTAMP WITH TIME ZONE,
    
    -- 其他信息
    delivery_code VARCHAR(10), -- 取货码
    remark TEXT,
    failure_reason TEXT,
    
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_delivery_status CHECK (status IN (1,2,3,4,5,6))
);

COMMENT ON TABLE public.ml_delivery_tasks IS '配送任务表';

-- 商品评价表
CREATE TABLE IF NOT EXISTS public.ml_product_reviews (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    order_id UUID NOT NULL REFERENCES public.ml_orders(id),
    order_item_id UUID NOT NULL REFERENCES public.ml_order_items(id),
    user_id UUID NOT NULL REFERENCES public.ak_users(id),
    product_id UUID NOT NULL REFERENCES public.ml_products(id),
    merchant_id UUID NOT NULL REFERENCES public.ak_users(id),
    
    rating INTEGER NOT NULL CHECK (rating >= 1 AND rating <= 5),
    content TEXT,
    images JSONB DEFAULT '[]', -- 评价图片
    is_anonymous BOOLEAN DEFAULT FALSE,
    
    -- 商家回复
    merchant_reply TEXT,
    merchant_replied_at TIMESTAMP WITH TIME ZONE,
    
    status INTEGER DEFAULT 1, -- 1:正常 2:已删除 3:已隐藏
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    CONSTRAINT chk_ml_review_status CHECK (status IN (1,2,3))
);

COMMENT ON TABLE public.ml_product_reviews IS '商品评价表';

-- =====================================================================================
-- 7. 创建用户行为和系统配置表
-- =====================================================================================

-- 用户收藏表
CREATE TABLE IF NOT EXISTS public.ml_user_favorites (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    target_type INTEGER NOT NULL, -- 1:商品 2:店铺
    target_id UUID NOT NULL,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    UNIQUE(user_id, target_type, target_id),
    CONSTRAINT chk_ml_favorite_type CHECK (target_type IN (1,2))
);

COMMENT ON TABLE public.ml_user_favorites IS '用户收藏表';

-- 用户浏览历史表
CREATE TABLE IF NOT EXISTS public.ml_browse_history (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID NOT NULL REFERENCES public.ak_users(id) ON DELETE CASCADE,
    product_id UUID NOT NULL REFERENCES public.ml_products(id) ON DELETE CASCADE,
    browse_duration INTEGER DEFAULT 0, -- 浏览时长(秒)
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    
    UNIQUE(user_id, product_id)
);

COMMENT ON TABLE public.ml_browse_history IS '用户浏览历史表';

-- 搜索记录表
CREATE TABLE IF NOT EXISTS public.ml_search_history (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    user_id UUID REFERENCES public.ak_users(id) ON DELETE CASCADE,
    keyword VARCHAR(200) NOT NULL,
    result_count INTEGER DEFAULT 0,
    ip_address INET,
    user_agent TEXT,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);

COMMENT ON TABLE public.ml_search_history IS '搜索记录表';

-- 系统配置表
CREATE TABLE IF NOT EXISTS public.ml_system_configs (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    config_key VARCHAR(100) UNIQUE NOT NULL,
    config_value JSONB,
    description TEXT,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
    updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);

COMMENT ON TABLE public.ml_system_configs IS '系统配置表';

-- 地区表
CREATE TABLE IF NOT EXISTS public.ml_regions (
    id UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
    parent_id UUID REFERENCES public.ml_regions(id),
    name VARCHAR(100) NOT NULL,
    code VARCHAR(20),
    level INTEGER NOT NULL, -- 1:省份 2:城市 3:区县 4:街道
    sort_order INTEGER DEFAULT 0,
    is_active BOOLEAN DEFAULT TRUE,
    created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);

COMMENT ON TABLE public.ml_regions IS '地区表';

-- =====================================================================================
-- 8. 创建索引
-- =====================================================================================

-- 用户扩展表索引
CREATE INDEX IF NOT EXISTS idx_ml_user_profiles_user_id ON public.ml_user_profiles(user_id);
CREATE INDEX IF NOT EXISTS idx_ml_user_profiles_type ON public.ml_user_profiles(user_type);
CREATE INDEX IF NOT EXISTS idx_ml_user_profiles_status ON public.ml_user_profiles(status);

-- 分类表索引
CREATE INDEX IF NOT EXISTS idx_ml_categories_cid ON public.ml_categories(cid);
CREATE INDEX IF NOT EXISTS idx_ml_categories_parent ON public.ml_categories(parent_id);
CREATE INDEX IF NOT EXISTS idx_ml_categories_slug ON public.ml_categories(slug);
CREATE INDEX IF NOT EXISTS idx_ml_categories_level ON public.ml_categories(level, sort_order);

-- 品牌表索引
CREATE INDEX IF NOT EXISTS idx_ml_brands_cid ON public.ml_brands(cid);
CREATE INDEX IF NOT EXISTS idx_ml_brands_name ON public.ml_brands(name);

-- 地址表索引
CREATE INDEX IF NOT EXISTS idx_ml_user_addresses_user_id ON public.ml_user_addresses(user_id);
CREATE INDEX IF NOT EXISTS idx_ml_user_addresses_default ON public.ml_user_addresses(user_id, is_default);
CREATE INDEX IF NOT EXISTS idx_ml_user_addresses_location ON public.ml_user_addresses(city, district);

-- 商品表索引
CREATE INDEX IF NOT EXISTS idx_ml_products_cid ON public.ml_products(cid);
CREATE INDEX IF NOT EXISTS idx_ml_products_merchant ON public.ml_products(merchant_id, status);
CREATE INDEX IF NOT EXISTS idx_ml_products_category ON public.ml_products(category_id, status);
CREATE INDEX IF NOT EXISTS idx_ml_products_status ON public.ml_products(status, created_at DESC);
CREATE INDEX IF NOT EXISTS idx_ml_products_featured ON public.ml_products(is_featured, status);
CREATE INDEX IF NOT EXISTS idx_ml_products_price ON public.ml_products(base_price);
CREATE INDEX IF NOT EXISTS idx_ml_products_rating ON public.ml_products(rating_avg DESC, rating_count DESC);
CREATE INDEX IF NOT EXISTS idx_ml_products_sale_count ON public.ml_products(sale_count DESC);
CREATE INDEX IF NOT EXISTS idx_ml_products_tags ON public.ml_products USING GIN(tags);
CREATE INDEX IF NOT EXISTS idx_ml_products_slug ON public.ml_products(slug);

-- 店铺表索引
CREATE INDEX IF NOT EXISTS idx_ml_shops_cid ON public.ml_shops(cid);
CREATE INDEX IF NOT EXISTS idx_ml_shops_merchant ON public.ml_shops(merchant_id);

-- SKU表索引
CREATE INDEX IF NOT EXISTS idx_ml_product_skus_product ON public.ml_product_skus(product_id);
CREATE INDEX IF NOT EXISTS idx_ml_product_skus_code ON public.ml_product_skus(sku_code);

-- 订单表索引
CREATE INDEX IF NOT EXISTS idx_ml_orders_cid ON public.ml_orders(cid);
CREATE INDEX IF NOT EXISTS idx_ml_orders_user ON public.ml_orders(user_id, created_at DESC);
CREATE INDEX IF NOT EXISTS idx_ml_orders_merchant ON public.ml_orders(merchant_id, created_at DESC);
CREATE INDEX IF NOT EXISTS idx_ml_orders_status ON public.ml_orders(order_status, created_at DESC);
CREATE INDEX IF NOT EXISTS idx_ml_orders_no ON public.ml_orders(order_no);

-- 订单商品表索引
CREATE INDEX IF NOT EXISTS idx_ml_order_items_order ON public.ml_order_items(order_id);
CREATE INDEX IF NOT EXISTS idx_ml_order_items_product ON public.ml_order_items(product_id);

-- 购物车表索引
CREATE INDEX IF NOT EXISTS idx_ml_shopping_cart_user ON public.ml_shopping_cart(user_id);

-- 优惠券模板表索引
CREATE INDEX IF NOT EXISTS idx_ml_coupon_templates_cid ON public.ml_coupon_templates(cid);
CREATE INDEX IF NOT EXISTS idx_ml_coupon_templates_merchant ON public.ml_coupon_templates(merchant_id);

-- 优惠券表索引
CREATE INDEX IF NOT EXISTS idx_ml_user_coupons_user ON public.ml_user_coupons(user_id, status);
CREATE INDEX IF NOT EXISTS idx_ml_user_coupons_code ON public.ml_user_coupons(coupon_code);

-- 收藏表索引
CREATE INDEX IF NOT EXISTS idx_ml_user_favorites_user ON public.ml_user_favorites(user_id, target_type);
CREATE INDEX IF NOT EXISTS idx_ml_user_favorites_target ON public.ml_user_favorites(target_type, target_id);

-- 浏览历史索引
CREATE INDEX IF NOT EXISTS idx_ml_browse_history_user ON public.ml_browse_history(user_id, created_at DESC);
CREATE INDEX IF NOT EXISTS idx_ml_browse_history_product ON public.ml_browse_history(product_id);

-- =====================================================================================
-- 9. 创建触发器函数
-- =====================================================================================

-- 自动更新 updated_at 字段的函数
CREATE OR REPLACE FUNCTION public.update_updated_at_column()
RETURNS TRIGGER AS $$
BEGIN
    NEW.updated_at = NOW();
    RETURN NEW;
END;
$$ LANGUAGE plpgsql;

-- 创建触发器 (使用 DO 块避免重复创建错误)
DO $$
BEGIN
    -- 用户档案更新触发器
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_user_profiles_updated_at') THEN
        CREATE TRIGGER trigger_ml_user_profiles_updated_at
            BEFORE UPDATE ON public.ml_user_profiles
            FOR EACH ROW EXECUTE FUNCTION public.update_updated_at_column();
    END IF;

    -- 用户地址更新触发器
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_user_addresses_updated_at') THEN
        CREATE TRIGGER trigger_ml_user_addresses_updated_at
            BEFORE UPDATE ON public.ml_user_addresses
            FOR EACH ROW EXECUTE FUNCTION public.update_updated_at_column();
    END IF;

    -- 商品更新触发器
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_products_updated_at') THEN
        CREATE TRIGGER trigger_ml_products_updated_at
            BEFORE UPDATE ON public.ml_products
            FOR EACH ROW EXECUTE FUNCTION public.update_updated_at_column();
    END IF;

    -- SKU更新触发器
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_product_skus_updated_at') THEN
        CREATE TRIGGER trigger_ml_product_skus_updated_at
            BEFORE UPDATE ON public.ml_product_skus
            FOR EACH ROW EXECUTE FUNCTION public.update_updated_at_column();
    END IF;

    -- 店铺更新触发器
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_shops_updated_at') THEN
        CREATE TRIGGER trigger_ml_shops_updated_at
            BEFORE UPDATE ON public.ml_shops
            FOR EACH ROW EXECUTE FUNCTION public.update_updated_at_column();
    END IF;

    -- 订单更新触发器
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_orders_updated_at') THEN
        CREATE TRIGGER trigger_ml_orders_updated_at
            BEFORE UPDATE ON public.ml_orders
            FOR EACH ROW EXECUTE FUNCTION public.update_updated_at_column();
    END IF;

    -- 购物车更新触发器
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_shopping_cart_updated_at') THEN
        CREATE TRIGGER trigger_ml_shopping_cart_updated_at
            BEFORE UPDATE ON public.ml_shopping_cart
            FOR EACH ROW EXECUTE FUNCTION public.update_updated_at_column();
    END IF;
END $$;

-- 确保每个用户只有一个默认地址的触发器
CREATE OR REPLACE FUNCTION public.ensure_single_default_address()
RETURNS TRIGGER AS $$
BEGIN
    IF NEW.is_default = TRUE THEN
        UPDATE public.ml_user_addresses 
        SET is_default = FALSE 
        WHERE user_id = NEW.user_id AND id != NEW.id;
    END IF;
    RETURN NEW;
END;
$$ LANGUAGE plpgsql;

DO $$
BEGIN
    IF NOT EXISTS (SELECT 1 FROM pg_trigger WHERE tgname = 'trigger_ml_single_default_address') THEN
        CREATE TRIGGER trigger_ml_single_default_address
            BEFORE INSERT OR UPDATE ON public.ml_user_addresses
            FOR EACH ROW EXECUTE FUNCTION public.ensure_single_default_address();
    END IF;
END $$;

-- =====================================================================================
-- 10. 创建实用函数
-- =====================================================================================

-- 创建订单序列
CREATE SEQUENCE IF NOT EXISTS public.ml_order_seq START 1;

-- 生成订单号的函数
CREATE OR REPLACE FUNCTION public.generate_order_no()
RETURNS TEXT AS $$
DECLARE
    order_no TEXT;
BEGIN
    order_no := 'ML' || TO_CHAR(NOW(), 'YYYYMMDD') || LPAD(NEXTVAL('ml_order_seq')::TEXT, 6, '0');
    RETURN order_no;
END;
$$ LANGUAGE plpgsql;

-- 生成优惠券码的函数
CREATE OR REPLACE FUNCTION public.generate_coupon_code()
RETURNS TEXT AS $$
DECLARE
    code TEXT;
    chars TEXT := 'ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
    result TEXT := '';
    i INTEGER;
BEGIN
    FOR i IN 1..8 LOOP
        result := result || substr(chars, (random() * length(chars))::integer + 1, 1);
    END LOOP;
    RETURN 'CP' || result;
END;
$$ LANGUAGE plpgsql;

-- 获取用户默认地址
CREATE OR REPLACE FUNCTION public.get_user_default_address(p_user_id UUID)
RETURNS TABLE (
    id UUID,
    receiver_name VARCHAR,
    receiver_phone VARCHAR,
    full_address TEXT,
    latitude DECIMAL,
    longitude DECIMAL
) AS $$
BEGIN
    RETURN QUERY
    SELECT 
        a.id,
        a.receiver_name,
        a.receiver_phone,
        (a.province || ' ' || a.city || ' ' || a.district || ' ' || a.address_detail) as full_address,
        a.latitude,
        a.longitude
    FROM public.ml_user_addresses a
    WHERE a.user_id = p_user_id AND a.is_default = TRUE AND a.status = 1
    LIMIT 1;
END;
$$ LANGUAGE plpgsql;

-- 检查用户是否为认证商家
CREATE OR REPLACE FUNCTION public.is_verified_merchant(p_user_id UUID)
RETURNS BOOLEAN AS $$
DECLARE
    result BOOLEAN := FALSE;
BEGIN
    SELECT (user_type = 2 AND verification_status = 1) INTO result
    FROM public.ml_user_profiles
    WHERE user_id = p_user_id;
    
    RETURN COALESCE(result, FALSE);
END;
$$ LANGUAGE plpgsql;

-- =====================================================================================
-- 11. 创建基础视图
-- =====================================================================================

-- 商城用户完整信息视图
CREATE OR REPLACE VIEW public.ml_users_view AS
SELECT 
    u.id,
    u.username,
    u.email,
    u.phone,
    u.avatar_url,
    u.gender,
    u.birthday,
    u.bio,
    u.created_at as user_created_at,
    u.updated_at as user_updated_at,
    p.user_type,
    p.status,
    p.real_name,
    p.credit_score,
    p.verification_status,
    p.created_at as profile_created_at,
    p.updated_at as profile_updated_at,
    CASE 
        WHEN p.user_type = 1 THEN '消费者'
        WHEN p.user_type = 2 THEN '商家'
        WHEN p.user_type = 3 THEN '配送员'
        WHEN p.user_type = 4 THEN '客服'
        WHEN p.user_type = 5 THEN '管理员'
        ELSE '未知'
    END as user_type_name
FROM public.ak_users u
LEFT JOIN public.ml_user_profiles p ON u.id = p.user_id;

COMMENT ON VIEW public.ml_users_view IS '商城用户完整信息视图';

-- =====================================================================================
-- 12. 插入初始配置数据
-- =====================================================================================

-- 插入系统配置
INSERT INTO public.ml_system_configs (config_key, config_value, description) VALUES
('shipping_fee', '{"default": 10, "free_threshold": 88}', '配送费配置'),
('platform_commission', '{"rate": 0.05}', '平台佣金配置'),
('coupon_settings', '{"max_per_user": 10}', '优惠券设置'),
('order_auto_confirm_days', '7', '订单自动确认天数')
ON CONFLICT (config_key) DO NOTHING;

-- 插入默认分类
INSERT INTO public.ml_categories (id, name, slug, level, path) VALUES
(uuid_generate_v4(), '数码电器', 'digital', 1, ARRAY['数码电器']),
(uuid_generate_v4(), '服装鞋帽', 'fashion', 1, ARRAY['服装鞋帽']),
(uuid_generate_v4(), '家居用品', 'home', 1, ARRAY['家居用品']),
(uuid_generate_v4(), '食品饮料', 'food', 1, ARRAY['食品饮料']),
(uuid_generate_v4(), '美妆护肤', 'beauty', 1, ARRAY['美妆护肤'])
ON CONFLICT (slug) DO NOTHING;

-- 为现有 ak_users 用户创建默认商城档案 (如果不存在)
INSERT INTO public.ml_user_profiles (user_id, user_type, status)
SELECT 
    id,
    1, -- 默认为消费者
    1  -- 默认状态正常
FROM public.ak_users
WHERE id NOT IN (SELECT user_id FROM public.ml_user_profiles WHERE user_id IS NOT NULL);

-- =====================================================================================
-- 13. 完成提示
-- =====================================================================================

DO $$
BEGIN
    RAISE NOTICE '=======================================================';
    RAISE NOTICE '商城数据库迁移完成！';
    RAISE NOTICE '=======================================================';
    RAISE NOTICE '已创建表数量: 17 张商城表';
    RAISE NOTICE '已创建索引: 30+ 个索引';
    RAISE NOTICE '已创建触发器: 8 个触发器';
    RAISE NOTICE '已创建函数: 6 个函数';
    RAISE NOTICE '已创建视图: 1 个视图';
    RAISE NOTICE '已插入基础配置和分类数据';
    RAISE NOTICE '已为现有用户创建默认商城档案';
    RAISE NOTICE '=======================================================';
    RAISE NOTICE '表名前缀: ml_';
    RAISE NOTICE '复用表: ak_users';
    RAISE NOTICE '兼容: Supabase';
    RAISE NOTICE '=======================================================';
END $$;
