Skip to content

Instantly share code, notes, and snippets.

@markusfisch
Last active March 25, 2016 10:54
Show Gist options
  • Save markusfisch/4582323 to your computer and use it in GitHub Desktop.
Save markusfisch/4582323 to your computer and use it in GitHub Desktop.
Shell script to tweet from the command line. Breaks longer messages into multiple tweets. Requires curl.
#!/usr/bin/env bash
# Post a tweet
#
# @param ... - tweet
tweet()
{
# Make a SSL request
#
# @param ... - request arguments
request()
{
curl -sL3 -b "$CF" -c "$CF" "$@"
}
# Extract and echo OAuth token from given URL
#
# @param 1 - URL to retrieve token from
token()
{
local D
D=$(request "$1")
D=${D##*authenticity_token}
D=${D#*value=\"}
echo "${D%%\"*}"
}
local CF URL='https://mobile.twitter.com' T=${*:-$(cat)} RV=1
CF=$(mktemp -t ".${0##*/}-XXXX") || return 1
# oauth requests
{
request \
-d "authenticity_token=$(token "$URL/session/new")&username=$TWITTER_USERNAME&password=$TWITTER_PASSWORD" \
$URL/session &&
request \
-d "authenticity_token=$(token "$URL/compose/tweet")&tweet[text]=${T// /+}&tweet[display_coordinates]=false" \
$URL &&
request \
-d "authenticity_token=$(token "$URL/account")" \
$URL/session/destroy &&
RV=0
} &>/dev/null
rm -f "$CF"
return $RV
}
# Cut some text into smaller snippets without cutting words in half
#
# @param ... - text to cut (optional)
snip()
{
local TEXT=$* LIMIT=${LIMIT:-140} GLUE=${GLUE:-'..'}
(( LIMIT -= ${#GLUE} ))
local N
for (( N=0; ${#TEXT} > LIMIT; ++N ))
do
local S=${TEXT:0:$LIMIT}
local U=${S%[ $'\n']*}
(( N > 0 )) && echo -n "$GLUE"
if [ "$U" ]
then
echo -n "$U"
TEXT=${TEXT:${#U}}
else
echo -n "$S"
TEXT=${TEXT:$LIMIT}
fi
echo "$GLUE"
(( N == 0 )) && (( LIMIT -= ${#GLUE} ))
done
(( N > 0 )) && echo -n "$GLUE"
echo "$TEXT"
}
# Send message in one or more tweets
#
# @param ... - message (optional)
smart_tweet()
{
snip "${@:-$(cat)}" | while read -r
do
tweet "$REPLY" || break
done
}
if [ "${BASH_SOURCE[0]}" == "$0" ]
then
# Get string form stdin
#
# @param 1 - prompt
gets()
{
read -r -p "$1: " && echo "$REPLY"
}
if (( $# ))
then
TWITTER_USERNAME=${TWITTER_USERNAME:-$(gets 'user')}
TWITTER_PASSWORD=${TWITTER_PASSWORD:-$(gets 'pass')}
fi
if [ -z "$TWITTER_USERNAME" ] || [ -z "$TWITTER_PASSWORD" ]
then
echo 'error: you need to set a user name and a password'
exit 1
fi
smart_tweet "$@"
fi
@Poltergeist
Copy link

What do I need to change or set up to get this to work?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment