Add documentation in README
This commit is contained in:
parent
47f3806825
commit
439326e1b6
|
@ -2,35 +2,105 @@
|
||||||
|
|
||||||
A Ruby gem for scripting imag modules.
|
A Ruby gem for scripting imag modules.
|
||||||
|
|
||||||
This crate contains both the Rust bindings for imag using `ruru` and a bunch of
|
## How does this work?
|
||||||
wrapper code for the actual `imag` gem.
|
|
||||||
|
|
||||||
## Why another layer of indirection?
|
Well, as we have some problems with lifetimes here, we have a fairly complex
|
||||||
|
codebase in this crate.
|
||||||
|
|
||||||
As "ruru" does not yet support modules, which is sad btw, we would end up with
|
### The Problem
|
||||||
|
|
||||||
|
The Problem is, that `libimagstore::store::FileLockEntry<'a>` has a lifetime. If
|
||||||
|
we would wrap this object into a ruru wrapper and pass to the Ruby code, we
|
||||||
|
couldn't guarantee anymore that the lifetime holds.
|
||||||
|
|
||||||
|
The problem is simple, you see...
|
||||||
|
|
||||||
|
### The solution?
|
||||||
|
|
||||||
|
Never pass anything to the Ruby code.
|
||||||
|
|
||||||
|
Yes, exactly. The Ruby code only sees 'handles'. It never actually gets the
|
||||||
|
`Store` object either.
|
||||||
|
We move the `Store` Object into a `Cache` object (actually, the Ruby code could
|
||||||
|
have multiple `Store` objects to work with this way) and return a `StoreHandle`
|
||||||
|
to the Ruby code (which is a UUID underneath).
|
||||||
|
|
||||||
|
Also, the Ruby code never actually touches a `FileLockEntry` - it only gets a
|
||||||
|
Handle for each `FileLockEntry` - which is a tuple of the `StoreHandle` and the
|
||||||
|
`libimagstore::storeid::StoreId` for the Entry.
|
||||||
|
|
||||||
|
Each operation on a `FileLockEntry` is then wrapped by this very library. Each
|
||||||
|
time `FileLockEntry` is touched, this library fetches the appropriate `Store`
|
||||||
|
object from the static `Cache`, then fetches the `FileLockEntry` object from it,
|
||||||
|
does the operation and then drops the object (which implies that the actual
|
||||||
|
`FileLockEntry` is `update()`d!).
|
||||||
|
|
||||||
|
### The Hell?
|
||||||
|
|
||||||
|
Yes, I know this is a lot of overhead. But what are we talking about here? This
|
||||||
|
is Ruby code we're talking about here, so speed is not our concern.
|
||||||
|
|
||||||
|
You could argue this is a hell of complexity introduced in this library and yes
|
||||||
|
it is.
|
||||||
|
If there are bugs (and I bet there are) they would be complex as hell.
|
||||||
|
But that's it... if you have a better approach, please file a PR.
|
||||||
|
|
||||||
|
## Tests?
|
||||||
|
|
||||||
|
We have tests Ruby scripts in `./test`, they are not executed by travis-ci, as
|
||||||
|
we need Ruby `2.3.0` for this and travis has `2.2.0` as latest version.
|
||||||
|
But I hope we get it in travis soonish.
|
||||||
|
|
||||||
|
## Ruby gem?
|
||||||
|
|
||||||
|
This crate will contain both the Rust bindings for imag using `ruru` and a bunch
|
||||||
|
of wrapper code for the actual `imag` gem.
|
||||||
|
|
||||||
|
We are not there yet, though.
|
||||||
|
|
||||||
|
### Why another layer of indirection?
|
||||||
|
|
||||||
|
As "ruru" does not yet support modules (which is sad btw) we would end up with
|
||||||
functions for all the things.
|
functions for all the things.
|
||||||
|
|
||||||
E.G.: `imag_runtime_setup()` instead of `IMAG::Runtime::setup()`
|
E.G.: `imag_runtime_setup()` instead of `Imag::Runtime::setup()`
|
||||||
|
|
||||||
I want to add a Ruby gem to wrap these things.
|
I want to add a Ruby gem to wrap these things.
|
||||||
So basically a piece of ruby which uses `imag.rb` (the Rust gem) to build
|
|
||||||
|
So basically a piece of Ruby which uses `imag.rb` (the Rust gem) to build
|
||||||
`imag` as a gem which then exports a fine module system.
|
`imag` as a gem which then exports a fine module system.
|
||||||
|
|
||||||
## Ideas for module system:
|
### Ideas for module system:
|
||||||
|
|
||||||
```text
|
```text
|
||||||
IMAG (Module)
|
Imag (Module)
|
||||||
Runtime (Module)
|
Runtime (Class)
|
||||||
Runtime (Class)
|
Store (Class)
|
||||||
Store (Module)
|
Entry (Class)
|
||||||
Store (Class)
|
EntryHeader (Class)
|
||||||
Entry (Class)
|
EntryContent (Class (inherits from String))
|
||||||
StoreId (Class)
|
StoreId (Class)
|
||||||
Util (Module, Ruby-only I guess)
|
|
||||||
```
|
```
|
||||||
|
|
||||||
I would name the types the same as in the Rust codebase, to avoid confusion.
|
I would name the types the same as in the Rust codebase, to avoid confusion.
|
||||||
Only exception would be the `Entry` class, which would be a `FileLockEntry`
|
Only exception would be the `Entry` class, which would be a `FileLockEntry`
|
||||||
underneath and if we adapt `libimagentrytag` and the other `libimagentry*`
|
underneath.
|
||||||
|
|
||||||
|
If we adapt `libimagentrytag` and the other `libimagentry*`
|
||||||
libraries, we would extend this type.
|
libraries, we would extend this type.
|
||||||
|
|
||||||
|
## More plans
|
||||||
|
|
||||||
|
I want to pull these libraries into the Ruby bindings:
|
||||||
|
|
||||||
|
* libimagentryedit
|
||||||
|
* libimagentryfilter
|
||||||
|
* libimagentrylink
|
||||||
|
* libimagentrylist
|
||||||
|
* libimagentrymarkdown
|
||||||
|
* libimagentrytag
|
||||||
|
* libimagentryview
|
||||||
|
|
||||||
|
Which all provide functions on top of `libimagstore::store::{FileLock,}Entry`,
|
||||||
|
so we will implement them on `Imag::Entry`.
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue