Youtube api upload videos not working "Error : NoLinkedYouTubeAccount " - api

am using youtube api to upload videos from my website, this is first time am using am got stuck with the google account.I gave youtube account username, password and developer key am getting the error "NoLinkedYouTubeAccount ".
Some one help me to fix this issue.
/**
* developerKey
*/
public $developerKey;
/**
* accessToken - authorization access taken
*/
public $accessToken;
/**
* next_index - used to track short results
*/
public $next_index;
/**
* authType - authentication type GoogleLogin or AuthSub
*/
public $authType;
/**
* initializes the token and API key information for API methods which requires authentication information
* #param developerKey - String
* #param accessToken - array
* #return void
* #access public
* Modified: Sandip
*/
public function __construct($params){
$this->accessToken = $params['accessToken'];
$this->authType = $params['authType'];
$this->developerKey=$params['developerKey'];
}
/**
* client login authentication
* #param username - String
* #param pass - String
* #return array
* #access public
* Modified: Sandip
*/
public function clientLoginAuth($username,$pass){
$this->authType = 'GoogleLogin';
$url = 'https://www.google.com/youtube/accounts/ClientLogin';
$data = 'Email='.urlencode($username).'&Passwd='.urlencode($pass).'&service=youtube&source=Test';
$result = array();
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$curlheader[0] = "Content-Type:application/x-www-form-urlencoded";
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
curl_setopt( $ch, CURLOPT_SSL_VERIFYPEER, false );
curl_setopt($ch, CURLOPT_HTTPHEADER, $curlheader);
$result['output'] = curl_exec($ch);
$result['err'] = curl_errno( $ch );
$result['errmsg'] = curl_error( $ch );
$result['header'] = curl_getinfo( $ch );
$temp = explode("YouTubeUser=",$result['output']);
$result['username'] = trim($temp[1]);
$temp2 = explode("=",trim($temp[0]));
$result['token'] = trim($temp2[1]);
$this->accessToken = $result['token'];
curl_close($ch);
return $result;
}
public function uploadVideo($filename,$fullFilePath,$title,$description,$tags)
{
$fdata = file_get_contents($fullFilePath);
$tmpdata = '<?xml version="1.0"?>
<entry xmlns="http://www.w3.org/2005/Atom" xmlns:media="http://search.yahoo.com/mrss/" xmlns:yt="http://gdata.youtube.com/schemas/2007">
<media:group>
<media:title type="plain">'.$title.'</media:title>
<media:description type="plain">'.$description.'</media:description>
<media:category scheme="http://gdata.youtube.com/schemas/2007/categories.cat">People</media:category> <media:keywords>'.$tags.'</media:keywords>
</media:group>
</entry>
';
$url = 'http://gdata.youtube.com/feeds/api/users/default/uploads';
$data = '--f93dcbA3
Content-Type: application/atom+xml; charset=UTF-8
'.$tmpdata.'
--f93dcbA3
Content-Type: video/quicktime
Content-Transfer-Encoding: binary
'.$fdata.'
--f93dcbA3--';
$token = $this->accessToken;
$developerKey = $this->developerKey;
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$curlheader[0] = "Host: uploads.gdata.youtube.com";
if($this->authType == 'GoogleLogin')
$curlheader[1] = "Authorization: ".$this->authType." auth=\"$token\"";
else
$curlheader[1] = "Authorization: ".$this->authType." token=\"$token\"";
$curlheader[2] = "GData-Version: 2";
$curlheader[3] = "X-GData-Key: key=\"$developerKey\"";
$curlheader[4] = "Slug: ".$filename;
$curlheader[5] = "Content-Type: multipart/related; boundary=\"f93dcbA3\"";
$curlheader[6] = "Content-Length: ".strlen($data);
$curlheader[7] = "Connection: close";
curl_setopt($ch, CURLOPT_HTTPHEADER, $curlheader);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
$output = curl_exec($ch);
$info = curl_getinfo($ch);
//print_r($info);
curl_close($ch);
unset($fdata);
$validresult = $this->checkErrors($output);
if($validresult['is_error'] == 'No')
{
$xml = $validresult['xml'];
$webSite = 'http://www.youtube.com/';
$criteria = 'uploads';
$mediaInfo = array();
$gdMedia = $xml->children('http://schemas.google.com/g/2005');
$media = $xml->children('http://search.yahoo.com/mrss/');
$ytMedia = $xml->children('http://gdata.youtube.com/schemas/2007');
$georssMedia = $xml->children('http://www.georss.org/georss');
if($media->group->title){
$mediaInfo['title'] = sprintf("%s",$media->group->title[0]);
}else{
$mediaInfo['title'] = '';
}
if($media->group->description){
$mediaInfo['description'] = sprintf("%s",$media->group->description[0]);
}else{
$mediaInfo['description'] = '';
}
if($media->group->player){
$video = $media->group->player[0]->attributes()->url;
$vLink = preg_replace('/=/', "/", $video);
$videoLink = preg_replace('/\?/', "/", $vLink);
$mediaInfo['contentUrl'] = $videoLink."&hl=en&fs=1";
$test_str = preg_split('/\/v\//', $videoLink, 2);
$video_id_array = preg_split('/&/', $test_str[1],2);
$mediaInfo['videoId'] = $video_id_array[0];
}else{
if($entry->link[0]->attributes()->href){
$video = $entry->link[0]->attributes()->href;
$vLink = preg_replace('/=/', "/", $video);
$videoLink = preg_replace('/\?/', "/", $vLink);
$mediaInfo['contentUrl'] = $videoLink."&hl=en&fs=1";
$test_str = preg_split('/\/v\//', $videoLink, 2);
$video_id_array = preg_split('/&/', $test_str[1],2);
$mediaInfo['videoId'] = $video_id_array[0];
}else{
return "video not found.";
}
}
$mediaInfo['path_url'] = $mediaInfo['contentUrl'];
$mediaInfo['webSite'] = $webSite;
$mediaInfo['genre'] = sprintf("%s",#$media->group->category[0]);
$mediaInfo['criteria'] = $criteria;
unset($xml);
unset($gdMedia);
unset($media);
unset($ytMedia);
unset($georssMedia);
return $mediaInfo;
}
else
{
$result = array();
$result['is_error'] = $validresult['is_error'];
$result['error'] = $validresult['error'];
unset($validresult);
return $result;
}
}
public function getUploadedVideos($username='default',$startIndex=1,$limit=10,$location='',$location_radius='',$safeSearch='strict',$strict='true'){
$url = 'http://gdata.youtube.com/feeds/api/users/'.$username.'/uploads?start-index='.$startIndex.'&max-results='.$limit.'&strict='.$strict;
if($location !='')
{
$url .= '&location='.$location;
$url .= '&location-radius='.$location_radius;
}
//echo "<br>".$url;
$criteria = 'uploads';
if($username == 'default')
$output = $this->make_api_call($url);
else
{
$response = $this->make_get_call($url);
$output = $response['output'];
}
$result = array();
$validresult = $this->checkErrors($output);
if($validresult['is_error'] == 'No')
{
$xml = $validresult['xml'];
$tmp = $xml->xpath("openSearch:totalResults");
$tmp_totalresults = (string)$tmp[0];
$tmp = $xml->xpath("openSearch:startIndex");
$result['startindex'] = (string)$tmp[0];
//$tmp = $xml->xpath("openSearch:itemsPerPage");
//$result['itemsPerPage'] = (string)$tmp[0];
$res = $this->getFormatedVideoresult($xml,$criteria);
//Pagination logic
$shortCnt = $this->getShortCount();
//
if($shortCnt > 0 && $tmp_totalresults > $limit)
{
$newStartIndex = $startIndex + $limit;
$newmaxresults = $shortCnt;
$iteration = 1;
while($shortCnt > 0 && $tmp_totalresults >= $newStartIndex){
if($iteration !=1){
$newStartIndex = $newStartIndex + $newmaxresults;
$newmaxresults = $shortCnt;
}
$iteration++;
$url = 'http://gdata.youtube.com/feeds/api/users/'.$username.'/uploads?start-index='.$newStartIndex.'&max-results='.$newmaxresults.'&strict='.$strict;
if($location !='')
{
$url .= '&location='.$location;
$url .= '&location-radius='.$location_radius;
}
$shortResult = $this->getShortResult($url,$criteria);
if(#$shortResult['is_error']=='No'){
if(!empty($shortResult['result']))
{
////echo "<br>INSIDE";
foreach($shortResult['result'] as $shortkey => $shortItem)
$res[] = $shortItem;
$shortCnt = $this->getShortCount();
}
else
{
continue;
}
}
else
{
break;
}
}//while
$result['nextPageIndex'] = #(isset($shortResult['nextPageIndex'])?$shortResult['nextPageIndex']:0);
}
else
{
$result['nextPageIndex'] = $result['startindex'] + count($this->next_index);
}
if($tmp_totalresults < $result['nextPageIndex'])
{
$result['nextPageIndex'] = 0;
}
//pagination logic
$result['itemsPerPage'] = $limit;
$result['totalresults'] = count($res);
$result['result'] = $res;
unset($res);
unset($xml);
}
else
{
$result['is_error'] = $validresult['is_error'];
$result['error'] = $validresult['error'];
}
unset($validresult);
return $result;
}
public function checkErrors($response){
$result = array();
$result['is_error'] = 'No';
$reg_ex = '/<H1>Bad Request<\/H1>/';
$res = preg_match_all($reg_ex,$response,$matches);
if(!empty($matches[0])) {
$result['is_error'] = 'Yes';
$result['error'] = "Bad Request";
}
else {
$xml = #simplexml_load_string($response);
if($xml === FALSE && $response !=''){
$result['error'] = $response;
$result['is_error'] = 'Yes';
}
else{
if(#$xml->error){
$msg = #(string)$xml->error->code.':'.#(string)$xml->error->internalReason;
unset($xml);
$result['error'] = $msg;
$result['is_error'] = 'Yes';
}
else{
$result['xml'] = $xml;
}
}
}
unset($xml);
unset($response);
return $result;
}
public function getContentURL($url){
$output = $this->make_api_call($url);
$result = array();
$validresult = $this->checkErrors($output);
if($validresult['is_error'] == 'No')
{
$xml = $validresult['xml'];
$ytMedia = $xml->children('http://gdata.youtube.com/schemas/2007');
$result['term'] = $xml->category[1]->attributes()->term;
$result['title'] = (string)$xml->title;
$result['username'] = (string)$ytMedia->username;
$result['contentURL'] = (string)$xml->content->attributes()->src;
if(stristr($result['title'],'Activity of'))
{
$result['contentURL'] = 'http://gdata.youtube.com/feeds/api/users/'.$result['username'].'/uploads?v=2';
}
}
else
{
$result['is_error'] = $validresult['is_error'];
$result['error'] = $validresult['error'];
}
unset($validresult);
return $result;
}
public function getRecentUploadedVideos($xml){
$i = 0;
$res = array();
foreach($xml->entry as $fentry){
$i++;
$term = $fentry->category[1]->attributes()->term;
if($term == 'video_uploaded')
{
$mediaInfo = array();
$entry = $fentry->link[1]->entry;
$gdMedia = $entry->children('http://schemas.google.com/g/2005');
$media = $entry->children('http://search.yahoo.com/mrss/');
$ytMedia = $entry->children('http://gdata.youtube.com/schemas/2007');
$georssMedia = $entry->children('http://www.georss.org/georss');
if($gdMedia->rating){
$rating = (string)$gdMedia->rating->attributes();
$mediaInfo['rating'] = $rating['average'];
}else{
$mediaInfo['rating'] = 0;
}
if($media->group->thumbnail){
$mediaInfo['iconImage'] = sprintf("%s",$media->group->thumbnail[0]->attributes()->url);
}else{
$mediaInfo['iconImage'] = '';
}
if($media->group->title){
$mediaInfo['title'] = sprintf("%s",$media->group->title[0]);
}else{
$mediaInfo['title'] = '';
}
if($media->group->description){
$mediaInfo['description'] = sprintf("%s",$media->group->description[0]);
}else{
$mediaInfo['description'] = '';
}
if($media->group->player){
$video = $media->group->player[0]->attributes()->url;
$vLink = preg_replace('/=/', "/", $video);
$videoLink = preg_replace('/\?/', "/", $vLink);
$mediaInfo['contentUrl'] = $videoLink."&hl=en&fs=1";
$test_str = preg_split('/\/v\//', $videoLink, 2);
$video_id_array = preg_split('/&/', #$test_str[1],2);
$mediaInfo['videoId'] = $video_id_array[0];
}
else{
$tmp = #$entry->xpath("app:control");
$tmp2 = #$tmp[0]->xpath("yt:state");
if(#$tmp2[0]->attributes()->name == 'restricted')
{
//echo "<br>INSIDE ".$mediaInfo['title'];
$this->next_index[$i] = 'n';
continue;
}
if(isset($entry->link) && $entry->link[0]->attributes()->href !=''){
$video = $entry->link[0]->attributes()->href;
$vLink = preg_replace('/=/', "/", $video);
$videoLink = preg_replace('/\?/', "/", $vLink);
$mediaInfo['contentUrl'] = $videoLink."&hl=en&fs=1";
$test_str = preg_split('/\/v\//', $videoLink, 2);
$video_id_array = preg_split('/&/', $test_str[1],2);
$mediaInfo['videoId'] = $video_id_array[0];
if(!$mediaInfo['videoId'])
{
$this->next_index[$i] = 'n';
//echo "video Skipped.";
continue;
}
}
else{
$this->next_index[$i] = 'n';
continue;
}
}
$this->next_index[$i] = 'y';
$res[] = $mediaInfo;
}
else
{
$this->next_index[$i] = 'n';
}
} // foreach
return $res;
}
public function getRecentShortResult($url){
$token = $this->accessToken;
$developerKey = $this->developerKey;
if($token !='' && $developerKey !='')
$output = $this->make_api_call($url);
else
{
$response = $this->make_get_call($url);
$output = $response['output'];
}
$result = array();
$validresult = $this->checkErrors($output);
if($validresult['is_error'] == 'No')
{
$xml = $validresult['xml'];
$tmp = $xml->xpath("openSearch:totalResults");
$tmp_totalresults = (string)$tmp[0];
$tmp = $xml->xpath("openSearch:startIndex");
$result['startindex'] = (string)$tmp[0];
$tmp = $xml->xpath("openSearch:itemsPerPage");
$result['itemsPerPage'] = (string)$tmp[0];
//$result['itemsPerPage'] = $maxresults;
if($tmp_totalresults > $result['startindex']){
$res = $this->getRecentUploadedVideos($xml);
$result['nextPageIndex'] = $result['startindex'] + count($this->next_index);
}
else
$result['nextPageIndex'] = 0;
$result['result'] = #$res;
}
else
{
$result['error'] = $validresult['error'];
}
$result['is_error'] = $validresult['is_error'];
unset($validresult);
unset($output);
unset($response);
return $result;
}
public function getVideosBysubscriptionID($subscriptionID,$startIndex=1,$limit=10,$safeSearch='strict',$strict='true'){
$url = 'http://gdata.youtube.com/feeds/api/users/default/subscriptions/'.$subscriptionID.'?v=2';
$feedResponse = $this->getContentURL($url);
$contentURL = #$feedResponse['contentURL'];
$tempcontentURL = $contentURL;
$contentURL .= '&start-index='.$startIndex.'&max-results='.$limit.'&strict='.$strict;
$result = array();
if($contentURL !=''){
$output = $this->make_api_call($contentURL);
$validresult = $this->checkErrors($output);
if($validresult['is_error'] == 'No'){
$xml = $validresult['xml'];
$tmp = $xml->xpath("openSearch:totalResults");
$tmp_totalresults = (string)$tmp[0];
$tmp = $xml->xpath("openSearch:startIndex");
$result['startindex'] = (string)$tmp[0];
if(#$feedResponse['recentUpload'] == 1){
$res = $this->getRecentUploadedVideos($validresult['xml']);
$shortCnt = $this->getShortCount();
if($shortCnt > 0 && $tmp_totalresults > $limit)
{
$newStartIndex = $startIndex + $limit;
$newmaxresults = $shortCnt;
$iteration = 1;
while($shortCnt > 0 && $tmp_totalresults >= $newStartIndex){
if($iteration !=1){
$newStartIndex = $newStartIndex + $newmaxresults;
$newmaxresults = $shortCnt;
}
$iteration++;
$url = $tempcontentURL.'&start-index='.$newStartIndex.'&max-results='.$newmaxresults.'&strict='.$strict;
$shortResult = $this->getRecentShortResult($url);
if(#$shortResult['is_error']=='No'){
if(!empty($shortResult['result']) && count($res) <= $limit)
{
foreach($shortResult['result'] as $shortkey => $shortItem)
$res[] = $shortItem;
$shortCnt = $this->getShortCount();
}
else
{
continue;
}
}
else
{
break;
}
}//WHILE
$result['nextPageIndex'] = #(isset($shortResult['nextPageIndex'])?$shortResult['nextPageIndex']:0);
}
else
{
$result['nextPageIndex'] = #$result['startindex'] + count($this->next_index);
}
if($tmp_totalresults < $result['nextPageIndex'])
{
$result['nextPageIndex'] = 0;
}
$result['itemsPerPage'] = $limit;
$result['totalresults'] = count($res);
$result['result'] = $res;
unset($res);
unset($xml);
}
else
{
$criteria = $feedResponse['title'];
$xml = $validresult['xml'];
$res = $this->getFormatedVideoresult($xml,$criteria);
//Pagination logic
$shortCnt = $this->getShortCount();
if($shortCnt > 0 && $tmp_totalresults > $limit)
{
$newStartIndex = $startIndex + $limit;
$newmaxresults = $shortCnt;
$iteration = 1;
while($shortCnt > 0 && $tmp_totalresults >= $newStartIndex){
if($iteration !=1){
$newStartIndex = $newStartIndex + $newmaxresults;
$newmaxresults = $shortCnt;
}
$iteration++;
$url = $tempcontentURL.'&start-index='.$newStartIndex.'&max-results='.$newmaxresults.'&strict='.$strict;
$shortResult = $this->getShortResult($url,$criteria);
if(#$shortResult['is_error']=='No'){
if(!empty($shortResult['result']))
{
foreach($shortResult['result'] as $shortkey => $shortItem)
$res[] = $shortItem;
$shortCnt = $this->getShortCount();
}
else
{
continue;
}
}
else
{
break;
}
}//while
$result['nextPageIndex'] = #(isset($shortResult['nextPageIndex'])?$shortResult['nextPageIndex']:0);
}
else
{
$result['nextPageIndex'] = $result['startindex'] + count($this->next_index);
}
if($tmp_totalresults < $result['nextPageIndex'])
{
$result['nextPageIndex'] = 0;
}
//pagination logic
$result['itemsPerPage'] = $limit;
$result['totalresults'] = count($res);
$result['result'] = $res;
unset($res);
unset($xml);
}
}// NO
else
{
$result['is_error'] = $validresult['is_error'];
$result['error'] = $validresult['error'];
}
}
else
{
$result['is_error'] = $feedResponse['is_error'];
$result['error'] = $feedResponse['error'];
}
unset($validresult);
unset($feedResponse);
return $result;
}
}
/* End of file Someclass.php */
Thanks.

For anyone that comes across this, I had this error and fixed it by logging into YouTube as the main user, going to the top right and clicking 'Youtube Settings'. Then I clicked 'create channel'. Error gone!

This doesn't have anything to do with your code or program. It simply means you have not linked your Google account with Youtube, or vice versa.
I encountered the same problem too. But for me, I initially created a Google account, and even though when I went to Youtube.com I could see that I was logged it, but that did not mean that my Google account was actually linked to YouTube yet. So in my case, when I was on youtube.com, I actually clicked on my username in the upper right corner and did something...but basically it just prompted me to link YouTube to my Google account. When that was all done, it finally took me to my YouTube profile page. And then when I ran my program again, the "NoLinkedYoutubeAccount" error message was gone.
Give that a try. For you, it might be the opposite. Hope this helps!

Related

How to update youtube annalytics to all previously registered youtube channels

I have a web app in which the users can register and connect their youtube channels. Next in the registration process I collect all the information I can get from youtube data api and youtube analytics and reporting api (with scopes and access tokens) and store it in the database. I show that info on their dashboards. I also display that info in the admin panel for the administrators to see.
The problem is, how can I refresh that info, lets say, once a day? I've tried with the access token but i get error 403 Forbidden message. I want to update the info to all of the registered youtube accounts, this is the function I use to update all but its not working
(In the bellow script, i send $code as a variable and the function is called on the redirect URI)
$youtube_channels = YouTubeChannels::get();
$key = env('NEW_YOUTUBE_API_KEY');
foreach($youtube_channels as $youtube_channel) {
$yt_channel_statistics = Http::get('https://www.googleapis.com/youtube/v3/channels', [
'part' => 'statistics,snippet',
'id' => $youtube_channel->youtube_channel_id,
'key' => $key
]);
$yt_channel_statistics_json = $yt_channel_statistics->json();
$update_yt = YouTubeChannels::where('youtube_channel_id', $youtube_channel->youtube_channel_id)->first();
if($update_yt != null) {
$update_yt->channel_name = $yt_channel_statistics_json['items'][0]['snippet']['title'];
$update_yt->channel_subscribers = $yt_channel_statistics_json['items'][0]['statistics']['subscriberCount'];
$update_yt->channel_total_views = $yt_channel_statistics_json['items'][0]['statistics']['viewCount'];
$update_yt->channel_videos_count = $yt_channel_statistics_json['items'][0]['statistics']['videoCount'];
$update_yt->save();
}
//test
$baseUrl = 'https://www.googleapis.com/youtube/v3/';
$apiKey = env('NEW_YOUTUBE_API_KEY');
$channelId = $youtube_channel->youtube_channel_id;
$params = [
'id'=> $channelId,
'part'=> 'contentDetails',
'key'=> $apiKey
];
$url = $baseUrl . 'channels?' . http_build_query($params);
$json = json_decode(file_get_contents($url), true);
$playlist = $json['items'][0]['contentDetails']['relatedPlaylists']['uploads'];
$params = [
'part'=> 'snippet',
'playlistId' => $playlist,
'maxResults'=> '50',
'key'=> $apiKey
];
$url = $baseUrl . 'playlistItems?' . http_build_query($params);
$json = json_decode(file_get_contents($url), true);
$videos = [];
foreach($json['items'] as $video)
$videos[] = $video['snippet']['resourceId']['videoId'];
while(isset($json['nextPageToken'])){
$nextUrl = $url . '&pageToken=' . $json['nextPageToken'];
$json = json_decode(file_get_contents($nextUrl), true);
foreach($json['items'] as $video)
$videos[] = $video['snippet']['resourceId']['videoId'];
}
$video_ids_string = collect($videos)->implode(',');
//
//endtest
//new test
//
$params = [
'part'=> 'snippet,contentDetails,statistics,status',
'id' => $video_ids_string,
'key'=> $apiKey
];
$url = $baseUrl . 'videos?' . http_build_query($params);
$json = json_decode(file_get_contents($url), true);
$videos_infos = $json;
//
YouTubeVideos::where('youtube_channel_id', $youtube_channel->id)->delete();
foreach ($videos as $video){
foreach($videos_infos['items'] as $info){
if ($info['id'] == $video) {
if($info['status']['privacyStatus'] == 'public') {
$youtube_video = new YouTubeVideos();
// if (!$live_error) {
// foreach ($live_videos as $live) {
// if ($live->youtube_id == $video) {
// $youtube_video->was_live = true;
// }
// }
// }
// dd($video);
$youtube_video->youtube_channel_id = $youtube_channel->id;
$youtube_video->yt_video_id = $video;
$youtube_video->yt_video_title = $info['snippet']['title'];
$youtube_video->yt_video_description = $info['snippet']['description'];
$youtube_video->yt_video_published_at = Carbon::parse($info['snippet']['publishedAt']);
if(isset($info['snippet']['defaultAudioLanguage'])) {
$youtube_video->yt_video_default_audio_language = $info['snippet']['defaultAudioLanguage'];
} else {
$youtube_video->yt_video_default_audio_language = '';
}
if (strcmp($info['contentDetails']['caption'], 'true') == 0) {
$youtube_video->is_video_captioned = true;
} else {
$youtube_video->is_video_captioned = false;
}
$youtube_video->yt_video_definition = $info['contentDetails']['definition'];
$youtube_video->yt_video_dislike_count = 0;
$youtube_video->yt_video_like_count = $info['statistics']['likeCount'];
$youtube_video->yt_video_views_count = $info['statistics']['viewCount'];
//proba type of views
//
$client = new Google_Client();
try{
$client->setAuthConfig(storage_path('app'.DIRECTORY_SEPARATOR. 'json'. DIRECTORY_SEPARATOR.'client_secret.json'));
}catch (\Google\Exception $e){
dd($e->getMessage());
}
// $client->addScope([GOOGLE_SERVICE_YOUTUBE::YOUTUBE_READONLY, 'https://www.googleapis.com/auth/yt-analytics.readonly', 'https://www.googleapis.com/auth/youtube.readonly']);
$client->addScope([GOOGLE_SERVICE_YOUTUBE::YOUTUBE_FORCE_SSL,GOOGLE_SERVICE_YOUTUBE::YOUTUBE_READONLY, GOOGLE_SERVICE_YOUTUBE::YOUTUBEPARTNER,'https://www.googleapis.com/auth/yt-analytics.readonly', 'https://www.googleapis.com/auth/yt-analytics-monetary.readonly']);
$client->setRedirectUri(env('APP_URL') . '/get_access_token_yt_test');
// offline access will give you both an access and refresh token so that
// your app can refresh the access token without user interaction.
$client->setAccessType('offline');
// Using "consent" ensures that your application always receives a refresh token.
// If you are not using offline access, you can omit this.
$client->setPrompt("consent");
$client->setApprovalPrompt('force');
$client->setIncludeGrantedScopes(true); // incremental auth
if (!isset($code)){
$auth_url = $client->createAuthUrl();
return redirect()->away($auth_url)->send();
}else{
if($code != null) {
$client->fetchAccessTokenWithAuthCode($code);
$client->setAccessToken($client->getAccessToken());
session()->push('refresh_token_youtube', $client->getRefreshToken());
session()->save();
}
}
$service = new Google_Service_YouTube($client);
$analytics = new Google_Service_YouTubeAnalytics($client);
$typeOfViews = $analytics->reports->query([
'ids' => 'channel==' . $youtube_channel->youtube_channel_id,
'startDate' => Carbon::parse($youtube_channel->channel_created_at)->format('Y-m-d'),
'endDate' => Carbon::today()->format('Y-m-d'),
'metrics' => 'views',
'dimensions' => 'liveOrOnDemand',
'filters' => 'video=='.$video
]);
foreach ($typeOfViews as $viewType) {
if ($viewType[0] == 'ON_DEMAND') {
$youtube_video->yt_video_on_demand_views_count = $viewType[1];
} else if ($viewType[0] == 'LIVE') {
$youtube_video->yt_video_live_views_count = $viewType[1];
}
}
$watch_times = $analytics->reports->query([
'ids' => 'channel=='.$youtube_channel->youtube_channel_id,
'startDate' => Carbon::parse($youtube_channel->channel_created_at)->format('Y-m-d'),
'endDate' => Carbon::today()->format('Y-m-d'),
'metrics' => 'estimatedMinutesWatched',
'dimensions' => 'day',
'filters' => 'video=='.$video
]);
// //update quotas
// // self::update_quotas(1);
$total = 0;
foreach ($watch_times as $watch_time){
$total += $watch_time[1];
}
$youtube_video->estimated_minutes_watch_time = $total;
$youtube_video->save();
//zacuvuva captions
$xmlString = file_get_contents("https://video.google.com/timedtext?type=list&v=" . $video);
$xmlObject = simplexml_load_string($xmlString);
$json = json_encode($xmlObject);
$phpArray = json_decode($json, true);
if (isset($phpArray['track'])) {
foreach ($phpArray['track'] as $array) {
$yt_video_captions = new YouTubeVideosCaptions();
$yt_video_captions->youtube_video_id = $youtube_video->id;
$yt_video_captions->language = $array['lang_code'];
$yt_video_captions->save();
}
}
//zacuvuva tags
if(isset($info['snippet']['tags'])) {
if ($info['snippet']['tags'] != null) {
foreach ($info['snippet']['tags'] as $tag) {
$youtube_video_tags = new YouTubeVideosTags();
$youtube_video_tags->youtube_video_id = $youtube_video->id;
$youtube_video_tags->tag = $tag;
$youtube_video_tags->save();
}
}
}
if ($youtube_video->is_video_captioned) {
$captions = YouTubeVideosCaptions::where('youtube_video_id', $youtube_video->id)->get();
foreach ($captions as $caption) {
$video_id = YouTubeVideos::where('id', $caption->youtube_video_id)->first();
$client->authorize();
$fp = fopen('../storage/app/captions/' . $caption->id . '.xml', 'w');
$xmlString = file_get_contents("http://video.google.com/timedtext?type=track&v=" . $video_id['yt_video_id'] . "&id=0&lang=" . $caption['language']);
fwrite($fp, $xmlString);
fclose($fp);
}
}
echo 'done';
}
}
}
}
// Command::line('Youtube videos updated');
//
//
//end new test
}
}

Is it possible to shorten this query

we have used loop for read between timestamps. This works but this way exhausting for server with million records.
The timestamps are determined by the $resolution variable and assigned to a new array. But we know this is poor way. I think we can do that without while. Maybe one query enough.
Route::get('/history', function (Request $request) {
//return response()->json([]);
$symbol = explode("-", $request->get("symbol"));
$coin = Coin::where("symbol", $symbol[1])->first();
$currency = Coin::where("symbol", $symbol[0])->first();
$resolution = $request->get("resolution");
$from = $request->get("from");
$to = $request->get("to");
$uniqueKey = sprintf("OHLCKEY%s%s%s%s",
$symbol[0], $symbol[1],
Carbon::createFromTimestamp($from)->second(0)->timestamp,
Carbon::createFromTimestamp($to)->second(0)->timestamp);
$redis=Redis::connection();
$cache = $redis->get($uniqueKey);
if($cache) {
$data = json_decode($cache);
return response()->json($data);
} else {
$t = [];
$o = [];
$h = [];
$l = [];
$c = [];
$v = [];
$s = "no_data";
$minMaxDates = TransactionDetail::where("type", "buy")
->whereBetween("created_at", [
Carbon::createFromTimestamp($from),
Carbon::createFromTimestamp($to)
])->where("coin_id", $coin->id)->where("currency_id", $currency->id)
->selectRaw("min(created_at) as minDate, max(created_at) as maxDate")->first();
if($minMaxDates->minDate) {
$minDate = Carbon::createFromTimeString($minMaxDates->minDate)->timestamp;
if($from < $minDate) {
$startDate = $minDate;
} else {
$startDate = (int)$from;
}
$maxDate = Carbon::createFromTimeString($minMaxDates->maxDate)->timestamp;
if($to > $maxDate) {
$to = $maxDate;
}
while ($startDate < $to):
switch ($resolution) {
case "30";
$endDate = Carbon::createFromTimestamp($startDate)->addMinutes(30)->timestamp;
break;
case "60";
$endDate = Carbon::createFromTimestamp($startDate)->addHour(1)->timestamp;
break;
case "180";
$endDate = Carbon::createFromTimestamp($startDate)->addHour(3)->timestamp;
break;
case "360";
$endDate = Carbon::createFromTimestamp($startDate)->addHour(6)->timestamp;
break;
case "720";
$endDate = Carbon::createFromTimestamp($startDate)->addHour(12)->timestamp;
break;
default:
$endDate = Carbon::createFromTimestamp($startDate)->addHour(1)->timestamp;
break;
}
if ($endDate > $to) $endDate = $to;
$transactions = TransactionDetail::where("type", "buy")
->whereBetween("created_at", [
Carbon::createFromTimestamp($startDate),
Carbon::createFromTimestamp($endDate)
])->where("coin_id", $coin->id)->where("currency_id", $currency->id)->get();
if (!$transactions->isEmpty()) {
$t[] = $transactions->first()->created_at->timestamp;
$o[] = floatval($transactions->first()->price);
$h[] = floatval($transactions->max("price"));
$l[] = floatval($transactions->min("price"));
$c[] = floatval($transactions->last()->price);
$v[] = floatval($transactions->sum("amount"));
}
$startDate = $endDate + 1;
endwhile;
}
if (!empty($t)) $s = "ok";
$data = ["t" => $t, "o" => $o, "h" => $h, "l" => $l, "c" => $c, "v" => $v, "s" => $s];
$redis->set($uniqueKey, json_encode($data));
return response()->json($data);
}
});
Can we reproduce this code with one mysql query?
thank you in advance.

New products from specific category prestashop

I want get new products from a category, so I tried to change the controller.
In prestashop 1.7 is  NewProductsController.php,
And inside there is this function 
protected function getProductSearchQuery()
{
$query = new ProductSearchQuery();
$query
->setQueryType('new-products')
->setSortOrder(new SortOrder('product', 'date_add', 'desc'))
;
return $query;
}
And I changed it into
protected function getProductSearchQuery()
{
$query = new ProductSearchQuery();
$query
->setIdCategory('MY-NEW-ID-CATEGORY')
->setQueryType('new-products')
->setSortOrder(new SortOrder('product', 'date_add', 'desc'))
;
return $query;
}
But it is still showing all the products, not the products from that category. 
I decided to use a different way,
In Product.php I write
public static function getNewProductsFromCategory($id_lang, $page_number = 0, $nb_products = 10, $count = false, $order_by = null, $order_way = null, $category_id = 2, Context $context = null)
{
$now = date('Y-m-d') . ' 00:00:00';
if (!$context) {
$context = Context::getContext();
}
$front = true;
if (!in_array($context->controller->controller_type, array('front', 'modulefront'))) {
$front = false;
}
if ($page_number < 1) {
$page_number = 1;
}
if ($nb_products < 1) {
$nb_products = 10;
}
if (empty($order_by) || $order_by == 'position') {
$order_by = 'date_add';
}
if (empty($order_way)) {
$order_way = 'DESC';
}
if ($order_by == 'id_product' || $order_by == 'price' || $order_by == 'date_add' || $order_by == 'date_upd') {
$order_by_prefix = 'product_shop';
} elseif ($order_by == 'name') {
$order_by_prefix = 'pl';
}
if (!Validate::isOrderBy($order_by) || !Validate::isOrderWay($order_way)) {
die(Tools::displayError());
}
$sql_groups = '';
if (Group::isFeatureActive()) {
$groups = FrontController::getCurrentCustomerGroups();
$sql_groups = ' AND EXISTS(SELECT 1 FROM `'._DB_PREFIX_.'category_product` cp
JOIN `'._DB_PREFIX_.'category_group` cg ON (cp.id_category = cg.id_category AND cg.`id_group` '.(count($groups) ? 'IN ('.implode(',', $groups).')' : '= '.(int)Configuration::get('PS_UNIDENTIFIED_GROUP')).')
WHERE cp.`id_product` = p.`id_product`)';
}
if (strpos($order_by, '.') > 0) {
$order_by = explode('.', $order_by);
$order_by_prefix = $order_by[0];
$order_by = $order_by[1];
}
$nb_days_new_product = (int) Configuration::get('PS_NB_DAYS_NEW_PRODUCT');
if ($count) {
$sql = 'SELECT COUNT(p.`id_product`) AS nb
FROM `'._DB_PREFIX_.'product` p
'.Shop::addSqlAssociation('product', 'p').'
WHERE (product_shop.`active` = 1 AND product_shop.`id_category_default`=10)
AND product_shop.`date_add` > "'.date('Y-m-d', strtotime('-'.$nb_days_new_product.' DAY')).'"
'.($front ? ' AND product_shop.`visibility` IN ("both", "catalog")' : '').'
'.$sql_groups;
return (int)Db::getInstance(_PS_USE_SQL_SLAVE_)->getValue($sql);
}
$sql = new DbQuery();
$sql->select(
'p.*, product_shop.*, stock.out_of_stock, IFNULL(stock.quantity, 0) as quantity, pl.`description`, pl.`description_short`, pl.`link_rewrite`, pl.`meta_description`,
pl.`meta_keywords`, pl.`meta_title`, pl.`name`, pl.`available_now`, pl.`available_later`, image_shop.`id_image` id_image, il.`legend`, m.`name` AS manufacturer_name,
(DATEDIFF(product_shop.`date_add`,
DATE_SUB(
"'.$now.'",
INTERVAL '.$nb_days_new_product.' DAY
)
) > 0) as new'
);
$sql->from('product', 'p');
$sql->join(Shop::addSqlAssociation('product', 'p'));
$sql->leftJoin('product_lang', 'pl', '
p.`id_product` = pl.`id_product`
AND pl.`id_lang` = '.(int)$id_lang.Shop::addSqlRestrictionOnLang('pl')
);
$sql->leftJoin('image_shop', 'image_shop', 'image_shop.`id_product` = p.`id_product` AND image_shop.cover=1 AND image_shop.id_shop='.(int)$context->shop->id);
$sql->leftJoin('image_lang', 'il', 'image_shop.`id_image` = il.`id_image` AND il.`id_lang` = '.(int)$id_lang);
$sql->leftJoin('manufacturer', 'm', 'm.`id_manufacturer` = p.`id_manufacturer`');
$sql->leftJoin('category_product', 'cp', 'cp.`id_product` = p.`id_product`');
$sql->where('product_shop.`active` = 1' );
$sql->where('cp.`id_category`='.(int)$category_id );
if ($front) {
$sql->where('product_shop.`visibility` IN ("both", "catalog")');
}
$sql->where('product_shop.`date_add` > "'.date('Y-m-d', strtotime('-'.$nb_days_new_product.' DAY')).'"');
if (Group::isFeatureActive()) {
$groups = FrontController::getCurrentCustomerGroups();
$sql->where('EXISTS(SELECT 1 FROM `'._DB_PREFIX_.'category_product` cp
JOIN `'._DB_PREFIX_.'category_group` cg ON (cp.id_category = cg.id_category AND cg.`id_group` '.(count($groups) ? 'IN ('.implode(',', $groups).')' : '= 1').')
WHERE cp.`id_product` = p.`id_product`)');
}
$sql->orderBy((isset($order_by_prefix) ? pSQL($order_by_prefix).'.' : '').'`'.pSQL($order_by).'` '.pSQL($order_way));
$sql->limit($nb_products, (int)(($page_number-1) * $nb_products));
if (Combination::isFeatureActive()) {
$sql->select('product_attribute_shop.minimal_quantity AS product_attribute_minimal_quantity, IFNULL(product_attribute_shop.id_product_attribute,0) id_product_attribute');
$sql->leftJoin('product_attribute_shop', 'product_attribute_shop', 'p.`id_product` = product_attribute_shop.`id_product` AND product_attribute_shop.`default_on` = 1 AND product_attribute_shop.id_shop='.(int)$context->shop->id);
}
$sql->join(Product::sqlStock('p', 0));
$result = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($sql);
if (!$result) {
return false;
}
if ($order_by == 'price') {
Tools::orderbyPrice($result, $order_way);
}
$products_ids = array();
foreach ($result as $row) {
$products_ids[] = $row['id_product'];
}
// Thus you can avoid one query per product, because there will be only one query for all the products of the cart
Product::cacheFrontFeatures($products_ids, $id_lang);
return Product::getProductsProperties((int)$id_lang, $result);
}
And in my controller I get the products id's from my new function in product controller and then getting products attributes
$products_id = Product::getNewProductsFromCategory($this->context->language->id,0, 1,false,'date_add', 'DESC',$category_ids);
$this->returnLastProductsFromCategory($products_id);
public function returnLastProductsFromCategory($products_id)
{
$products = Product::getProductsProperties($this->context->language->id, $products_id);
$assembler = new ProductAssembler($this->context);
$presenterFactory = new ProductPresenterFactory($this->context);
$presentationSettings = $presenterFactory->getPresentationSettings();
$presenter = new ProductListingPresenter(
new ImageRetriever(
$this->context->link
),
$this->context->link,
new PriceFormatter(),
new ProductColorsRetriever(),
$this->context->getTranslator()
);
$products_for_template = [];
foreach ($products as $rawProduct) {
$products_for_template[] = $presenter->present(
$presentationSettings,
$assembler->assembleProduct($rawProduct),
$this->context->language
);
}
return $this->context->smarty->assign('products', $products_for_template);
//return $this->context->smarty->fetch('module:cmsproducts/products.tpl');
}
It's working, but I think there are too many operations comparing to NewProductsController.
I solve problem. Solution :
In class Product.php i add function to which we send several categories as a string.
public static function getNewProductsFromCategory($id_lang, $page_number = 0, $nb_products = 10, $count = false, $order_by = null, $order_way = null, $category_ids , Context $context = null)
{
$now = date('Y-m-d') . ' 00:00:00';
if (!$context) {
$context = Context::getContext();
}
$front = true;
if (!in_array($context->controller->controller_type, array('front', 'modulefront'))) {
$front = false;
}
if ($page_number < 1) {
$page_number = 1;
}
if ($nb_products < 1) {
$nb_products = 10;
}
if (empty($order_by) || $order_by == 'position') {
$order_by = 'date_add';
}
if (empty($order_way)) {
$order_way = 'DESC';
}
if ($order_by == 'id_product' || $order_by == 'price' || $order_by == 'date_add' || $order_by == 'date_upd') {
$order_by_prefix = 'product_shop';
} elseif ($order_by == 'name') {
$order_by_prefix = 'pl';
}
if (!Validate::isOrderBy($order_by) || !Validate::isOrderWay($order_way)) {
die(Tools::displayError());
}
$sql_groups = '';
if (Group::isFeatureActive()) {
$groups = FrontController::getCurrentCustomerGroups();
$sql_groups = ' AND EXISTS(SELECT 1 FROM `'._DB_PREFIX_.'category_product` cp
JOIN `'._DB_PREFIX_.'category_group` cg ON (cp.id_category = cg.id_category AND cg.`id_group` '.(count($groups) ? 'IN ('.implode(',', $groups).')' : '= '.(int)Configuration::get('PS_UNIDENTIFIED_GROUP')).')
WHERE cp.`id_product` = p.`id_product`)';
}
if (strpos($order_by, '.') > 0) {
$order_by = explode('.', $order_by);
$order_by_prefix = $order_by[0];
$order_by = $order_by[1];
}
$nb_days_new_product = (int) Configuration::get('PS_NB_DAYS_NEW_PRODUCT');
if ($count) {
$sql = 'SELECT COUNT(p.`id_product`) AS nb
FROM `'._DB_PREFIX_.'product` p
'.Shop::addSqlAssociation('product', 'p').'
WHERE (product_shop.`active` = 1 )
AND product_shop.`date_add` > "'.date('Y-m-d', strtotime('-'.$nb_days_new_product.' DAY')).'"
'.($front ? ' AND product_shop.`visibility` IN ("both", "catalog")' : '').'
'.$sql_groups;
return (int)Db::getInstance(_PS_USE_SQL_SLAVE_)->getValue($sql);
}
$sql = new DbQuery();
$sql->select(
'p.*, product_shop.*, stock.out_of_stock, IFNULL(stock.quantity, 0) as quantity, pl.`description`, pl.`description_short`, pl.`link_rewrite`, pl.`meta_description`,
pl.`meta_keywords`, pl.`meta_title`, pl.`name`, pl.`available_now`, pl.`available_later`, image_shop.`id_image` id_image, il.`legend`, m.`name` AS manufacturer_name,
(DATEDIFF(product_shop.`date_add`,
DATE_SUB(
"'.$now.'",
INTERVAL '.$nb_days_new_product.' DAY
)
) > 0) as new'
);
$sql->from('product', 'p');
$sql->join(Shop::addSqlAssociation('product', 'p'));
$sql->leftJoin('product_lang', 'pl', '
p.`id_product` = pl.`id_product`
AND pl.`id_lang` = '.(int)$id_lang.Shop::addSqlRestrictionOnLang('pl')
);
$sql->leftJoin('image_shop', 'image_shop', 'image_shop.`id_product` = p.`id_product` AND image_shop.cover=1 AND image_shop.id_shop='.(int)$context->shop->id);
$sql->leftJoin('image_lang', 'il', 'image_shop.`id_image` = il.`id_image` AND il.`id_lang` = '.(int)$id_lang);
$sql->leftJoin('manufacturer', 'm', 'm.`id_manufacturer` = p.`id_manufacturer`');
$sql->leftJoin('category_product', 'cp', 'cp.`id_product` = p.`id_product`');
$sql->where('product_shop.`active` = 1' );
$test = (string)$sql->where('cp.`id_category` IN ('.$category_ids.')' );
if ($front) {
$sql->where('product_shop.`visibility` IN ("both", "catalog")');
}
$sql->where('product_shop.`date_add` > "'.date('Y-m-d', strtotime('-'.$nb_days_new_product.' DAY')).'"');
if (Group::isFeatureActive()) {
$groups = FrontController::getCurrentCustomerGroups();
$sql->where('EXISTS(SELECT 1 FROM `'._DB_PREFIX_.'category_product` cp
JOIN `'._DB_PREFIX_.'category_group` cg ON (cp.id_category = cg.id_category AND cg.`id_group` '.(count($groups) ? 'IN ('.implode(',', $groups).')' : '= 1').')
WHERE cp.`id_product` = p.`id_product`)');
}
$sql->orderBy((isset($order_by_prefix) ? pSQL($order_by_prefix).'.' : '').'`'.pSQL($order_by).'` '.pSQL($order_way));
$sql->limit($nb_products, (int)(($page_number-1) * $nb_products));
if (Combination::isFeatureActive()) {
$sql->select('product_attribute_shop.minimal_quantity AS product_attribute_minimal_quantity, IFNULL(product_attribute_shop.id_product_attribute,0) id_product_attribute');
$sql->leftJoin('product_attribute_shop', 'product_attribute_shop', 'p.`id_product` = product_attribute_shop.`id_product` AND product_attribute_shop.`default_on` = 1 AND product_attribute_shop.id_shop='.(int)$context->shop->id);
}
$sql->join(Product::sqlStock('p', 0));
$result = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($sql);
if (!$result) {
return false;
}
if ($order_by == 'price') {
Tools::orderbyPrice($result, $order_way);
}
$products_ids = array();
foreach ($result as $row) {
$products_ids[] = $row['id_product'];
}
// Thus you can avoid one query per product, because there will be only one query for all the products of the cart
Product::cacheFrontFeatures($products_ids, $id_lang);
return Product::getProductsProperties((int)$id_lang, $result);
}
To generate ids children categories from main category i add function in class NewProductsControllerCore and set in query ->setIdsCategories($categories_ids)
public function getChildrenCategories($category_id)
{
$this->category = new Category((int) $category_id, (int) $this->context->cookie->id_lang);
$subcategories = $this->category->getSubCategories($this->context->language->id, true);
if($subcategories) {
foreach($subcategories as $subcategory) {
$source2 = $this->getChildrenCategories($subcategory["id_category"]);
$source .= (string)$subcategory["id_category"].",".$source2;
}
}
$source = rtrim($source, ',');
return $source;
}
In class ProductSearchQuery.php
private $ids_categories;
public function setIdsCategories($ids_categories)
{
$this->ids_categories = $id_categories;
return $this;
}
public function getIdsCategories()
{
var_dump($this->ids_categories);
return $this->ids_categories;
}
And in NewProductsProductSearchProvider.php
private function getProductsOrCount(
ProductSearchContext $context,
ProductSearchQuery $query,
$type = 'products'
) {
return Product::getNewProductsFromCategory(
$context->getIdLang(),
$query->getPage(),
$query->getResultsPerPage(),
$type !== 'products',
$query->getSortOrder()->toLegacyOrderBy(),
$query->getSortOrder()->toLegacyOrderWay(),
$query->getIdsCategories() // Added categories
);
}
But still is problem. Pagination not working properly. I have only one product but pagination showing 12. If i click next page, then all products appear.
Controller NewProductsController.php eventually relies on Product.php controller and use a method getNewProducts(). You can follow this relation through a file src/Adapter/NewProducts/NewProductsProductSearchProvider.php. So, maybe only what you can do to simplify your implementation it is to modify a default method getNewProducts() and add some extra variable which will point out to search throughout only one category or all.
I am using prestashop 1.7.4 and wanted the same functionality of displaying new products by category. Both the answers above helped. I created product.php override for the same. If there is id, and is a valid category, then I look for subcategories too. And then modify the query accordingly. This is the product.php override file. Hope this helps..
<?php
/**
* This override is developed to take care of new products by category.
# id From URL - which is category id
* If the category id is validated, then looks for subcategories
* and creates a comma seperated string that contains category and all the subcategories under it.
*/
if (!defined('_CAN_LOAD_FILES_'))
exit;
class Product extends ProductCore
{
/**
* Get new products
*
* #param int $id_lang Language id
* #param int $pageNumber Start from (optional)
* #param int $nbProducts Number of products to return (optional)
* #return array New products
*/
public static function getNewProducts($id_lang, $page_number = 0, $nb_products = 10, $count = false, $order_by = null, $order_way = null, Context $context = null)
{
$now = date('Y-m-d') . ' 00:00:00';
if (!$context) {
$context = Context::getContext();
}
$front = true;
if (!in_array($context->controller->controller_type, array('front', 'modulefront'))) {
$front = false;
}
if ($page_number < 1) {
$page_number = 1;
}
if ($nb_products < 1) {
$nb_products = 10;
}
if (empty($order_by) || $order_by == 'position') {
$order_by = 'date_add';
}
if (empty($order_way)) {
$order_way = 'DESC';
}
if ($order_by == 'id_product' || $order_by == 'price' || $order_by == 'date_add' || $order_by == 'date_upd') {
$order_by_prefix = 'product_shop';
} elseif ($order_by == 'name') {
$order_by_prefix = 'pl';
}
if (!Validate::isOrderBy($order_by) || !Validate::isOrderWay($order_way)) {
die(Tools::displayError());
}
$sql_groups = '';
if (Group::isFeatureActive()) {
$groups = FrontController::getCurrentCustomerGroups();
$sql_groups = ' AND EXISTS(SELECT 1 FROM `'._DB_PREFIX_.'category_product` cp
JOIN `'._DB_PREFIX_.'category_group` cg ON (cp.id_category = cg.id_category AND cg.`id_group` '.(count($groups) ? 'IN ('.implode(',', $groups).')' : '= '.(int)Configuration::get('PS_UNIDENTIFIED_GROUP')).')
WHERE cp.`id_product` = p.`id_product`)';
}
if (strpos($order_by, '.') > 0) {
$order_by = explode('.', $order_by);
$order_by_prefix = $order_by[0];
$order_by = $order_by[1];
}
$nb_days_new_product = (int) Configuration::get('PS_NB_DAYS_NEW_PRODUCT');
// changes to incorporate new products by category
$catId = Tools::getValue('id');
$category = new Category((int)$catId, (int)$id_lang);
if ( ! Validate::isLoadedObject($category)) {
// not valid category
// kill catagory id
$catId = "";
}
if($catId && $catId!="") {
$categories_ids = self::getChildrenCategories($catId);
//echo "$catId, $categories_ids <br>";
}
if ($count) {
$sql = 'SELECT COUNT(DISTINCT p.`id_product`) AS nb
FROM `'._DB_PREFIX_.'product` p
'.Shop::addSqlAssociation('product', 'p');
if($catId && $catId!="") {
$sql .= ' LEFT JOIN `'._DB_PREFIX_.'category_product` cp ON ( p.`id_product` = cp.`id_product`)';
}
$sql .= ' WHERE product_shop.`active` = 1';
if($catId && $catId!="") {
$sql .= ' AND p.`id_product` = cp.`id_product` ';
$sql .= ' AND cp.`id_category` IN ('.$categories_ids.') ';
}
$sql .= ' AND product_shop.`date_add` > "'.date('Y-m-d', strtotime('-'.$nb_days_new_product.' DAY')).'"
'.($front ? ' AND product_shop.`visibility` IN ("both", "catalog")' : '').'
'.$sql_groups;
// echo $sql ."<br>";
return (int)Db::getInstance(_PS_USE_SQL_SLAVE_)->getValue($sql);
}
$sql = new DbQuery();
$sql->select(
'p.*, product_shop.*, stock.out_of_stock, IFNULL(stock.quantity, 0) as quantity, pl.`description`, pl.`description_short`, pl.`link_rewrite`, pl.`meta_description`,
pl.`meta_keywords`, pl.`meta_title`, pl.`name`, pl.`available_now`, pl.`available_later`, image_shop.`id_image` id_image, il.`legend`, m.`name` AS manufacturer_name,
(DATEDIFF(product_shop.`date_add`,
DATE_SUB(
"'.$now.'",
INTERVAL '.$nb_days_new_product.' DAY
)
) > 0) as new'
);
$sql->from('product', 'p');
$sql->join(Shop::addSqlAssociation('product', 'p'));
$sql->leftJoin('product_lang', 'pl', '
p.`id_product` = pl.`id_product`
AND pl.`id_lang` = '.(int)$id_lang.Shop::addSqlRestrictionOnLang('pl')
);
$sql->leftJoin('image_shop', 'image_shop', 'image_shop.`id_product` = p.`id_product` AND image_shop.cover=1 AND image_shop.id_shop='.(int)$context->shop->id);
$sql->leftJoin('image_lang', 'il', 'image_shop.`id_image` = il.`id_image` AND il.`id_lang` = '.(int)$id_lang);
$sql->leftJoin('manufacturer', 'm', 'm.`id_manufacturer` = p.`id_manufacturer`');
// changes to incorporate new products by category
$catId = Tools::getValue('id');
if($catId && $catId!="") {
$sql->leftJoin('category_product', 'catp', 'catp.`id_product` = p.`id_product`');
$test = (string)$sql->where('catp.`id_category` IN ('.$categories_ids.')' );
}
$sql->where('product_shop.`active` = 1');
if ($front) {
$sql->where('product_shop.`visibility` IN ("both", "catalog")');
}
$sql->where('product_shop.`date_add` > "'.date('Y-m-d', strtotime('-'.$nb_days_new_product.' DAY')).'"');
if (Group::isFeatureActive()) {
$groups = FrontController::getCurrentCustomerGroups();
$sql->where('EXISTS(SELECT 1 FROM `'._DB_PREFIX_.'category_product` cp
JOIN `'._DB_PREFIX_.'category_group` cg ON (cp.id_category = cg.id_category AND cg.`id_group` '.(count($groups) ? 'IN ('.implode(',', $groups).')' : '= 1').')
WHERE cp.`id_product` = p.`id_product`)');
}
$sql->groupBy('p.`id_product`');
$sql->orderBy((isset($order_by_prefix) ? pSQL($order_by_prefix).'.' : '').'`'.pSQL($order_by).'` '.pSQL($order_way));
$sql->limit($nb_products, (int)(($page_number-1) * $nb_products));
if (Combination::isFeatureActive()) {
$sql->select('product_attribute_shop.minimal_quantity AS product_attribute_minimal_quantity, IFNULL(product_attribute_shop.id_product_attribute,0) id_product_attribute');
$sql->leftJoin('product_attribute_shop', 'product_attribute_shop', 'p.`id_product` = product_attribute_shop.`id_product` AND product_attribute_shop.`default_on` = 1 AND product_attribute_shop.id_shop='.(int)$context->shop->id);
}
$sql->join(Product::sqlStock('p', 0));
// echo "sql=" . $sql ."<br>";
$result = Db::getInstance(_PS_USE_SQL_SLAVE_)->executeS($sql);
if (!$result) {
return false;
}
if ($order_by == 'price') {
Tools::orderbyPrice($result, $order_way);
}
$products_ids = array();
foreach ($result as $row) {
$products_ids[] = $row['id_product'];
}
// Thus you can avoid one query per product, because there will be only one query for all the products of the cart
Product::cacheFrontFeatures($products_ids, $id_lang);
return Product::getProductsProperties((int)$id_lang, $result);
}
public function getChildrenCategories($category)
{
// get category - sub category list in a comma seperated string
$id_category = $category .',';
$sql = "SELECT a.`id_category`, `active` FROM `ps_category` a LEFT JOIN `ps_category_lang` b ON (b.`id_category` = a.`id_category` AND b.`id_lang` = 1 AND b.`id_shop` = 1) LEFT JOIN `ps_category_shop` sa ON (a.`id_category` = sa.`id_category` AND sa.id_shop = 1) WHERE 1 AND `id_parent` = $category ";
$subcats_in_cat = Db::getInstance()->executeS($sql);
foreach($subcats_in_cat as $subcat) {
// echo $subcat ."<br>";
$id_category .= $subcat["id_category"] . ',' ;
$sql = "SELECT a.`id_category`, `active` FROM `ps_category` a LEFT JOIN `ps_category_lang` b ON (b.`id_category` = a.`id_category` AND b.`id_lang` = 1 AND b.`id_shop` = 1) LEFT JOIN `ps_category_shop` sa ON (a.`id_category` = sa.`id_category` AND sa.id_shop = 1) WHERE 1 AND `id_parent` = $subcat[id_category] ";
$subSubcats_in_cat = Db::getInstance()->executeS($sql);
foreach($subSubcats_in_cat as $subSubcat) {
$id_category .= $subSubcat["id_category"] . ',' ;
}
}
//echo "$id_category <br>";
$id_category = substr($id_category, 0, -1);
$id_category = "$id_category";
return $id_category;
}
}

