Google Gemini API 的 PHP API 客户端

1.0.2 2024-09-12 15:19 UTC

This package is not auto-updated.

Last update: 2024-09-26 15:39:27 UTC


README

Gemini API PHP Client - Example

Total Downloads Latest Version License

PHP Gemini API

Gemini API PHP 客户端允许您使用 Google 的生成式 AI 模型,如 Gemini Pro 和 Gemini Pro Vision。

此库不是由 Google 开发或支持的。

目录

安装

您需要 API 密钥才能访问 Google 的 Gemini API。请访问 Google AI Studio 获取 API 密钥。

第一步是使用 Composer 安装 Gemini API PHP 客户端。

composer require gemini-api-php/client

Gemini API PHP 客户端不包含 HTTP 客户端。如果您只是在测试或项目中没有 HTTP 客户端库,则需要允许 php-http/discovery Composer 插件或安装一个 PSR-18 兼容的客户端库。

如何使用

基本文本生成

use GeminiAPI\Gemini;
use GeminiAPI\Resources\Parts\TextPart;

$gemini = new Gemini('GEMINI_API_KEY');
$response = $gemini->geminiPro()->generateContent(
    new TextPart('PHP in less than 100 chars'),
);

print $response->text();
// PHP: A server-side scripting language used to create dynamic web applications.
// Easy to learn, widely used, and open-source.

使用缓存内容或上传文件进行文本生成

use GeminiAPI\Gemini;
use GeminiAPI\Resources\Parts\TextPart;
use GeminiAPI\Resources\Parts\FilePart;

$gemini = new Gemini('GEMINI_API_KEY');
$response = $gemini->geminiPro15Flash001()->generateContentWithCache(
    ["cachedContent" => "cachedContents/n9l42h1iszbd"],
    new TextPart("Give me the summary of the file uploaded")
);

print $response->text();
// PHP: This will give the summary of the file uploaded

多模态输入

仅对 Gemini Pro Vision 模型启用图像输入模式

use GeminiAPI\Gemini;
use GeminiAPI\Enums\MimeType;
use GeminiAPI\Resources\Parts\ImagePart;
use GeminiAPI\Resources\Parts\TextPart;

$gemini = new Gemini('GEMINI_API_KEY');
$response = $gemini->geminiProVision()->generateContent(
    new TextPart('Explain what is in the image'),
    new ImagePart(
        MimeType::IMAGE_JPEG,
        base64_encode(file_get_contents('elephpant.jpg')),
    ),
);

print $response->text();
// The image shows an elephant standing on the Earth.
// The elephant is made of metal and has a glowing symbol on its forehead.
// The Earth is surrounded by a network of glowing lines.
// The image is set against a starry background.

聊天会话(多轮对话)

use GeminiAPI\Gemini;
use GeminiAPI\Resources\Parts\TextPart;

$gemini = new Gemini('GEMINI_API_KEY');
$chat = $gemini->geminiPro()->startChat();

$response = $chat->sendMessage(new TextPart('Hello World in PHP'));
print $response->text();

$response = $chat->sendMessage(new TextPart('in Go'));
print $response->text();
<?php
echo "Hello World!";
?>

This code will print "Hello World!" to the standard output.
package main

import "fmt"

func main() {
    fmt.Println("Hello World!")
}

This code will print "Hello World!" to the standard output.

带历史的聊天会话

use GeminiAPI\Gemini;
use GeminiAPI\Enums\Role;
use GeminiAPI\Resources\Content;
use GeminiAPI\Resources\Parts\TextPart;

$history = [
    Content::text('Hello World in PHP', Role::User),
    Content::text(
        <<<TEXT
        <?php
        echo "Hello World!";
        ?>
        
        This code will print "Hello World!" to the standard output.
        TEXT,
        Role::Model,
    ),
];

$gemini = new Gemini('GEMINI_API_KEY');
$chat = $gemini->geminiPro()
    ->startChat()
    ->withHistory($history);

$response = $chat->sendMessage(new TextPart('in Go'));
print $response->text();
package main

import "fmt"

func main() {
    fmt.Println("Hello World!")
}

This code will print "Hello World!" to the standard output.

流式响应

需要启用 curl 扩展

在流式响应中,每当服务器返回响应时,回调函数都会被调用。

长响应可能会被分成单独的响应,您可以通过内容流开始更快地接收响应。

use GeminiAPI\Gemini;
use GeminiAPI\Resources\Parts\TextPart;
use GeminiAPI\Responses\GenerateContentResponse;

