#!/bin/bash #comchat.sh - very lazy terminal client for Chat@Heyuri #this program has become substantial enough that I added license terms #but said terms are basically just "leave my fucking name on it lmao" #Copyright (c) 2026 miredo # #Permission is hereby granted, free of charge, to any person obtaining a #copy of this software and associated documentation files (the "Software"), #to deal in the Software without restriction, including without limitation #the rights to use, copy, modify, merge, publish, distribute, sublicense, #and/or sell copies of the Software, and to permit persons to whom the #Software is furnished to do so, subject to the following conditions: # #The above copyright notice and this permission notice shall be included in #all copies or substantial portions of the Software. # #THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR #IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, #FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL #THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER #LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING #FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER #DEALINGS IN THE SOFTWARE. #TODO list: # * load settings from files (~/.config/mrd_comchat/...) # * load settings from arguments (getops!) # * sound effect for new posts # * kaomoji selector # * eventually, rewrite in Python but I dunno if I care enough to bother version="4.0" refresh_time=30 user_color=15 my_trip="" user_agent="$(curl --version | awk '{print $1"/"$2;exit}') comchat.sh/$version" #very dumb hack because curl doesn't give you a nice way to just get the version number msg_raw="" msg_old="" new_msg=false #strip out excess keypresses cleanbuffer() { while read -t 0 do read -N 1 -s done } #reset all colors reset_col() { echo -e -n "\033[0m" } #show the full scrollback check_scrollback() { echo "$msg_raw" | fold -w `tput cols` -s | less } #set the display color #usage: set_col color bold #color 30-37: blk, red, grn, ylw, blu, mag, cyn, wht #40-47 set the background color #bold is 1 or 0 set_col() { echo -e -n "\033[$2;$1m" } #read in the tripcode set_tripcode() { reset_col IFS= read -p "tripcode (optional): " -e -r my_trip } #read in the username set_username() { reset_col IFS= read -p "username: " -e -r username } #read in the update interval set_interval() { reset_col IFS= read -p "update interval (min 15, default 30): " -e -r refresh_time refresh_time=$(($refresh_time)) if (( refresh_time < 15 )) then refresh_time=15 fi } #sends a message via cURL #TODO: should we set our own referrer? might be useful/fun send_msg() { reset_col IFS= read -p "message: " -e -r mymsg curl -s \ --user-agent "$user_agent" \ --data-urlencode "mode=regist" \ --data-urlencode "name=$username" \ --data-urlencode "email=" \ --data-urlencode "password=$my_trip" \ --data-urlencode "comment=$mymsg" \ --data-urlencode "face=" \ --data-urlencode "color=$user_color" \ --data-urlencode "retime=0" \ --data-urlencode "lines=1" \ --data-urlencode "autoclear=on" \ https://cgi.heyuri.net/chat/comchat.cgi > /dev/null } #shows the help show_help() { reset_col clear set_col 36 1 echo "command keys:" reset_col echo "q, Q - quit" echo "? - show this help message" echo "/ - send a message (leave blank to cancel) [refreshes]" echo "r, space, enter - refresh the chat [obviously refreshes lol]" echo "p, ; - view the chat scrollback (via the less command, press q" echo " to exit the scrollback view)" echo "#, T - set the tripcode" echo "i - set the update interval (min 20s) [refreshes]" echo set_col 36 1 echo "other notes:" reset_col echo "* refresh the chat if you change your terminal size" echo "* only the commands marked by [refreshes] will refresh, all" echo " other commands will not (and the auto-refresh counter will" echo " start back from the top)" echo "* all screens expect a minimum 80x24 terminal; you can get away" echo " with less, but things may not look right" echo set_col 32 1 echo "Press any key to continue." reset_col read -N 1 -s } #main program starts here reset_col clear #show intro text set_col 36 0 echo "miredo's very very lazy comchat client for Chat@Heyuri" echo "version $version" echo "user-agent: '$user_agent'" #get user info set_col 36 1 set_username set_tripcode echo #chat refresh info refresh=true refresh_date=never #main loop here while true do #get terminal size scr_w=`tput cols` scr_h=`tput lines` #load and format the message list reset_col #TODO: handle HTML entities somehow lol (or at least find and replace " and &) #TODO: strip all control characters - probably not ever going to be an issue, but there isn't a real reason to not do it for sanity's sake if [[ "$refresh" == "true" ]] then set_col 31 1 echo -n "[loading...]" cleanbuffer msg_old="$msg_raw" msg_raw="$( curl -s https://cgi.heyuri.net/chat/simplelog.txt) " if [[ "$msg_raw" != "$msg_old" ]] then new_msg=true fi msg="$( echo "$msg_raw" | fold -s -w $scr_w | head -n $(expr $scr_h - 4) )" refresh_date="$(date)" refresh=false fi #draw the main screen clear set_col 44 0 set_col 37 1 echo "[refeshed on $refresh_date | ($scr_w"x"$scr_h) | reload: $refresh_time"s"]" #display the messages reset_col #highlight new message/most recent #white if old, yellow if new #TODO: this is where I'd play a sound too if [[ "$new_msg" == "true" && "$show_update" == "true" ]] then set_col 33 1 else set_col 37 1 fi new_msg=false show_update=false echo "$msg" | head -n 1 #dumb hack, highlights the first line reset_col echo "$msg" | tail -n +2 set_col 44 0 set_col 37 1 echo "keys: q-quit, /-send, r-refresh, ?-help" reset_col #handle user commands read -t $refresh_time -N 1 -s inp case "$inp" in r| "" | " ") #refresh refresh=true show_update=true ;; q | Q) #quit clear exit 1 ;; "/") #post send_msg refresh=true show_update=false ;; p | s | ";") #view whole scrollback of posts check_scrollback ;; h | "?") #show help show_help ;; T | "#") #set tripcode set_tripcode ;; i) #set update interval set_interval refresh=true show_update=true ;; esac cleanbuffer if [[ "$refresh" == "true" ]] then set_col 33 1 echo -n "[refreshing...] " #minimum time so we don't hammer the site with a bunch of requests #lowered it from before to improve responsiveness sleep 0.5 fi reset_col done