This is a little project simply to make trivial tools in Go effortless for my personal usage. These tools are almost surely of low utility to most people, but may be instructive nonetheless.
I have CI/CD to build this into a single
binary and an
explode
tool that builds
symlinks for each
tool in the busybox style.
I have automation in my
dotfiles
to pull the latest binary at install time and run the explode
tool.
Here's a copy pasteable script to install the leatherman on OSX or Linux:
OS=$([ $(uname -s) = "Darwin" ] && echo "-osx")
LMURL="$(curl -s https://api.github.com/repos/frioux/leatherman/releases/latest |
grep browser_download_url |
cut -d '"' -f 4 |
grep -F leatherman${OS}.xz )"
mkdir -p ~/bin
curl -sL "$LMURL" > ~/bin/leatherman.xz
xz -d -f ~/bin/leatherman.xz
chmod +x ~/bin/leatherman
~/bin/leatherman explode
This asssumes that ~/bin
is in your path. The explode
command will create a
symlink for each of the tools listed below.
Each tool takes different args, but to run a tool you can either use a symlink
(presumably created by explode
):
$ echo "---\nfoo: 1" | yaml2json
{"foo":1}
or use it as a subcommand:
echo "---\nfoo: 1" | leatherman yaml2json
{"foo":1}
alluni
: Prints all unicode character names (internal/tool/allpurpose/uni/alluni.md)clocks
: Shows my personal, digital, wall of clocks (internal/tool/allpurpose/clocks/clocks.md)csv2json
: Reads CSV on stdin and writes JSON on stdout (internal/tool/allpurpose/csv/csv2json.md)csv2md
: Reads CSV on stdin and writes Markdown on stdout (internal/tool/allpurpose/csv/csv2md.md)debounce
: Run debounces input from stdin to stdout (internal/tool/allpurpose/debounce/debounce.md)dump-mozlz4
: Dumps the contents of amozlz4
(akajsonlz4
) file. (internal/tool/allpurpose/dumpmozlz4/dump-mozlz4.md)expand-url
: Converts links in text to markdown links. (internal/tool/allpurpose/expandurl/expand-url.md)fn
: Creates persistent functions by generating scripts. (internal/tool/allpurpose/fn/fn.md)group-by-date
: Creates time series data by counting lines and grouping them by a given date format. (internal/tool/allpurpose/groupbydate/group-by-date.md)minotaur
: Watches directories and runs a command when files change. (internal/tool/allpurpose/minotaur/minotaur.md)name2rune
: Prints characters based on name. (internal/tool/allpurpose/uni/name2rune.md)netrc-password
: Prints password for a hostname, login pair. (internal/tool/allpurpose/netrcpassword/netrc-password.md)pomotimer
: Conveniently counts down a duration. (internal/tool/allpurpose/pomotimer/pomotimer.md)replace-unzip
: Does whatunzip
does more safely. (internal/tool/allpurpose/replaceunzip/replace-unzip.md)srv
: Serves a directory over http, automatically refreshing when files change. (internal/tool/allpurpose/srv/srv.md)toml2json
: Reads TOML on stdin and writes JSON on stdout. (internal/tool/allpurpose/toml/toml2json.md)uni
: Describes unicode characters. (internal/tool/allpurpose/uni/uni.md)yaml2json
: Reads YAML on stdin and writes JSON on stdout. (internal/tool/allpurpose/yaml/yaml2json.md)
auto-emote
: Reacts to discord messages with vaguely related emoji. (internal/tool/chat/automoji/auto-emote.md)slack-deaddrop
: Sends messages to a slack channel. (internal/tool/chat/slack/slack-deaddrop.md)slack-open
: Opens a channel, group message, or direct message by name. (internal/tool/chat/slack/slack-open.md)slack-status
: Sets slack status. (internal/tool/chat/slack/slack-status.md)
update
: Installs new version of leatherman if one exists. (internal/tool/leatherman/update/update.md)
backlight
: Modifies screen brightness. (internal/tool/misc/backlight/backlight.md)draw
: Draws images with lua. (internal/tool/misc/img/draw.md)export-bamboohr
: Exports company directory as JSON. (internal/tool/misc/bamboo/export-bamboohr.md)media-remote
:media-remote
control media players on Linux. (internal/tool/misc/desktop/media-remote.md)prepend-hist
: Combines a history file and stdin. (internal/tool/misc/prependhist/prepend-hist.md)status
: Serves information about host machine. (internal/tool/misc/status/status.md)steamsrv
: Steamsrv renders steam screenshots and the steam log (what games you played and when) over http. (internal/tool/misc/steamsrv/steamsrv.md)twilio
: Makes callbacks like twilio. (internal/tool/misc/twilio/twilio.md)wuphf
: Sends notifications on lots (2) of platforms. (internal/tool/misc/wuphf/wuphf.md)
amygdala
: Automated assistant. (internal/tool/notes/amygdala/amygdala.md)brainstem
: Interacts with amygdala without using any server components. (internal/tool/notes/brainstem/brainstem.md)notes
: Serves my notes from disk or Dropbox. (internal/tool/notes/now/notes.md)proj
: Integrates my various project management tools. (internal/tool/notes/proj/proj.md)zine
: Read only view of my notes via the filesystem. (internal/tool/notes/zine/zine.md)
In an effort to make debugging simpler, I've created three ways to see what
leatherman
is doing:
LMTRACE=$somefile
will write an execution trace to $somefile
; look at that with go tool trace $somefile
Since so many of the tools are short lived my assumption is that the execution trace will be the most useful.
LMPROF=$somefile
will write a cpu profile to $somefile
; look at that with go tool pprof -http localhost:10123 $somefile
If you have a long running tool, the pprof http endpoint is exposed on
localhost:6060/debug/pprof
but picks a random port if that port is in use; the
port can be overridden by setting LMHTTPPROF=$someport
.
Some tools are annoying to have in the main leatherman tool. Maybe they pull
in deps that are huge or need cgo, but in any case I try to keep them separate.
For now, these tools are under leatherman/cmd
and must be built and run
separately. At some point I may come up with a policy around building or naming these,
but for now they are simply extra tools.