Google Apps ScriptとTwitter APIで自動でツイートといいねするtwitter botを作ってみた
目的
あっという間に3月になっていることに気づき、定期的に日時を教えてくれるtwitter botでも作って時間の大切さを噛み締めようかなと思い作りました。
設計
定期的に日時をツイートしているbotを探してみると見つかりました
2021年3月15日になりました。今年は残り292日です。あと80.0%です。
— 今年の残り日数 (@remaining_days) March 14, 2021
ただ、毎日ツイートされると鬱陶しいので毎週ツイートしてくれるbotにしようと思いました。
タイミングはもうこんなに時間が過ぎたのかと思ったときに、先延ばしにしていることを始めやすいように土曜日の朝6時にしました。
文面についても残りの日数だけでなく過ぎた日数も記述することにしました。
1つのgmailで複数のツイッターアカウントの作り方
以下の記事を参照してください。
コード
// ツイッター認証 function getTwitterService() { return OAuth1.createService('twitter') .setAuthorizationUrl('https://api.twitter.com/oauth/authorize') .setConsumerKey('CONSUMER_API_KEY') .setConsumerSecret('CONSUMER_API_SECRET_KEY') .setAccessToken('ACCESS_TOKEN','ACCESS_TOKEN_SECRET'); } // ツイッター投稿 function makeRequest() { //ツイッター認証 var twitterService = getTwitterService(); var today = new Date(); var month = today.getMonth() + 1; var date = today.getDate(); var hour = today.getHours(); //今年の指定の日付を取得 var oomisoka = today.getFullYear() + "/12/31"; var ganzitsu = today.getFullYear() + "/1/1"; //秒単位同士を引き算して日数に戻す var leftDays = Math.floor((Date.parse(oomisoka) - today.getTime() ) / (24*60*60*1000)); var pastDays = Math.floor(( today.getTime() - Date.parse(ganzitsu) ) / (24*60*60*1000)) + 1 ; //0日の場合(大晦日または元旦)は残り時間を表示 if (pastDays === 0) { pastDays = hour + '時間'; } else { pastDays = pastDays + '日'; } if (leftDays === 0) { leftDays = 24 - hour + '時間'; } else { leftDays = leftDays + '日'; } // 文面 var text = '今日は' + month + '月' + date + '日です\n' + '今年ももう' + pastDays + 'が過ぎ、残すところあと' + leftDays + 'です'; // ツイッター投稿 var response = twitterService.fetch('https://api.twitter.com/1.1/statuses/update.json', { method: "post", payload: {status: text} }) }
コードの解説
- Date.parse()
協定世界時(1970 年 1 月 1 日 00:00:00 )からのミリ秒を算出。
timeZoneの変更
Twitter Developerに登録して鍵を取得
以下サイトを参照のこと
www.itti.jp
入手した鍵をgetTwitterService関数の該当箇所に入力
.setConsumerKey('CONSUMER_API_KEY') .setConsumerSecret('CONSUMER_API_SECRET_KEY') .setAccessToken('ACCESS_TOKEN','ACCESS_TOKEN_SECRET');
ライブラリの追加
初回時の確認
結果
今日は4月1日です
— Time is money (@XAoQSxuOCNBbs4B) April 1, 2021
今年ももう90日が過ぎ、残すところあと274日です
変数ganzitsuとoomisokaを今日(4/1)と設定する(もし今日が元日と大晦日なら)と
今日は4月1日です
— Time is money (@XAoQSxuOCNBbs4B) April 1, 2021
今年ももう14時間が過ぎ、残すところあと10時間です
自動化
感想
前回のGoogle Apps Scriptを使ったときと比べて格段に早くかたちにできた。成長が感じられて嬉しい。
追記(オリンピック開催までの残り日数)
botを作ったからにはフォロワーが増えることを期待していたのですが、全く増えないためにフォロワー獲得のためにオリンピック開催までの残り日数もツイートに追加してみました。
今日は4月14日です
— 東京オリンピック開催までの残り日数bot (@XAoQSxuOCNBbs4B) April 14, 2021
今年ももう103日が過ぎ、残すところあと261日です
東京オリンピックまではあと100日です
7月23日の夜の8時が開会式らしく、ちょうど4月14日が残り100日だということでそれに乗っかってフォロワー数が増やす狙いです
youtu.be
コードは以下の通り(makeRequest関数内に追加)
//オリンピックの日にち var olympic = today.getFullYear() + "/7/23" //オリンピックの日にちから今日の日にちを引いて残りの日数を算出 var olympicDay = Math.floor((Date.parse(olympic) - today.getTime() ) / (24*60*60*1000)) + 1; //残りの日数が0、つまり残り〇〇時間の場合と残り1日以上の場合を条件分岐 if (olympicDay === 0) { olympicDay = '東京オリンピック開催まであと' + 20 - hour + '時間'; } else { olympicDay = '東京オリンピック開催まではあと' + olympicDay + '日'; }
さらに自動でいいねする機能も追加
function favoriteTweets() { //前回実行時の一番新しいツイートのidをスプレッドシートから取得 var sheet = SpreadsheetApp .getActiveSpreadsheet() .getActiveSheet() .getRange('A1') .getValues(); var id = sheet[0][0] //ツイッター認証 var twitterService = getTwitterService(); /* 「五輪まで」または「オリンピックまで」を 「RT」(リツートされたツイートには検索結果の文面に含まれる)とメンション(@)を排除して 新しい順で前回のツイートから最新のツイートの範囲を検索 初回時は &since_id=' + id をコメントアウトしてください ※ その後「'」を最後に付け加えてください */ var json = twitterService.fetch('https://api.twitter.com/1.1/search/tweets.json?q=%22五輪まで%22%20OR%20%22オリンピックまで%22%20RT%20filter%3Amentions&result_type=recent&since_id=' + id); var array = JSON.parse(json); //検索結果が0(新しいツイートがない)なら終了 if (array.statuses.length === 0) { return; } //一番新しいツイートのidをスプレッドシートに転機 var sheet = SpreadsheetApp .getActive() .getSheetByName('シート1') .getRange(1, 1) .setValue(array.statuses[0].id_str); // 検索結果のツイートのいいねがされていないならそのツイートのidからいいねをつける for (let i = 0; i < array.statuses.length; i++) { if (array.statuses[i].favorited === false) { let id_str = array.statuses[i].id_str; var response = twitterService.fetch('https://api.twitter.com/1.1/favorites/create.json?id=' + id_str, { method: 'post' }); } else { return; } } }
コード解説
- .setValue(array.statuses[0].id_str);
ツイートの検索結果は検索の範囲で現在から過去へ処理されていきます。
なので一番新しいツイートのidを取得する際には検索結果の0番目の配列を指定します。
アカウントのスパム扱い
タイマーを1分に設定して運用していると、半日で1000いいねを超えたあたりでスパム扱いされて3日間制限がかかりました。
apiまたは手動での1日のいいねの上限は1000だそうです。気をつけましょう。
1日のいいねの上限を1000までにする
/* カウントを0にリセットする makeRequest関数に追記してツイートしたら実行するようにもできる */ function clearCount() { var sheet = SpreadsheetApp .getActive() .getSheetByName('シート1') .getRange(1, 2) .setValue(0); } /* favoriteTweets関数に以下のコードを追加。 カウントの値を取得 */ var sheet = SpreadsheetApp .getActiveSpreadsheet() .getActiveSheet() .getRange('A1:B1') .getValues(); var id = sheet[0][0]; var count = sheet[0][1]; //検索結果が0なら終了。カウント+検索結果が1000より多ければ終了、1000未満であればカウントに検索結果を足す if (array.statuses.length === 0) { return; } else { if (count + array.statuses.length > 1000) { return } else { count = count + array.statuses.length; } } //スプレッドシートにカウントを転記 var sheet = SpreadsheetApp .getActive() .getSheetByName('シート1') .getRange(1, 2) .setValue(count);
半分過ぎたら
今年が半分過ぎた時にアナウンスしてほしかったので追加しました。
if (pastDays === Math.ceil(365 / 2)) { pastDays = '半分(' + pastDays + '日)' } if (pastDays === Math.ceil(365 / 3)) { pastDays = '1/3(' + pastDays + '日)' } if (pastDays === Math.ceil(365 * 2 / 3)) { pastDays = '2/3(' + pastDays + '日)' } if (pastDays === Math.ceil(365 / 4)) { pastDays = '1/4(' + pastDays + ')' } if (pastDays === Math.ceil(365 * 3 / 4)) { pastDays = '3/4(' + pastDays + '日)' }
Math.ceil()(小数点繰り上げ)をしているのは、例えば365/2の答えは182.5でこの小数点5というのは1日の半分ということで12時間になります。
自動ツイートの設定は毎日朝5〜6時なのでコードのif文のすべての場合で少数を時間になおすと、自動ツイートの時刻はまだその時間に到達していないことになります。
なので整数部分の日数+1日するために小数点を繰り上げしているわけです。