$callback = function (GenerateContentResponse $response): void {
    static $count = 0;

    print "\nResponse #{$count}\n";
    print $response->text();
    $count++;
};

$gemini = new Gemini('GEMINI_API_KEY');
$gemini->geminiPro()->generateContentStream(
    $callback,
    [new TextPart('PHP in less than 100 chars')],
);
// Response #0
// PHP: a versatile, general-purpose scripting language for web development, popular for
// Response #1
//  its simple syntax and rich library of functions.

流式聊天会话

需要启用 curl 扩展

use GeminiAPI\Gemini;
use GeminiAPI\Enums\Role;
use GeminiAPI\Resources\Content;
use GeminiAPI\Resources\Parts\TextPart;
use GeminiAPI\Responses\GenerateContentResponse;

$history = [
    Content::text('Hello World in PHP', Role::User),
    Content::text(
        <<<TEXT
        <?php
        echo "Hello World!";
        ?>
        
        This code will print "Hello World!" to the standard output.
        TEXT,
        Role::Model,
    ),
];

$callback = function (GenerateContentResponse $response): void {
    static $count = 0;

    print "\nResponse #{$count}\n";
    print $response->text();
    $count++;
};

$gemini = new Gemini('GEMINI_API_KEY');
$chat = $gemini->geminiPro()
    ->startChat()
    ->withHistory($history);

$chat->sendMessageStream($callback, new TextPart('in Go'));
Response #0
package main

import "fmt"

func main() {

Response #1
    fmt.Println("Hello World!")
}

This code will print "Hello World!" to the standard output.

嵌入内容

use GeminiAPI\Gemini;
use GeminiAPI\Enums\ModelName;
use GeminiAPI\Resources\Parts\TextPart;

$gemini = new Gemini('GEMINI_API_KEY');
$response = $gemini->embeddingModel(ModelName::Embedding)
    ->embedContent(
        new TextPart('PHP in less than 100 chars'),
    );

print_r($response->embedding->values);
// [
//    [0] => 0.041395925
//    [1] => -0.017692696
//    ...
// ]

缓存内容资源

创建

创建 CachedContent 资源。

此示例使用文档中使用的 《福尔摩斯小子》电影 视频。文件首先通过 媒体上传 上传

use GeminiAPI\Data\CachedContent;
use GeminiAPI\Data\Content;

$file = 'https://generativelanguage.googleapis.com/v1beta/files/7j0qhgcmeeqh';

$response = $gemini->cachedContents()->create(
    new CachedContent(
        model: 'models/gemini-1.5-flash-001',
        displayName: 'sherlock jr movie',
        systemInstruction: Content::createTextContent("You are an expert video analyzer, and your job is to answer the user\'s query based on the video file you have access to."),
        contents: [
            Content::createFileContent($file, 'video/mp4', 'user'),
        ],
        ttl: '3600s',
    ),
);

$response->model; // models/gemini-1.5-flash-001
$response->name; // cachedContents/lg5adbi62ykx
$response->displayName; // sherlock jr movie
$response->createTime->format('Y-m-d H:i:s'); // 2024-07-04 23:15:53
$response->updateTime->format('Y-m-d H:i:s'); // 2024-07-04 23:15:53
$response->usageMetadata->totalTokenCount; // 
$response->expireTime->format('Y-m-d H:i:s'); // 2024-07-05 00:15:53

$response->toArray(); // ['model' => 'models/gemini-1.5-flash-001', ...]
使用缓存内容生成内容

设置 generateContent 的超时为 60 秒,请求超时为 120 秒。如果您的请求仍然超过这些限制,您可能需要提出增加。

use GeminiAPI\Data\Content;

$response = $gemini->geminiPro15Flash001()->generateContentWithCache(
            ["cachedContent" => "cachedContents/n9l42h1iszbd"],
            new TextPart("Give me the summary of the file uploaded")
        );

echo $response->text();

删除

删除 CachedContent 资源。

$response = $gemini->cachedContents()->delete('cachedContents/2wojeqz7srpu');

if ($response === true) {
    echo 'Successfully deleted the cached Content';
}

获取

读取 CachedContent 资源。

$response = $gemini->cachedContents()->get('cachedContents/2wojeqz7srpu');

$response->model; // models/gemini-1.5-flash-001
$response->name; // cachedContents/2wojeqz7srpu
$response->displayName; // Repository Specialist
$response->createTime->format('Y-m-d H:i:s'); // 2024-07-04 23:15:53
$response->updateTime->format('Y-m-d H:i:s'); // 2024-07-04 23:15:53
$response->usageMetadata->totalTokenCount; // 259246
$response->expireTime->format('Y-m-d H:i:s'); // 2024-08-04 23:15:53