How to grab contacts from gmail using google API's and contact grabber in PHP?

In my project i want to grab the contacts from gmail using google API's. I provide three keys such as client id, client secret and signature key. When i trying to get contacts the pop-up window is showing error message "Signature key must be formatted". What i have done wrong? Thanks in advance.
Here is my code
keyConfig.php
<?php
$apiRequestUrl = "https://stescodes.com/api/contactsapi.aspx"; // StesCodes contact grabber API request url
$originalsignaturekey = "lxFWDA5ng36sdvlFGukof75vyi";//replace with your signature key
$gmailConsumerKey = "1009516162377-n5s7lo5b4dvlt8e7s3rt12f8i02lpk1f.apps.googleusercontent.com";
$gmailConsumerSecret = "raCUba1smsZCzrVNjqFIqiqC";
$YahooConsumerKey = "your yahoo api key";
$YahooConsumerSecret = "your yahoo api key";
$LiveConsumerKey = "your live api key";
$LiveConsumerSecret = "your live api key";
$fbConsumerKey = "your facebook api key";
$fbConsumerSecret = "your facebook api key";
$callbackurl = "http://localhost/grab/oauth.php";// eg: return url after user authentication http://yourdomain/oauth.php
$currentdirpath = "http://dev.stescodes.com/";//your current web directory path eg:http://yourdomain/
?>
oauth.php
<?php
session_start();
?>
<?php include 'keyConfig.php'; ?>
<html>
<head><title></title>
<script>
function redirectrequest(a)
{
window.location = a;
}
function closepopup(a,b,c,d) {
window.opener.startGrabbingContactsOauth(a,b,c,d);
window.self.close();
}
</script>
</head>
<body>
<?php
$servicename = "gmail";
$token = "";
$ConsumerKey = "";
$ConsumerSecret="";
$tokensecret="";
$tokenverifier="";
$flag=0;
$parameters="";
if($_GET['currpage']!=null)
$_SESSION['currpage']=$_GET['currpage'];
if($_SESSION['currpage']=="gmail")
{
$servicename = "gmail";
$ConsumerKey = $gmailConsumerKey;
$ConsumerSecret = $gmailConsumerSecret;
if ($_GET['code'] != null)
{
$token = $_GET['code'];
$tokensecret = $_SESSION['tokensecret'];
$flag = 1;
}
}
else if($_SESSION['currpage']=="yahoo")
{
$servicename = "yahoo";
$ConsumerKey = $YahooConsumerKey;
$ConsumerSecret = $YahooConsumerSecret;
if (($_GET['oauth_token'] != null) && ($_GET['oauth_verifier'] != null))
{
$token = $_GET['oauth_token'];
$tokenverifier = $_GET['oauth_verifier'];
$tokensecret = $_SESSION['tokensecret'];
$flag = 1;
}
}
else if($_SESSION['currpage']=="facebook")
{
$servicename = "facebook";
$ConsumerKey = $fbConsumerKey;
$ConsumerSecret = $fbConsumerSecret;
if (($_GET['code'] != null))
{
$token = $_GET['code'];
$tokenverifier = "";
$tokensecret = "";
$flag = 1;
}
}
else if(($_SESSION['currpage']=="msn") || ($_SESSION['currpage']=="hotmail") || ($_SESSION['currpage']=="msnmessenger"))
{
$servicename = $_SESSION['currpage'];
$ConsumerKey = $LiveConsumerKey;
$ConsumerSecret = $LiveConsumerSecret;
//Live settings
if ($_GET["code"] != null)
{
$token = $_GET["code"];
$flag = 1;
}
}
if ($flag == 1)
{
$parameters = "type=accesstoken&ServiceName=" . urlencode($servicename) . "&ConsumerKey=" . urlencode($ConsumerKey) . "&ConsumerSecret=" . urlencode($ConsumerSecret);
$parameters = $parameters . "&ReturnUrl=" . urlencode($callbackurl) . "&Token=" . urlencode($token) . "&TokenSecret=" . urlencode($tokensecret) . "&TokenVerifier=" . urlencode($tokenverifier);
$result = file_get_contents($apiRequestUrl."?".$parameters);
$authdetails = json_decode($result,true);
$_SESSION['token'] = $authdetails[details][token];
$_SESSION['tokensecret'] = $authdetails[details][tokenSecret];
$_SESSION['uid'] = $authdetails[details][userID];
$_SESSION['tokenverifier'] = $_SESSION['tokenverifier'];
$_SESSION["consumerkey"] = $ConsumerKey;
$_SESSION["consumersecret"] = $ConsumerSecret;
echo "<SCRIPT LANGUAGE=\"javascript\"> closepopup('".$servicename."',". $result .",'".$ConsumerKey."','".$ConsumerSecret."');</SCRIPT>";
}
else
{
$parameters = "type=authenticationurl&ServiceName=" . urlencode($servicename) . "&ConsumerKey=" . urlencode($ConsumerKey) . "&ConsumerSecret=" . urlencode($ConsumerSecret);
$parameters = $parameters . "&ReturnUrl=" . urlencode($callbackurl) ;
$result = file_get_contents($apiRequestUrl."?".$parameters);
$authdetails = json_decode($result,true);
$_SESSION['token'] = $authdetails[details][token];
$_SESSION['tokensecret'] = $authdetails[details][tokenSecret];
$_SESSION['uid'] = $authdetails[details][userID];
$_SESSION['tokenverifier'] = $tokenverifier;
echo "<SCRIPT LANGUAGE=\"javascript\"> redirectrequest('".$authdetails[details][authUrl]."'); </SCRIPT>";
}
?>

