Skip to content

command line bibliography management with fzf and postgresql (linux)

License

Notifications You must be signed in to change notification settings

thjbdvlt/retrolire

Repository files navigation

rétrolire

Command line bibliography management with fzf and PostgreSQL.

Synopsis

retrolire COMMAND [OPTIONS]
command description
list list entries matching criteria.
json export entries in csl-json format.
edit edit the reading note attached to an entry.
open open a file attached to an entry.
file attach a file to an entry.
add add one or more bibliography entries.
quote get a quote and its citation.
refer get a concept and its citation.
cite get the id of an entry (citation key).
tag edit tags attached to an entry.
update edit the value of a field (title, translator, etc.) for an entry.
print print information about entries (all fields, files, notes, tags).
delete delete an entry.

Most commands operate on a single entry (e.g. edit, cite). Some others show information about many (e.g. list). Thus, rétrolire mostly relies upon selection and filter mechanisms. Filtering is done statically through options, while fzf is used as the interactive selection (picking) interface.

options

filters

Filter options define searching criteria. They are added one to another using the logical operator AND. Except for -l, they can be used multiple times.

# Print entries that:
#   - have tags 'poetry' and 'recording'
#   - have been published by 'amsterdam' or 'p.o.l' publisher
retrolire list \
    --tag 'poetry' --tag 'recording' \
    --var 'publisher.amsterdam|p\.o\.l'
option description argument
-v key-value filter on csl variables field=regex
-t search in tags tag
-s search a pattern in reading notes regex
-q search a pattern in quotes regex
-c search a pattern in concepts regex
-l select the last edited entry

there are also two options for logical operators:

short long description
-n --not negates next condition
-o --or next condition is grouped with previous one using the SQL operator OR
# select entries that DO NOT have the tag "_read"
# but that DO have the tag "poetry".
retrolire open --not --tag _read --tag poetry
retrolire open -nt _read -t poetry
# select entries that have tag 'cool' or tag 'magic'.
retrolire -t cool -ot magic
retrolire --tag 'cool' --or --tag 'magic'

fzf interface

option description
-e no fuzzy matching
-p preview pane with information on the entry
-r order entries by last editing
-T show tags in picking interface

misc

option description argument
-? show help
-V show version
-i select an entry by its id id

selection

While filtering through options can use any csl variable (title, translator, publisher, etc.), the selection with fzf only uses variables title and author (if an entry has no author, then its editor or translator). You can call some commands (open, tag, edit and delete) from within the fzf selection interface, using : (for example :delete ). The preview can be toggled using ? (its default state, hidden or nohidden could be defined in config.h.)

notes parsing

When a reading note is modified (or added), its content is parsed to find and extract quotes and concepts.

quotes

If some quotes are found, they are indexed and put in another table: with the command quote, the user can get these quotes (formatted to be put in pandocs-markdown document).

The parsing/extraction requires that the reading note is written in markdown. Only blockquotes are indexed as quotes. Page number can be precised at the end of the quote, in parentheses or in brackets,:

a normal paragraph

> a quote [32]

> another quote (p. 32)

> here too, another quote (32-33)

another normal paragraph

concepts

Reading notes are also parsed in order to find concept definitions (that user can get using concept command). The syntax used is the syntax for definition list in pandoc markdown, with one difference: a concept may only have one definition.

concept
: definition

configuration

The configuration file is ./config.h. The software needs to be recompiled (make && make install) so the changes can be effective.

completion (bash)

The completion script (bash) allows for automatic completion of actions, options, tags, and fields (variables). To use it, source it in the .bashrc.

source ~/.local/share/retrolire/retrolire-completion.bash

installation

git clone https://github.com/thjbdvlt/retrolire retrolire
cd retrolire
make # compile
sudo make install # install retrolire
pipx install . # install some small command line python programs

retrolire does not by itself create a database. you must do it by yourself (the database name must match the name set in config.h) and then you can just pipe the PostgreSQL schema into that empty database:

psql -c 'create database retrolire'
retrolire _schema | psql -d retrolire

In addition to the executable retrolire (installed in /usr/bin), four other executables (python) are installed using pipx:

  • jsonarray2psql: Converts a array of objects json to a table (PostgreSQL).
  • csljson-update: Builds unique ids for a csl-json.
  • csl2psql: Converts a csl-json to a table (PostgreSQL): combines the other two commands (so that the JSON is parsed only once).
  • fetchref: Get a bibtex reference from a DOI or ISBN.

neovim integration

To install the neovim minimal plugin for rétrolire, e.g. with Lazy:

{ 'thjbdvlt/retrolire.nvim', ft = 'markdown' },

Two commands will be available from within neovim: Quote and Cite.

commands

Each command can be called by its complete name or by a small part of it (e.g., ed for edit). All actions (except add) can be used with any options.

cite

Command cite is used to get the ID (citation key) of an entry, for example, to be inserted in a pandoc-markdown document for which footnotes and bibliography will be automatically produced with citeproc.

retrolire cite | xclip -selection clipboard

edit

Edit the reading note of an entry with the program defined as the editor (in config.h).

quote

Command quote outputs a formatted quote.

Unlike cite, the whole quote is output (with the citation key).

open

The open action opens a file associated with an entry. By default, xdg-open to define the software to use (depending on the extension), but it can be changed in the config file.

retrolire open -v 'author.quintane' -v 'publisher.^p\.?o\.?l$'
retrolire open -t '_àlire'

file

The file action adds a file to an entry. It takes the file path as an argument.

# Associate the file './la_maison_de_wittgenstein.pdf' with the entry 'commetti2017'
retrolire add file './la_maison_de_wittgenstein.pdf' -i 'cometti2017'

tag

The tag action edits (in the $EDITOR) the tags of an entry. It takes an optional argument pick that allows selecting (with fzf) tags from the tags already used.

add

The add action adds bibliographic entries from a bibtex or csl-json file, or a single one from a doi, an isbn, or a template to fill.

It requires two arguments:

  • The method: bibtex or json to import multiple entries from a file, doi or isbn to retrieve information of an entry from an identifier, or template to manually fill values from a file already containing the fields.
  • The file (if method is bibtex or json), or the identifier (if doi or isbn). It can be left empty if the method is template.
# Add an entry from DOI
retrolire add doi 10.58282/lht.3619
# Import a bibliography in CSL-JSON format
retrolire add json ../found_bibliography.json
# Create a bibtex file from a template
retrolire add template book

(The filter options are ignored.)

print

The print action shows the information of the chosen bibliography entries. (If no filter option is selected, it displays the entire bibliography. Unlike other options that use filters, there is no selection of an entry with fzf: the json command displays all entries that match the filters.)

retrolire print -l

json

The json action works like list, but the entries are displayed in csl-json format.

retrolire json -v 'author.(la )?rédaction' -t 'enquête'
[
    {
        "id": "larédaction2012",
        "type": "book",
        "title": "Les Berthier: portraits statistiques",
        "author": [{"literal": "La Rédaction"}],
        "issued": {"date-parts": [[2012]]},
        "publisher": "Questions théoriques",
        "title-short": "Les Berthier"
    }
]

update

The update action modifies the value of a field (title, publisher, etc.). It requires an argument (field): the field whose value needs to be updated. The second argument (value) is optional: if absent, the current value will be opened in the $EDITOR to be modified directly; if provided, it is used as the new value.

# Edit in the `$EDITOR` the current title of the entry 'becker2013'
retrolire update "container-title" -i 'becker2013'

doi / isbn

Retrieving bibliographic references from a doi or an isbn is done using the isbnlib library.

dependencies

For the importation to the database in the python command line tools:

To get references from doi/isbn:

Correction, structuring, formatting, and conversion from bibtex to csl-json:

license

License CC BY-NC-SA 4.0

todo / ideas

  • SQLite instead of PostgreSQL.
  • PDF annotations extraction, using pdfannots.
  • Vim plugin (vim script).
  • option -n --not
  • option -o --or
  • call commands from within fzf interface using : (e.g. :delete).
  • bash completion for author names and words in title?