Following a rather radical pruning of my Twitter followings (people who I am following) my timeline has got both better and less exciting. So I wanted to follow some new people but not just random accounts.
I have a list of ununfollowables: the followings I like best. Those people are probably good judges of the people I should follow – or in any case better at it than random followings.
This script looks who they are following and follows those account. The result is that periodically I automatically follow some of my friends’ friends. It keeps a list of those I’ve followed automatically. If it doesn’t work out I unfollow them again. Of course nothing is keeping me from re-following them manually.
The script relies heavily on @sferik’s Twitter client for Ruby called ‘t’. It’s easy to install but it helps if you read the help file and get to know it a bit should you need to troubleshoot or adjust the script.
It is designed to be run from cron and written on a Debian 8 system but it should run on any Linux flavour. Be sure to add t’s path to your cron file.
The script is called freshmeat.sh on my system.
[code]
#!/bin/bash
#######################################################################
# Purpose of this script: #
# Follow random followings from followings from the ununfollowables #
# list, hopefully generating a bit more diversity in your timeline. #
# #
# The ununfollowables list is just a list of people you like. #
# A ‘following’ is someone you are following. It is the reverse of #
# a follower. #
# #
# Requires: #
# – Working and authenticated installation of Ruby gem t: #
# https://github.com/sferik/t #
# – Twitter list called ‘Ununfollowables’ (change as needed) #
# containing friends whose followings you might like to follow #
# – Twitter list called ‘freshmeat’ for the new followings #
# #
# Feel free to use, change and redistribute this script as long as #
# you include a link to https://vorkbaard.nl and this text. Enjoy :) #
# #
# @Vorkbaard, 2017 #
#######################################################################
#######################################################################
# Settings #
#######################################################################
# Ununfollowables list
UNUNFOLLOWABLES_LIST=de-onontvolgbaren
# Freshmeat list
FRESHMEAT_LIST=freshmeat
# Number to days to wait before unfollowing if they’re not interested
WAITDAYS=13
# Number of new random followings to add – must be more than 0.
# Note that this script uses up your api access allowance:
# https://dev.twitter.com/rest/public/rate-limiting
# Also note that a list cannot contain over 5000 members.
NEWADDINGS=5
# Do not follow people with the following words in their bio.
NOTFOLLOW="entrepreneur|founder|coach"
## MAIL – Make sure your server can send out mail first.
## I’m using xmail but you may want to change it.
# Send mail here:
MY_EMAIL=your@email.here
# The mail’s from address
FROMADDR=your@servers_email.here
#######################################################################
# End of settings #
#######################################################################
# Change to directory this script is in so we can use relative file locations when running from cron
cd "$(dirname "$0")";
# Retrieve Twitter handle
ME=@$(t whoami | head -4 | tail -1 | cut -d’@’ -f2)
if [ "$?" != "0" ] ; then
echo "Unable to retrieve Twitter handle, please make sure t is installed and working correctly."
echo "Either that or we’ve ran out of api calls."
exit
fi
echo "———————- $(date) ——————–" >> freshmeat.log
echo "Twitter handle: $ME" >> freshmeat.log
if [ -e mailtext ] ; then rm mailtext; fi
# Ok, here’s the gist.
# Unfollow those not interested
# 1. Get list of randomfollowings followed over two weeks ago.
# 2. If they’re not interested then unfollow them.
# 3. Remove them from the freshmeat list and the inprocess file.
# Get new users
# 4. Select random user from ununfollowables list.
# 5. Select random following from selected user.
# 6. Check if we’re not already following the random following. If we do, select another one.
# 7. Follow the random following.
# 8. Put following on the freshmeat list.
# Create list of leaders so we only need to retrieve it once.
# Leaders are people who you are following but who don’t follow you.
echo "Creating list of leaders. Please hold." >> freshmeat.log
t leaders > leaderslist
if [ "$?" != "0" ] ; then
echo "Error: probably not enough api calls left. Try again later." >> freshmeat.log
echo "We ran out of api calls. Better luck next time!" | mailx -a "From: Freshmeat provider <$FROMADDR>" -s "Fresh meat!" $MY_EMAIL
exit
fi
if [ -e freshmeat.inprocess ] ; then
let WAITSECONDS=$WAITDAYS*60*60*24
echo "WAITSECONDS: $WAITSECONDS" >> freshmeat.log
echo "Getting list of randomfollowings followed over two weeks ago" >> freshmeat.log
NOW=`date +%s`
while read RANDOMFOLLOWING; do
SINCE=$(echo $RANDOMFOLLOWING | cut -d’ ‘ -f2)
RAFO=$(echo $RANDOMFOLLOWING | cut -d’ ‘ -f1)
echo "Rafo: $RAFO" >> freshmeat.log
echo "Since: $SINCE" >> freshmeat.log
echo "NOW..: $NOW" >> freshmeat.log
let DIFF=$NOW-$SINCE
let HDIFF=$DIFF/3600
echo "Time difference: $DIFF ($HDIFF hours)" >> freshmeat.log
if [ "$DIFF" -lt "$WAITSECONDS" ] ; then
echo "Time difference is less than $WAITDAYS days." >> freshmeat.log
# Not doing anything with them now, just add them to the list for next time
echo $RANDOMFOLLOWING >> freshmeat.inprocess_new.log
else
echo "Time difference is greater than $WAITDAYS days." >> freshmeat.log
# Check if they’re following back
grep -iq "^$RAFO$" leaderslist
if [ "$?" == "1" ] ; then
# They’re following back
echo "$RAFO is following back!" >> freshmeat.log
echo "$RAFO" >> newfollowers.log
echo "New connection made: $RAFO – https://twitter.com/$RAFO" >> mailtext
else
# They’re not following back
echo "$RAFO is not interested so unfollowing them." >> freshmeat.log
t unfollow $RAFO >/dev/null 2>&1
echo "Unfollowed $RAFO." >> mailtext
fi
echo "Removing $RAFO from freshmeat list." >> freshmeat.log
t list remove $FRESHMEAT_LIST $RAFO >/dev/null 2>&1
if [ "$?" == "0" ] ; then
echo "Removing $RAFO from random follower log file." >> freshmeat.log
else
echo "Error unfollowing $RAFO. Perhaps we’ve ran out of api calls." >> freshmeat.log
fi
fi
echo "—-" >> freshmeat.log
done <freshmeat.inprocess
# Recreate freshmeat.inprocess file with only remaining (current) followings
mv freshmeat.inprocess_new.log freshmeat.inprocess
else
# if not exist freshmeat.inprocess
echo "freshmeat.inprocess doesn’t exist; nothing to compare so skipping the unfollow part." >> freshmeat.log
fi
# Create list of ununfollowables so we only need to retrieve it once
echo "Creating list of ununfollowables. This may take a while." >> freshmeat.log
t list members $ME/$UNUNFOLLOWABLES_LIST > ununfollowableslist
if [ "$?" != "0" ] ; then
echo "Error: probably not enough api calls left. Try again later." >> freshmeat.log
echo "We ran out of api calls. Better luck next time!" | mailx -a "From: Freshmeat provider <$FROMADDR>" -s "Fresh meat!" $MY_EMAIL
exit
fi
# Create list of followings so we only need to retrieve it once.
echo "Creating list of followings. Please hold." >> freshmeat.log
t followings > followingslist
if [ "$?" != "0" ] ; then
echo "Error: probably not enough api calls left. Try again later." >> freshmeat.log
echo "We ran out of api calls. Better luck next time!" | mailx -a "From: Freshmeat provider <$FROMADDR>" -s "Fresh meat!" $MY_EMAIL
exit
fi
# Initialize the number of succesfull new followings
ADDINGS=0
printf "\n\n" >> mailtext
echo "New followings" >> mailtext
echo "——————————" >> mailtext
while [ $ADDINGS -lt $NEWADDINGS ] ; do
echo "Succesfull addings: $ADDINGS" >> freshmeat.log
# Get random ununfollowable
UNUNFOLLOWABLES=$(cat ununfollowableslist | shuf -n 1)
echo "Following from ununfollowableslist: $UNUNFOLLOWABLES" >> freshmeat.log
for UNUNFOLLOWABLE in $UNUNFOLLOWABLES; do
echo "Getting random following from $UNUNFOLLOWABLES_LIST." >> freshmeat.log
RANDOMFOLLOWING=$(t followings $UNUNFOLLOWABLE | shuf -n 1)
echo "Randomfollowing: $RANDOMFOLLOWING" >> freshmeat.log
if [ -n "$RANDOMFOLLOWING" ] ; then
# Check if we’re not already following this particular random following
grep -iq "^$RANDOMFOLLOWING$" followingslist
if [ "$?" == "1" ] ; then
echo "Not already following, but is this a protected account?" >> freshmeat.log
# Protected accounts don’t have the ‘Last update’ bit set in their public profile.
# Also, get to know them a bit by reading their bio.
t whois $RANDOMFOLLOWING > tmpwhois
# Check if the account is protected
grep -q "Last update" tmpwhois
if [ "$?" == "0" ] ; then
# Check if they’re not unwanted
BIO=$(grep "Bio" tmpwhois)
if echo $BIO | egrep -iqv $NOTFOLLOW; then
echo "Not already following $RANDOMFOLLOWING AND not a protectect account AND they’re not unwanted so following them now." >> freshmeat.log
t follow $RANDOMFOLLOWING >/dev/null 2>&1
if [ "$?" == "0" ] ; then
echo "Follow succesful so adding them to $FRESHMEAT_LIST." >> freshmeat.log
t list add $FRESHMEAT_LIST $RANDOMFOLLOWING >/dev/null 2>&1
NOW=`date +%s`
echo "$RANDOMFOLLOWING $NOW" >> freshmeat.inprocess
# Increase addings number
ADDINGS=$(( $ADDINGS + 1 ))
SHOWBIO="$(echo $BIO|cut -c5-)"
echo "Via $UNUNFOLLOWABLES: $RANDOMFOLLOWING – $SHOWBIO [https://twitter.com/$RANDOMFOLLOWING]" >> mailtext
fi
else
echo "Not going to follow $NOTFOLLOW." >> freshmeat.log
fi
else
echo "Not going to follow protected account." >> freshmeat.log
fi
else
echo "Already following $RANDOMFOLLOWING." >> freshmeat.log
fi
echo "—- done —-" >> freshmeat.log
else
echo "We’ve probably ran out of api calls so let’s call it a day." >> freshmeat.log
ADDINGS=$(( $NEWADDINGS + 1 ))
# if -n $RANDOMFOLLOWING
fi
# for UNUNFOLLOWABLE
done
# Addings
done
# Mail logfile
# Get number of connections generated
if [ -e newfollowers.log ] ; then
FreshFollNr=$(wc -l newfollowers.log | cut -d’ ‘ -f1)
echo "Freshmeat has generated $FreshFollNr connections." >> mailtext
else
echo "Freshmeat has not generated any connections yet." >> mailtext
fi
# Get number of people in Freshmeat list
FreshmeatMembersNr=$(t list information $FRESHMEAT_LIST | head -5 | tail -1 | cut -d ‘ ‘ -f7)
echo "There are now $FreshmeatMembersNr people on the $FRESHMEAT_LIST list." >> mailtext
# Send mail
cat mailtext | mailx -a "From: Freshmeat provider <$FROMADDR>" -s "Fresh meat!" $MY_EMAIL
rm mailtext
# Clean up
if [ -e tmpwhois ] ; then rm tmpwhois; fi
if [ -e followingslist ] ; then rm followingslist; fi
if [ -e ununfollowableslist ] ; then rm ununfollowableslist; fi
if [ -e leaderslist ] ; then rm leaderslist; fi
[/code]