PHP项目如何实现模型选择?

wen java案例 1

本文目录导读:

PHP项目如何实现模型选择?

  1. 方案一:基于配置文件的硬编码切换(最简单,适合小型项目)
  2. 方案二:基于策略模式 + 工厂模式(推荐,中大型项目)
  3. 方案三:数据库驱动的动态选择(适合SaaS后台管理)
  4. 高级优化建议

这是一个关于在PHP项目中实现“模型选择”的常见问题,这里的“模型”通常指机器学习模型(如预测、分类)或AI大模型(如OpenAI、Claude等),为了实现模型选择,你需要考虑调用方式切换逻辑以及性能与成本平衡

下面为你提供几种主流实现方案,涵盖从简单到复杂的场景:

基于配置文件的硬编码切换(最简单,适合小型项目)

通过修改配置文件,在代码中判断当前使用的模型。

定义配置(config/model.php)

<?php
return [
    'default' => env('MODEL_PROVIDER', 'openai'), // 或 'gemini', 'local'
    'providers' => [
        'openai' => [
            'model' => 'gpt-4o',
            'api_key' => env('OPENAI_API_KEY'),
            'temperature' => 0.7,
        ],
        'gemini' => [
            'model' => 'gemini-1.5-flash',
            'api_key' => env('GEMINI_API_KEY'),
        ],
        'local_llm' => [
            'model' => 'llama3',
            'endpoint' => 'http://localhost:11434/api/generate', // Ollama
        ],
    ],
];

创建模型分发器类

<?php
namespace App\Services;
class ModelRouter
{
    protected $config;
    public function __construct(array $config)
    {
        $this->config = $config;
    }
    public function chat(string $prompt): string
    {
        $provider = $this->config['default'];
        $providerConfig = $this->config['providers'][$provider];
        return match ($provider) {
            'openai' => $this->callOpenAI($prompt, $providerConfig),
            'gemini' => $this->callGemini($prompt, $providerConfig),
            'local_llm' => $this->callLocalLlama($prompt, $providerConfig),
            default => throw new \InvalidArgumentException("未知模型提供商"),
        };
    }
    protected function callOpenAI(string $prompt, array $config): string
    {
        // 使用 GuzzleHttp 或 cURL 调用 OpenAI API
        $response = \Http::withToken($config['api_key'])
            ->post('https://api.openai.com/v1/chat/completions', [
                'model' => $config['model'],
                'messages' => [['role' => 'user', 'content' => $prompt]],
            ]);
        return $response->json()['choices'][0]['message']['content'];
    }
    // ... 其他模型调用方法
}

优点:实现简单,直接生效。
缺点:切换模型依赖修改配置文件,不适合生产动态切换。

基于策略模式 + 工厂模式(推荐,中大型项目)

这是最优雅的面向对象解决方案,解耦模型逻辑,易于扩展。

定义模型接口

<?php
namespace App\Contracts;
interface AIModelInterface
{
    public function generate(string $prompt, array $params = []): string;
    public function supports(array $task): bool; // 可选:判断模型是否符合任务
}

实现具体模型

<?php
namespace App\Models\AI;
class OpenAIModel implements AIModelInterface
{
    public function generate(string $prompt, array $params = []): string
    {
        $model = $params['model'] ?? 'gpt-4o-mini';
        // OpenAI API 调用逻辑...
        return response();
    }
    public function supports(array $task): bool
    {
        return $task['type'] === 'chat' || $task['complexity'] < 7;
    }
}
class LocalLlamaModel implements AIModelInterface
{
    public function generate(string $prompt, array $params = []): string
    {
        // 调用本地 Ollama 服务...
        return response();
    }
    public function supports(array $task): bool
    {
        return $task['type'] === 'code' || $task['complexity'] <= 3;
    }
}

创建工厂类(模型选择器)

