Skip to content

Instantly share code, notes, and snippets.

@kriskowal
Last active March 28, 2020 17:08
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kriskowal/8bff7993712c328d945710800da8c42c to your computer and use it in GitHub Desktop.
Save kriskowal/8bff7993712c328d945710800da8c42c to your computer and use it in GitHub Desktop.
shell memo
#!/bin/bash
# Very slow build step.
sleep 5
jq .+1
#!/bin/bash
time bash -c 'echo 1 | MEMO=inc-memo memo.sh inc.sh' # Slow
time bash -c 'echo 1 | MEMO=inc-memo memo.sh inc.sh' # Fast
#!/bin/bash
# Memoizes a pure command, using git notes.
# $MEMO is the name of the git note.
INPUT=$(git hash-object -w --stdin)
OUTPUT=$(git notes --ref="$MEMO" show "$INPUT" 2>/dev/null) ||
OUTPUT=$(git cat-file blob "$INPUT" | "$@" | git hash-object -w --stdin) &&
git notes --ref="$MEMO" add -f -m "$OUTPUT" "$INPUT" 2>/dev/null
git cat-file blob "$OUTPUT"
@jcorbin
Copy link

jcorbin commented Mar 28, 2020

gist-pro-gist https://gist.github.com/jcorbin/2b6be1f57f26e6068516e6bcb663f411 thoughts:

  • control flow for mortals: there's only so much || and && chaining a body can tolerate ;-)
  • your MEMO variable can just be computed by hashing the the command string
  • there's several "obivous-ish" applications to trees/directories and alternate command calling conventions
  • ...those aspects might probably be especially useful to a project build tool
  • ...but maybe not too much actually since you'd want to memoize at appropriate boundaries

@jcorbin
Copy link

jcorbin commented Mar 28, 2020

The ideas just keep coming:

# TODO support for argv_0 versioning: if the first command arg is a tracked
#      file under the current git repo, then use its sha in place of command
#      name to compute $memo_id

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