Firefox and Electron apps offer `text/html` first when copying images,
which causes stash to store the HTML wrapper (`<img src="...">`) instead
of the actual image data, which is what we want. We handicap, i.e.,
deprioritize `text/html` in the "any" preference mode and prefer
`image/*` types first, then any non-html type.
This sounds a little illogical, but in user will almost always prefer
the image itself rather than the text representation. So it's intuitive.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: I6bd5969344893e15226c27071442475f6a6a6964
Adds a `db` subcommand with `DbAction` for three new database
operations: wipe, vacuum and stats. We can extend this database later,
but this is a very good start for now and plays nicely with the
`--expired` flag. This soft-deprecates `stash wipe` in favor of a `stash
db wipe` with the addition of a new `--expired` flag that wipes the
expired entries only.
The `list` subcommand has also been refactored to allow for a similar
`--expired` flag that lists only expired entries.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: I34107880185d231d207b0dab7782d5d96a6a6964
The previous `--expire-after` flag behave more like *delete* after
rather than *expire*. This fixes that, and changes the behaviour to
excluding expired entries from list commands and already-marked expired
entries from expiration queue. Updates log messages accordingly.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: Ib162dff3a76e23edcdfbd1af13b01b916a6a6964
Migrates schema to v5; `is_expired` column is added with partial index
and `include_expired` parameter to `list_entries()` and `list_json()`
methods. Also adds `vacuum()` and `stats()` methods for SQlite
"administration", and removes `next_sequence()` from trait and impl.
This has been a valuable addition to stash, as the database is now *less
abstract* in the sense that user is made aware of its presence (stash
wipe -> stash db wipe) and can modify it.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: Icfab67753d7f18e3798c0a930b16d05e6a6a6964
This adds a Neg wrapper struct for min-heap behaviour on BinaryHeap
which has proven *really* valuable. Also modify `watch()` to take the
`expire_after` argument for various new features. See my previous commit
for what is actually new.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: I8705d404eae5d93ad48f738a24f698196a6a6964
Schema v4: add expires_at REAL column with partial index for NULL values
Other relevant methods that were added:
- `now()` for Unix timestamp with sub-second precision
- `cleanup_expired()` to remove all expired entries
- `get_expired_entries()` for for diagnostic output (`stash list --expired`)
- `get_next_expiration()` for heap initialization
- `set_expiration()` to update expiration timestamp
This feature has proven larger than I had anticipated (and hoped) but
that's the reality of dealing with databases. Some of the methods are
slightly redundant but it helps keep tracing the code manageable and
semantically correct. We'll probably not regret those later. Probably.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: Ie9e5b0767673e74389b8e59c466afd946a6a6964
This makes Stash's database handler a bit more robust. The changes
started as me trying to add an entry expiry, but I've realized that the
database system is a little fragile and it assumed the database does not
change, ever. Well that's not true, it does change and when it does
there's a chance that everything implodes.
We now wrap migrations in transaction for atomicity and track version
via PRAGMA user_version (0 -> 3). We also check column existence before
ALTER TABLE and use `last_insert_rowid()` instead of `next_sequence()`.
Last but not least, a bunch of regression tests have been added to the
database system because I'd rather not discover regressions in
production.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: Ifeab42b0816a5161d736767cb82065346a6a6964
Adds a `content_hash` column and index for deduplication, and a
`last_accessed` column & index for time tracking. We now de-duplicate on
copy by not copying if present, but instead bubbling up matching entry.
Signed-off-by: NotAShelf <raf@notashelf.dev>
Change-Id: Icbcdbd6ac28bbb21324785cae30911f96a6a6964