123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306 |
- <?php
- namespace App\Services\Smm;
- use App\Services\Contracts\SmmPlatformInterface;
- use Carbon\Carbon;
- use Illuminate\Http\Request;
- use \Facebook\Facebook;
- use Illuminate\Support\Facades\Session;
- use \Facebook\Exceptions\FacebookResponseException;
- use \Facebook\Exceptions\FacebookSDKException;
- class FacebookService implements SmmPlatformInterface
- {
- public $fb = null;
- public $pageAccessToken = null;
- // 构造函数,传入配置信息
- public $configData = [];
- public function __construct($configData) {
- $this->configData = $configData;
- $this->fb = new Facebook([
- 'app_id' => env('SSM_FACEBOOK_APP_ID'), // 替换为您的App ID
- 'app_secret' => env('SSM_FACEBOOK_APP_SECRET'), // 替换为您的App Secret
- 'default_graph_version' => 'v19.0', // 使用当前版本
- ]);
- //$this->pageAccessToken = $pageAccessToken;
- }
- /*
- * OAuth 2.0 授权登录
- * 返回授权地址:https://example.com/fb-callback.php
- */
- public function login()
- {
- session_start();
- // 实现Facebook登录逻辑
- $helper = $this->fb->getRedirectLoginHelper();
- $permissions = [
- 'publish_video',
- 'pages_manage_cta',
- 'pages_show_list',
- 'business_management',
- 'pages_read_engagement',
- 'pages_manage_metadata',
- 'pages_read_user_content',
- 'pages_manage_ads',
- 'pages_manage_posts',
- 'pages_manage_engagement',
- ];
- $loginUrl = $helper->getLoginUrl(env('DIST_SITE_URL').'/dist/callback/facebook', $permissions);
- return ['status'=>true, 'data' => ['url'=>$loginUrl]];
- }
- /*
- * OAuth 2.0 授权回调
- * 授权成功后,得到access_token,refresh_token等信息, 保存到数据库中
- * 授权成功后,返回回调需要的数据
- */
- public function loginCallback(Request $request)
- {
- $helper = $this->fb->getRedirectLoginHelper();
- if (isset($_GET['state'])) {
- // 由于session的原因,这里需要重新设置state
- $helper->getPersistentDataHandler()->set('state', $_GET['state']);
- }
- try {
- $accessToken = $helper->getAccessToken();
- } catch (Facebook\Exceptions\FacebookResponseException $e) {
- return ['status' => false, 'data' => 'Graph API错误:' . $e->getMessage()];
- } catch (Facebook\Exceptions\FacebookSDKException $e) {
- return ['status' => false, 'data' => 'SDK错误:' . $e->getMessage()];
- }
- if (isset($accessToken)) {
- // 可选:将短期令牌转换为长期令牌(有效期约60天)
- $oAuth2Client = $this->fb->getOAuth2Client();
- $longLivedAccessToken = $oAuth2Client->getLongLivedAccessToken($accessToken);
- $useriInfo = $this->getFacebookUser($longLivedAccessToken->getValue());
- if ($useriInfo['status'] == false) {
- return ['status' => false, 'data' => $useriInfo['data']];
- }
- $expiresAt = $longLivedAccessToken->getExpiresAt();
- //DateTime转 carbon
- if ($expiresAt != null) {
- $expiresAt = $expiresAt->format('Y-m-d H:i:s');
- } else {
- $expiresAt = Carbon::now()->addDays(60)->format('Y-m-d H:i:s');
- }
- //$expiresAt = $expiresAt->format('Y-m-d H:i:s');
- //保存到数据库中
- return ['status' => true, 'data' => ['accessToken' => $longLivedAccessToken->getValue(),'accessToken_expiresAt'=>$expiresAt,'userName'=>$useriInfo['data']['name'],'userId'=>$useriInfo['data']['id']]];
- } else {
- return ['status' => false, 'data' => '无法获取访问令牌'];
- }
- }
- /*
- * 发布图片,可以发多个图片
- * $imagePath = ['/path/to/image1.jpg','/path/to/image2.jpg'];
- */
- public function postImage($message,$imagePaths,$accessToken) {
- // 获取pageAccessToken
- $info = $this->getAccountsInfo($accessToken);
- if ($info['status'] == false) {
- return ['status' => false, 'data' => $info['data']];
- }
- try {
- $requestContent = [];
- $responseContent = [];
- $postIds = [];
- foreach ($info['data'] as $value) {
- $mediaIds = [];
- $pageId = $value['id'];
- // 第一步:上传每张图片,获取 media_id
- foreach ($imagePaths as $imagePath){
- //dd($imagePath);
- $pageAccessToken = $value['pageAccessToken'];
- $postData = [
- 'source' => $this->fb->fileToUpload($imagePath), // 上传图片文件
- // 'source' => $imagePath, // 上传图片文件
- 'published' => false, // 添加描述
- ];
- $postUrl = '/'.$pageId.'/photos';
- $response = $this->fb->post(
- $postUrl,
- $postData,
- $pageAccessToken
- );
- $requestContent[] = ['postUrl'=>$postUrl,'data'=>$postData,'pageAccessToken'=>$pageAccessToken];
- $responseContent[] = $response->getDecodedBody();
- $mediaIds[] = $response->getDecodedBody()['id'];
- }
- // 第二步:发布帖子,附加多个 media_id
- $attachedMedia = array_map(function($id) {
- return ['media_fbid' => $id];
- }, $mediaIds);
- $feedParams = [
- 'message' => $message,
- 'attached_media' => json_encode($attachedMedia)
- ];
- $postUrl = '/'.$pageId.'/feed';
- $response = $this->fb->post(
- $postUrl,
- $feedParams, $pageAccessToken
- );
- $requestContent[] = ['postUrl'=>$postUrl,'data'=>$feedParams,'pageAccessToken'=>$pageAccessToken];
- $responseContent[] = $response->getDecodedBody();
- $postIds[] = $response->getDecodedBody()['id'];
- }
- return ['status' => true, 'data' => ['responseIds' => $postIds,'requestContent'=>$requestContent,'responseContent'=>$responseContent]];
- } catch (Facebook\Exceptions\FacebookResponseException $e) {
- $errorMsg = 'Graph API错误:' . $e->getMessage();
- } catch (Facebook\Exceptions\FacebookSDKException $e) {
- $errorMsg = 'SDK错误:' . $e->getMessage();
- }
- return ['status'=>false,'data' => $errorMsg];
- }
- /*
- * 发布视频,只能发一个视频
- */
- public function postVideo($message,$videoPath,$accessToken) {
- $info = $this->getAccountsInfo($accessToken);
- if ($info['status'] == false) {
- return ['status' => false, 'data' => $info['data']];
- }
- try {
- $postIds = [];
- $requestContent = [];
- $responseContent = [];
- foreach ($info['data'] as $value) {
- $pageId = $value['id'];
- $pageAccessToken = $value['pageAccessToken'];
- $data = [
- 'source' => $this->fb->fileToUpload($videoPath), // 上传图片文件
- 'description' => $message, // 添加描述
- ];
- $response = $this->fb->post(
- '/'.$pageId.'/videos',
- $data,
- $pageAccessToken
- );
- $requestContent[] = ['url'=>'/'.$pageId.'/videos','data'=>$data,'pageAccessToken'=>$pageAccessToken];
- $responseContent[] = $response->getDecodedBody();
- $postIds[] = $response->getDecodedBody()['id'];
- //第二步:发布帖子,附加 media_id
- }
- return ['status' => true, 'data' => ['responseIds' => $postIds,'requestContent'=>$requestContent,'responseContent'=>$responseContent]];
- } catch (Facebook\Exceptions\FacebookResponseException $e) {
- $errorMsg = 'Graph API错误:' . $e->getMessage();
- } catch (Facebook\Exceptions\FacebookSDKException $e) {
- $errorMsg = 'SDK错误:' . $e->getMessage();
- }
- return ['status'=>false,'data' => $errorMsg];
- }
- public function getComments($postId) {
- }
- public function replyToComment($commentId) {
- }
- public function deleteComment($commentId) {
- }
- /**
- * 获取Facebook用户信息
- * @param string $accessToken
- * @return array [
- * 'name' => string,
- * 'id' => string,
- * 'error' => string|null
- * ]
- */
- public function getFacebookUser($accessToken)
- {
- try {
- // 验证并设置访问令牌
- $this->fb->setDefaultAccessToken($accessToken);
- // 发送请求获取用户信息
- $response = $this->fb->get('/me?fields=name,id');
- $userNode = $response->getGraphUser();
- return [
- 'status' => true,
- 'data' => [
- 'name' => $userNode->getName(),
- 'id' => $userNode->getId(),
- ]
- ];
- } catch (FacebookResponseException $e) {
- // API 响应错误处理
- $errorMsg = 'Graph API Error: ' . $e->getMessage();
- } catch (FacebookSDKException $e) {
- // SDK 错误处理
- $errorMsg = 'SDK Error: ' . $e->getMessage();
- } catch (Exception $e) {
- // 其他错误处理
- $errorMsg = 'General Error: ' . $e->getMessage();
- }
- return [
- 'status' => false,
- 'data' => $errorMsg
- ];
- }
- public function getAccountsInfo($accessToken) {
- try {
- // 验证并设置访问令牌
- $this->fb->setDefaultAccessToken($accessToken);
- // 发送请求获取用户信息
- $response = $this->fb->get('/me/accounts');
- $userNode = $response->getDecodedBody();
- if ($userNode['data'] == [] || $userNode['data'] == null || $userNode['data'] == '') {
- return [
- 'status' => false,
- 'data' => '没有获取到任何账号信息'
- ];
- }
- $data = [];
- foreach ($userNode['data'] as $value) {
- $data[] = [
- 'id' => $value['id'],
- 'name' => $value['name'],
- 'pageAccessToken' => $value['access_token'],
- ];
- }
- return [
- 'status'=>true,
- 'data' => $data
- ];
- } catch (FacebookResponseException $e) {
- // API 响应错误处理
- $errorMsg = 'Graph API Error: ' . $e->getMessage();
- } catch (FacebookSDKException $e) {
- // SDK 错误处理
- $errorMsg = 'SDK Error: ' . $e->getMessage();
- } catch (Exception $e) {
- // 其他错误处理
- $errorMsg = 'General Error: ' . $e->getMessage();
- }
- return [
- 'status'=>false,
- 'data' => $errorMsg
- ];
- }
- }
|