$response->toArray(); // ['model' => 'models/gemini-1.5-flash-001', ...]

列表

列出 CachedContents。

$response = $gemini->cachedContents()->list();

$response->nextPageToken; // 

foreach ($response->cachedContents as $cachedContent) {
    $cachedContent->model; // models/gemini-1.5-flash-001
    $cachedContent->name; // cachedContents/2wojeqz7srpu
    $cachedContent->displayName; // Repository Specialist
    $cachedContent->createTime->format('Y-m-d H:i:s'); // 2024-07-04 23:15:53
    $cachedContent->updateTime->format('Y-m-d H:i:s'); // 2024-07-04 23:15:53
    $cachedContent->usageMetadata->totalTokenCount; // 259246
    $cachedContent->expireTime->format('Y-m-d H:i:s'); // 2024-10-28 17:02:31
}

$response->toArray(); // ['cachedContents' => [...], ...]

修补

更新 CachedContent 资源(只有过期时间可更新)。

$response = $gemini->cachedContents()->patch([
    'name' => 'cachedContents/2wojeqz7srpu',
    'updateMask' => 'ttl',
    'cachedContent' => new CachedContent(
        ttl: '3600s'
    ),
]);

$response->model; // models/gemini-1.5-flash-001
$response->name; // cachedContents/2wojeqz7srpu
$response->displayName; // Repository Specialist
$response->createTime->format('Y-m-d H:i:s'); // 2024-07-04 23:15:53
$response->updateTime->format('Y-m-d H:i:s'); // 2024-07-05 07:02:21
$response->usageMetadata->totalTokenCount; // 259246
$response->expireTime->format('Y-m-d H:i:s'); // 2024-07-05 08:02:21

$response->toArray(); // ['model' => 'models/gemini-1.5-flash-001', ...]

文件资源

删除

删除 File

$response = $gemini->files()->delete('files/qrbxtbaehccw');
if ($response === true) {
    echo 'File deleted successfully';
}

获取

获取给定 File 的元数据。

$response = $gemini->files()->get('files/m8uuuytf6niz');

$response->name; // files/m8uuuytf6niz
$response->displayName; // Sample File 2
$response->mimeType; // image/jpeg
$response->sizeBytes; // 44485
$response->createTime->format('Y-m-d H:i:s'); // 2024-07-08 20:51:46
$response->updateTime->format('Y-m-d H:i:s'); // 2024-07-08 20:51:46
$response->expirationTime->format('Y-m-d H:i:s'); // 2024-07-10 20:51:46
$response->sha256Hash; // TZhZGZiMDUzMzM...
$response->uri; // https://generativelanguage.googleapis.com/v1beta/files/m8uuuytf6niz
$response->state->value; // ACTIVE

$response->toArray(); // ['name' => 'files/m8uuuytf6niz', ...]

列表

列出请求项目拥有的 File 的元数据。

$response = $gemini->files()->list();

$response->nextPageToken; // 

foreach ($response->files as $file) {
    $file->name; // files/qrbxtbaehccw
    $file->displayName; // Sample File
    $file->mimeType; // image/png
    $file->sizeBytes; // 357556
    $file->createTime->format('Y-m-d H:i:s'); // 2024-07-08 20:26:59
    $file->updateTime->format('Y-m-d H:i:s'); // 2024-07-08 20:26:59
    $file->expirationTime->format('Y-m-d H:i:s'); // 2024-07-10 20:26:59
    $file->sha256Hash; // NmI4NmM3M...
    $file->uri; // https://generativelanguage.googleapis.com/v1beta/files/qrbxtbaehccw
    $file->state->value; // ACTIVE
}

$response->toArray(); // ['files' => [...]]

媒体资源

上传

创建 File

use GeminiAPI\Data\File;

# Example uses video downloaded from
# https://storage.googleapis.com/generativeai-downloads/data/Sherlock_Jr_FullMovie.mp4

$metaData = new File(
    displayName: 'Demo File'
);

# The file was excluded from commit due to impact it'd have on cloning this repo,
# download and change path, or can upload any file of choice
$response = $gemini->media()->upload(__DIR__ .'/files/Sherlock_Jr_FullMovie.mp4', $metaData);

