Скрипт управлява bea с четири решения: кой ledger чете, --json за машинно-четим изход, jq за стойността, от която се нуждае, и exit кода, по който се разклонява. Това ръководство преминава през тези четири решения от начало до край, след което ги планира.
Трябва ви bea на машината, която изпълнява задачата, и ledger, до който може да достигне. Ако започвате нови книги, следвайте CLI бърз старт първо. Всеки факт за флагове, ключове на обвивката и exit кодове се проверява в Beancount CLI справка, а не се повтаря тук.
Изберете ledger-а изрично
Посочете файла. Локална команда разрешава своята цел от --file, след това от $BEA_FILE, след това от ./main.bean в работната директория, а планирана задача рядко се изпълнява там, където мислите.
bea --file ~/books/main.bean check
BEA_FILE=~/books/main.bean bea check
cd ~/books && bea checkГлобалните опции отиват преди командата, както в bea --file main.bean check. Ако разрешеният файл не съществува, командата излиза с 2 и изброява всичките три източника, така че правописна грешка в cron запис се проваля шумно, вместо да валидира грешните книги. Хостирано насочване чрез --ledger флаг все още не съществува; bea никога не качва локален файл имплицитно.
Прочетете JSON обвивката
Добавете глобален --json и всяка поддържана команда отговаря със същата обвивка: bea, target, data, truncated и limit на ограничени списъци. Сумите са десетични низове, а датите са ISO YYYY-MM-DD, така че стойност е безопасна за сравнение, без float някога да влезе в тръбопровода. Ключовете на обвивката са таблично представени в JSON и exit код справка.
bea --json --file main.bean report income-statement | jq .data.net_profit
bea --json --file main.bean list transaction --limit 2 | jq '.data[0].postings[0].units'
bea --json --file main.bean import statement.csv --csv date=Date,amount=Amount,payee=Payee \
--account Assets:Checking --apply --duplicates skip | jq '.data | {written, ready, duplicates}'Тези три команди — report, list и import — запазват своите форми на резултати, така че jq път, написан срещу тях, остава валиден. bea --json check и bea --json query също издават обвивката днес, но те са командите, които се предават на родните Beancount изпълними файлове, така че скрипт трябва да се фокусира върху exit статуса на check, а не върху формата на неговия изход. Изберете вашата политика за дубликати умишлено: --duplicates все още е задължителен, когато импорт се нуждае от решение, както прегледът на импорт обяснява.
Спрете на правилния exit код
Разклонявайте се по статуса и прочетете обекта за греща, преди да опитате отново нещо, което записва. В --json режим неуспех не записва нищо на stdout и точно един обект на stderr, чийто error.category назовава класа: validation (1), usage (2), auth (3), conflict (4).
#!/usr/bin/env bash
set -euo pipefail
out=$(mktemp)
err=$(mktemp)
status=0
bea --json --file main.bean report income-statement >"$out" 2>"$err" || status=$?
case "$status" in
0) jq -r '.data.net_profit | to_entries[] | "net profit: \(.value) \(.key)"' "$out" ;;
4) echo "conflict — inspect the ledger before retrying" >&2
jq -r '.error.message' "$err" >&2
exit 4 ;;
*) jq -r '.error | "\(.category) (exit \(.exit_code)): \(.message)"' "$err" >&2
exit "$status" ;;
esacExit 4 е този, който скрипт никога не трябва да повтаря сляпо: той означава, че резултатът е конфликт или е неизвестен, като външна редакция, пристигаща по средата на запис, или init цел, която вече съществува. Проверете ledger-а, след това опитайте отново от свежо четене. Exit 1 покрива грешки при валидиране и всяка друга грешка по време на изпълнение; error.details носи индивидуалните грешки на ledger-а, а error.result носи какво всъщност е направил частичен запис. Ненулев exit никога не гарантира, че нищо не се е променило.
Изпълнете без терминал
bea спира да подканва самостоятелно. --no-input се подразбира винаги, когато stdin не е терминал, винаги, когато --json е зададен, и винаги, когато CI е истина — 1, true, yes или on. В този режим липсващо потвърждение се проваля с exit 2, вместо да чака вечно.
CI=true BEA_NO_UPDATE_NOTIFIER=1 bea --json --file main.bean report balance-sheet
bea --json --file main.bean list transaction --limit 100 --sort oldestЧетенията са снизходителни в терминал и строги навсякъде другаде. Когато ledger-ът има грешки при зареждане, query, list и report излизат с 1 под --json, под тръбен stdout, под истина CI или с --strict; предайте собствената --allow-errors на командата, за да приемете частичния отговор вместо това, което също задава ledger_valid: false и попълва ledger_errors в JSON. --strict е огледалният образ: той отказва частични отговори дори в терминал, което е това, което искате, когато човек изпълнява същия скрипт на ръка. bea check няма --allow-errors — докладването на грешки е цялата му работа — и винаги излиза с 1, когато намери такива. Задайте BEA_NO_UPDATE_NOTIFIER=1, за да заглушите пасивното известие за актуализация; истина CI вече прави това.
Планирайте проверка
Изпълнявайте валидиране всяка нощ и оставете exit кода да бъде алармата. И двата блока по-долу са шаблони — пътищата, графикът и изпълнителят са ваши.
# crontab -e — 07:15 daily; cron mails you only when bea exits nonzero
15 7 * * * BEA_NO_UPDATE_NOTIFIER=1 /opt/homebrew/bin/bea --file /home/alice/books/main.bean checkname: ledger
on:
schedule:
- cron: "15 7 * * *"
push:
jobs:
check:
runs-on: ubuntu-latest
env:
BEA_NO_UPDATE_NOTIFIER: "1"
steps:
- uses: actions/checkout@v4
- uses: astral-sh/setup-uv@v5
- run: uv tool install beancount-io==0.1.0
- run: bea --file main.bean check
- run: bea --json --file main.bean report balance-sheet > balance-sheet.jsonЗакачете версията, когато задачата трябва да бъде възпроизводима, и махнете закачката, когато предпочитате да следите изданията. CI вече е истина на GitHub Actions, така че подканванията са изключени и известието за актуализация е тихо, преди да зададете нещо. Няма стъпка за форматиране тук умишлено. Планирана задача не трябва да пренаписва файлове, които не е трябвало, така че използвайте bea format --check в pre-commit кука, която не докосва нищо и излиза с 1, когато файл се нуждае от форматиране.
Използвайте хостирано удостоверение в задача
Задайте BEA_TOKEN, от хранилището за тайни на вашия CI доставчик, и пропуснете влизането в браузъра изцяло. Токенът се чете от средата и никога не се записва на диск, така че нищо не попада в домашната директория на изпълнителя за следващата задача да намери.
export BEA_TOKEN="$YOUR_CI_SECRET"
bea --json cloud statusExit 0 означава, че удостоверението е разрешено и обвивката назовава акаунта, към който принадлежи; exit 3 с error.category от auth означава, че не е, и съобщението разграничава незададено удостоверение от отхвърлено. bea cloud logout не прави нищо на токен, предоставен по този начин — нито го отменя, нито го премахва, тъй като друга задача може да го споделя — така че отменете изтекъл токен от таблото вместо това. Локалните команди не се нуждаят от никакво удостоверение; само bea cloud и bea ask достигат до хостираната услуга. Пълният списък с променливи е в справката за настройки.
Не всичко отговаря в JSON. bea ask отхвърля JSON режима напълно, bea cloud login се нуждае от човек, а успешен bea cloud logout или bea cloud ledger clone не връща JSON обект за успех — прочетете техния exit статус вместо това. Помощ, версия и изход за завършване на обвивката остават текстови.
Следващи стъпки
- Автоматизирайте банкови файлове с прегледа на CLI импорт.
- Проверете всеки флаг, ключ на обвивката или exit код в Beancount CLI справка.
- Използвайте Python само когато CLI свърши: вижте скриптируеми работни потоци.