Been using socialite for quite a while now and i'm wondering if there is any built-in method that allows me to retrieve a user repositories.
I'm familiar with the list on method offered on laravel website.
Any idea how to fetch the Repos given the user token ?
I found another to do that . Find the code below :
In the callback function i added a function that uses curl to fetch repos
public function handleProviderCallback()
{
$user = Socialite::driver('github')->user();
$this->getUserRepos($user);
}
The Get Repos function is as below :
private function getUserRepos($user)
{
$name=$user->getNickname();
$token=$user->token;
// We generate the url for curl
$curl_url = 'https://api.github.com/users/' .$name. '/repos';
// We generate the header part for the token
$curl_token_auth = 'Authorization: token ' . $token;
// We make the actuall curl initialization
$ch = curl_init($curl_url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
// We set the right headers: any user agent type, and then the custom token header part that we generated
curl_setopt($ch, CURLOPT_HTTPHEADER, array('User-Agent: Awesome-Octocat-App', $curl_token_auth));
// We execute the curl
$output = curl_exec($ch);
// And we make sure we close the curl
curl_close($ch);
// Then we decode the output and we could do whatever we want with it
$output = json_decode($output);
foreach ($output as $repo) {
print '' . $repo->name . '<br />';
}
}
And it works swiftly .
Related
How can I send data from controller to external api in Laravel?
public function syncData(Request $request)
{
$datas = Data::all();
$newDatas = NewData::all();
$url = 'mydomain.com/api/sync-data';
}
I want to send $datas and $newDatas to $url through Laravel controller and perform some actions on those data. How can I achieve that?
You could use the Laravel HTTP Client (which is a wrapper for Guzzle HTTP Client) to perform a request to that API.
use Illuminate\Support\Facades\Http;
$response = Http::post('mydomain.com/api/sync-data', [
'data' => Data::all(),
'newdata' => NewData::all(),
]);
public function syncData(Request $request)
{
$datas = Data::all();
$newDatas = NewData::all();
$url = 'mydomain.com/api/sync-data';
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($datas));
$output = curl_exec($ch);
curl_close($ch);
}
let me know if it is helpful.
important things to notice here.
you have to know what your external API type is. is it POST or in GET method.
my example above is just a sample code to make you understand how you will use curl it is not tested in regard to your context
In local development systems I did not get any such errors but while deploying in live production server I am getting following errors.
EventSource's response has a MIME type ("text/html") that is not "text/event-stream". Aborting the connection.
I am using laravel. I have set headers in controller function as following.
I found many people are having same issues in different framworks but could not found working solution for me.
Can anyone have solution or suggestion to this? Thanks in advance.
Following is javascript SSE call.
<script>
if(typeof(EventSource) !== "undefined"){
var source = new EventSource("/sse");
source.addEventListener("response", function(event) {
document.getElementById("result").innerHTML += "<p>RESPONSE DATA</p><p>" + event.data + "</p>";
});
} else {
document.getElementById("result").innerHTML = "Sorry, your browser does not support server-sent events.";
}
Following is Laravel Controller function. I have also tried setting headers in public function __construct(){} and also tried setting in public function index(){} That didnot helped either.
public function sse($userid,Request $request){
header('Content-Type: text/event-stream');
header('Cache-Control: no-cache');
$SERVER = env('SERVER','');
$url = $SERVER.'/stream';
$user = Auth::user();
$gwuser = $user->gwuser;
$gwpass = $user->gwpass;
ini_set('output_buffering', 'off');
ini_set('zlib.output_compression',false);
ini_set('implicit_flush',true);
while (#ob_end_flush()){
ob_implicit_flush(true);
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($ch, CURLOPT_USERPWD, $gwuser . ':' . $gwpass);
$error = 0;
//$result = curl_exec($ch);
//This while loop is only for server timeout after 5 minutes
while(true){
$result = curl_exec($ch);
}
}
}
I have also tried using Middleware to set headers for selected route call and assign middleware to that route. That didnot helped.
namespace App\Http\Middleware;
use Closure;
class setHeader
{
public function handle($request, Closure $next)
{
$response = $next($request);
$response->header('Content-Type', 'text/event-stream');
$response->header('Cache-Control', 'no-cache');
return $response;
}
}
I have a Post Route in Laravel, so if a user post data to the route I want to add data to request then posting it to another post route that I have then show the user the result that I get from the second route.
Is there way to do it? or I should use GuzzleHttp?
You can use curl to perform the sub request.
Route::any('/proxy', function (Request $request) {
//Get all of the input from the request and store them in $data.
$data = $request->all();
//initialise your other data.
$data2 = ['xyz' => "xyz"];
$newPayload = array_merge($data, $data2);
$endPoint = "https://example.org";
$ch = curl_init($endPoint);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, $newPayload);
// execute!
$response = curl_exec($ch);
// close the connection, release resources used
curl_close($ch);
return (string)$response;
});
I need a PHP script which has to create an event on google calendar.
I've already read google API documentation and I've understood that I have to use an offline access to API because I'd like that my script would create the calendar event itself, without asking for user auth every time.
I've also read here in stackoverflow that some ppl had problems resfreshing the token and have fixed the problem using cURL; I've tried to do that but I got an error: Uncaught exception 'Google_ServiceException' with message 'Error calling POST and 401 Login Required; now in $json_response var, there is the access_token; I've not understood how to use it to renew my connection. Thanks in advance for your help!
<?php
require_once 'src/Google_Client.php';
require_once 'src/contrib/Google_CalendarService.php';
session_start();
// I need that my script refresh the token itself, starting from a token that I've generated one time with user interaction
$oauth2token_url = "https://accounts.google.com/o/oauth2/token";
$clienttoken_post = array(
"client_id" => '...',
"client_secret" => '...');
$clienttoken_post["refresh_token"] = "1/vIQ......";
$clienttoken_post["grant_type"] = "refresh_token";
$curl = curl_init($oauth2token_url);
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $clienttoken_post);
curl_setopt($curl, CURLOPT_HTTPAUTH, CURLAUTH_ANY);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$json_response = curl_exec($curl);
curl_close($curl);
$authObj = json_decode($json_response);
print_r($authObj);
$client = new Google_Client();
$client->setApplicationName("Google Calendar PHP Starter Application");
$client->setClientId('....');
$client->setClientSecret('....'); $client->setRedirectUri('...');
$client->setDeveloperKey('....');
$client->setAccessType('offline');
//$client-> setApprovalPrompt("auto");
$cal = new Google_CalendarService($client);
if (isset($_GET['logout'])) {
unset($_SESSION['token']);
}
if (isset($_GET['code'])) {
$client->authenticate();
$_SESSION['token'] = $client->getAccessToken();
header('Location: http://' . $_SERVER['HTTP_HOST'] . $_SERVER['PHP_SELF']);
}
if(isset($_SESSION['token'])) {
// echo $_SESSION['token'];
$client->setAccessToken($_SESSION['token']);
}
$event = new Google_Event();
$event->setSummary($event_name);
$event->setLocation('');
$start = new Google_EventDateTime();
$start->setDate($scadenza);
$event->setStart($start);
$end = new Google_EventDateTime();
$end->setDate($scadenza);
$event->setEnd($end);
$createdEvent = $cal->events->insert('cal_id_xyz', $event);
?>
Thanks in advance!
(Disclaimer: I'm not a PHP expert (or even novice) - but I do know Google's OAuth flows)
A few things to note:
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false); - if that is disabling certificate validation, then I strongly suggest not doing that - you should want to verify that you are sending the refresh token to accounts.google.com and no-one else.
Make sure you set the content-type to "application/x-www-form-urlencoded" on the POST - it's not clear to me whether setting CURLOPT_POSTFIELDS does this or something else for you.
I don't know why you are setting CURLOPT_HTTPAUTH - I wouldn't expect that to make any positive effect on the request.
That all said, my suggestion would be to take advantage of the Google provided client library - which it looks like you are already using.
After looking at the src for Google_Client.php, I believe that adding a:
$client->refreshToken("1/xxxxxx....");
after all of the other ->setXXXs will have it go ahead and get a new access token for you that it should then automatically add to subsequent APIs calls. I suggest trying that and removing the manual calls to curl.
I've finally solved my problem this way:
First of all I've obtained an access token and a refresh token with a human interaction using the PHP sample script found at this URL: https://code.google.com/p/google-api-php-client/
So I've put the access token in actok.txt and then I've run the following script.
Hope that could help beginners (and I am one of them :-) ), to better understand how OAuth works with offline access.
<?php
// I've put the last valid access token in a txt file
$my_file = 'actok.txt';
$handle = fopen($my_file, 'r');
$data = fread($handle,filesize($my_file));
fclose($handle);
$first_answer = "{\"access_token\":\"" . $data . "\",\"expires_in\":3920,\"token_type\":\"Bearer\",\"refresh_token\":\"1/xxxxx\"}"; // the refresh_token is always the same and it's the one obtained at the beginning.
require_once 'src/Google_Client.php';
require_once 'src/contrib/Google_CalendarService.php';
session_start();
$oauth2token_url = "https://accounts.google.com/o/oauth2/token";
$clienttoken_post = array(
"client_id" => '....',
"client_secret" => '....');
$clienttoken_post["refresh_token"] = "...."; // the same as before
$clienttoken_post["grant_type"] = "refresh_token";
$curl = curl_init($oauth2token_url);
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $clienttoken_post);
curl_setopt ($curl, CURLOPT_HTTPHEADER, Array("application/x-www-form-urlencoded"));
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, true);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$client = new Google_Client();
$client->setApplicationName("Google Calendar PHP Starter Application");
$client->setClientId('xyz'); // ClientID
$client->setClientSecret('xyz'); // ClientSecret
$client->setRedirectUri('http://www.xyz/zzz.php'); // RedirectUri
$client->setDeveloperKey('ffffff'); // DeveloperKey
$client->setAccessType('offline');
$cal = new Google_CalendarService($client);
$client->setAccessToken($first_answer); // here I set the last valid access_token, taken from the txt file
if (isset($_GET['logout'])) {
unset($_SESSION['token']);
}
if(isset($_GET['code'])) {
$client->authenticate();
$_SESSION['token'] = $client->getAccessToken();
header('Location: http://' . $_SERVER['HTTP_HOST'] . $_SERVER['PHP_SELF']);
}
if(isset($_SESSION['token'])) {
$client->setAccessToken($_SESSION['token']);
}
if($client->isAccessTokenExpired()) { // if the token is expired, I have to refresh it
echo 'Access Token Expired'; // debug
$json_response = curl_exec($curl); // JSON value returned
curl_close($curl);
$authObj = json_decode($json_response);
$sec_answer = "{\"access_token\":\"" . $authObj->access_token . "\",\"expires_in\":3920,\"token_type\":\"Bearer\",\"refresh_token\":\"1/xxxxxx\"}"; // same refresh_token as always
$client->setAccessToken($sec_answer);
$handle2 = fopen($my_file, 'w') or die('Cannot open file: '.$my_file);
$new_accesstk = $authObj->access_token;
fwrite($handle2, $new_accesstk);
fclose($handle2);
}
// Event Creation
$event = new Google_Event();
$event->setSummary('xyz'); // Event name
$event->setLocation(''); // Event location
$start = new Google_EventDateTime();
$start->setDate('2013-xx-xx');
$event->setStart($start);
$end = new Google_EventDateTime();
$end->setDate('2013-xx-xx');
$event->setEnd($end);
$createdEvent = $cal->events->insert('xyz', $event); // insert(calendar_id, event)
?>
I've got a function, "Function A", in a CodeIgniter controller that includes a redirect to another function, "Function B" to send an email when it's done gathering data. My problem is that when I enter Function A's url into the browser, the function works as expected and the redirect to Function B also works... but Function A is called by a cURL script, and when this happens Function A is performed but the redirected Function B does not work. Is it possible to have a redirected function in this scenario (when the request is made via cURL)?
Can you show your CURL code? I think you use something like:
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_HEADER, true);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
$result = curl_exec($ch);
curl_close( $ch );
Check this string (it should set to true):
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
And you can use next thing (in stormdrain's example):
function first_function(){
ob_start();
//do stuff
$this->second_function();
ob_end_flush();
}
function second_function(){
//send email
}
It's hard to say without seeing any code. But, if these functions are in the same controller, you can call the other function when the first completes
function first_function(){
//do stuff
$this->second_function();
}
function second_function(){
//send email
}