CREATE TABLE IF NOT EXISTS model_pricing_rule_sets (
  id uuid PRIMARY KEY DEFAULT gen_random_uuid(),
  rule_set_key text NOT NULL UNIQUE,
  name text NOT NULL,
  description text,
  category text NOT NULL DEFAULT 'general',
  currency text NOT NULL DEFAULT 'resource',
  status text NOT NULL DEFAULT 'active',
  metadata jsonb NOT NULL DEFAULT '{}'::jsonb,
  created_at timestamptz NOT NULL DEFAULT now(),
  updated_at timestamptz NOT NULL DEFAULT now()
);

ALTER TABLE IF EXISTS model_pricing_rules
  ADD COLUMN IF NOT EXISTS rule_set_id uuid REFERENCES model_pricing_rule_sets(id) ON DELETE CASCADE,
  ADD COLUMN IF NOT EXISTS rule_key text NOT NULL DEFAULT ('rule_' || replace(gen_random_uuid()::text, '-', '')),
  ADD COLUMN IF NOT EXISTS display_name text NOT NULL DEFAULT '',
  ADD COLUMN IF NOT EXISTS calculator_type text NOT NULL DEFAULT 'unit_weight',
  ADD COLUMN IF NOT EXISTS dimension_schema jsonb NOT NULL DEFAULT '{}'::jsonb,
  ADD COLUMN IF NOT EXISTS formula_config jsonb NOT NULL DEFAULT '{}'::jsonb,
  ADD COLUMN IF NOT EXISTS priority integer NOT NULL DEFAULT 100,
  ADD COLUMN IF NOT EXISTS status text NOT NULL DEFAULT 'active',
  ADD COLUMN IF NOT EXISTS metadata jsonb NOT NULL DEFAULT '{}'::jsonb;

ALTER TABLE IF EXISTS integration_platforms
  ADD COLUMN IF NOT EXISTS pricing_rule_set_id uuid REFERENCES model_pricing_rule_sets(id) ON DELETE SET NULL;

ALTER TABLE IF EXISTS platform_models
  ADD COLUMN IF NOT EXISTS pricing_rule_set_id uuid REFERENCES model_pricing_rule_sets(id) ON DELETE SET NULL;

DO $$
BEGIN
  IF NOT EXISTS (
    SELECT 1
    FROM pg_constraint c
    JOIN pg_attribute a ON a.attrelid = c.conrelid AND a.attnum = ANY(c.conkey)
    WHERE c.contype = 'f'
      AND c.conrelid = 'integration_platforms'::regclass
      AND a.attname = 'pricing_rule_set_id'
  ) THEN
    ALTER TABLE integration_platforms
      ADD CONSTRAINT fk_integration_platforms_pricing_rule_set
      FOREIGN KEY (pricing_rule_set_id) REFERENCES model_pricing_rule_sets(id) ON DELETE SET NULL;
  END IF;

  IF NOT EXISTS (
    SELECT 1
    FROM pg_constraint c
    JOIN pg_attribute a ON a.attrelid = c.conrelid AND a.attnum = ANY(c.conkey)
    WHERE c.contype = 'f'
      AND c.conrelid = 'platform_models'::regclass
      AND a.attname = 'pricing_rule_set_id'
  ) THEN
    ALTER TABLE platform_models
      ADD CONSTRAINT fk_platform_models_pricing_rule_set
      FOREIGN KEY (pricing_rule_set_id) REFERENCES model_pricing_rule_sets(id) ON DELETE SET NULL;
  END IF;
END $$;

CREATE INDEX IF NOT EXISTS idx_model_pricing_rule_set
  ON model_pricing_rules(rule_set_id, resource_type, priority);

CREATE UNIQUE INDEX IF NOT EXISTS idx_model_pricing_rule_set_key
  ON model_pricing_rules(rule_set_id, rule_key)
  WHERE rule_set_id IS NOT NULL;

CREATE INDEX IF NOT EXISTS idx_integration_platforms_pricing_rule_set
  ON integration_platforms(pricing_rule_set_id);

CREATE INDEX IF NOT EXISTS idx_platform_models_pricing_rule_set
  ON platform_models(pricing_rule_set_id);

INSERT INTO model_pricing_rule_sets (rule_set_key, name, description, category, currency, status, metadata)
VALUES (
  'default-multimodal-v1',
  '默认多模态计价规则',
  '覆盖文本、图像和视频的默认计价规则，可作为平台或平台模型的基础价格模板。',
  'default',
  'resource',
  'active',
  '{"source":"gateway.default","version":1}'::jsonb
)
ON CONFLICT (rule_set_key) DO UPDATE SET
  name = EXCLUDED.name,
  description = EXCLUDED.description,
  category = EXCLUDED.category,
  currency = EXCLUDED.currency,
  status = EXCLUDED.status,
  metadata = EXCLUDED.metadata,
  updated_at = now();

WITH default_set AS (
  SELECT id FROM model_pricing_rule_sets WHERE rule_set_key = 'default-multimodal-v1'
)
INSERT INTO model_pricing_rules (
  rule_set_id, rule_key, display_name, scope_type, scope_id, resource_type, unit,
  base_price, currency, base_weight, dynamic_weight, calculator_type,
  dimension_schema, formula_config, priority, status, metadata
)
SELECT default_set.id, item.rule_key, item.display_name, 'rule_set', default_set.id,
       item.resource_type, item.unit, item.base_price, 'resource',
       item.base_weight, item.dynamic_weight, item.calculator_type,
       item.dimension_schema, item.formula_config, item.priority, 'active',
       '{"source":"gateway.default"}'::jsonb
FROM default_set
CROSS JOIN (
  VALUES
    (
      'text_input_tokens',
      '文本输入 Token',
      'text_input',
      '1k_tokens',
      0.01::numeric,
      '{"meter":"input_tokens"}'::jsonb,
      '{}'::jsonb,
      'token_usage',
      '{"metrics":["input_tokens"],"unitScale":1000}'::jsonb,
      '{"formula":"ceil(input_tokens / 1000) * base_price"}'::jsonb,
      10
    ),
    (
      'text_cached_input_tokens',
      '文本缓存输入 Token',
      'text_cached_input',
      '1k_tokens',
      0.001::numeric,
      '{"meter":"cached_input_tokens"}'::jsonb,
      '{}'::jsonb,
      'token_usage',
      '{"metrics":["cached_input_tokens"],"unitScale":1000}'::jsonb,
      '{"formula":"ceil(cached_input_tokens / 1000) * base_price"}'::jsonb,
      15
    ),
    (
      'text_output_tokens',
      '文本输出 Token',
      'text_output',
      '1k_tokens',
      0.03::numeric,
      '{"meter":"output_tokens"}'::jsonb,
      '{}'::jsonb,
      'token_usage',
      '{"metrics":["output_tokens"],"unitScale":1000}'::jsonb,
      '{"formula":"ceil(output_tokens / 1000) * base_price"}'::jsonb,
      20
    ),
    (
      'image',
      '图像',
      'image',
      'image',
      10::numeric,
      '{"meter":"count"}'::jsonb,
      '{"resolutionFactors":{"1K":1,"2K":1.5,"3K":1.75,"4K":2,"8K":4},"qualityFactors":{"low":0.5,"medium":1,"high":1.5}}'::jsonb,
      'unit_weight',
      '{"dimensions":["count","resolution","quality"],"defaults":{"count":1,"quality":"medium","resolution":"1K"}}'::jsonb,
      '{"formula":"count * base_price * resolution_factor * quality_factor"}'::jsonb,
      30
    ),
    (
      'video_generation',
      '视频生成',
      'video',
      '5s',
      100::numeric,
      '{"meter":"duration","unitSeconds":5}'::jsonb,
      '{"resolutionWeights":{"480p":0.75,"720p":1,"1080p":1.5,"2160p":2},"audioWeights":{"true":2,"false":1},"referenceVideoWeights":{"true":1.5,"false":1},"voiceSpecifiedWeights":{"true":1.2,"false":1}}'::jsonb,
      'duration_weight',
      '{"dimensions":["duration_seconds","resolution","audio","reference_video","voice_specified","count"],"defaults":{"count":1,"duration_seconds":5,"resolution":"720p","audio":false,"reference_video":false,"voice_specified":false}}'::jsonb,
      '{"formula":"count * ceil(duration_seconds / 5) * base_price * resolution_weight * audio_weight * reference_video_weight * voice_specified_weight"}'::jsonb,
      50
    )
) AS item(rule_key, display_name, resource_type, unit, base_price, base_weight, dynamic_weight, calculator_type, dimension_schema, formula_config, priority)
ON CONFLICT (rule_set_id, rule_key) WHERE rule_set_id IS NOT NULL DO UPDATE SET
  display_name = EXCLUDED.display_name,
  scope_type = EXCLUDED.scope_type,
  scope_id = EXCLUDED.scope_id,
  resource_type = EXCLUDED.resource_type,
  unit = EXCLUDED.unit,
  base_price = EXCLUDED.base_price,
  currency = EXCLUDED.currency,
  base_weight = EXCLUDED.base_weight,
  dynamic_weight = EXCLUDED.dynamic_weight,
  calculator_type = EXCLUDED.calculator_type,
  dimension_schema = EXCLUDED.dimension_schema,
  formula_config = EXCLUDED.formula_config,
  priority = EXCLUDED.priority,
  status = EXCLUDED.status,
  metadata = EXCLUDED.metadata,
  updated_at = now();
