Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

TweetBot Retweeter failing authorization

On Twitter, you can only make posts that fit in 140 characters. That includes the handles you are tweeting at: @handle. This creates a problem when attempting to tweet at a larger group. In an attempt to create a workaround for my basketball team, I am attempting to create a twitter bot that when tweeted at, it take the text from the tweet and then send a series of tweets @ each person's handle on the team.

I started with code from this tutorial. Then I edited out the Wolfram Alpha stuff and came up with this code to start with: (The key and secret arent really xxxxx)

/**     ScotsTeamRetweeter                               **/
/**     =======================================          **/
/**     Written by John Holland    
/**     Taken from: Amit Agarwal @labnol on 10/09/2013   **/  
/**     Tutorial link: http://www.labnol.org/?p=27902    **/

function start() {      
  Logger.log("Did actually start"); 

  // REPLACE THESE DUMMY VALUES     
  var TWITTER_CONSUMER_KEY     = "XXXXXX";
  var TWITTER_CONSUMER_SECRET  = "XXXXXX";
  var TWITTER_HANDLE           = "ScotsTeam";  

  // Store variables
  ScriptProperties.setProperty("TWITTER_CONSUMER_KEY",    TWITTER_CONSUMER_KEY);
  ScriptProperties.setProperty("TWITTER_CONSUMER_SECRET", TWITTER_CONSUMER_SECRET);
  ScriptProperties.setProperty("TWITTER_HANDLE",          TWITTER_HANDLE);
  ScriptProperties.setProperty("MAX_TWITTER_ID",          0);

  // Delete exiting triggers, if any
  var triggers = ScriptApp.getScriptTriggers();
  for(var i=0; i < triggers.length; i++) {
    ScriptApp.deleteTrigger(triggers[i]);
  }

  // Setup trigger to read Tweets every five minutes
  ScriptApp.newTrigger("fetchTweets")
           .timeBased()
           .everyMinutes(1)
           .create();
}

function oAuth() {
  var oauthConfig = UrlFetchApp.addOAuthService("twitter");
  oauthConfig.setAccessTokenUrl("https://api.twitter.com/oauth/access_token");
  oauthConfig.setRequestTokenUrl("https://api.twitter.com/oauth/request_token");
  oauthConfig.setAuthorizationUrl("https://api.twitter.com/oauth/authorize");
  oauthConfig.setConsumerKey(ScriptProperties.getProperty("TWITTER_CONSUMER_KEY"));
  oauthConfig.setConsumerSecret(ScriptProperties.getProperty("TWITTER_CONSUMER_SECRET"));
}

function fetchTweets() {
  oAuth();
  var twitter_handle = ScriptProperties.getProperty("TWITTER_HANDLE");

  var phrase = "lang:en+to:" + twitter_handle; 
  var search = "https://api.twitter.com/1.1/search/tweets.json?count=5&include_entities=false&result_type=recent&q="; 
  search = search + encodeString(phrase) + "&since_id=" + ScriptProperties.getProperty("MAX_TWITTER_ID");    

  var options =
  {
    "method": "get",
    "oAuthServiceName":"twitter",
    "oAuthUseToken":"always"
  };

  try {

    var result = UrlFetchApp.fetch(search, options);    
    if (result.getResponseCode() === 200) {
      var data = Utilities.jsonParse(result.getContentText());
      if (data) {
        var tweets = data.statuses;
        for (var i=tweets.length-1; i>=0; i--) {
          var question = tweets[i].text.replace(new RegExp("\@" + twitter_handle, "ig"), "");              
          var answer   = "Looks Like it worked"
          sendTweet(tweets[i].user.screen_name, tweets[i].id_str, answer);
          Logger.log("Tweet should have sent");          
        }
      }
    }
  } catch (e) {
    Logger.log(e.toString());
  }
}

function sendTweet(user, reply_id, tweet) {

  var options =
  {
    "method": "POST",
    "oAuthServiceName":"twitter",
    "oAuthUseToken":"always"    
  };

  var status = "https://api.twitter.com/1.1/statuses/update.json";

  status = status + "?status=" + encodeString("@" + user + " " + tweet);
  status = status + "&in_reply_to_status_id=" + reply_id;

  try {
    var result = UrlFetchApp.fetch(status, options);
    ScriptProperties.setProperty("MAX_TWITTER_ID", reply_id);
    Logger.log(result.getContentText());    
  }  
  catch (e) {
    Logger.log(e.toString());
  }
}

function encodeString (q) {
  // Update: 09/06/2013
  // Google Apps Script is having issues storing oAuth tokens with the Twitter API 1.1 due to some encoding issues.
  // Hence this workaround to remove all the problematic characters from the status message.

  var str = q.replace(/\(/g,'{').replace(/\)/g,'}').replace(/\[/g,'{').replace(/\]/g,'}').replace(/\!/g, '|').replace(/\*/g, 'x').replace(/\'/g, '');
  return encodeURIComponent(str);

//   var str =  encodeURIComponent(q);
//   str = str.replace(/!/g,'%21');
//   str = str.replace(/\*/g,'%2A');
//   str = str.replace(/\(/g,'%28');
//   str = str.replace(/\)/g,'%29');
//   str = str.replace(/'/g,'%27');
//   return str;

}

(My understanding is) This code should just cause the twitter bot to post a tweet that says "looks like it worked" when tweeted at.

However I seem to have an authorization problem that I dont understand. I recieve this email most nights:

Your script, ScotsTeamRetweeter, has recently failed to finish successfully. A summary of the failure(s) is shown below. To configure the triggers for this script, or change your setting for receiving future failure notifications, click here.

Summary:

Error Message   Count
Authorization is required to perform that action.   18
Details:

Start   Function    Error Message   Trigger End
10/9/13 9:11 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:11 PM
10/9/13 9:12 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:12 PM
10/9/13 9:13 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:13 PM
10/9/13 9:14 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:14 PM
10/9/13 9:15 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:15 PM
10/9/13 9:16 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:16 PM
10/9/13 9:17 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:17 PM
10/9/13 9:18 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:18 PM
10/9/13 9:19 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:19 PM
10/9/13 9:20 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:20 PM
10/9/13 9:21 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:21 PM
10/9/13 9:22 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:22 PM
10/9/13 9:23 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:23 PM
10/9/13 9:24 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:24 PM
10/9/13 9:25 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:25 PM
10/9/13 9:26 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:26 PM
10/9/13 9:27 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:27 PM
10/9/13 9:28 PM fetchTweets Authorization is required to perform that action.   time-based  10/9/13 9:28 PM

What should I do to fix my bot?

like image 442
George Mikan Avatar asked Oct 11 '13 17:10

George Mikan


People also ask

How to authorize on Twitter?

If you're already logged in to your account, use the Authorize app button to connect the app. If you're not already logged in to your account, you will need to log in. Before you enter your username and password, check that the page is secure by verifying the URL starts with https://twitter.com.

Are bots allowed on twitter?

A. You may only take automated actions through another Twitter user's account if you: clearly describe to the user the types of automated actions that will occur; receive express consent from the user to take those automated actions; and. immediately honor a user's request to opt-out of further automated actions.


1 Answers

You need to go into your script editor and call your function directly. (Play button). After that it will display an authorization screen to you and after that everything will be ok.

like image 101
br araujo Avatar answered Oct 19 '22 15:10

br araujo