mirror of
https://github.com/FBukovina/burn-baby-burn.git
synced 2026-10-29 08:04:31 +00:00
Compare commits
No commits in common. "480dbd5c1a4acc17b58c95ec3bce0b8f9535642a" and "d249712b13e808080c14730d709bef68fd0af159" have entirely different histories.
480dbd5c1a
...
d249712b13
4 changed files with 14 additions and 1413 deletions
|
|
@ -26,19 +26,12 @@ Drops `burn` into `~/.local/bin` — no sudo, no Homebrew tap. Needs
|
||||||
## Usage
|
## Usage
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
burn 10000 # the Claude minimum
|
burn 10000 # the minimum
|
||||||
burn 50000 --model haiku # cheap and fast
|
burn 50000 --model haiku # cheap and fast
|
||||||
burn 100000 --model sonnet # walk away
|
burn 100000 --model sonnet # walk away
|
||||||
burn 13000 --backend codex # the Codex minimum
|
|
||||||
burn 50000 --backend codex # 🤖 burn OpenAI tokens
|
burn 50000 --backend codex # 🤖 burn OpenAI tokens
|
||||||
```
|
```
|
||||||
|
|
||||||
Run `burn` with no arguments to open the TUI. When you select OpenAI
|
|
||||||
Codex and press `IGNITE`, the TUI launches the default browser OAuth
|
|
||||||
flow if Codex is not already connected. You can also use the `AUTH` row
|
|
||||||
to recheck or sign in manually, or run `codex login` before opening
|
|
||||||
`burn`. The TUI adjusts the minimum target automatically per backend.
|
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
|
||||||
86
bin/burn
86
bin/burn
|
|
@ -17,8 +17,6 @@ FILLER_TOKENS=1000
|
||||||
CLAUDE_SYSTEM_OVERHEAD_TOKENS=9000 # claude -p with --tools ""
|
CLAUDE_SYSTEM_OVERHEAD_TOKENS=9000 # claude -p with --tools ""
|
||||||
CODEX_SYSTEM_OVERHEAD_TOKENS=12000 # codex exec --sandbox read-only
|
CODEX_SYSTEM_OVERHEAD_TOKENS=12000 # codex exec --sandbox read-only
|
||||||
FILLER_LINE="Burn baby burn, this is a disco inferno, burning tokens is for great engineers. "
|
FILLER_LINE="Burn baby burn, this is a disco inferno, burning tokens is for great engineers. "
|
||||||
TUI_CHILD=0
|
|
||||||
[[ "${BURN_TUI_CHILD:-}" == "1" ]] && TUI_CHILD=1
|
|
||||||
|
|
||||||
usage() {
|
usage() {
|
||||||
cat <<EOF
|
cat <<EOF
|
||||||
|
|
@ -94,20 +92,6 @@ while [[ $# -gt 0 ]]; do
|
||||||
done
|
done
|
||||||
|
|
||||||
if [[ -z "$tokens" ]]; then
|
if [[ -z "$tokens" ]]; then
|
||||||
if [[ -t 0 && -t 1 ]]; then
|
|
||||||
if ! command -v node >/dev/null 2>&1; then
|
|
||||||
echo "error: No token count provided, and 'node' is not installed to launch the TUI." >&2
|
|
||||||
usage >&2
|
|
||||||
exit 2
|
|
||||||
fi
|
|
||||||
if [[ ! -f "$SCRIPT_DIR/tui.js" ]]; then
|
|
||||||
echo "error: TUI entrypoint not found at '$SCRIPT_DIR/tui.js'." >&2
|
|
||||||
usage >&2
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
exec node "$SCRIPT_DIR/tui.js"
|
|
||||||
fi
|
|
||||||
|
|
||||||
usage >&2
|
usage >&2
|
||||||
exit 2
|
exit 2
|
||||||
fi
|
fi
|
||||||
|
|
@ -194,17 +178,7 @@ for ((i = 0; i < repeats; i++)); do
|
||||||
done
|
done
|
||||||
prompt=$(printf "Reply with the single word 'burned' and nothing else. Ignore the filler text below; it exists only to consume tokens.\n\n%s" "$filler")
|
prompt=$(printf "Reply with the single word 'burned' and nothing else. Ignore the filler text below; it exists only to consume tokens.\n\n%s" "$filler")
|
||||||
|
|
||||||
if ((TUI_CHILD)); then
|
if [[ -t 1 ]]; then
|
||||||
ORANGE=''
|
|
||||||
MAGENTA=''
|
|
||||||
CYAN=''
|
|
||||||
RED=''
|
|
||||||
YELLOW=''
|
|
||||||
DIM=''
|
|
||||||
RESET=''
|
|
||||||
HIDE_CURSOR=''
|
|
||||||
SHOW_CURSOR=''
|
|
||||||
elif [[ -t 1 || -n "${FORCE_COLOR:-}" || -n "${CLICOLOR_FORCE:-}" ]]; then
|
|
||||||
ORANGE=$'\033[1;33m'
|
ORANGE=$'\033[1;33m'
|
||||||
MAGENTA=$'\033[1;35m'
|
MAGENTA=$'\033[1;35m'
|
||||||
CYAN=$'\033[1;36m'
|
CYAN=$'\033[1;36m'
|
||||||
|
|
@ -345,7 +319,6 @@ total_cost=0.000000
|
||||||
BAR_WIDTH=30
|
BAR_WIDTH=30
|
||||||
cli_pid=""
|
cli_pid=""
|
||||||
last_output=""
|
last_output=""
|
||||||
last_error=""
|
|
||||||
|
|
||||||
# Build CLI command for the chosen backend.
|
# Build CLI command for the chosen backend.
|
||||||
case "$backend" in
|
case "$backend" in
|
||||||
|
|
@ -394,13 +367,6 @@ draw_bar() {
|
||||||
local pct filled empty bar="" i suffix="${1:-}"
|
local pct filled empty bar="" i suffix="${1:-}"
|
||||||
pct=$((burned * 100 / tokens))
|
pct=$((burned * 100 / tokens))
|
||||||
((pct > 100)) && pct=100
|
((pct > 100)) && pct=100
|
||||||
|
|
||||||
if ((TUI_CHILD)); then
|
|
||||||
printf 'BURN_PROGRESS\t%d\t%d\t%d\t%s\t%d\t%s\n' \
|
|
||||||
"$pct" "$burned" "$tokens" "$(format_cost_field)" "$iteration" "$suffix"
|
|
||||||
return
|
|
||||||
fi
|
|
||||||
|
|
||||||
filled=$((pct * BAR_WIDTH / 100))
|
filled=$((pct * BAR_WIDTH / 100))
|
||||||
empty=$((BAR_WIDTH - filled))
|
empty=$((BAR_WIDTH - filled))
|
||||||
for ((i = 0; i < filled; i++)); do bar+='█'; done
|
for ((i = 0; i < filled; i++)); do bar+='█'; done
|
||||||
|
|
@ -465,67 +431,31 @@ trap on_interrupt INT
|
||||||
# Run one CLI call in the background while animating flames. On success
|
# Run one CLI call in the background while animating flames. On success
|
||||||
# leaves the parsed stdout in $last_output. Returns the CLI exit status.
|
# leaves the parsed stdout in $last_output. Returns the CLI exit status.
|
||||||
run_cli() {
|
run_cli() {
|
||||||
local output_file error_file
|
local output_file
|
||||||
output_file=$(mktemp)
|
output_file=$(mktemp)
|
||||||
error_file=$(mktemp)
|
|
||||||
# </dev/null prevents codex from waiting on stdin when run in background.
|
# </dev/null prevents codex from waiting on stdin when run in background.
|
||||||
"${cli_cmd[@]}" "$prompt" >"$output_file" 2>"$error_file" </dev/null &
|
"${cli_cmd[@]}" "$prompt" >"$output_file" 2>/dev/null </dev/null &
|
||||||
cli_pid=$!
|
cli_pid=$!
|
||||||
|
|
||||||
local frame=0
|
local frame=0
|
||||||
while kill -0 "$cli_pid" 2>/dev/null; do
|
while kill -0 "$cli_pid" 2>/dev/null; do
|
||||||
if ! ((TUI_CHILD)); then
|
|
||||||
redraw_disco $((frame % 4))
|
redraw_disco $((frame % 4))
|
||||||
fi
|
|
||||||
frame=$((frame + 1))
|
frame=$((frame + 1))
|
||||||
sleep 0.4
|
sleep 0.4
|
||||||
done
|
done
|
||||||
|
|
||||||
if wait "$cli_pid" 2>/dev/null; then
|
if wait "$cli_pid" 2>/dev/null; then
|
||||||
last_output=$(<"$output_file")
|
last_output=$(<"$output_file")
|
||||||
last_error=""
|
rm -f "$output_file"
|
||||||
rm -f "$output_file" "$error_file"
|
|
||||||
cli_pid=""
|
cli_pid=""
|
||||||
return 0
|
return 0
|
||||||
else
|
else
|
||||||
last_error=$(<"$error_file")
|
rm -f "$output_file"
|
||||||
rm -f "$output_file" "$error_file"
|
|
||||||
cli_pid=""
|
cli_pid=""
|
||||||
return 1
|
return 1
|
||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
last_error_summary() {
|
|
||||||
awk '
|
|
||||||
NF {
|
|
||||||
line = $0
|
|
||||||
}
|
|
||||||
END {
|
|
||||||
gsub(/\t/, " ", line)
|
|
||||||
gsub(/\r/, "", line)
|
|
||||||
print line
|
|
||||||
}
|
|
||||||
' <<<"$last_error"
|
|
||||||
}
|
|
||||||
|
|
||||||
report_backend_failure() {
|
|
||||||
local err message
|
|
||||||
err=$(last_error_summary)
|
|
||||||
message="two consecutive ${backend} calls failed; aborting."
|
|
||||||
if [[ -n "$err" ]]; then
|
|
||||||
message="${message} Last error: ${err}"
|
|
||||||
fi
|
|
||||||
|
|
||||||
if ((TUI_CHILD)); then
|
|
||||||
printf 'BURN_ERROR\t%s\n' "$message"
|
|
||||||
fi
|
|
||||||
|
|
||||||
printf "\nerror: two consecutive %s calls failed; aborting.\n" "$backend" >&2
|
|
||||||
if [[ -n "$err" ]]; then
|
|
||||||
printf "last %s error: %s\n" "$backend" "$err" >&2
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
# Parse one CLI call's output into "<tokens> <cost>" (tab-separated).
|
# Parse one CLI call's output into "<tokens> <cost>" (tab-separated).
|
||||||
parse_usage() {
|
parse_usage() {
|
||||||
case "$backend" in
|
case "$backend" in
|
||||||
|
|
@ -559,14 +489,10 @@ parse_usage() {
|
||||||
esac
|
esac
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((TUI_CHILD)); then
|
|
||||||
:
|
|
||||||
else
|
|
||||||
printf '%s' "$HIDE_CURSOR"
|
printf '%s' "$HIDE_CURSOR"
|
||||||
echo
|
echo
|
||||||
draw_disco 0
|
draw_disco 0
|
||||||
echo
|
echo
|
||||||
fi
|
|
||||||
draw_bar
|
draw_bar
|
||||||
|
|
||||||
while ((burned < tokens)); do
|
while ((burned < tokens)); do
|
||||||
|
|
@ -575,7 +501,7 @@ while ((burned < tokens)); do
|
||||||
if ! run_cli; then
|
if ! run_cli; then
|
||||||
draw_bar " (retrying)"
|
draw_bar " (retrying)"
|
||||||
if ! run_cli; then
|
if ! run_cli; then
|
||||||
report_backend_failure
|
printf "\nerror: two consecutive %s calls failed; aborting.\n" "$backend" >&2
|
||||||
exit 1
|
exit 1
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
|
|
||||||
1316
bin/tui.js
1316
bin/tui.js
File diff suppressed because it is too large
Load diff
|
|
@ -10,15 +10,13 @@ mkdir -p "$DEST_DIR"
|
||||||
curl -fsSL "$BASE_URL/burn" -o "$DEST_DIR/burn"
|
curl -fsSL "$BASE_URL/burn" -o "$DEST_DIR/burn"
|
||||||
# Sourced by burn when using --backend codex to compute estimated cost.
|
# Sourced by burn when using --backend codex to compute estimated cost.
|
||||||
curl -fsSL "$BASE_URL/codex_rates.sh" -o "$DEST_DIR/codex_rates.sh"
|
curl -fsSL "$BASE_URL/codex_rates.sh" -o "$DEST_DIR/codex_rates.sh"
|
||||||
curl -fsSL "$BASE_URL/tui.js" -o "$DEST_DIR/tui.js"
|
chmod +x "$DEST_DIR/burn"
|
||||||
chmod +x "$DEST_DIR/burn" "$DEST_DIR/tui.js"
|
|
||||||
|
|
||||||
echo "✅ installed burn → $DEST_DIR/burn"
|
echo "✅ installed burn → $DEST_DIR/burn"
|
||||||
|
|
||||||
case ":${PATH}:" in
|
case ":${PATH}:" in
|
||||||
*":${DEST_DIR}:"*)
|
*":${DEST_DIR}:"*)
|
||||||
echo "🔥 ready to go: run 'burn 10000' to torch some tokens."
|
echo "🔥 ready to go: run 'burn 10000' to torch some tokens."
|
||||||
echo "🕹️ or run 'burn' with no arguments to open the TUI."
|
|
||||||
;;
|
;;
|
||||||
*)
|
*)
|
||||||
echo
|
echo
|
||||||
|
|
@ -27,6 +25,6 @@ case ":${PATH}:" in
|
||||||
echo
|
echo
|
||||||
echo " export PATH=\"\$HOME/.local/bin:\$PATH\""
|
echo " export PATH=\"\$HOME/.local/bin:\$PATH\""
|
||||||
echo
|
echo
|
||||||
echo " then reload your shell and run 'burn 10000' or just 'burn' for the TUI."
|
echo " then reload your shell and run 'burn 10000'."
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue