Skip to content

Latest commit

 

History

History
190 lines (133 loc) · 6.78 KB

P_README.md

File metadata and controls

190 lines (133 loc) · 6.78 KB

TL;DR: This converts a file like this (config file at ~/.config/ttally.py):

>>>PMARK
#!/usr/bin/env bash
perl -E 'print "`"x3, "python", "\n"'
cat ~/.config/ttally.py
perl -E 'print "`"x3, "\n"'

to (shell aliases)...

>>>PMARK
#!/usr/bin/env bash
perl -E 'print "`"x3, "\n"'
ttally generate
perl -E 'print "`"x3, "\n"'

Whenever I run any of those aliases, it inspects the model in the config file, and on-the-fly creates and runs an interactive interface like this:

... which saves what I enter to a file:

- when: 1598856786,
  glasses": 2.0

ttally

ttally is an interactive module using autotui to save things I do often to YAML/JSON

Currently, I use this to store info like whenever I eat something/drink water/my current weight/thoughts on concerts

Given a NamedTuple defined in ~/.config/ttally.py, this creates interactive interfaces which validates my input and saves it to a file

The {tuple}-now aliases set the any datetime values for the prompted tuple to now

This also gives me {tuple}-recent aliases, which print recent items I've logged. For example:

$ water-recent 5
2021-03-20 18:23:24     2.0
2021-03-20 01:28:27     1.0
2021-03-19 23:34:12     1.0
2021-03-19 22:49:05     1.5
2021-03-19 16:05:34     1.0

The -recent aliases can accept all to print all items, or a duration like 1d or 6h to print data from the last few hours/days.

Why/How

Goals

  • validates my user input to basic types
  • stores it as a user-editable format (YAML)
  • can be loaded into python as typed objects
  • minimal boilerplate to add a new model
  • can be synced across multiple machines without conflicts
  • allow completely custom types or prompts - see autotui docs, my custom prompts

This intentionally uses YAML and doesn't store the info into a single "merged" database. That way:

  • you can just open the YAML file and quickly change/edit some item, no need to re-invent a CRUD interface (though ttally edit-recent does exist)
  • files can be synced across machines and to my phone using syncthing without file conflicts
  • prevents issues with trying to merge multiple databases from different machines together (I've tried)

The YAML files are versioned with the date/OS/platform, so I'm able to add items on my linux, mac, or android (using termux) and sync them across all my devices using SyncThing. Each device creates its own file it adds items to, like:

food-darwin-mbp.localdomain-2021-03.yaml
food-linux-bastion-2021-03.yaml
food-linux-localhost-2021-04.yaml

... which can then be combined back into python, like:

>>> from more_itertools import take  # just to grab a few items
>>> from ttally.__main__ import ext
>>> from ttally.config import Food
>>> take(3, ext.glob_namedtuple(Food))

[Food(when=datetime.datetime(2020, 9, 27, 6, 49, 34, tzinfo=datetime.timezone.utc), calories=440, food='ramen, egg'),
Food(when=datetime.datetime(2020, 9, 27, 6, 52, 16, tzinfo=datetime.timezone.utc), calories=160, food='2 eggs'),
Food(when=datetime.datetime(2020, 9, 27, 6, 53, 44, tzinfo=datetime.timezone.utc), calories=50, food='ginger chai')]

... or into JSON using ttally export food

The from-json command can be used to send this JSON which matches a model, i.e. providing a non-interactive interface to add items, in case I want to call this from a script

hpi query from HPI can be used with the ttally.__main__ module, like:

# how many calories in the last day
$ hpi query ttally.__main__.food --recent 1d -s | jq -r '(.quantity)*(.calories)' | datamash sum 1
2252

If you'd prefer to use JSON files, you can set the TTALLY_EXT=json environment variable.

This can load data from YAML or JSON (or both at the same time), every couple months I'll combine all the versioned files to a single merged file using the merge command:

ttally merge food

Installation

pip install ttally  # can use 'pip install ttally[optional]' for extra features
>>>PMARK
#!/usr/bin/env bash
perl -E 'print "`"x3, "\n"'
python3 -m ttally --help
perl -E 'print "`"x3, "\n"'

Configuration

You need to setup a ~/.config/ttally.py file. You can use the block above as a starting point, or with mine:

curl -s 'https://purarue.xyz/d/ttally.py' > ~/.config/ttally.py

To setup aliases; You can do it each time you launch you terminal like:

eval "$(python3 -m ttally generate)"

Or, 'cache' the generated aliases by putting a block like this in your shell config:

TTALLY_ALIASES="${HOME}/.cache/ttally_aliases"
if [[ ! -e "${TTALLY_ALIASES}" ]]; then  # alias file doesn't exist
	python3 -m ttally generate >"${TTALLY_ALIASES}"  # generate and save the aliases
fi
source "${TTALLY_ALIASES}"  # make aliases available in your shell

i.e., it runs the first time I open a terminal, but then stays the same until I remove the file

You can set the TTALLY_DATA_DIR environment variable to the directory that ttally should save data to, defaults to ~/.local/share/ttally. If you want to use a different path for configuration, you can set the TTALLY_CFG to the absolute path to the file.

For shell completion to autocomplete options/model names:

eval "$(_TTALLY_COMPLETE=bash_source ttally)"  # in ~/.bashrc
eval "$(_TTALLY_COMPLETE=zsh_source ttally)"  # in ~/.zshrc
eval "$(_TTALLY_COMPLETE=fish_source ttally)"  # in ~/.config/fish/config.fish

Caching

ttally update-cache can be used to speedup the export and recent commands:

>>>PMARK
perl -E 'print "`"x3, "\n"'
python3 -m ttally update-cache --help
perl -E 'print "`"x3, "\n"'

I run this using entr whenever the data files change. In the background, like:

find ~/data/ttally -type f | entr -n ttally update-cache

Default cache directory can be overwritten with the TTALLY_CACHE_DIR environment variable

Subclassing/Extension

The entire ttally library/CLI can also be subclassed/extended for custom usage, by using ttally.core.Extension class and wrap_cli to add additional click commands. For an example, see flipflop.py

Shell Scripts

cz lets me fuzzy select something I've eaten in the past using fzf, like: