I am trying to get OAuth to work with Google Analytics, but I'm not having any luck. My code looks like this:
require_once('common.inc.php');
$consumerKey = "my.url.net";
$consumerSecret = "nzZ....TX";
$sig_method = "HMAC-SHA1";
$oauth_token = $token ? new OAuthToken($token, $token_secret) : NULL;
$token_endpoint = '/accounts/OAuthGetRequestToken';
$scope = 'https://www.google.com/analytics/feeds/';
$callback_url = "http://my.url.net/pete/oauth/";
$privKey = NULL;
$params = array('scope' => $scope, 'oauth_callback' => $callback_url);
$url = $token_endpoint . '?scope=' . urlencode($scope);
$consumer = new OAuthConsumer($consumerKey, $consumerSecret);
$req = OAuthRequest::from_consumer_and_token($consumer, $oauth_token, 'GET',
$url, $params);
//$req->sign_request($sig_method, $consumer, $oauth_token, NULL);
echo "<PRE>";
print_r($req);
// Fill response
echo json_encode(array(
'html_link' => '',
'base_string' => $req->get_signature_base_string(),
'response' => send_signed_request('GET', $url, array($req->to_header())),
'authorization_header' => $req->to_header()
));
So when this code runs it prints this:
OAuthRequest Object
(
[parameters:OAuthRequest:private] => Array
(
[oauth_version] => 1.0
[oauth_nonce] => 5f....11
[oauth_timestamp] => 1306433873
[oauth_consumer_key] => my.url.net
[scope] => https://www.google.com/analytics/feeds/
[oauth_callback] => http://my.url.net/pete/oauth/
)
[http_method:OAuthRequest:private] => GET
[http_url:OAuthRequest:private] => /accounts/OAuthGetRequestToken?scope=https%3A%2F%2Fwww.google.com%2Fanalytics%2Ffeeds%2F
[base_string] =>
)
When I uncomment this line:
//$req->sign_request($sig_method, $consumer, $oauth_token, NULL);
The script just fails to load showing Server Error. What am I doing wrong? Any advice would help, thanks!
Thanks for your comment Mark, this was actually because my "$sig_method" variable was actually just a string containing "HMAC..." when it actually needed to be an object called this:
$sig_method = new OAuthSignatureMethod_HMAC_SHA1();
Hope this helps someone in the future!
Related
I have tried to create a new user on the Moodle by web service api.
I tried with a example that i found on the github and with another php code
In the both i receive the same response:
"Missing required key in single structure: users"
the response:
{
"exception":"invalid_parameter_exception",
"errorcode":"invalidparameter",
"message":"Invalid parameter value detected",
"debuginfo":"Missing required key in single structure: users"
}
I try to change the object by a array, but the error continues.
my code:
$functionname = 'core_user_create_users';
$user1 = new stdClass();
$user1->id = 1;
$user1->username = 'testusername1';
$user1->password = 'testpassword1';
$user1->firstname = 'testfirstname1';
$user1->lastname = 'testlastname1';
$user1->email = 'testemail1#moodle.com';
$user1->auth = 'manual';
$user1->idnumber = 'testidnumber1';
$user1->description = 'Hello World!';
$user1->city = 'testcity1';
$user1->country = 'BR';
$token = 'mytoken';
$domainname = 'localhost/moodle';
$functionname = 'core_user_create_users';
$restformat = 'json';
$serverurl = $domainname . '/webservice/rest/server.php'. '?wstoken=' . $token . '&wsfunction='.$functionname.'&moodlewsrestformat=' . $restformat;
$users = array($user1);
$params = array('users' => $users);
$context = stream_context_create(array(
'http' => array(
'method' => 'POST',
'header' => 'Content-Type: text/plain',
'content' => $params
)
));
$contents = file_get_contents($serverurl, null, $context);
//print_r($contents);
$resposta = json_decode($contents);
I have a valid token and the user is allowed to use the core_user_create_users function
get same problem with required key 'users'
solve problem with this =>
$serverurl = $domainname . '/webservice/rest/server.php'. '?wstoken=' . $token . '&wsfunction='.$functionname;
//require_once('../curl.php');
$curl = new curl;
$params = "&users[0][username]=loginnn&users[0][password]=4815162342Qq*&users[0][firstname]=allala&users[0][lastname]=trest&users[0][email]=ty#mail.ru";
//if rest format == 'xml', then we do not add the param for backward compatibility with Moodle < 2.2
$restformat = ($restformat == 'json')?'&moodlewsrestformat=' . $restformat:'';
$resp = $curl->post($serverurl . $restformat, $params);
I think You must high the debugging level in your moodle system, I hope you will get more useful information regarding this error, debugging will help you to reach the exact problem. go through following path:
Home ► Site administration ► Development ► Debugging
choose Developer level from the debug messages and save the changes
I have a similar problem once, in my experience is a problema with $user1->password = 'testpassword1'; Moodle needs a password with one uppercase letter and at least one simbol like / . , - _ etc.
try a new password maybe it works...
Do not pass the ID into the user array, as it doesn't accept it as a parameter. For more details, please read the WebService API documentation for creating a user in Moodle.
came across the same need today and I used your post to get the code from GitHUB so I guess I'd tell you how I fixed the error:
change your code to the following:
$users = array((array)$user1);
$params = array('users' => (array)$users);
The code from GitHUB $user1 is an object. Moodle required an Array.
Below is copied from Moodle's documentation.
[users] =>
Array
(
[0] =>
Array
(
[username] => string
[password] => string
[firstname] => string
[lastname] => string
[email] => string
[auth] => string
[idnumber] => string
[lang] => string
[calendartype] => string
[theme] => string
[timezone] => string
[mailformat] => int
[description] => string
[city] => string
[country] => string
[firstnamephonetic] => string
[lastnamephonetic] => string
[middlename] => string
[alternatename] => string
[preferences] =>
Array
(
[0] =>
Array
(
[type] => string
[value] => string
)
)
[customfields] =>
Array
(
[0] =>
Array
(
[type] => string
[value] => string
)
)
)
)
In our case, we added Https support, but we were still calling the Http version of the Moodle url. Changing to Https solved the problem.
This is tested and working on Moodle 3.1.2 - I find this a much cleaner and easier to understand solution, using a proper array (as Moodle expects) native cURL and http_build_query...
Make sure the password you are providing to Moodle meets your security requirements.
$moodledata['users'][] = array(
'username' => 'testuser123',
'password' => 'TestPass1!',
'firstname' => 'Firstname',
'lastname' => 'Lastname',
'email' => 'test#test.com',
);
//open connection
$token = 'your-token-goes-here';
$domainname = 'https://yourmoodlesite.tld';
$functionname = 'core_user_create_users';
$url = $domainname . '/webservice/rest/server.php?wstoken=' . $token . '&wsfunction='.$functionname."&moodlewsrestformat=json";
$ch = curl_init();
//set the url, number of POST vars, POST data
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($moodledata));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
//execute post, and get our JSON as defined above with moodlewsrestformat=json
$result = curl_exec($ch);
//if you want it in an array
//$result = json_decode($result, true);
i'm trying to connect my page to a webservice soap. My hosting doesn't support soap so SoapClient isn't recognized. I have a working example to connect to that ws but uses SoapClient. This is:
$params = array('location'=>"www.wssite.com/test.php",
'trace'=>1,
'exceptions'=>1);
$client = new SoapClient("url_of_wsdl",$params);
var_dump($client->__getFunctions());
var_dump($client->__getTypes());
$pars = array('ipcInvocationName' => 'wsinvokeservice',
'ipcMethodNamespace' => 'svcmsgxml.bldximsgin',
'ttIn' => array(
'ttInRow' => array( array('ParPos' => '0','ParNam' => 'MethodName',
'ParVal' => POST),
array('ParPos' => '1','ParNam' => 'XMLDocumentIn',
'ParVal' => 'LoginXmlValue'))),
'ttOut' => array('ttOutRow' => array(array('ParPos' => '0',
'ParNam' => 'ContentType','ParVal' => ''),array('ParPos' => '1',
'ParNam' => 'Result','ParVal' => ''),
array('ParPos' => '2','ParNam' => 'XMLDocumentOut','ParVal' => '')));
$return = $client->wssigateway($pars);
It works good!
I used NuSoap in this way:
require_once 'soap/nusoap.php';
$wsdl = 'url_of_wsdl';
$client = new soapclient($wsdl,true);
$err = $client -> getError();
if ($err) {
echo '<h2>Constructor error</h2><pre>' . $err . '</pre>';
exit();
}
$pars = array()//the same as above
$result = $client -> call('wssigateway',$pars);
The script works for too much time and does get me nothing.. why? can someone help me?
Try $client = new nusoap_client($wsdl,true);
instead of $client = new soapclient($wsdl,true);
Here is My code :
<?
session_start();
require_once($_SERVER['DOCUMENT_ROOT'].'/admin/config.php');
require_once($_SERVER['DOCUMENT_ROOT'].'/admin/fonctions.php');
include '../api/facebook.php';
include '../api/xhttp.php';
$config = array();
$config['appId'] = '35455XXXXXXX207';
$config['secret'] = '6006855f3aXXXXXXXXX9bce45a426';
$config['fileUpload'] = false; // optional
$facebook = new Facebook($config);
$args = array(
'message' => 'Hello from my App!',
'link' => 'http://www.masteringapi.com/',
'caption' => 'Visit MasteringAPI.com For Facebook API Tutorials!',
'access_token' => $access_token
);
$retour_login = json_decode(stripslashes($_GET['session']), true);
$uid = $retour_login['uid'];
$access_token = $retour_login['access_token'];
$post_id = $facebook->api("/me/feed", "post", $args);
?>
But it returns : Uncaught OAuthException: An active access token must be used to query information about the current user.
Any ideas ?
Thanks!
Here is My new code :
<?
$config = array();
$config['appId'] = '3545XXXXXXX6207';
$config['secret'] = '60068XXXXXXXXXXXe45a426';
$facebook = new Facebook($config);
$retour_login = json_decode(stripslashes($_GET['session']), true);
$uid = $retour_login['uid'];
$access_token = $retour_login['access_token'];
$me = null;
// Session based API call.
if ($session) {
try {
$uid = $facebook->getUser();
$me = $facebook->api('/me');
} catch (FacebookApiException $e) {
error_log($e);
}
}
if(!isset($_GET['session'])) {
$params = array(
'locale' => 'fr_FR',
'display' => 'popup',
'req_perms' => 'email,user_about_me,user_birthday,user_location',
'ext_perms' => 'publish_stream,share_item,manage_pages'
);
header("Location: ".$facebook->getLoginUrl($params));
}
$args = array(
'message' => "XXXX",
'link' => 'XXXX',
'name' => 'XXXX',
'picture' => 'XXXX',
"caption"=> "lien.com",
"type"=> "link");
$post_id = $facebook->api("/me/links", "post", $args);
?>
This time i get this error : OAuthException: (#282) Requires extended permission: share_item thrown
Any ideas ?
Thanks!
You're not passing it the access token.
Check out getAccessToken().
From your code sample it looks like you are trying to use the variable $access_token to create your $args array, before you define the $access_token variable. I would switch the order of variable definitions:
$retour_login = json_decode(stripslashes($_GET['session']), true);
$uid = $retour_login['uid'];
$access_token = $retour_login['access_token'];
$args = array(
'message' => 'Hello from my App!',
'link' => 'http://www.masteringapi.com/',
'caption' => 'Visit MasteringAPI.com For Facebook API Tutorials!',
'access_token' => $access_token
);
This is assuming $retour_login['access_token'] contains a valid Facebook access token. Otherwise you will need to fetch the current user's access token using the Facebook SDK:
$access_token = $facebook->getAccessToken();
using examples I have this code. It works fine, authorizes the proper scopes and everything:
<?php
ini_set("display_errors",1);
error_reporting(E_ALL);
session_start();
set_include_path('/home/library/'.get_include_path());
require_once 'Zend/Oauth/Consumer.php';
$oauthOptions = array(
'requestScheme' => Zend_Oauth::REQUEST_SCHEME_HEADER,
'version' => '1.0',
'consumerKey' => 'ivana.2x.to',
'consumerSecret' => '*********',
'signatureMethod' => 'HMAC-SHA1',
'requestTokenUrl' => 'https://www.google.com/accounts/OAuthGetRequestToken',
'userAuthorizationUrl' => 'https://www.google.com/latitude/apps/OAuthAuthorizeToken',
'accessTokenUrl' => 'https://www.google.com/accounts/OAuthGetAccessToken',
'callbackUrl' => 'http://ivana.2x.to/geo/?show=callback',
);
$consumer = new Zend_Oauth_Consumer($oauthOptions);
if (!isset($_SESSION['ACCESS_TOKEN_GOOGLE'])) {
if (!empty($_GET)) {
$token = $consumer->getAccessToken($_GET, unserialize($_SESSION['REQUEST_TOKEN_GOOGLE']));
$_SESSION['ACCESS_TOKEN_GOOGLE'] = serialize($token);
} else {
$token = $consumer->getRequestToken(array('scope'=>'https://www.googleapis.com/auth/latitude'));
$_SESSION['REQUEST_TOKEN_GOOGLE'] = serialize($token);
$customparams = array('domain' => 'ivana.2x.to', 'granularity' => 'best', 'location' => 'current');
$consumer->redirect($customparams );
exit;
}
} else {
$token = unserialize($_SESSION['ACCESS_TOKEN_GOOGLE']);
//$_SESSION['ACCESS_TOKEN_GOOGLE'] = null; // do not use, we want to keep the access token
}
$client = $token->getHttpClient($oauthOptions);
$client->setUri('https://www.googleapis.com/latitude/v1/currentLocation');
$client->setMethod(Zend_Http_Client::GET);
$response = $client->request();
$body = $response->getBody();
header('Content-Type: ' . $response->getHeader('Content-Type'));
echo $response->getBody();
No my problem is that i get an empty location resource. It just looks like this:
{"data":{"kind":"latitude#location"}}
The data is missing. But no error or anything.
I am logged in and my location is set and google guarantees lon and lat to be returned.
Any ideas?
I was a little miss guided by the api description. Once i passed the granularity parameter, everything worked fine. I also had to add it with $client->addParameterGet('granularity','best'), because oterhwise the oauth signing would not work.
I have sucessfully connected to twitter using Zend_Oauth_Consumer and got an access token, however when i try to use this access token i am getting an error.
This is the code:
$token = unserialize($twsession->access_token); # would be in DB
$twitter = new Zend_Service_Twitter(array(
'username' => $token->screen_name,
'accessToken' => $token
));
$response = $twitter->account->verifyCredentials();
This outputs:
Zend_Rest_Client_Result Object (
[_sxml:protected] => SimpleXMLElement Object
(
[request] => /1/account/verify_credentials.xml
[error] => Incorrect signature
)
[_errstr:protected] => )
I assume the code is actually correct, its hard to tell as the examples on the ZF site are incomplete.
FWIW i am using Zend Framework 1.10.8
some fields were missing:
$token = unserialize($twsession->access_token); # would be in DB
$twitter = new Zend_Service_Twitter(array(
'username' => $token->screen_name,
'accessToken' => $token
));
$response = $twitter->account->verifyCredentials();
should be:
$token = unserialize($twsession->access_token); # would be in DB
$twitter = new Zend_Service_Twitter(array(
'username' => $token->screen_name,
'accessToken' => $token,
'consumerKey' => YOUR_APP_CONSUMER_KEY,
'consumerSecret' => YOUR_APP_CONSUMER_SECRET,
'callbackUrl' => YOUR_CALLBACK_URL
));
$response = $twitter->account->verifyCredentials();
To confirm, for a valid signature you need all the same fields that you are using with Zend_Oauth_Consumer