From 25db146dd5a7692a7b6229555dbf201ac598de3a Mon Sep 17 00:00:00 2001 From: Matthias Beyer Date: Thu, 10 Aug 2017 19:44:19 +0000 Subject: [PATCH] Add architecture (and types) documentation --- doc/src/01010-architecture.md | 68 +++++++++++++++++++++++++++++++++++ 1 file changed, 68 insertions(+) create mode 100644 doc/src/01010-architecture.md diff --git a/doc/src/01010-architecture.md b/doc/src/01010-architecture.md new file mode 100644 index 00000000..6b074c0c --- /dev/null +++ b/doc/src/01010-architecture.md @@ -0,0 +1,68 @@ +# Architecture of the imag code + +The imag codebase has a rather simple overall architecture. But before introducing the reader to it, a few things have to be introduced. + +## Crate types + +There are different types of crates in the imag world. A crate is a rust project. + +First of all, there are core crates. These crates provide the very core of imag and almost all other crates use them: + +* libimagstore - The imag store is the abstraction overbthe filesystem. It provides primitives to get, write and manipulate store entries and their header information. +* libimagrt - The runtime library, which provides functionality to create a store object from libimagstore, helps with configurarion loading and commandline argument handling (through the external "clap" crate). +* libimagerror - Error handling library for handling errors the imag way. Used in all other crates, even the store itself. It also offers functionality to log and trace errors as well as exiting the application, if necessary. +* libimagutil - Utilities. + +The next type of imag crates are entry extension libraries. Those provide extensional functionality for the types from libimagstore. For example, there is "libimagentrylink" which provides functionality to link two entries in the store. + +The next kind of crate is the one that offers end-user functionality for a imag aspect, for example "libimagtodo" provides functionality to track todos. + +And last, but not least, the commandline frontend crates provide the user interface. These are the kind of crates that are not library crates, but binaries. + +## Architecture of an imag module + +With the things from above, a module could have the following architecture: + +``` ++---------------------------------------------+ +| imag-foo | ++-----------------------------------+---------+ +| libimagfoo | | ++-----------------+-----------------+ | +| | | | +| libimagentrybar | libimagentrybaz | | +| | | lib | ++-----------------+-----------------+ | +| | | +| ... | | +| | imag | ++-----------------------------------+ | +| | | +| libimagrt | | +| | error | ++-----------------------------------+ | +| | | +| libimagstore | | +| | | ++-----------------------------------+---------+ +``` + +The foundation of all imag modules is the store, as one can see from the image. Above this there is the libimagrt, which provides the basic runtime and access to the `Store` object. Cross-cutting, there is the error library (and possibly the util library, but we do not care about this one here), which is used through all levels. The highest level of all imag modules is the commandline interface on top of the domain library. +In between can be any number of entry extension libraries, or none if not needed. + +## Types + +The imag core, hence the libimagstore, libimagrt and libimagerror, provide a set of types that a user (as in a library writer) should be aware of. + +First of all, there is the Runtime type which is provided by the libimagrt. It provides basic access to whether debugging or verbosity is enabled as well as the most important core object: The `Store`. + +It is provided by the libimagstore library, the heart of everything. + +When interacting with the store, two types are visible: `FileLockEntry` and `Entry` whereas the former derefs to the latter, which basically means that the former wraps the latter. +The `FileLockEntry` is a necessary wrapper for ensuring that when working concurrently with the store, an entry is only _borrowed_ once from the store. It also ensures that the object is alive as long as the store is. + +The `Entry` type provides functionality like reading the actual content, its header and so on. Extensions for its functionality are implemented on this type, not on the `FileLockEntry`. + +The `Entry` provides access to its header, which is a `toml::Value`, where toml is the toml-rs crate (external project). Conveniance functionality is provided via the `toml-query` crate, which is an external project which was initiated and extracted from the imag project. + +Error types are also important. All errors in the imag prijects are generated by libimagerror usage and are interoperable. User code hardly handles the actual `Error` type but its inner one, `ErrorKind`, which is an enum where each member can be mapped to a representing text. Imag error types do never contain payload (they can via extensions, though it is not really practical and there is no usage for it).