$file = $response->file;
$file->name; // files/7j0qhgcmeeqh
$file->displayName; // Sherlock Jr. video
$file->mimeType; // video/mp4
$file->sizeBytes; // 331623233
$file->createTime->format('Y-m-d H:i:s'); // 2024-07-27 22:31:25
$file->updateTime->format('Y-m-d H:i:s'); // 2024-07-27 22:31:25
$file->expirationTime->format('Y-m-d H:i:s'); // 2024-07-29 22:31:25
$file->sha256Hash; // ZjAwNGM2ZjJiMzNlNjYxYzYwOTU1MzU3MDliYzUzMjY4ZDUzMjNlYzdhNTdlOGJjNGFlOTczNjJlZDM0MWI1Yg==
$file->uri; // https://generativelanguage.googleapis.com/v1beta/files/7j0qhgcmeeqh
$file->state->value; // PROCESSING

$response->toArray(); // ['file' => [...]]

令牌计数

use GeminiAPI\Gemini;
use GeminiAPI\Resources\Parts\TextPart;

$gemini = new Gemini('GEMINI_API_KEY');
$response = $gemini->geminiPro()->countTokens(
    new TextPart('PHP in less than 100 chars'),
);

print $response->totalTokens;
// 10

列出模型

use GeminiAPI\Gemini;

$gemini = new Gemini('GEMINI_API_KEY');
$response = $gemini->listModels();

print_r($response->models);
//[
//  [0] => GeminiAPI\Resources\Model Object
//    (
//      [name] => models/gemini-pro
//      [displayName] => Gemini Pro
//      [description] => The best model for scaling across a wide range of tasks
//      ...
//    )
//  [1] => GeminiAPI\Resources\Model Object
//    (
//      [name] => models/gemini-pro-vision
//      [displayName] => Gemini Pro Vision
//      [description] => The best image understanding model to handle a broad range of applications
//      ...
//    )
//]

高级用法

安全设置和生成配置

use GeminiAPI\Gemini;
use GeminiAPI\Enums\HarmCategory;
use GeminiAPI\Enums\HarmBlockThreshold;
use GeminiAPI\GenerationConfig;
use GeminiAPI\Resources\Parts\TextPart;
use GeminiAPI\SafetySetting;

$safetySetting = new SafetySetting(
    HarmCategory::HARM_CATEGORY_HATE_SPEECH,
    HarmBlockThreshold::BLOCK_LOW_AND_ABOVE,
);
$generationConfig = (new GenerationConfig())
    ->withCandidateCount(1)
    ->withMaxOutputTokens(40)
    ->withTemperature(0.5)
    ->withTopK(40)
    ->withTopP(0.6)
    ->withStopSequences(['STOP']);

$gemini = new Gemini('GEMINI_API_KEY');
$response = $gemini->geminiPro()
    ->withAddedSafetySetting($safetySetting)
    ->withGenerationConfig($generationConfig)
    ->generateContent(
        new TextPart('PHP in less than 100 chars')
    );

使用您自己的 HTTP 客户端

use GeminiAPI\Gemini as Gemini;
use GeminiAPI\Resources\Parts\TextPart;
use GuzzleHttp\Client as GuzzleClient;

$guzzle = new GuzzleClient([
  'proxy' => 'https://:8125',
]);

$gemini = new Gemini('GEMINI_API_KEY', $guzzle);
$response = $gemini->geminiPro()->generateContent(
    new TextPart('PHP in less than 100 chars')
);

使用您自己的 HTTP 客户端进行流式响应

需要启用 curl 扩展

由于流式响应是通过 curl 扩展获取的,因此它们不能使用传递给 Gemini 客户端的自定义 HTTP 客户端。如果您想覆盖连接选项,则需要传递 CurlHandler

以下 curl 选项将由 Gemini 覆盖。

  • CURLOPT_URL
  • CURLOPT_POST
  • CURLOPT_POSTFIELDS
  • CURLOPT_WRITEFUNCTION

您还可以传递您希望在请求中使用的头信息。

use GeminiAPI\Gemini;
use GeminiAPI\Resources\Parts\TextPart;
use GeminiAPI\Responses\GenerateContentResponse;

$callback = function (GenerateContentResponse $response): void {
    print $response->text();
};

$ch = curl_init();
curl_setopt($ch, \CURLOPT_PROXY, 'https://:8125');

$gemini = new Gemini('GEMINI_API_KEY');
$gemini->withRequestHeaders([
        'User-Agent' => 'My Gemini-backed app'
    ])
    ->geminiPro()
    ->generateContentStream(
        $callback,
        [new TextPart('PHP in less than 100 chars')],
        $ch,
    );