WHMCS License Addon not working

I have just authored a WHMCS addon module that works great on my server; however, others that have tried to use it are not having success. There are 2 issues...
1) I use the WHMCS License Addon; however, it does not appear that their remote machines are making a successful connection to my machine to validate the license. I use the WHMCS supplied code to handle the connection and validation. No idea on what else to check... Any ideas?
2) I have a database that my script checks to see if the user has the most current version of the script. Access to the database works great from my local machine and RemoteSQL is enabled with a % wildcard so anyone should be able to connect but yet the remote machines do not seem to be able to connect. Here is my info...
$link = mysql_connect('gjinternetsolutions.com', 'gj_Guest', 'Password1');
mysql_select_db("gj_Software", $link);
$query = "SELECT * FROM `VersionCheck` where `Software`='RedemptionFee'";
... additional code to display the results
Is anyone able to successfully make a remote connection to the above database?
=========== UPDATE ===========
The second issue above has been resolved. We are still having an issue with the licensing code.... Here is what we have....
# Values obtained from our database...
$localkey=$row['LocalKey'];
$licensekey=$vars['License'];
$results = RedemptionFee_check_gj_license($licensekey,$localkey);
function RedemptionFee_check_gj_license($licensekey,$localkey="")
{
$whmcsurl = "http://gjinternetsolutions.com/home/";
$licensing_secret_key = "####-VALUE REMOVED FOR THIS POST-####"; # Unique value, should match what is set in the product configuration for MD5 Hash Verification
$check_token = time().md5(mt_rand(1000000000,9999999999).$licensekey);
$checkdate = date("Ymd"); # Current date
$usersip = isset($_SERVER['SERVER_ADDR']) ? $_SERVER['SERVER_ADDR'] : $_SERVER['LOCAL_ADDR'];
$localkeydays = 1; # How long the local key is valid for in between remote checks
$allowcheckfaildays = 5; # How many days to allow after local key expiry before blocking access if connection cannot be made
$localkeyvalid = false;
if ($localkey) {
$localkey = str_replace("\n",'',$localkey); # Remove the line breaks
$localdata = substr($localkey,0,strlen($localkey)-32); # Extract License Data
$md5hash = substr($localkey,strlen($localkey)-32); # Extract MD5 Hash
if ($md5hash==md5($localdata.$licensing_secret_key)) {
$localdata = strrev($localdata); # Reverse the string
$md5hash = substr($localdata,0,32); # Extract MD5 Hash
$localdata = substr($localdata,32); # Extract License Data
$localdata = base64_decode($localdata);
$localkeyresults = unserialize($localdata);
$originalcheckdate = $localkeyresults["checkdate"];
if ($md5hash==md5($originalcheckdate.$licensing_secret_key)) {
$localexpiry = date("Ymd",mktime(0,0,0,date("m"),date("d")-$localkeydays,date("Y")));
if ($originalcheckdate>$localexpiry) {
$localkeyvalid = true;
$results = $localkeyresults;
$validdomains = explode(",",$results["validdomain"]);
if (!in_array($_SERVER['SERVER_NAME'], $validdomains)) {
$localkeyvalid = false;
$localkeyresults["status"] = "Invalid";
$results = array();
}
$validips = explode(",",$results["validip"]);
if (!in_array($usersip, $validips)) {
$localkeyvalid = false;
$localkeyresults["status"] = "Invalid";
$results = array();
}
if ($results["validdirectory"]!=dirname(__FILE__)) {
$localkeyvalid = false;
$localkeyresults["status"] = "Invalid";
$results = array();
}
}
}
}
}
if (!$localkeyvalid) {
$postfields["licensekey"] = $licensekey;
$postfields["domain"] = $_SERVER['SERVER_NAME'];
$postfields["ip"] = $usersip;
$postfields["dir"] = dirname(__FILE__);
if ($check_token) $postfields["check_token"] = $check_token;
if (function_exists("curl_exec")) {
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $whmcsurl."modules/servers/licensing/verify.php");
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $postfields);
curl_setopt($ch, CURLOPT_TIMEOUT, 30);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$data = curl_exec($ch);
curl_close($ch);
} else {
$fp = fsockopen($whmcsurl, 80, $errno, $errstr, 5);
if ($fp) {
$querystring = "";
foreach ($postfields AS $k=>$v) {
$querystring .= "$k=".urlencode($v)."&";
}
$header="POST ".$whmcsurl."modules/servers/licensing/verify.php HTTP/1.0\r\n";
$header.="Host: ".$whmcsurl."\r\n";
$header.="Content-type: application/x-www-form-urlencoded\r\n";
$header.="Content-length: ".#strlen($querystring)."\r\n";
$header.="Connection: close\r\n\r\n";
$header.=$querystring;
$data="";
#stream_set_timeout($fp, 20);
#fputs($fp, $header);
$status = #socket_get_status($fp);
while (!#feof($fp)&&$status) {
$data .= #fgets($fp, 1024);
$status = #socket_get_status($fp);
}
#fclose ($fp);
}
}
if (!$data) {
$localexpiry = date("Ymd",mktime(0,0,0,date("m"),date("d")-($localkeydays+$allowcheckfaildays),date("Y")));
if ($originalcheckdate>$localexpiry) {
$results = $localkeyresults;
} else {
$results["status"] = "Invalid";
$results["description"] = "Remote Check Failed";
return $results;
}
} else {
preg_match_all('/<(.*?)>([^<]+)<\/\\1>/i', $data, $matches);
$results = array();
foreach ($matches[1] AS $k=>$v) {
$results[$v] = $matches[2][$k];
}
}
if ($results["md5hash"]) {
if ($results["md5hash"]!=md5($licensing_secret_key.$check_token)) {
$results["status"] = "Invalid";
$results["description"] = "MD5 Checksum Verification Failed";
return $results;
}
}
if ($results["status"]=="Active") {
$results["checkdate"] = $checkdate;
$data_encoded = serialize($results);
$data_encoded = base64_encode($data_encoded);
$data_encoded = md5($checkdate.$licensing_secret_key).$data_encoded;
$data_encoded = strrev($data_encoded);
$data_encoded = $data_encoded.md5($data_encoded.$licensing_secret_key);
$data_encoded = wordwrap($data_encoded,80,"\n",true);
$results["localkey"] = $data_encoded;
}
$results["remotecheck"] = true;
}
unset($postfields,$data,$matches,$whmcsurl,$licensing_secret_key,$checkdate,$usersip,$localkeydays,$allowcheckfaildays,$md5hash);
return $results;
}
Yes, I can connect using the details above.
Query run:
SELECT * FROM `gj_Software`.`VersionCheck` where `Software`='RedemptionFee'
Result:
# Software, Version, URL
'RedemptionFee', '1.0', 'http://GJinternetSolutions.com/home/upgrade.php?type=package&id=660'
Hope this helps.
Ash