I have been looking for any solution for my case, but I haven't found it. Therefore I decided to share my solution.
CASE
I want to share some user information between domains. It means I want to get all collected info about user who already visited my web1.com last week and come to web2.com right now. The user is for first time at web2.com but I already know who he is.
SOLUTION:
Requirements:
PHP server - central server whose generate cookies and serve user data
Database server (optionally) - keep cookies and user data (you can use file etc.) I'm using Postgres.
Possibility to include part of JS code into webs.
PHP server http://cookie-server.local index.php:
<?php
$hash = array_key_exists('my-cookie', $_COOKIE) ? $_COOKIE["my-cookie"] : NULL;
try {
$connection = new PDO("pgsql:dbname=cookie;host=localhost", 'postgres', 'postgres');
$data = findHash($connection, $hash);
if ($data) {
setcookie('my-cookie', $data['hash'], strtotime("+1 year"));
sendResponse($data);
} else {
$hash = generateHash();
$data = storeHash($connection, $hash);
setcookie('my-cookie', $hash, strtotime("+1 year"));
}
} catch (PDOException $e) {
echo $e->getMessage();
die();
}
function findHash($connection, $hash) {
$sql = 'SELECT * from cookie WHERE hash = :hash';
$stm = $connection->prepare($sql, array(PDO::ATTR_CURSOR => PDO::CURSOR_FWDONLY));
$stm->execute(array(':hash' => $hash));
$result = $stm->fetchAll(PDO::FETCH_ASSOC);
if ($result === FALSE) {
printError($stm->errorInfo());
}
return count($result) > 0 ? $result[0] : NULL;
}
function sendResponse($data) {
header('Content-Type: text/javascript; charset=utf8');
header('Access-Control-Allow-Origin: *');
header('Access-Control-Max-Age: 3628800');
header('Access-Control-Allow-Methods: GET, POST, PUT, DELETE');
echo 'showData('. json_encode($data) .');';
}
function printError($error) {
echo 'SQL error: ' . $error[2];
die();
}
function generateHash() {
return $hash = md5(uniqid(mt_rand(), TRUE));
}
function storeHash($connection, $hash) {
$sql = "INSERT INTO cookie (id, hash) VALUES (nextval('cookie_id_seq'), :hash)";
$stm = $connection->prepare($sql);
$result = $stm->execute(['hash' => $hash]);
if ($result === FALSE) {
printError($stm->errorInfo());
}
return [
'id' => $connection->lastInsertId(),
'hash' => $hash,
'name' => ''
];
}
?>
Basic web page on web1.com (The JS code hast to be everywhere you need to know info about user)
<html>
<body>
WEB 1:<br> <span id="hash"></span>
</body>
<script type="text/javascript">
function showData(data) {
document.getElementById('hash').innerHTML = "<br>ID: " + data.id + "<br>Hash: " + data.hash + "<br>Jmeno: " + data.name;
}
var script = document.createElement("script");
script.type = 'application/javascript';
script.src = "http://cookie-server.local";
document.getElementsByTagName("head")[0].appendChild(script);
</script>
<script type="text/javascript" src="http://cookie-server.local">
</html>
Database:
How it works?
When user visit web1.com, the JS code execute and include
<script type="text/javascript" src="http://cookie-server.local"> to page head element. The browser try to download content of file and it execute PHP code on server. The server look at passed cookies and find out there is no my-cookie. Therefore it generate cookie hash, store it in database, set it to user (cookie with name "my-cookie" for domain cookie-server.local) and send user data with JSONP. For another request to server it find previously generated hash in database and only extends expiration and sends user data for sure. Since now, when this user open any other web page (web2.com...) with the JS code, you know who it is.
Related
I am using phantomjs to print the webpage and create a pdf. As the UI needs the user's authentication before finding the data, I used persistent cookies to authenticate the user. But somehow I got login screen every time in the created PDF. I observed that the user authenticated successfully and also the result's webpage showing proper result (debug logs showing the proper data array) but while printing the web page or creating a PDF, it somehow gets the login screen. Sometimes I observed that I got two different cookies in my PHP code while getting the report data and in javascript 'document.cookies'.
Please let me know how can I fix this.
var page = require('webpage').create(),
system = require('system'), t, address;
page.settings.userName = 'myusername';
page.settings.password = 'mypassword';
if (system.args.length === 1) {
console.log('Usage: scrape.js ');
phantom.exit();
} else {
t = Date.now();
address = system.args[1];
page.open(address, function (status) {
if (status !== 'success') {
console.log('FAIL to load the address');
} else {
t = Date.now() - t;
var title = page.evaluate(function() { return document.title;})
console.log('Page title is ' + title);
console.log('Loading time ' + t + ' msec');
}
phantom.exit();
});
}
Another piece of code of sending a cookie file
bin/phantomjs --cookies-file=/tmp/cookies.txt --disk-cache=yes --ignore-ssl-errors=yes /phantomjs/pdf.js 'username' 'params' '/tmp/phantomjs_file' /tmp/phantom_pdf.pdf
And
phantomjs --cookies-file=cookies.txt examples/rasterize.js localhost:7000/reports /tmp/report.pdf
I have my index.php file which is calling web service out of sugar and it returns me as response when I run it on my local Apache this result which is OK:
<soapenv:Envelope <soapenv:Body> <ns:CommandResponseData>
<ns:Operation name="BalanceAdjustment"> </ns:Operation>
</ns:CommandResponseData> </soapenv:Body> </soapenv:Envelope>
I created one additional button within Detail View which I plan to call this web service but I do not know how to bind that button, my index.php file and result from that web service to pack in some field.
For testing purposes I would like to put this whole response on example in field Comment of Contact module: so that field Comment should Contain above whole response (I will later parse it).
I created new button (which does not do anything currently )
I created button in view.detail.php.
<?php
if(!defined('sugarEntry') || !sugarEntry) die('Not A Valid Entry Point');
require_once('include/json_config.php');
require_once('include/MVC/View/views/view.detail.php');
class ContactsViewDetail extends ViewDetail
{
function ContactsViewDetail()
{
parent::ViewDetail();
}
function display()
{
$this->dv->defs['templateMeta']['form']['buttons'][101] = array (
'customCode' => '<input title="Call" accesskey="{$APP.LBL_PRINT_PDF_BUTTON_KEY}" class="button" onClick="javascript:CustomFunctionHere();" name="tckpdf" value="Call" type="button">');
parent::display();
}
}
?>
I will appreciate help with this. So to recapitulate : With this my button I want to call my index.php file which will call web service and I want to set web service response in my field Comment (I am getting response in index.php file as htmlspecialchars($client->__getLastResponse())
this is the whole index.php file that I am using currently to call some web service.
<?php
include_once 'CommandRequestData.php';
include_once 'CommandResponseData.php';
$client = new SoapClient("http://127.0.0.1:8181/TisService?WSDL", array(
"trace" => 1, // enable trace to view what is happening
"exceptions" => 1, // disable exceptions
"cache_wsdl" => 0) // disable any caching on the wsdl, encase you alter the wsdl server
);
$req = new CommandRequestData();
$req->Environment->Parameter[0]->name = "ApplicationDomain";
$req->Environment->Parameter[0]->value = "CAO_LDM_00";
$req->Environment->Parameter[1]->name = "DefaultOperationNamespace";
$req->Environment->Parameter[1]->value = "CA";
$req->Command->Operation->namespace = "CA";
$req->Command->Operation->name = "BalanceAdjustment";
$req->Command->Operation->ParameterList->StringParameter[0]->name = "CustomerId";
$req->Command->Operation->ParameterList->StringParameter[0]->_ = "387671100009";
$req->Command->Operation->ParameterList->IntParameter[0]->name = "AmountOfUnits";
$req->Command->Operation->ParameterList->IntParameter[0]->_ = "1000";
$req->Command->Operation->ParameterList->IntParameter[1]->name = "ChargeCode";
$req->Command->Operation->ParameterList->IntParameter[1]->_ = "120400119";
try {
$result = $client->ExecuteCommand($req);
$result->CommandResult->OperationResult->Operation->name . "<br /><br />";
}
catch(SoapFault $e){
echo "<br /><br />SoapFault: " . $e . "<br /><br />";
}
catch(Exception $e){
}
echo "<p>Response:".htmlspecialchars($client->__getLastResponse())."</p>";
?>
If you share a photo on Instagram you see the following message above the photo on your timeline.
"FB User took a photo with Instagram."
My test currently just shows:
"FB User 3 seconds ago via AppName"
My image Post code is:
$args = Array(
'url' => 'http://www.mySiteName.com/imageName.png',
'message' => 'Made on SiteName http://www.mySiteName.com',
);
$post_id = $this->facebook->api("/me/photos", "post", $args);
I think I need to set OpenGraph Actions and Objects, which I've done, but I'm not sure I've set them up correctly or how to test them.
I've created an Action "Make" and an Object "Collection" and tried the following:
$post_id = $this->facebook->api("/me/Namespace:make", "post", $args);
but get error:
"The action you're trying to publish is invalid because it does not specify any reference objects. At least one of the following properties must be specified: collection."
Collection Get Code gives:
<head prefix="og: http://ogp.me/ns# fb: http://ogp.me/ns/fb# collection: http://ogp.me/ns/collection#">
<meta property="fb:app_id" content="appId" />
<meta property="og:type" content="collection" />
<meta property="og:url" content="Put your own URL to the object here" />
<meta property="og:title" content="Sample Collection" />
<meta property="og:image" content="https://s-static.ak.fbcdn.net/images/devsite/attachment_blank.png" />
Action Get Code gives:
curl 'https://graph.facebook.com/me/nameSpace:make?access_token=TOKEN'
I've managed to get it working and have posted below an image of resulting Post, reference URLs and Codeigniter code.
Make is my OpenGraph Action and Collection is my OpenGraph Object.
Reference:
http://developers.facebook.com/docs/tutorials/ios-sdk-tutorial/publish-open-graph-story/
http://developers.facebook.com/docs/opengraph/usergeneratedphotos/
$userId = $this->facebook->getUser();
// If user is not yet authenticated, the id will be zero
if($userId == 0){
// Generate a login url
$url = $this->facebook->getLoginUrl(array('scope'=>'email,user_photos,friends_photos,publish_stream'));
echo "<h2><a href='" . $url . "'>Login</a></h2>";
} else {
// Make Logout URL
$logoutUrl = $this->facebook->getLogoutUrl(array(
'next' => 'http://www.myUrl.com/logout/',
// URL to which to redirect the user after logging out
));
echo "<h2><a href='" . $logoutUrl . "'>Logout</a></h2>";
// Get User's data
$user = $this->facebook->api('/me');
echo "<p>Welcome <b>" . $user["name"] . '</b></p>';
echo("<p><b>User Details: </b>");
print_r($user);
echo("</p>");
// Get user's Permissions
$permissions = $this->facebook->api('/me/permissions');
echo("<p><b>User Permissions: </b>");
print_r($permissions);
echo("</p>");
if (isset($permissions['data'][0]['publish_stream'])) {
echo "<h3>Permission to Post</h3>";
} else {
$url = $this->facebook->getLoginUrl(array('scope'=>'email,user_photos,friends_photos,publish_stream'));
echo "<h3>NO Permission to Post: ";
echo "<a href='" . $url . "'>Get extra permissions</a></h3>";
}
// Upload an via OpenGraph Collection Object
$og_type = 'collection'; // Your Opengraph Object
$og_title = urlencode('This is my Title');
$og_description = urlencode('This is my Description');
$og_image = 'http://www.myUrl.com/big.png'; // At least 480px by 480px
$object_url = 'http://www.myUrl.com/fb_object_meta.php?fb:app_id=398917983475605&og:type='.$og_type.'&og:title='.$og_title.'&og:description='.$og_description.'&og:image='.urlencode($og_image);
// See this URL if you need the code for the dynamic meta data page
// http://developers.facebook.com/docs/tutorials/ios-sdk-tutorial/publish-open-graph-story/
$args = Array(
'collection' => $object_url,
'image[0][url]' => $og_image, // Possible to upload more than one user gen image e.g. image[1][url]
'image[0][user_generated]' => 'true',
//'message' => 'Made on myUrl http://www.myUrl.com', // This shows above the large pic
);
try {
$post_id = $this->facebook->api("/me/myUrl:make", "post", $args);
print_r($post_id);
}
catch (Exception $e)
{
print_r($e);
}
}
To the right of where you added your OG actions in the App console there will be a link that says "Get Code". This will show you the information you need to include.
In your case, you should have a parameter in your args which is collection which contains the URL of the page containing the OG markup for your photo.
You can find this markup by clicking on the "Get Code" link next to the collection object you created in the app console.
Update
Open graph works by adding meta tags to the head of an accessible web page. You need to add the colleation meta to some page and then in the collection parameter in the request you're making, add the URL of the page.
Now I'm bulding game by UNITY3D. I want to send json file to server to store it in database I build server by php with Yii Framework, i have problem with send data in client [UNITY3D] and retrieve it in server [Yii]. Please help me.UNITY3D code: I want to send 'name' -> to server
var url = "http://localhost:8888/TPP/index.php/site/saveName";
var form = new WWWForm();
form.AddField( "player", "Henry" );
var download = new WWW( url, form );
print(download);
yield download;
if(download.error) {
print( "Error downloading: " + download.error );
return;
} else {
// show the highscores
Debug.Log(download.text);
}
In Yii, i tried to get data in request
public function actionSaveName() {
if(isset($_POST['name']) {
echo $_POST['name'];
} else {
echo "nothing";
}
}
Is that right?
The unity part is fine, but in yii you'll have to check for $_POST['player'] instead of $_POST['name'] because according to the AddField() documentation, the first parameter is the name of the generated form element.
If you want to have it as name then you'll have to change AddField as : form.AddField("name", "Henry");
http://apps.facebook.com/karmabalance/
I am trying to get the login and authorization working on my FB App, but it seems to do funny stuff. Basically all I want is when the user clicks on my app, I want fb to do their check to make sure they are logged in and have approved the app, and after that I need the program to do a check of the database to see if their is already a record in the database with the User FB ID. If their is no record, I want the program to send the user to a create acct. page that will enable the user to enter a Username. If there is a record, I want to send the user to the app home page.
I thought I got it to work, but its still not right, and I can't figure out why. Here is my code. I'm sure there is a better way to do this also, I am a newbie, so I'm trying to figure this all out as I go. Any help would be appreciated.
Thanks
When the user clicks my app it goes to this index.php page.
<?php
require 'config.php';
session_start();
$usercheck = $user_profile['id'];
$result = mysql_query("SELECT FBID FROM PLAYER WHERE (FBID = '$usercheck') ");
if ($facebook->getUser())
{
if(mysql_num_rows($result))
{
header('location: Home.php');
} else
{ ?>
<p>Please choose a Username for yourself. </p>
<form action='includes/signup.php' method='post'>
<fieldset style="width:600px";>
<label>Username</label>
<input name='username' type='text' value='<? if ($facebook->getUser())
{echo'Choose a Username';} ?>' />
<input name='submit' type='submit' value='submit' />
</fieldset>
</form>
<? }
} else
{ ?>
<p>Sign up with Facebook <fb:login-button perms='email'> Connect</fb:login-button>
It only takes a few seconds</p>
<div id='fb-root'></div>
<script src='http://connect.facebook.net/en_US/all.js'></script>
<script>
FB.init({
appId:'334230339967350', cookie:true,
status:true, xfbml:true
});
FB.Event.subscribe('auth.login', function(response) {
window.location.reload(); //will reload your page you are on
});
</script>
<? }
?>
The config file:
<?php
//Facebook Configuration
require 'facebook-php-sdk/src/facebook.php';
$app_id = "xxxxxxxxxxxx";
$app_secret = "xxxxxxx";
$facebook = new Facebook(array(
'appId' => $app_id,
'secret' => $app_secret,
'cookie' => true
));
// Get User ID
$user = $facebook->getUser();
if ($user) {
try {
// Proceed knowing you have a logged in user who's authenticated.
$user_profile = $facebook->api('/me');
} catch (FacebookApiException $e) {
error_log($e);
$user = null;
}
}
// login or logout url will be needed depending on current user state.
if ($user) {
$logoutUrl = $facebook->getLogoutUrl();
} else {
$loginUrl = $facebook->getLoginUrl();
}
//SQL Configuration
// i start most if not all pages with this depending on what Im using it for.
$host = 'localhost'; // host name OR IP
$username = 'security';//username
$pass = 'blockedout'; //password
$dbname = 'Security'; // Database Name
$conn = mysql_connect($host, $username, $pass) or die(mysql_error());
if ($conn)
{
mysql_select_db($dbname) or die(mysql_error());
}
else
{
echo 'Connection failed.';
} // The above code connects to your database or errors if it cannot connect.
// Again this is simple, security is your own priority.
//GLOBAL VALUES??
$usercheck = $user_profile['id'];
$usernamequery = mysql_query("SELECT UserName FROM PLAYER WHERE (FBID = '$usercheck') ");
$username = mysql_fetch_array($usernamequery);
$levelquery = mysql_query("SELECT LevelID FROM PLAYER WHERE (FBID = '$usercheck') ");
$level = mysql_fetch_array($levelquery);
$result = mysql_query("SELECT FBID FROM PLAYER WHERE (FBID = '$usercheck') ");
?>
And here is the signup.php page
<?
require_once '../config.php';
//here you could add checks for any empty fields using (!($_POST['first_name']))
$first_name = $user_profile['first_name']; // this line will collect our information from the
// field in our form that has the facebook first_name in it.
$last_name = $user_profile['last_name']; // same as above
$email = $user_profile['email']; //same as above
$id = $user_profile['id']; //same as above
$username1 = $_POST['username'];
$query = mysql_query
("
INSERT INTO PLAYER (FirstName, LastName, EMail, FBID, UserName, Status, LevelID, Cash, LifePoints, RespectPoints, ReputationPoints, UpgradePoints, HealthPercent)
VALUES ('$first_name', '$last_name', '$email', '$id', '$username1', '1', '1', '25000', '3', '3', '3', '20', '100')
")
or die(mysql_error());
// The query will insert our fields in to the database as the above line shows, make
//sure your database table headers are exactly correct otherwise this will not work
// You can now either send an email or if you wanted header to a new page. This is
//up to you. Tutorials on google will show you how to do this part
if($query){
header('location: ../Home.php');
}else {
echo 'error adding to database';
}
?>
You are missing the oauth token for the user. thats the handle of the user you want to pull.
if you are still confuse, let me know.