Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dependency Injection docs #195

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion docs/src/main/resources/microsite/data/menu.yml
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ options:
url: docs/effects/Cache/

- title: Dependency Injection
url: TODO.html
url: docs/patterns/dependency-injection

- title: Configuration
url: docs/patterns/config
Expand Down
2 changes: 0 additions & 2 deletions docs/src/main/tut/docs/http/finch.md
Original file line number Diff line number Diff line change
Expand Up @@ -74,8 +74,6 @@ import shapeless.::
We can use a freestyle program within `Endpoint#apply`.

```tut:book
cats.Monad[Future]

val gcdEndpointTwo = get(int :: int) { (a: Int, b: Int) =>
Calc[Calc.Op].gcd(a, b).map(Ok(_))
}
Expand Down
24 changes: 24 additions & 0 deletions docs/src/main/tut/docs/patterns/dependency-injection/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
---
layout: docs
title: Dependency Injection
permalink: /docs/patterns/dependency-injection/
---

## Dependency Injection

Freestyle makes it easy to create programs where the business logic is separated from specific implementation concerns like error handling, configuration, (asynchronous) communication with (remote) services, etc. The business logic is written using the operations from one or more algebras and every algebra by itself is implemented in a handler (interpreter).

As the business logic is built by glueing together simple algebra operations, it is just a pure description and only at the edge of the program (a main method, a http route, a UI handler, etc) a handler is needed, that can translate the description to a more concrete data type. These pure descriptions are also easy to test by supplying an appropriate test handler (eg a simpler one using just `Id`).

If you are using more than one algebra, freestyle makes it easy to execute or translate your resulting program because it will provide a handler for your combined algebra by combining all the individual handlers (see the [modules](/docs/core/modules/)) section).

Pairing up the right interpreter when you want to execute a program happens at compile time, so compiling your projects using freestyle may take a bit longer, but you don't need to worry about something going wrong at runtime.


### Runtime Dependency using Reader

For runtime dependency injection you can use a `Reader` data type.

Freestyle has a [`reader` effect algebra](/docs/effects/#reader), that is used in [the target stack example](/docs/stack/). However there are also cases where you don't want to put this dependency on some environment explicitly in your algebra and then you can use `Reader` or `ReaderT` (`Kleisli`) as part of you target type.

Imagine you are writing a `Persistence` algebra, you would not want to pollute it with implementation details like which connection pool is used to execute the persistence operations.