如何在使用 laravel/socialite 和 facebook/graph-sdk 时从控制器发送 Facebook 页面 post?

How can I send Facebook page post from controller while using laravel/socialite and facebook/graph-sdk?

我知道对于有经验的 Laravel 开发人员来说,这个问题听起来很愚蠢,但我遵循 this article 实施 Facebook SDK。

我遵循了从在数据库中添加新标记列到实现控制器的所有操作。

这是我的 GraphController.php 文件:

class GraphController extends Controller
{
  private $api;
  public function __construct(Facebook $fb)
  {
      $this->middleware(function ($request, $next) use ($fb) {
          $fb->setDefaultAccessToken(Auth::user()->token);
          $this->api = $fb;
          return $next($request);
      });
  }

  public function getPageAccessToken($page_id){
      try {
           // Get the \Facebook\GraphNodes\GraphUser object for the current user.
           // If you provided a 'default_access_token', the '{access-token}' is optional.
           $response = $this->api->get('/me/accounts', Auth::user()->token);
      } catch(FacebookResponseException $e) {
          // When Graph returns an error
          echo 'Graph returned an error: ' . $e->getMessage();
          exit;
      } catch(FacebookSDKException $e) {
          // When validation fails or other local issues
          echo 'Facebook SDK returned an error: ' . $e->getMessage();
          exit;
      }

      try {
          $pages = $response->getGraphEdge()->asArray();
          foreach ($pages as $key) {
              if ($key['id'] == $page_id) {
                  return $key['access_token'];
              }
          }
      } catch (FacebookSDKException $e) {
          dd($e); // handle exception
      }
  }

    public function publishToPage(Request $request, $title){

        $page_id = 'XXXXXXXXXXXXX';

        try {
            $post = $this->api->post('/' . $page_id . '/feed', array('message' => $title), $this->getPageAccessToken($page_id));

            $post = $post->getGraphNode()->asArray();


        } catch (FacebookSDKException $e) {
            dd($e); // handle exception
        }
    }
}

这是我的 routes/web.php :

Route::group(['middleware' => [
    'auth'
]], function(){

    Route::post('/page', 'GraphController@publishToPage');

});

FacebookServiceProvider:


class FacebookServiceProvider extends ServiceProvider
{
    /**
     * Register services.
     *
     * @return void
     */
    public function register()
    {
        $this->app->singleton(Facebook::class, function ($app) {
            $config = config('services.facebook');
            return new Facebook([
                'app_id' => $config['client_id'],
                'app_secret' => $config['client_secret'],
                'default_graph_version' => 'v2.6',
            ]);
        });
    }
}

现在,我需要在 PostController.php 文件中使用 publishToPage:

  public function store(Requests\PostRequest $request)
    {

          $data = $this->handleRequest($request);

          $newPost = $request->user()->posts()->create($data);
          $newPost->createTags($data["post_tags"]);

/*
             // My other notifications that are working:

              // OneSignal
              OneSignal::sendNotificationToAll(
                "New warning ".$newPost->title
              );

              // MailChimp
              $this->notify($request, $newPost);

              // Twitter
              $newPost->notify(new ArticlePublished());
*/

              // I WOULD NEED SOMETHING IN THIS WAY ALSO FOR FACEBOOK BUT THIS OBVIOUSLY DOESN'T WORK
              GraphController::publishToPage($request, $newPost->title);
   }

你能从这里建议如何做的好方法吗?

如果您觉得我应该了解 Laravel 的基础知识,我需要再次道歉,但我真的很难理解这一点,您的建议确实可以帮助我更好地理解它。

集成 Twitter、MailChimp、OneSignal 通知真的很容易,但 Facebook 的限制政策让我很困惑。

谢谢你们。非常感谢!

遗憾的是,Facebook 仍然没有获得我自动发布的许可,所以我不能尝试,如果它真的有效。

我想我找到了解决这个特定问题的方法。感谢来自 Laracast 的 Sti3bas。

namespace App\Services;

class FacebookPoster
{
   protected $api;

   public function __construct(Facebook $fb)
   {
      $fb->setDefaultAccessToken(Auth::user()->token);
      $this->api = $fb;
   }

   protected function getPageAccessToken($page_id){
      try {
           // Get the \Facebook\GraphNodes\GraphUser object for the current user.
           // If you provided a 'default_access_token', the '{access-token}' is optional.
           $response = $this->api->get('/me/accounts', Auth::user()->token);
      } catch(FacebookResponseException $e) {
          // When Graph returns an error
          echo 'Graph returned an error: ' . $e->getMessage();
          exit;
      } catch(FacebookSDKException $e) {
          // When validation fails or other local issues
          echo 'Facebook SDK returned an error: ' . $e->getMessage();
          exit;
      }

      try {
          $pages = $response->getGraphEdge()->asArray();
          foreach ($pages as $key) {
              if ($key['id'] == $page_id) {
                  return $key['access_token'];
              }
          }
      } catch (FacebookSDKException $e) {
          dd($e); // handle exception
      }
  }

   public function publishToPage($page, $title){
      try {
         $post = $this->api->post('/' . $page . '/feed', array('message' => $title), $this->getPageAccessToken($page));

         $post = $post->getGraphNode()->asArray();
        } catch (FacebookSDKException $e) {
            dd($e); // handle exception
        }
    }
}

然后重构控制器:

use App\Services\FacebookPoster;

//...

class GraphController extends Controller
{
   public function publishToPage(Request $request, FacebookPoster $facebookPoster)
   {
      $page_id = 'XXXXXXXXXXXXX';
      $title = 'XXXXXXXXXXXXX';

      $facebookPoster->publishToPage($page_id, $title);
   }
}

use App\Services\FacebookPoster;

//...

public function store(PostRequest $request, FacebookPoster $facebookPoster)
{
   $data = $this->handleRequest($request);

   $newPost = $request->user()->posts()->create($data);
   $newPost->createTags($data["post_tags"]);

   //...

   $facebookPoster->publishToPage($page, $newPost->title);
 }