I need to reply to one particular twitter status. I'm using following functions. And I've used Abraham's twitteroauth library in php.
public function replyToTwitterStatus($user_id,$status_id,$twitt_reply,$account_name)
{
$connection= $this->getTwitterConnection($user_id,$account_name);
try{
$responce = $this->postApiData('statuses/update', array('status' => $twitt_reply,'in_reply_to_status_id '=> $status_id),$connection);
}
catch(Exception $e){
echo $message = $e->getMessage();
exit;
}
}
// this function will handle all post requests
// To post/update twitter data
// To post/update twitter data
public function postApiData($request,$params = array(),$connection)
{
if($params == null)
{
$data = $connection->post($request);
}
else
{
$data = $connection->post($request,$params);
}
// Need to check the error code for post method
if($data->errors['0']->code == '88' || $data->errors['0']->message == 'Rate limit exceeded')
{
throw new Exception( 'Sorry for the inconvenience,Please wait for minimum 15 mins. You exceeded the rate limit');
}
else
{
return $data;
}
}
But the issue is that it is not maintaining the conversation view and it is update like normal status for e.g #abraham hello how are you. but that "View conversation" is not coming. Like expanding menu is not coming.
Please do needful
Thanks
You've got an unwanted space in your in_reply_to_status_id key which causes that parameter to be ignored.
This call:
$responce = $this->postApiData('statuses/update', array(
'status' => $twitt_reply,
'in_reply_to_status_id ' => $status_id
), $connection);
should look like this:
$responce = $this->postApiData('statuses/update', array(
'status' => $twitt_reply,
'in_reply_to_status_id' => $status_id
), $connection);
Also, make sure that the $status_id variable is being handled as a string. Although they look like numbers, most ids will be too big to be represented as integers in php, so they'll end up being converted to floating point which isn't going to work.
Lastly, make sure you have include the username of the person you are replying to in the status text. Quoting from the documentation for the in_reply_to_status_id parameter:
Note:: This parameter will be ignored unless the author of the tweet this parameter references is mentioned within the status text. Therefore, you must include #username, where username is the author of the referenced tweet, within the update.
Related
In the Slack API End point URL, I used the cursor fields and I got all the public channels. But I am unable to set all the below curson values in the End point URL.
Could you please advise me how I can set these multiple cursor values in a parameter ""cursor ?
Please find below the End point URL :
req.setEndpoint('https://slack.com/api/conversations.list?limit=999&types=public_channel&exclude_archived=true&cursor=dGVhbTpDRjBDOUdWUk4=&cursor=dGVhbTpDMDFGMlFNR0g4Qw==&cursor=dGVhbTpDMDFTV0hOTDM0NA==');
Here is the cursor values :
dGVhbTpDRjBDOUdWUk4=
dGVhbTpDMDFGMlFNR0g4Qw==
dGVhbTpDMDFTV0hOTDM0NA==
dGVhbTpDMDIwSFFRSzlHUQ==
dGVhbTpDMDIzTkIwQ0FDQg==
dGVhbTpDMDI2TkVCUEU3Mg==
dGVhbTpDMDI5SzFZUzNVSA==
dGVhbTpDMDJERUJDQTVBTQ==
dGVhbTpDMDJGV1M3QUtGRw==
dGVhbTpDMDJKNUhaVVNOOA==
dGVhbTpDMDJMUzFLVjNQRg==
dGVhbTpDMDJQRDhZQjBQSg==
dGVhbTpDMDJTSkVLUTlQVg==
dGVhbTpDMDMwME1DMTdKVA==
dGVhbTpDMDMyTENESEE3Nw==
dGVhbTpDMDM1Rjg5NTJVVw==
dGVhbTpDMDM4QlNYQVQ4Vw==
dGVhbTpDMDNCOE5HQ01CUA==
ZXh0ZXJuYWw6QzAySFFLOFBCNUU=
Thanks !!
cursor parameter is used for paginating the data fetched using given API.
Each cursor value points to the next page of data.
You need to iteratively call the API (adding the received cursor value from each request) and store each response, till the cursor value becomes blank.
Best approach will be to implement a Do...While loop, where while condition will be cursor != ""
Sample Code:
var channelRecords = []
var nextCursor = ''
do{
await axios.get(`https://slack.com/api/conversations.list?limit=999&types=public_channel&exclude_archived=true&${(nextCursor == '') ? '': `&cursor=${nextCursor}`}`,{
headers: {
'Authorization': `Bearer ${SLACK_USER_TOKEN}`
}})
.then(response => {
if (response.status == 200)
{
channelRecords = channelRecords.concat(response.data.channels)
}
nextCursor = response.data.response_metadata.next_cursor
})
.catch(error => {
console.log(error);
});
}while (nextCursor != '')
//This code does not take care of API's rate limit
You can also use Slack's Bolt framework and their sample code:
https://api.slack.com/methods/conversations.list/code
I am trying to add pagination to my Zapier trigger.
The API I am using for the trigger supports pagination, but not using a page number in the traditional sense (ie. page 1,2,3,...). Instead, the API response includes a key (ie. "q1w2e3r4") which should be passed as a parameter to the next request to get the next page of results.
From looking at the docs, I can use {{bundle.meta.page}} (which defaults to 0 unless otherwise set).
I am trying to set {{bundle.meta.page}} in the code editor, with an example shown below:
const options = {
url: 'company_xyz.com/api/widgets',
method: 'GET',
...,
params: {
...,
'pagination_key': bundle.meta.page,
}
}
return z.request(options)
.then((response) => {
response.throwForStatus();
const json_response = response.json;
widgets = json_response.widgets
...
bundle.meta.page = json_response["next_pagination_key"]
return widgets;
});
The problem is that when Zapier tries to retrieve the next page, bundle.meta.page will be 1 instead of the value of "next_pagination_key" from the result of the previous request.
There are docs on cursor-based pagination in the CLI docs.
The relevant block is:
const performWithAsync = async (z, bundle) => {
let cursor;
if (bundle.meta.page) {
cursor = await z.cursor.get(); // string | null
}
const response = await z.request(
'https://5ae7ad3547436a00143e104d.mockapi.io/api/recipes',
{
// if cursor is null, it's sent as an empty query
// param and should be ignored by the server
params: { cursor: cursor }
}
);
// we successfully got page 1, should store the cursor in case the user wants page 2
await z.cursor.set(response.nextPage);
return response.items;
};
This should work in the Zapier Visual Builder, but you might need to use the CLI instead. You can export your integration using the zapier convert CLI command (docs).
For example I would like to send the users score to the database and instead of it returning the typical status, id and rev I would like it to return the users rank. I'm guessing this isn't possible but figured I would ask.
The response to an HTTP POST/PUT should really only be used to help you confirm that it succeeded.
I'm even struggling to see even how you can get the rank of a user returned by a couchdb view, unless you retrieve the data for all users and work out the position of your user.
This use case ...
Simple structured data clearly tabular
The requirement to respond fast to a numerical column (Method to calculate the rank for a score)
OR the requirement to trigger an update a score table each time a rank is submitted.
... very much smells like a classical case where you may want to use a relational DB.
If the result can be calculated from the document you are to change with your http request, then you can use an update handler to PUT a change to the document and return that result:
// 'myhandler' update function
function(doc, req) {
// create a shorthand for json reponses
var json_reponse = function(obj, code) {
return {
headers: { 'Content-Type': 'application/json' }
, body: JSON.stringify(obj)
, code: code
}
}
// assume the incoming body is json and parse it
// needs proper error handling still
var body = JSON.parse(req.body)
// doc is the user document we are patching
// return an error if it isn't there
if(!doc)
return [null, json_response({error: 'user document not found'}, 404)]
// return an error if new_score is missing from body
if(!body.new_score)
return [null, json_response({error: 'missing property new_score'}, 400)
// now patch the user doc
doc.score = body.new_score
// calculate the new rank depending on your own method
var my_rank = my_rank_function(doc.score, Math.PI, 'bananarama')
return [doc, json_response({success: true, rank: my_rank}, 200)
}
Now PUT new data to receive the new rank:
request(
{ method: 'PUT'
, url: httptp://127.0.0.1:5984/mydb/_design/myddoc/_update/myhandler/myuserdocid
, json: {"new_score": 42}
, headers: { "Content-Type: application/json" }
}
, function(err, response, body) {
console.log("user's new rank:", JSON.parse(body).rank)
}
)
should print user's new rank: LEVEL 11 EIGHTIES GIRL GROUP LEADER
nb: I'm not at work so cannot confirm the code works, but you should get the hang of it...
Too bad my php knowledge.I'm using YouTube-api.Where will write this code: Retrieve Youtube Channel info for "Vanity" channel
If you are talking about this line :
GET https://www.googleapis.com/youtube/v3/channels?part=snippet%2CcontentDetails%2Cstatistics&id=UC6ltI41W4P14NShIBHU8z1Q&key={YOUR_API_KEY}
You are simply making a get request, you can use file_get_contents to get the response for you :
$response = file_get_contents("https://www.googleapis.com/youtube/v3/channels?part=snippet%2CcontentDetails%2Cstatistics&id=UC6ltI41W4P14NShIBHU8z1Q&key={YOUR_API_KEY}");
Two notes :
You have to replace {YOUR_API_KEY} with the developer key. You can easily request one from youtube: http://code.google.com/apis/youtube/dashboard/
This is just an example in one line of code, I suggest you use a better approach for making this request like the following :
// Encode the parameters of the link
function encode_param($params) {
foreach ($params as $field => $value){
$encoded_params[] = $field . '=' . urlencode($value);
}
return $encoded_params;
}
// Get the response
function get_response($url) {
$response = file_get_contents($url);
// If error, send message back to the client
if ($response === false) {
exit("Couldn't get response from the api");
}
return $response;
}
$params = array(
"part" => "snippet,contentDetails,statistics",
"id" => "UC6ltI41W4P14NShIBHU8",
"key" => "-----------", // Your API key
);
$encoded_params = encode_param($params);
$request_url = "https://www.googleapis.com/youtube/v3/channels?".implode('&', $encoded_params);
$response = get_response($request_url);
//............
Currently my app posts to the users wall every time they access the app. I only want it to post to the wall one time when they first authorize the app. Then every time they access it afterward it only updates the news feed status.
here is my current code:
// Get User ID
$user = $facebook->getUser();
if ($user) {
try {
// Proceed knowing you have a logged in user who's authenticated.
$access_token = $facebook->getAccessToken();
$vars = array(
'message' => "Message goes here",
'picture' => "image",
'link' => "link here",
'name' => "Name here",
'caption' => "Caption here"
);
$result = $facebook->api('/me/feed', 'post', $vars);
} 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(array('redirect_uri'=> $app_url));
echo "<script type='text/javascript'>";
echo "top.location.href = '{$loginUrl}';";
echo "</script>";
}
What do I need to change in order to make that happen?
You have 2 choices of methods to achieve this behavior.
Utilize the Feed Dialog on the landing page for your users. This will popup a Facebook window prompting your users to share something on their wall. This method requires that you implement the JavaScript SDK as well.
Utilize the PHP SDK and programatically posting a feed story to the /me/feed endpoint. (As you have done in the try-catch block of your code sample).
With regard to only posting on the users first visit you should store in your database a boolean value. When you create a new record for the new user in your database you should include a field called something like first_visit and populate it with a "true" value.
Then when you detect a returning user (that means he is already in your database) you can check to see that the first_visit field is set to "false". Then your post via the PHP SDK can be the result of a conditional expression to test the first_visit value :
...
...
if ($first_visit == 'true'){
$result = $facebook->api('/me/feed', 'post', $vars);
}
An additional solution (not requiring a database) could be something similar to this :
When you so cunningly generate the login URL with the $facebook->getLoginUrl() method for your un-authorized users, you can add a temporary GET parameter to the redirect_uri parameter. Something like :
$redirect_uri = 'https://apps.facebook.com/waffle-ville?new_user=true';
Then your conditional expression for posting to the users wall would look something like this :
...
...
if ($_GET['new_user'] == 'true'){
$result = $facebook->api('/me/feed', 'post', $vars);
}
Don't forget to redirect the user back to the original URL after you have made the post :
var app_url = "https://apps.facebook.com/waffle-ville";
echo "<script type='text/javascript'>";
echo "top.location.href = app_url;";
echo "</script>";
The redirect is also possible with PHP :
$app_url = "https://apps.facebook.com/waffle-ville";
header("Location: {$app_url}");
IMO - Posting to a users wall automagically is a little bit annoying. There is a parameter in your application settings that is called Social Discovery. When this is set to "enabled" a story is automagically created as soon as a user installs your application. I recommend leaving posting to a users wall as an optional user initiated action.
I've figured it out. I created a database to store info and it checks to see if the User ID already exists or not. If it doesn't, then they are placed in the database and a post is made to their wall. If they are in the database, then nothing happens.
<?php
require 'facebook.php';
require 'dbconnect.php';
// Create our application instance
// (replace this with your appId and secret).
$app_id = "APP_ID";
$secret = "APP_SECRET";
$app_url = "APP_URL";
$facebook = new Facebook(array(
'appId' => $app_id,
'secret' => $secret,
'cookie' => true,
));
// Get User ID
$user = $facebook->getUser();
// We may or may not have this data based on whether the user is logged in.
//
// If we have a $user id here, it means we know the user is logged into
// Facebook, but we don't know if the access token is valid. An access
// token is invalid if the user logged out of Facebook.
if ($user) {
try {
// Proceed knowing you have a logged in user who's authenticated.
$user_profile = $facebook->api('/me');
$access_token = $facebook->getAccessToken();
$name = $user_profile['name'];
$birthday = $user_profile['birthday'];
} 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(array('redirect_uri'=> $app_url));
echo "<script type='text/javascript'>top.location.href = '$loginUrl';</script>";
}
//DO NOT EDIT BELOW
$db=mysql_connect($hostname, $dbuser, $pass);
mysql_select_db($database, $db);
//check if user has already signed up before
$insert = true;
$result = mysql_query("SELECT * FROM table_name") or die(mysql_error());
while($row = mysql_fetch_array($result)){
//if user id exists, do not insert
if(( $row['UID'] == $user)){
$insert = false;
}
}
// if new user, insert user details in your mysql table
if($insert){
mysql_query("INSERT INTO table_name (UID, username, userbirthday) VALUES ('$user','$name','$birthday') ") or die(mysql_error());
$access_token = $facebook->getAccessToken();
$vars = array(
'message' => "message goes here",
'picture' => "image",
'link' => "Link here",
'name' => "Name here",
'caption' => "Caption here",
);
$result = $facebook->api('/me/feed', 'post', $vars);
}
?>