X-Git-Url: https://git.mdrn.pl/wolnelektury.git/blobdiff_plain/6e32f55e3ef50d9f7d3a291c2388c5220851a9b4..86ece3be121fe57d58e76bffcd52713d413cacc1:/doc/architecture.rst diff --git a/doc/architecture.rst b/doc/architecture.rst index fd36de5a6..db5b6989d 100644 --- a/doc/architecture.rst +++ b/doc/architecture.rst @@ -1,40 +1,65 @@ Architecture overview ===================== -Books ------ +Catalogue of books +------------------ -Books are kept in the :py:class:`catalogue.models.Book` model. Dublin Core -metadata, read by :py:mod:`librarian.dcparser.BookInfo`, are put in the -`extra_info` JSON field. +Books are kept in the :py:class:`catalogue.models.Book` model. -Authors, kinds, epochs, genres are kept in :py:class:`catalogue.models.Tag` -model with `category` field set to appriopriate value. +Books have fragments, annotated with themes. Those are kept in the +:py:class:`catalogue.models.Fragment` model. -:py:class:`catalogue.models.Tag` also contains :ref:`user-shelves` -and :ref:`parent-relations`. +Both ``Books`` and ``Fragments`` can have ``Tags``, which are +:py:class:`catalogue.models.Tag` objects. +What are ``Tags`` used for? +--------------------------- -User shelves ------------- +Each ``Tag`` objects has a ``category`` field specyfying its meaning. +The categories are enumerated in :py:const:`catalogue.models.TAG_CATEGORIES`. -User shelves (or tags on user's shelf) are just :py:class:`catalogue.models.Tag` -objects with ``category='set'`` and ``user`` set to the owner. Shelves' slugs -are generated automatically using :py:fun:`catalogue.utils.get_random_hash`. +Tags are used for: +* Keeping browsable metadata. Each ``Book`` can have any number of tags + of categories: ``author``, ``epoch``, ``kind``, ``genre``. + Each ``Fragment`` of a book has all of those, + and also a number of ``theme`` tags. +* User shelves. A User can put a ``Book`` on a shelf and add some labels + by adding a number of ``set`` tags to it. A book put on a shelf without + any labels has a Tag with an empty name. +* Denoting :ref:`ancestor-descendant-relations` using ``book`` tags. -Parent relations ----------------- -The source of parent relations is the -:py:class:`librarian.dcparser.BookInfo.parts` metadata. +.. _ancestor-descendant-relations: -Parent relations are kept primarily in the :py:attribute:`catalogue.models.Book.parent` -and :py:attribute:`catalogue.models.Book.parent_number` fields. +Relations between ``Books``, ``Fragments`` and other ``Books`` +-------------------------------------------------------------- -They're also cached as :py:class:`Tag ` relations. -Each book has its tag (with :py:attribute:`slug ` -starting with ``l-``). All of book's descendants (NOT the book -itself) have its tag attached. +Obviously, every ``Fragment`` comes from a particular ``Book``. This +relation is expressed with the Fragment's ``book`` field. -Arguably, this scheme has some potential for inconsistency. +The source of parent-child relations between ``Books`` is +the ``dc:relation.hasPart`` metadata field, exposed by +:py:class:`librarian.dcparser.BookInfo` as ``parts``. This relation +and the order of children of one parent is expressed with the child +book's ``parent`` and ``parent_number`` fields. + +But aside from that, Tags are used for managing those relationships, too. + +Every ``Book`` has a matching `l-tag`. It's a ``Tag`` of category +``book`` and matching slug with an added 'l-' prefix (the prefix +is superfluous and we should remove it as some point, as it was only +needed when tag slugs had to be unique). + +The `l-tag` of a ``Book`` is used on: + +* all of the book's fragments, +* all of the book's descendants, +* all of the book's descendants' fragments. + +This is used for: + +* finding fragments of a given theme in books with a given user label, +* on a filtered book list (i.e., author's page), for eliminating + descendants, if an ancestor is already on the list, +* when calculating tag book counts, for eliminating descendants as above,