You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PHP中Gmail API的Send/Get接口实现及现有代码优化咨询

Gmail API PHP Guzzle 调用指南

一、获取单封邮件(users.messages.get)

参数说明

  • access_token: 授权令牌,必填
  • email_address: 目标用户邮箱,可使用me指代当前授权用户
  • message_id: 要获取的邮件ID,从list接口返回结果中获取

Guzzle调用示例

use GuzzleHttp\Client;

public function getEmail($access_token, $email_address, $message_id) {
    $client = new Client();
    $uri = "https://gmail.googleapis.com/gmail/v1/users/{$email_address}/messages/{$message_id}";
    
    // 可选:指定返回格式,默认full,可选metadata/raw/minimal
    $query = ['format' => 'full'];
    
    $response = $client->request('GET', $uri, [
        'headers' => [
            'Authorization' => "Bearer {$access_token}",
            'Accept' => 'application/json'
        ],
        'query' => $query
    ]);
    
    return json_decode($response->getBody()->getContents(), true);
}

二、发送邮件(users.messages.send)

发送邮件分普通无附件和带附件两种场景,核心是构造符合RFC 2822规范的邮件内容,再进行base64url编码。

1. 普通无附件发送

参数说明

  • access_token: 授权令牌,必填
  • email_address: 发件人邮箱(或me)
  • raw_content: 符合RFC 2822的邮件原文,示例格式:
    From: 发件人 <sender@example.com>
    To: 收件人 <recipient@example.com>
    Subject: 邮件标题
    Content-Type: text/plain; charset="UTF-8"
    
    邮件正文内容
    

Guzzle调用示例

use GuzzleHttp\Client;

public function sendPlainEmail($access_token, $email_address, $raw_content) {
    // 转换为base64url编码(Gmail要求的编码格式)
    $raw_base64 = rtrim(strtr(base64_encode($raw_content), '+/', '-_'), '=');
    
    $client = new Client();
    $uri = "https://gmail.googleapis.com/gmail/v1/users/{$email_address}/messages/send";
    
    $response = $client->request('POST', $uri, [
        'headers' => [
            'Authorization' => "Bearer {$access_token}",
            'Content-Type' => 'application/json'
        ],
        'json' => [
            'raw' => $raw_base64
        ]
    ]);
    
    return json_decode($response->getBody()->getContents(), true);
}

2. 带附件发送

带附件需使用上传接口,且邮件内容要构造为multipart/mixed格式的RFC 2822内容,同时指定uploadType=multipart参数。

参数说明

  • 除上述参数外,需构造包含附件的multipart/mixed格式邮件原文
  • 接口URI需添加uploadType=multipart查询参数

Guzzle调用示例

use GuzzleHttp\Client;

public function sendEmailWithAttachment($access_token, $email_address, $multipart_content) {
    $raw_base64 = rtrim(strtr(base64_encode($multipart_content), '+/', '-_'), '=');
    
    $client = new Client();
    $uri = "https://gmail.googleapis.com/upload/gmail/v1/users/{$email_address}/messages/send?uploadType=multipart";
    
    $response = $client->request('POST', $uri, [
        'headers' => [
            'Authorization' => "Bearer {$access_token}",
            'Content-Type' => 'application/json'
        ],
        'json' => [
            'raw' => $raw_base64
        ]
    ]);
    
    return json_decode($response->getBody()->getContents(), true);
}

注:multipart_content需按MIME规范构造,包含正文、附件的独立部分,用自定义边界分隔符区分各块内容。

三、原emailSend函数优化指导

原函数存在几个关键问题,以下是修正后的版本及说明:

问题分析

  1. 使用form_params传递参数错误:Gmail send接口要求请求体为JSON格式,而非表单提交
  2. 带附件场景缺失uploadType参数:上传接口必须添加?uploadType=multipart才能正确处理附件
  3. 逻辑无问题,但参数传递方式不符合接口要求

修正后的函数

use GuzzleHttp\Client;

public function emailSend($access_token, $data, $email_address, $attach_status)
{
    // 确保$data是完整的RFC 2822格式邮件内容,转换为base64url编码
    $raw_base64 = rtrim(strtr(base64_encode($data), '+/', '-_'), '=');
    $client = new Client();
    
    // 基础接口地址
    $uri = "https://gmail.googleapis.com/gmail/v1/users/{$email_address}/messages/send";
    
    // 带附件时切换到上传接口并添加必要参数
    if ($attach_status == 1) {
        $uri = "https://gmail.googleapis.com/upload/gmail/v1/users/{$email_address}/messages/send?uploadType=multipart";
    }
    
    $params = [
        'headers' => [
            'Authorization' => "Bearer {$access_token}",
            'Content-Type' => 'application/json',
            'Accept' => 'application/json'
        ],
        'json' => [ // 替换form_params为json,匹配接口要求的请求格式
            'raw' => $raw_base64
        ]
    ];
    
    $response = $client->request('POST', $uri, $params);
    return json_decode($response->getBody()->getContents(), true);
}

调用注意事项

  • $data必须是完整的RFC 2822格式邮件内容,包含发件人、收件人、主题、正文(带附件时需包含附件MIME块)
  • 使用me作为$email_address时,需确保access_token对应的授权用户为目标邮箱账号

内容的提问来源于stack exchange,提问作者codewiz

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.11 17:35:24