#!/bin/bash # rchat # Simple rautafarmi chat client # Licensed under GNU GPLv3. RCHAT_EXIT() { ENDMSG="rchat terminated. (exit code 0)" rm -f $HOME/.config/rchat/rchat-editor-message $HOME/.config/rchat/rchat-cchat ; clear ; echo $ENDMSG ; exit 0 } RCHAT_LOGOUT() { rm -f $HOME/.config/rchat/rchat-joined $HOME/.config/rchat/rchat-editor-message $HOME/.config/rchat/rchat-msg $HOME/.config/rchat/rchat-cchat ; clear ; ${0} ; RCHAT_EXIT } RCHAT_INIT() { mkdir -p $HOME/.config/rchat > /dev/null DEFAULT_INSTANCE="https://donut.gq/rautafarmi" # Set instance if one already exists if [ -e "$HOME/.config/rchat/rchat-instance" ]; then cat $HOME/.config/rchat/rchat-instance > /dev/null else printf "$DEFAULT_INSTANCE" > $HOME/.config/rchat/rchat-instance fi INSTANCE=$(cat $HOME/.config/rchat/rchat-instance) REFRESH_TIMEOUT=3 LINECOUNT="$(expr $(tput lines) "-" 4)" # How many lines to print MAXCHARACTERCOUNT="$(tput cols)" COLOR_01="$(printf '\033[0m')" # White COLOR_02="$(printf '\033[0;33m')" # Yellow COLOR_03="$(printf '\033[0;35m')" # Purple COLOR_04="$(printf '\033[0;36m')" # Blue COLOR_05="$(printf '\033[0;33m')" # Orange COLOR_06="$(printf '\033[0;31m')" # Red COLOR_07="$(printf '\033[0;32m')" # Green NAME="rchat" # rchat.. simple as that VER="1.41" # Version of rchat VERSION="$VER-06-29-2022" # Version of rchat SEP=▀ # Separator that will be used for borders SEPCOUNT=$(tput cols) # Check what to set the nick to if [ -e "$HOME/.config/rchat/rchat-nick" ]; then NICK=$(cat $HOME/.config/rchat/rchat-nick) else NICK="anon" fi MODE="-- NORMAL --" RCHAT_URL="$INSTANCE/messages.txt" RCHAT_WRITE_UPDATE() { if [ -e "/usr/bin/doas" ]; then doas curl -o $0 "https://raw.githubusercontent.com/speediegq/rchat/main/rchat" && $0 && exit 0 elif [ -e "/usr/bin/sudo" ]; then sudo curl -o $0 "https://raw.githubusercontent.com/speediegq/rchat/main/rchat" && $0 && exit 0 elif [ -e "/bin/su" ]; then su -c "curl -o $0 "https://raw.githubusercontent.com/speediegq/rchat/main/rchat"" root && $0 && exit 0 fi } RCHAT_UPDATE_CLIENT() { clear printf "${COLOR_02}A new version of rchat ($(curl -s https://raw.githubusercontent.com/speediegq/rchat/main/rchat-latestver)) is available replacing $VER.\n\n${COLOR_03}$(curl -s https://raw.githubusercontent.com/speediegq/rchat/main/rchat-cupdatelog)\n\n${COLOR_02}Would you like to update from $VER? (yes/no/ignore/never/diff)\n${COLOR_01}> "; read UPT_CHOICE case "$UPT_CHOICE" in "yes") RCHAT_WRITE_UPDATE ;; "no") LATEST=true ;; "ignore") curl -so $HOME/.config/rchat/rchat-ignore-updt https://raw.githubusercontent.com/speediegq/rchat/main/rchat-latestver ;; "never") touch $HOME/.config/rchat/rchat-do-not-update ;; "fuck off") touch $HOME/.config/rchat/rchat-do-not-update ;; "diff") curl -so $HOME/.config/rchat/rchat-newupt https://raw.githubusercontent.com/speediegq/rchat/main/rchat && diff -up $HOME/.config/rchat/rchat-newupt $0 | less ;; "") $0 && exit 0 ;; esac } # Check for updates if [ "$(curl -s https://raw.githubusercontent.com/speediegq/rchat/main/rchat-latestver)" = "$VER" ]; then LATEST=true else if [ -e "$HOME/.config/rchat/rchat-do-not-update" ]; then LATEST=true else if [ -e "$HOME/.config/rchat/rchat-ignore-updt" ]; then if [ "$(cat $HOME/.config/rchat/rchat-ignore-updt)" = "$(curl -s https://raw.githubusercontent.com/speediegq/rchat/main/rchat-latestver)" ]; then LATEST=true fi fi fi fi if [ "$LATEST" = "true" ]; then LATEST=true else RCHAT_UPDATE_CLIENT fi # Load rchat settings if [ -e "$HOME/.config/rchat/rchat-settings" ]; then . $HOME/.config/rchat/rchat-settings fi FSEP="$(seq $(tput cols) | xargs -Iz printf "${COLOR_01}$SEP${COLOR_01}")" # Download all messages from the instance RCHAT_DOWNLOAD_MESSAGES & # Check if an existing session is active if [ -e "$HOME/.config/rchat/rchat-joined" ]; then printf "Existing session exists, joining.." else RCHAT_STARTER_HEADER fi # Check if an editor is defined, if not set it to vim if [ "$EDITOR" = "" ]; then EDITOR=vim fi # Config file if [ -e "$HOME/.config/rchat/rchatrc" ]; then . $HOME/.config/rchat/rchatrc else mkdir -p $HOME/.config/rchat; touch $HOME/.config/rchat/rchatrc fi RCHAT_GREP_MESSAGES } RCHAT_DOWNLOAD_MESSAGES() { sleep $REFRESH_TIMEOUT curl -so $HOME/.config/rchat/rchat-msg "$RCHAT_URL" > /dev/null } RCHAT_STARTER_HEADER() { clear printf "$NAME $VERSION\n" printf "$FSEP" printf "\n\n" printf "${COLOR_02}Last login: $(date '+%Y/%m/%d at %T')${COLOR_01}" printf "\n\nWelcome to $NAME $VERSION. $NAME is a rautafarmi chat client with Vim keybinds." printf "\n${COLOR_02}rchat is licensed under the GNU GPLv3 license. Client written by speedie & potential contributors, rautafarmi is owned by donut.gq.\n${COLOR_01}" printf "\n${COLOR_04}Type ':j' to join." printf "\n${COLOR_03}Type ':set instance' and then enter your instance URL to set an instance." printf "\n${COLOR_06}Type ':set instance default' to change it back.${COLOR_01}" printf "\n${COLOR_07}Type ':h' to get help.${COLOR_01}" printf "\n${COLOR_02}Type ':donate' to donate.${COLOR_01}" printf "\nType ':q' to quit.\n" read starter_command case "$starter_command" in ":q") RCHAT_EXIT ;; ":q!") RCHAT_EXIT ;; ":quit") RCHAT_EXIT ;; ":j") touch $HOME/.config/rchat/rchat-joined && RCHAT_INIT ;; ":set instance") echo -n "Enter your instance: " ; read CUSTOM_INSTANCE ; printf "$CUSTOM_INSTANCE" > $HOME/.config/rchat/rchat-instance && printf "\n${COLOR_06}000 - SYSTEM at $(date '+%Y/%m/%d %T:')\nSet instance to $CUSTOM_INSTANCE.${COLOR_01}" && sleep 3 && ${0} && RCHAT_EXIT ;; ":set instance default") echo $DEFAULT_INSTANCE > $HOME/.config/rchat/rchat-instance && printf "${COLOR_06}\n000 - SYSTEM at $(date '+%Y/%m/%d %T:')\nSet instance to default.${COLOR_01}" && sleep 3 && ${0} && RCHAT_EXIT ;; ":h") RCHAT_HELP | less ;; ":help") RCHAT_HELP | less ;; ":changelog") RCHAT_CHANGELOG | less ;; ":donate") RCHAT_DONATE && $0 && RCHAT_EXIT ;; ":reset") RCHAT_RESET ;; esac # Confirm we joined if [ -e "$HOME/.config/rchat/rchat-joined" ]; then printf "Joining" else ${0} && RCHAT_EXIT fi } RCHAT_DONATE() { if [ -e "/usr/bin/xdg-open" ]; then xdg-open "https://speedie.gq/donate" else $BROWSER "https://speedie.gq/donate" fi } RCHAT_HEADER() { printf "$NAME $VERSION\n" printf "$FSEP" } RCHAT_CAT_MESSAGES() { if [ -e "$HOME/.config/rchat/rchat-msg" ]; then RCHAT_FULL_MESSAGE_DATA="$(cat $HOME/.config/rchat/rchat-msg | \ sed -n 1,$LINECOUNT\p | \ sed "s//${COLOR_03}/" | \ sed "s//${COLOR_05}- /" | \ sed "s|||" | \ sed "s| | ${COLOR_06}at ${COLOR_04}|" | \ sed "s||${COLOR_01}:|" | \ sed "s|:|${COLOR_03}|" | \ sed "s||:${COLOR_03}|" | \ sed "s|||" | \ sed "/.\{$MAXCHARACTERCOUNT\}/d" | \ sed "/^[[:space:]]*$/d" | \ sed "s|>>|${COLOR_05}>>|g" | \ sed "s|>|${COLOR_07}>|g" | \ sed "s#^#${COLOR_01}#g")" printf "$RCHAT_FULL_MESSAGE_DATA${COLOR_01}" > $HOME/.config/rchat/rchat-cchat printf "$RCHAT_FULL_MESSAGE_DATA\n\n${COLOR_01}" >> $HOME/.config/rchat/rchat-history head -n "$(expr $(tput lines) "-" 7)" $HOME/.config/rchat/rchat-cchat printf "${COLOR_01}$FSEP" printf "\n${COLOR_04}I: $INSTANCE L: $LINECOUNT/$(cat $HOME/.config/rchat/rchat-msg | wc -l) LL: $(date '+%Y/%m/%d at %T')${COLOR_01}\n" printf "$FSEP" printf "\n" else printf "\n${COLOR_06}\n000 - SYSTEM at $(date '+%Y/%m/%d %T:')\nDownloading messages.${COLOR_01}"; sleep 5 && clear && RCHAT_CAT_MESSAGES fi } RCHAT_GREP_MESSAGES() { clear RCHAT_HEADER # Print the header/banner RCHAT_CAT_MESSAGES # Print the messages RCHAT_FOOTER # Print the footer/banner printf " $MODE \n" # Print the default mode RCHAT_CHECK_UPDATE } RCHAT_SEND_MESSAGE() { case "$RCHAT_MESSAGE_TYPE" in "editor") curl -sX POST $INSTANCE/post.php -F "name=$NICK" -F "msg=$(cat $HOME/.config/rchat/rchat-editor-message)" > /dev/null ;; "normal") curl -sX POST $INSTANCE/post.php -F "name=$NICK" -F "msg=$RCHAT_SEND_MESSAGE" > /dev/null ;; esac printf "${COLOR_06}\n000 - SYSTEM at $(date '+%Y/%m/%d %T:')\nMessage '$RCHAT_SEND_MESSAGE' sent. ${COLOR_01}" && sleep 0.5 clear ${0} && RCHAT_EXIT } RCHAT_CHECK_UPDATE() { case "$(cat $HOME/.config/rchat/rchat-msg)" in "$(curl -s $RCHAT_URL)") RCHAT_CHECK_MODE ;; esac if [ "$MAXCHARACTERCOUNT" = "$(tput cols)" ]; then MAXCHARACTERCOUNT=$(tput cols) else MAXCHARACTERCOUNT=$(tput cols) fi if [ "$SEPCOUNT" = "$(tput cols)" ]; then SEPCOUNT=$(tput cols) else SEPCOUNT=$(tput cols) fi ${0} && RCHAT_EXIT # Reset the script if there are new messages } RCHAT_GREP_MESSAGES() { clear RCHAT_HEADER # Print the header/banner RCHAT_CAT_MESSAGES # Print the messages printf " $MODE " # Print the default mode RCHAT_CHECK_UPDATE } RCHAT_INSERT() { clear && RCHAT_HEADER && RCHAT_CAT_MESSAGES case "$MODE" in "INSERT") MODE="INSERT" ;; esac echo -n "-- $MODE --" echo -ne "\n> " read RCHAT_SEND_MESSAGE && RCHAT_MESSAGE_TYPE=normal # Reload if it's empty case "$RCHAT_SEND_MESSAGE" in "") ${0} && RCHAT_EXIT ;; "^[") ${0} && RCHAT_EXIT ;; esac RCHAT_SEND_MESSAGE ; ${0} && RCHAT_EXIT } RCHAT_CMD() { clear && RCHAT_HEADER && RCHAT_CAT_MESSAGES echo -n ":" && read CMD case "$CMD" in "q") RCHAT_EXIT ;; "leave") RCHAT_LOGOUT ;; "h") RCHAT_HELP | less ;; "help") RCHAT_HELP | less ;; "r") ${0} && RCHAT_EXIT ;; "reset") RCHAT_RESET ;; "set nick") echo -n "Enter nick: " && read NICK && echo $NICK > $HOME/.config/rchat/rchat-nick && ${0} && RCHAT_EXIT ;; "set refreshdelay") echo -n "How many seconds: " && read refreshdelay && printf "REFRESHDELAY=$REFRESHDELAY\n" >> $HOME/.config/rchat/rchat-settings ;; "set sep") echo -n "What should your separator be?: " && read SEP && printf "SEP=$SEP\n" >> $HOME/.config/rchat/rchat-settings ;; "!") echo -n "What shell command should run? " && read RCHAT_SHELL_COMMAND && "/bin/sh -c" "$RCHAT_SHELL_COMMAND" && ${0} && RCHAT_EXIT ;; "history") less $HOME/.config/rchat/rchat-history ; ${0} && RCHAT_EXIT ;; "history clear") rm $HOME/.config/rchat/rchat-history ; ${0} && RCHAT_EXIT ;; "changelog") RCHAT_CHANGELOG | less ;; "forceupdate") RCHAT_UPDATE_CLIENT ;; "news") RCHAT_NEWS | less ;; "instance") RCHAT_INSTANCE_LIST | less ;; "e") $EDITOR $HOME/.config/rchat/rchat-editor-message && RCHAT_MESSAGE_TYPE=editor && RCHAT_SEND_MESSAGE ;; "donate") RCHAT_DONATE && $0 && RCHAT_EXIT ;; esac ${0} && RCHAT_EXIT } # Help screen RCHAT_HELP() { HSEP="-" printf "${COLOR_02}${HSEP}${HSEP} rchat help | Use hjkl to read ${HSEP}${HSEP}\n\n" printf "${COLOR_01}rchat is a chat client with Vim keybinds. To enter text, press I at any time.\n" printf "When you initially run it from a terminal, you need to join.\n" printf "Joining is done using a command. Commands in rchat are used similar to Vim. This means most commands start with ':'.\n\n" printf "${COLOR_04}${HSEP}${HSEP} COMMANDS ${HSEP}${HSEP}${COLOR_01}" printf "\n${HSEP}${COLOR_03} To join the set instance, type ':j'. *CAN ONLY BE DONE IF YOU AREN'T ALREADY IN AN INSTANCE*" printf "\n${HSEP}${COLOR_03} To set an instance (Otherwise the default will be used), type ':set instance'. *CAN ONLY BE DONE IF YOU AREN'T ALREADY IN AN INSTANCE*" printf "\n${HSEP}${COLOR_03} If you wanna run a terminal command, type ':!'." printf "\n${HSEP}${COLOR_03} To see the help screen, do ':h'." printf "\n${HSEP}${COLOR_03} To change your nickname from '$NICK' to anything you want, ':set nick'." printf "\n${HSEP}${COLOR_03} To change how often messages are downloaded, ':set refreshdelay'. *PLEASE DO NOT ABUSE THIS*" printf "\n${HSEP}${COLOR_03} To change separator, ':set sep'." printf "\n${HSEP}${COLOR_03} To reset settings, ':reset'." printf "\n${HSEP}${COLOR_03} To see the changelog, type ':changelog'." printf "\n${HSEP}${COLOR_03} To type out a message in your defined $EDITOR, type ':e'." printf "\n${HSEP}${COLOR_03} To see a list of popular instances, type ':instance'." printf "\n${HSEP}${COLOR_03} To download and see news, type ':news'." printf "\n${HSEP}${COLOR_03} To see a full list of all messages downloaded combined, type ':history'." printf "\n${HSEP}${COLOR_03} To clear the saved history, type ':history clear'." printf "\n${HSEP}${COLOR_03} To leave the instance, type ':leave'. (You can also do ZQ)" printf "\n${HSEP}${COLOR_03} To quit rchat (You'll stay logged in), type ':q'. (You can also do ZZ)${COLOR_01}" printf "\n${HSEP}${COLOR_03} To donate, type ':donate'.${COLOR_01}" } RCHAT_CHANGELOG() { printf "${COLOR_04}rchat 0.1 (Released 2022-04-18): Initial release" printf "\n${COLOR_04}rchat 0.1-r2 (Released 2022-04-18): Added color support, writing messages in \$EDITOR and config file" printf "\n${COLOR_04}rchat 0.2 (Released 2022-04-19): Added custom instance support and fixed sysop garbage being printed when it shouldn't. Also performed other minor improvements." printf "\n${COLOR_04}rchat 0.2-r2 (Released 2022-04-19): Small aesthetic tweaks and defined \$EDITOR if it wasn't already." printf "\n${COLOR_04}rchat 0.3 (Released 2022-04-20): Removed more trash present in some instances, added :news and :instance commands and other small tweaks." printf "\n${COLOR_04}rchat 0.4 (Released 2022-04-24): Added :history, :history clear and other bug fixes." printf "\n${COLOR_04}rchat 0.5 (Released 2022-04-26): Added :set refreshdelay and other fixes." printf "\n${COLOR_04}rchat 1.0 (Released 2022-06-07): 1.0 release, bug fixes, added colors for :help, added config file support, removed useless bash-isms. Also added fancy borders and messages now fit into exactly your terminal size." printf "\n${COLOR_04}rchat 1.1 (Released 2022-06-12): Fixed terminal size issues and :donate command." printf "\n${COLOR_04}rchat 1.2 (Released 2022-06-14): New auto update feature added, :h command improved, ZZ and ZQ can now be used instead of :q and :leave, and other improvements to insert mode and borders." printf "\n${COLOR_04}rchat 1.3 (Released 2022-06-23): Fixed VERY stupid mistake. That's it." printf "\n${COLOR_04}rchat 1.3-r2 (Released 2022-06-29): Fixed even stupider mistake. That's it." printf "\n${COLOR_04}rchat 1.4 (Released 2022-06-30): Fixed small bugs, shouldn't break patches though." printf "\n${COLOR_04}rchat 1.41 (Released 2022-08-10): Fixed bug caused by 'head' stupidity." } RCHAT_RESET() { rm -rf $HOME/.config/rchat/rchat* && rm -rf $HOME/.config/rchat && ${0} && RCHAT_EXIT } RCHAT_NEWS() { curl -so $HOME/.config/rchat/rchat-news https://raw.githubusercontent.com/speediegq/rchat/main/rchat-news cat $HOME/.config/rchat/rchat-news | less rm $HOME/.config/rchat/rchat-news } # Print instance list RCHAT_INSTANCE_LIST() { curl -so $HOME/.config/rchat/rchat-instance-list https://raw.githubusercontent.com/speediegq/rchat/main/rchat-instance-list if [ -e "$HOME/.config/rchat/rchat-instance-list" ]; then cat $HOME/.config/rchat/rchat-instance-list | less rm -f $HOME/.config/rchat/rchat-instance-list fi } RCHAT_Z_EXIT() { read -n 1 MODE case "$MODE" in "") MODE="NORMAL" && RCHAT_CHECK_UPDATE ;; "Q") RCHAT_LOGOUT ;; "Z") RCHAT_EXIT ;; esac } # Check what mode we're in RCHAT_CHECK_MODE() { read -t 1 -n 1 MODE case "$MODE" in "i") MODE="INSERT" && RCHAT_INSERT ;; "") MODE="NORMAL" && RCHAT_CHECK_UPDATE ;; ":") RCHAT_CMD ;; "Z") RCHAT_Z_EXIT ;; "q") RCHAT_EXIT ;; "l") RCHAT_LOGOUT ;; esac ${0} && RCHAT_EXIT } # Bottom RCHAT_INIT RCHAT_CHECK_UPDATE