<?php
namespace App\Services;
use App\Contracts\AIModelInterface;
class ModelFactory
{
    protected array $models = [];
    // 注册模型(通过服务容器绑定,或手动注册)
    public function register(string $name, AIModelInterface $model): void
    {
        $this->models[$name] = $model;
    }
    // 根据任务选择模型
    public function selectForTask(array $task): AIModelInterface
    {
        // 1. 精确匹配:task 里指定了模型名
        if (isset($task['model']) && isset($this->models[$task['model']])) {
            return $this->models[$task['model']];
        }
        // 2. 智能选择:基于能力、成本、性能评分
        $bestModel = null;
        $bestScore = -1;
        foreach ($this->models as $name => $model) {
            if ($model->supports($task)) {
                $score = $this->calculateScore($name, $task); // 根据规则算分(成本、速度等)
                if ($score > $bestScore) {
                    $bestScore = $score;
                    $bestModel = $model;
                }
            }
        }
        if ($bestModel === null) {
            throw new \RuntimeException("没有合适的模型处理此任务");
        }
        return $bestModel;
    }
    protected function calculateScore(string $name, array $task): int
    {
        // 自定义评分逻辑:简单任务用低成本模型,复杂任务用高智能模型
        return match ($name) {
            'gpt-4o' => $task['complexity'] > 5 ? 100 : 10,
            'llama3' => $task['complexity'] < 4 ? 90 : 30,
            default => 50,
        };
    }
    // 获取当前所有模型列表(用于管理后台)
    public function getAvailableModels(): array
    {
        return array_keys($this->models);
    }
}

在 Laravel 等服务容器中注册

// AppServiceProvider.php
public function register()
{
    $this->app->singleton(ModelFactory::class, function ($app) {
        $factory = new ModelFactory();
        $factory->register('gpt-4o', new OpenAIModel());
        $factory->register('llama3', new LocalLlamaModel());
        // 未来添加 Claude、Gemini 只需增加一行
        return $factory;
    });
}

使用示例

$factory = app(ModelFactory::class);
$model = $factory->selectForTask(['type' => 'code', 'complexity' => 4]);
$result = $model->generate("写一个PHP排序算法");

数据库驱动的动态选择(适合SaaS后台管理)

将模型配置存储在数据库中,管理员可在后台动态添加、启用/禁用模型。

数据库表设计

CREATE TABLE ai_models (
    id INT PRIMARY KEY AUTO_INCREMENT,
    name VARCHAR(50) NOT NULL UNIQUE,
    provider VARCHAR(50),  -- openai, gemini, local
    api_key_encrypted TEXT,
    model_name VARCHAR(100), -- gpt-4o, gemini-1.5-pro
    cost_per_token DECIMAL(10,8),
    speed_score INT,       -- 1-10
    intelligence_score INT, -- 1-10
    is_active BOOLEAN DEFAULT TRUE,
    created_at TIMESTAMP
);
CREATE TABLE task_model_rules (
    id INT PRIMARY KEY AUTO_INCREMENT,
    task_type VARCHAR(50),  -- 'chat', 'code', 'embedding'
    complexity_range JSON,  -- {"min": 1, "max": 5}
    priority INT DEFAULT 0,
    model_id INT FOREIGN KEY REFERENCES ai_models(id)
);

选择逻辑

public function selectModel(string $taskType, int $complexity): string
{
    $model = DB::table('ai_models')
        ->join('task_model_rules', 'ai_models.id', '=', 'task_model_rules.model_id')
        ->where('ai_models.is_active', true)
        ->where('task_model_rules.task_type', $taskType)
        ->whereRaw('JSON_UNQUOTE(JSON_EXTRACT(complexity_range, "$.min")) <= ?', [$complexity])
        ->whereRaw('JSON_UNQUOTE(JSON_EXTRACT(complexity_range, "$.max")) >= ?', [$complexity])
        ->orderBy('task_model_rules.priority')
        ->first();
    return $model ? $model->name : 'default_fallback_model';
}

高级优化建议

  1. 缓存模型选择结果:如果同一用户同一任务反复调用,缓存选择的模型ID,避免重复计算。
  2. 降级与熔断:如果主模型(如GPT-4)超时或报错,自动切换到备用模型(如GPT-3.5或本地模型)。
    try {
        return $selectedModel->generate($prompt);
    } catch (TimeoutException $e) {
        return $this->fallbackModel->generate($prompt);
    }
  3. 成本追踪:记录每次调用使用了哪个模型、耗费了多少token,方便出账单和优化。
  4. A/B测试:对不同用户组使用不同模型,观察效果差异。
方案 适用场景 复杂度 灵活性
配置文件切换 个人项目、Demo
策略模式+工厂 企业级应用、中大型项目
数据库驱动 SaaS平台、多租户系统 非常高

推荐你使用方案二(策略模式 + 工厂模式),它兼顾了可维护性、扩展性和清晰的代码结构,如果你需要给用户提供后台管理界面来选择模型,则结合方案三。

抱歉,评论功能暂时关闭!