facebook october 2013 migration affects likes.count field in Graph Api call - php

When i enable migration to october 2013, likes.count field is not seen for each post of fb page/group by Graph Api feed call.So this field per post will be permanently removed from Graph api call like pageid/feed?limit=20 on october.
But i show this feed in many websites with how many total likes per post.so then i have to find alternatives,so is i got through google.com that -
It's needed to have another Graph api or fql query call for likes count per post along with the first call for page feed
so if it's possible to know likes count per post in only one Graph Api call, then tell me or what is the correct way to go for another Graph Api,Fql query call for all likes count per post?

Once you have loaded the Facebook page feed:
$config = array();
$config['appId'] = your_app_id;
$config['secret'] = your_secret_number;
$confif['fileUpload'] = false;
$facebook = new Facebook($config);
$pageid = facebook_page_id;
$pagefeed = $facebook->api('/' . $pageid . '/feed');
You can loop through the data and find a field called 'likes'.
With an other loop you can get the total number of likes for the corresponding post.
If you want the number of likes for a posted comment there is also a field called 'like_count'
that directly gives the number of likes for this comment.
Retrieving likes count per post :
foreach ($pagefeed['data'] as $post)
{
$likes_number = 0;
if (isset($post['likes']))
{
foreach ($post['likes']['data'] as $like)
$likes_number++;
}
}
Retrieving likes count for each comment :
if (isset($post['comments']))
{
foreach ($post['comments']['data'] as $comment)
{
echo $comment['like_count'];
}
}

Related

Facebook API (PHP) : Get Full Ads List

I am using Facebook API to fetch the full Ads list.
The Code is working, But it return only 25 Ad in case of i have 150+ Ad in my account.
I guess that happens because of the query limits on the Facebook API.
My Code:
$account = new AdAccount('act_<AD_ACCOUNT_ID>');
$account->read();
$fields_adset = array(
AdSetFields::ID,
AdSetFields::NAME,
AdSetFields::CAMPAIGN_ID,
AdSetFields::STATUS,
);
$ads = $account->getAds($fields_adset);
foreach ($ads as $adset) {
$adset_id = $adset->{AdSetFields::ID};
echo $adset_id;
//print_r($adset);
//exit();
}
So, they mentioned in the documentation that :
Use Asynchronous Requests to query a huge amount of data
Reference (1) : https://developers.facebook.com/docs/marketing-api/best-practices/
Reference (2) : https://developers.facebook.com/docs/marketing-api/insights/best-practices/#asynchronous
But, I can't apply that "Asynchronous" requests to my code to fetch the Full Ad List,
Please help me to fetch the full Ads list
Thank you.
You should implement pagination (or request a limit more high). With the PHP SDK you can implement the cursor as described in the doc here or more simply set the Implicit Fetching, as example:
..
use FacebookAds\Cursor;
...
Cursor::setDefaultUseImplicitFetch(true);
$account = new AdAccount('act_<AD_ACCOUNT_ID>');
$account->read();
$fields_adset = array(
AdSetFields::ID,
AdSetFields::NAME,
AdSetFields::CAMPAIGN_ID,
AdSetFields::STATUS,
);
$ads = $account->getAds($fields_adset);
foreach ($ads as $adset) {
$adset_id = $adset->{AdSetFields::ID};
echo $adset_id;
//print_r($adset);
//exit();
}
Hope this help

How to retrieve all my active Facebook ads?

