无尘阁日记

无尘阁日记

使用 Yii2 将数据库中的数据通过 API 推送到微信公众号草稿箱的教程
2024-07-28

一、配置数据库

首先,在 Yii2 的配置文件中配置数据库连接。修改 `config/db.php` 文件:

return [
'class' => 'yii\db\Connection',
'dsn' => 'mysql:host=localhost;dbname=your_database_name',
'username' => 'your_username',
'password' => 'your_password',
'charset' => 'utf8',
];

二、创建数据库表

创建一个数据库表用于存储文章数据。执行以下 SQL 语句:

CREATE TABLE `articles` (
`id` INT AUTO_INCREMENT PRIMARY KEY,
`title` VARCHAR(255) NOT NULL,
`content` TEXT NOT NULL,
`author` VARCHAR(255) NOT NULL,
`summary` TEXT,
`cover_image` VARCHAR(255)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

三、创建模型

在 Yii2 中创建一个模型类 `Article`,用于操作 `articles` 表:

namespace app\models;

use Yii;
use yii\db\ActiveRecord;

class Article extends ActiveRecord
{
public static function tableName()
{
return 'articles';
}

public function rules()
{
return [
[['title', 'content', 'author'], 'required'],
[['content', 'summary'], 'string'],
[['title', 'author', 'cover_image'], 'string', 'max' => 255],
];
}
}

四、实现微信公众号的 API 调用

创建一个服务类 `WechatService`,用于处理微信公众号的 API 请求。使用 Yii2 的 HTTP 客户端发送请求。

获取 Access Token

namespace app\services;

use Yii;
use yii\httpclient\Client;

class WechatService
{
   const APP_ID = 'your_wechat_app_id';
   const APP_SECRET = 'your_wechat_app_secret';
   const TOKEN_URL = 'https://api.weixin.qq.com/cgi-bin/token';
   const DRAFT_URL = 'https://api.weixin.qq.com/cgi-bin/draft/add';
   const UPLOAD_URL = 'https://api.weixin.qq.com/cgi-bin/media/upload';

   private $accessToken;

   public function getAccessToken()
   {
       if ($this->accessToken) {
           return $this->accessToken;
       }

       $client = new Client();
       $response = $client->get(self::TOKEN_URL, [
           'grant_type' => 'client_credential',
           'appid' => self::APP_ID,
           'secret' => self::APP_SECRET,
       ])->send();

       if ($response->isOk) {
           $this->accessToken = $response->data['access_token'];
           return $this->accessToken;
       } else {
           throw new \Exception('Failed to get access token: ' . $response->data['errmsg']);
       }
   }

   public function uploadImage($imagePath)
   {
       $client = new Client();
       $response = $client->createRequest()
           ->setMethod('POST')
           ->setUrl(self::UPLOAD_URL . '?access_token=' . $this->getAccessToken())
           ->setData(['type' => 'image'])
           ->addFile('media', $imagePath)
           ->send();

       if ($response->isOk) {
           return $response->data['media_id'];
       } else {
           throw new \Exception('Failed to upload image: ' . $response->data['errmsg']);
       }
   }

   public function pushArticleToDraft($article)
   {
       $thumbMediaId = $this->uploadImage(Yii::$app->basePath . DIRECTORY_SEPARATOR . $article->cover_image);
       $data = [
           'articles' => [
               [
                   'title' => $article->title,
                   'thumb_media_id' => $thumbMediaId,
                   'author' => $article->author,
                   'digest' => $article->summary,
                   'content' => $article->content,
                   'content_source_url' => '',
                   'need_open_comment' => 1,
                   'only_fans_can_comment' => 0,
               ],
           ],
       ];

       $client = new Client();
       $response = $client->createRequest()
           ->setMethod('POST')
           ->setUrl(self::DRAFT_URL . '?access_token=' . $this->getAccessToken())
           ->setFormat(Client::FORMAT_JSON)
           ->setData($data)
           ->send();

       if ($response->isOk) {
           return $response->data;
       } else {
           throw new \Exception('Failed to push article to draft: ' . $response->data['errmsg']);
       }
   }
}

五、从数据库取出数据并推送文章到草稿箱

在控制器中创建一个方法,用于从数据库中取出数据,并调用 `WechatService` 进行推送:

namespace app\controllers;

use Yii;
use yii\web\Controller;
use app\models\Article;
use app\services\WechatService;

class ArticleController extends Controller
{
   public function actionPushToDraft()
   {
       $articles = Article::find()->all();
       $wechatService = new WechatService();

       foreach ($articles as $article) {
           try {
               $result = $wechatService->pushArticleToDraft($article);
               Yii::info('Article pushed to draft: ' . json_encode($result));
           } catch (\Exception $e) {
               Yii::error('Failed to push article: ' . $e->getMessage());
           }
       }

       return 'Articles pushed to draft successfully.';
   }
}

六、验证和调试

1. 启动 PHP 内置服务器

    php -S localhost:8080 -t web

2. 访问 `actionPushToDraft` 方法

  启用了 URL 美化:

      http://localhost:8080/article/push-to-draft

  没有启用 URL 美化:

      http://localhost:8080/index.php?r=article/push-to-draft

3. 调试输出:在推送文章到草稿箱之前,可以打印出请求对象,确保所有设置都已正确应用。

    print_r($request->getHeaders()); // 打印出请求头部信息

通过以上步骤,你可以实现从数据库中取出数据,并通过微信公众号的 API 推送文章到草稿箱。通过调试输出和日志记录,确保请求数据和 API 调用符合预期。

发表评论: