You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
This repository was archived by the owner on Aug 1, 2023. It is now read-only.
Copy file name to clipboardExpand all lines: ARCHITECTURE.md
+7-7Lines changed: 7 additions & 7 deletions
Original file line number
Diff line number
Diff line change
@@ -23,7 +23,7 @@ For example, let's suppose we want to create a very simple logging/monitoring _f
23
23
We see that the _feature_ requires a specific *configuration and has some global exception handling*.
24
24
The specific configuration can be something really specific to logging, for example. We may need to read the default log level, whether it's info, debug, warn or something else - we need to define the level of information we want to save in the logs. For that, we require a specific configuration. That configuration is not part of the default configuration we usually parse when we start the _cardano-shell_ - when we parse the initial key configuration, we parse what *every feature requires*, not
25
25
something specific for each _feature_.
26
-
Then we have the _feature_ ready for usage and we can use the functions it contains. We will restrict this a bit later, but for now, let's suppose we can use all the functions in the module export.
26
+
Then we have the _feature_ ready for usage and we can use the functions it contains. We will restrict this a bit later, but for now, let's suppose we can use all the functions in the module export.
27
27
And so, all is well. We are done! But wait! What about the other _features_? Ok, so I lied, we are not done. We need to able to communicate with the other nodes. What do we need for that? Networking! So we need to construct the _networking feature_. And what does networking use? It uses loggging! How does that look like?
When we complete the construction of this logging/monitoring _feature_, we get the initialized _layer_, which is the interface toward the _feature_. It's essentially a record of functions.
53
+
When we complete the construction of this logging/monitoring _feature_, we get the initialized _layer_, which is the interface toward the _feature_. It's essentially a record of functions.
54
54
Let's make this a bit more concrete. Let's say we have an extremely simple interface for _logging_ and all we want our users (developers) to use is this:
55
55
```
56
56
logInfo :: Text -> IO ()
@@ -87,7 +87,7 @@ I lied again. I simplified it a bit. If you take a look at the actual _layer_ ex
In the example, we suppose that the interface is abstract (the `m` type is abstract) and we later on define it to be `forall m. (MonadIO m, MonadLog m) => m`, so an _mtl style effect_ which has two constraints on it - it can log and do IO, which sounds good. But there is nothing perfect and there are trade-offs everywhere. Even in our nice little example. How?
90
-
Let me show you. The abstract type is now constrained by two types - `MonadIO` and `MonadLog`.
90
+
Let me show you. The abstract type is now constrained by two types - `MonadIO` and `MonadLog`.
0 commit comments