I'm creating a dashboard for myself that helps me keep track of the Facebook ads I'm running.
What I've not been able to figure out is:
How can I retrieve an array of ad IDs for all ads that are active or could soon be active after no further action on my part?
In other words, I want all ads that I've set to Active and that exist within Adsets and Campaigns that are active (and therefore these ads are live right now)... plus all the ads that from my perspective are Active but that Facebook has set to another status such as Pending Review (and will soon set back to Active).
I have some code below, but the problem is that it also accidentally includes Pending ads that--once reviewed and approved by Facebook--will be inactive rather than active (because I've set them that way). And I do NOT want this type of ad to be included in my report.
My report should only show me ones where I'm actively spending money or have the potential to spend money as soon as FB approves them.
I think I understand the difference between configured_status and effective_status in AbstractArchivableCrudObjectFields, but I don't know that it's enough to help me because I have lots of ads set to Active that are within Adsets that are Inactive, and I don't want to see those listed in my report.
Any recommendations?
public function getActiveAdIds() {
$key = 'activeAdIds';
$adIdsJson = Cache::get($key);
if ($adIdsJson) {
$adIds = json_decode($adIdsJson);
} else {
$adsResponse = $this->getAdsByStatus([ArchivableCrudObjectEffectiveStatuses::ACTIVE, ArchivableCrudObjectEffectiveStatuses::PENDING_REVIEW]);
$ads = $adsResponse->data;
$adIds = [];
foreach ($ads as $ad) {
$adIds[] = $ad->id;
}
$adIdsJson = json_encode($adIds);
Cache::put($key, $adIdsJson, 1);
}
return $adIds;
}
public function getAdsByStatus($statuses) {
$params = [\FacebookAds\Object\Fields\AbstractArchivableCrudObjectFields::EFFECTIVE_STATUS => $statuses];
$adAccount = new AdAccount(self::ACT_PREPEND . $this->fbConfig['account_id']);
$cursor = $adAccount->getAds([], $params);
$response = $cursor->getResponse();
$jsonString = $response->getBody();
return json_decode($jsonString);
}
I get stats based on assets for my active campaigns. I have 119 ad accounts. This is php code which I used it for this purpose (any suggestion to improve it will be appreciated):
$fields = array(AdsInsightsFields::ACCOUNT_NAME,AdsInsightsFields::CAMPAIGN_ID,
AdsInsightsFields::CAMPAIGN_NAME, AdsInsightsFields::ADSET_ID,
AdsInsightsFields::ADSET_NAME,AdsInsightsFields::DATE_START,
AdsInsightsFields::DATE_STOP,AdsInsightsFields::REACH,
AdsInsightsFields::SPEND, AdsInsightsFields::IMPRESSIONS,
AdsInsightsFields::CLICKS, AdsInsightsFields::WEBSITE_CLICKS,
AdsInsightsFields::CALL_TO_ACTION_CLICKS,AdsInsightsFields::ACTIONS,
AdsInsightsFields::TOTAL_ACTIONS,AdsInsightsFields::CPC,
AdsInsightsFields::CPM,AdsInsightsFields::CPP,
AdsInsightsFields::CTR,AdsInsightsFields::OBJECTIVE,);
$params_c['date_preset'] = AdDatePresetValues::YESTERDAY;
$params_c['time_increment'] = 1;
$params_c['action_attribution_windows'] = array('1d_view', '28d_click');
$params_c['effective_status'] = AdStatusValues::ACTIVE;
$params_c['level'] = AdsInsightsLevelValues::ADSET;
$params_c['filtering'] = [array("field"=>"campaign.delivery_info",
"operator"=>"IN",
"value"=>array("active"))];
$params_c['fields']= $fields;
try{
// Initialize a new Session and instanciate an Api object
Api::init(self::api_key, self::secret_token, self::extended_token)->getHttpClient()->setCaBundlePath( $this->path_cert);
// The Api object is now available trough singleton
$api = Api::instance();
$user = new \FacebookAds\Object\Business($business_id);
$user->read(array(BusinessFields::ID));
//get all ad_account from Business
$accounts = $user->getAssignedAdAccounts(
array(
AdAccountFields::ID,
),
array('limit'=>1000,)
);
} catch (FacebookAds\Exception\Exception $ex) {
return $ex->getMessage();
}
if(isset($accounts) && ($accounts->count() > 0)):
do{
$ad_account = $accounts->current();
$adset_insights = $ad_account->getInsights($fields,$params_c);
do {
$adset_insights->fetchAfter();
} while ($adset_insights->getNext());
$adsets = $adset_insights->getArrayCopy(true);
}
while ($accounts->current());
endif;
If you include the adset{end_time} field in the query for the ad, you can assume that ad is not actually running if the end_time was in the past. This is how we get a base list of ads to query on.
The next step we take (which probably won't help you, unfortunately, but may help others) is building a batch of simple requests (one per ad) to see if there are any insights data for that day. If the response is an empty 'data' array, we can remove that ID from the ad list.
After we've reduced the size of the ad list with those two steps we can then make requests to run all of our breakdown reports. This method almost cut our API requests in half.
I have yet to find a way to do a "give me all ads that are for sure running this day" query in one step.
Edit:
I just found a better way to do this.... :
curl -G \
-d 'access_token=<ACCESS_TOKEN>' \
-d 'level=campaign' \
-d 'filtering=[{field:"ad.impressions",operator:"GREATER_THAN",value:0}]' \
'https://graph.facebook.com/v2.7/act_<ACCOUNT_ID>/insights'

YouTube API v3 get last video in playlist

Some basic background: I help run a gaming channel on YouTube, and I'm building a utility (using PHP) to integrate the channel's content with a companion website. Our playlists are primarily "let's play" series ordered by publication date that follow chronological progress through various games, and I would like the website to display the "latest episode" from a select number of series.
I know that I can work my way to the last video by chaining calls to the following:
$youtubeService->playlistItems->listPlaylistItems(
"snippet",
array(
"playlistId" => $playlistId
"pageToken" => $nextPageToken
)
)
And simply grab the last item in the response set when $nextPageToken is unset.
However, this strikes me as incredibly inefficient--partly because I believe it eats away at my API request quota, but mostly because it's going to slow down the overall response time of the site. Neither of those are ideal.
It seems like there should be an easier way to grab the "latest" video in a playlist either by changing the order of the response, or with some handy function, but I can't find any documentation on it.
I've looked at using the Search functions over the PlaylistItems, but (according to the documentation), Search only accepts Channel IDs as a parameter and not Playlist IDs, which makes me think that its the wrong direction to head.
The short answer here is that this appears to be impossible under the current version of the API. There is no apparent way to essentially select videos in reverse, but I did make a minor change which resulted in whole process being a tad more efficient.
This is the original code:
$items = $youtube->playlistItems->listPlaylistItems(
"snippet",
array(
"playlistId" => $playlistId,
"maxResults" => 50
)
);
while ($items->nextPageToken) {
$items = $youtube->playlistItems->listPlaylistItems(
"snippet",
array(
"playlistId" => $playlistId,
"maxResults" => 50,
"pageToken" => $items->nextPageToken
)
);
}
if ($items) {
return end($items->getItems());
}
This is the fix:
First, I added an object to assist with caching:
class PlaylistCache {
protected $expirationDate;
protected $playlistId;
protected $latestEpisode;
__construct($playlistId, $latestEpisode) {
$this-playlistId = $playlistId;
$this->latestEpisode = $latestEpisode;
$this->expirationDate = time() + 86400;
// get current time + 24 hours
}
public function getLatestEpisode() {
return $this->latestEpisode;
}
public function getPlaylistId() {
return $this->playlistId;
}
public function isExpired() {
return $this->expirationDate < time();
}
}
Then, before polling the API, I look to see if I have a cached version available, and I only resort to the API if that cached version is expired.
$playlistCache = json_decode(get_option('playlist_cache_' . $playlistId));
if ($playlistCache->isExpired()) {
$items = $youtube->playlistItems->listPlaylistItems(
"id",
array(
"playlistId" => $playlistId,
"maxResults" => 50
)
);
while ($items->nextPageToken) {
$items = $youtube->playlistItems->listPlaylistItems(
"id",
array(
"playlistId" => $playlistId,
"maxResults" => 50,
"pageToken" => $items->nextPageToken
)
);
}
if ($items) {
$videoId = end($items->getItems()[0]->getId());
$video = $youtube->videos->listVideos("snippet", array('id' => $videoId))
$video = $video->getItems()[0];
$playlistCache = new PlaylistCache($playlistId, $video);
update_option('playlist_cache_' . $playlistId, json_encode($playlistCache)));
}
}
return $playlistCache->getLatestEpisode();
The other big change here is that my calls to listPlaylistItems() are requesting the id instead of the snippet.
According to the documentation, the snippet costs 2 units of the API quota while requests for the id are 0. So, I don't need to snag the snippet for every single item on every single page. I only need to grab the snippet of the final video in the results, which I can do with the more refined call to
$youtube->videos->listVideos()
With the addition of the PlaylistCache class I only reach out to the API when the cached version of the Playlist returns true on the $playlistCache->isExpired() call, so I only need to poll the entire playlist one time every 24 hours instead of 1 time every page load for every user.
It's still not exactly ideal, but as far as I can tell, it's the best option available right now.
Firstly, you need to get the channelId for the user via HTTP request:
Sample request:
https://www.googleapis.com/youtube/v3/channels?part=snippet&forUsername={0}&key={1}
where {0} is the USERNAME and key is you API key
Then, get the list of videos by calling 'PlaylistItems:list', it returns a collection of playlist items that match the API request parameters. You can retrieve all of the playlist items in a specified playlist or retrieve one or more playlist items by their unique IDs.
Sample request:
https://www.googleapis.com/youtube/v3/search?order=date&part=snippet&channelId={0}&key={1}
From there, you can create an array to get the last video in the playlist. Include max-results parameter, the max-results specifies the maximum number of results that included in the result set.
Typically, the latest video in a playlist in added to the front, not the end.

Facebook PHP SDK event wall posts limit and pagination

Hi I created an app to load facebook event "wall posts" and "attending list" into a searchable form for use by door staff as a guestlist.
Recently it won't pull more than 10 posts from an events wall posts.
I've been playing about on the open graph explorer and have ran into the same problem. I can't get it to display more than ten results.
Why does it paginate now and why even if I add "since" and "until" parameters to the call does it still only display the last 10 posts on the wall?
If anyone could help me remove the pagination and get all results at once that would be magical!
Here's my call in my php:
$event_id = intval($_GET['id']);
$comments_id = '/' . $event_id . '/feed?fields=id,from,message';
$guestlist = (new FacebookRequest( $session, 'GET', $comments_id ))->execute()->getGraphObject()->getPropertyAsArray('data');
$i = 0; while($guestlist[$i]) {
echo $guestlist[$i]->getProperty('from')->getProperty('name');
echo nl2br($guestlist[$i]->getProperty('message'));
$i++;
}
Here's an example of an open graph request:
941122979255816/feed?fields=id,from,message
Here's an example facebook event:
facebook.com/events/941122979255816/
Here's my app:
events.sawhost.co.uk
Thanks
It seems that facebook is having some pagination issues. I guess all we can do is sit tight while they fix it
https://developers.facebook.com/bugs/809829259052996/

How do I pull the subscriber count from a MailChimp list with the API?

I'm trying to display the subscriber count from a MailChimp mailing list using their API, and I've got it partially working, except the code below is currently spitting out the subscriber count for all lists, rather than for one specific list. I've specified the list id in the line $listId ='XXX'; but that doesn't seem to be working. Because I have five lists in total, the output from the PHP below shows this:
10 0 0 1 9
What do I need to do in my code below to get the subscriber count from a specific list id?
<?php
/**
This Example shows how to pull the Members of a List using the MCAPI.php
class and do some basic error checking.
**/
require_once 'inc/MCAPI.class.php';
$apikey = 'XXX';
$listId = 'XXX';
$api = new MCAPI($apikey);
$retval = $api->lists();
if ($api->errorCode){
echo "Unable to load lists()!";
echo "\n\tCode=".$api->errorCode;
echo "\n\tMsg=".$api->errorMessage."\n";
} else {
foreach ($retval['data'] as $list){
echo "\t ".$list['stats']['member_count'];
}
}
?>
I just came across this function (see below) that let's me return a single list using a known list_id. The problem is, I'm not sure how to add the list_id in the function.
I'm assuming I need to define it in this line? $params["filters"] = $filters;
The MailChimp lists() method documentation can be referred to here: http://apidocs.mailchimp.com/rtfm/lists.func.php
function lists($filters=array (
), $start=0, $limit=25) {
$params = array();
$params["filters"] = $filters;
$params["start"] = $start;
$params["limit"] = $limit;
return $this->callServer("lists", $params);
}
I'd strongly recommend not mucking with the internals of the wrapper as it's not going to be nearly as helpful as the online documentation and the examples included with the wrapper. Using the wrapper means the line you tracked down will effectively be filled when make the proper call.
Anywho, this is what you want:
$filters = array('list_id'=>'XXXX');
$lists = $api->lists($filters);
Mailchimp provides a pre-built php wrapper around their api at http://apidocs.mailchimp.com/downloads/#php. This api includes a function lists() which, according to its documentation, returns among other things:
int member_count The number of active members in the given list.
It looks like this is the function which you are referring to above. All you should have to do is iterate through the lists that are returned to find the one with the proper id. From there you should be able to query the subscriber count along with a number of other statistics about the list.

Categories