|
| 1 | +--- |
| 2 | +id: mapref |
| 3 | +title: MapRef |
| 4 | +--- |
| 5 | + |
| 6 | +A total map from a key to a `Ref` of its value. |
| 7 | + |
| 8 | +```scala mdoc:silent |
| 9 | +import cats.effect.Ref |
| 10 | + |
| 11 | +trait MapRef[F[_], K, V] { |
| 12 | + |
| 13 | + /** |
| 14 | + * Access the reference for this Key |
| 15 | + */ |
| 16 | + def apply(k: K): Ref[F, V] |
| 17 | +} |
| 18 | +``` |
| 19 | + |
| 20 | +It is conceptually similar to a `Ref[F, Map[K, V]]`, |
| 21 | +but with better ergonomics when working on a per key basis. |
| 22 | +Note, however, that it does not support atomic updates to multiple keys. |
| 23 | + |
| 24 | +Additionally, some implementations also provide less contention: |
| 25 | +since all operations are performed on individual key-value pairs, |
| 26 | +the pairs can be sharded by key. |
| 27 | +Thus, multiple concurrent updates may be executed independently to each other, |
| 28 | +as long as their keys belong to different shards. |
| 29 | + |
| 30 | +### In-Memory database |
| 31 | + |
| 32 | +This is probably one of the most common uses of this datatype. |
| 33 | + |
| 34 | +```scala mdoc:reset:silent |
| 35 | +//> using lib "org.typelevel::cats-effect::3.5.2" |
| 36 | + |
| 37 | +import cats.effect.IO |
| 38 | +import cats.effect.std.MapRef |
| 39 | + |
| 40 | +trait DatabaseClient[F[_], Id, Data] { |
| 41 | + def getDataById(id: Id): F[Option[Data]] |
| 42 | + def upsertData(id: Id, data: Data): F[Unit] |
| 43 | +} |
| 44 | + |
| 45 | +object DatabaseClient { |
| 46 | + def inMemory[Id, Data]: IO[DatabaseClient[IO, Id, Data]] = |
| 47 | + MapRef.ofShardedImmutableMap[IO, Id, Data]( |
| 48 | + shardCount = 5 // Arbitrary number of shards just for demonstration. |
| 49 | + ).map { mapRef => |
| 50 | + new DatabaseClient[IO, Id, Data] { |
| 51 | + override def getDataById(id: Id): IO[Option[Data]] = |
| 52 | + mapRef(id).get |
| 53 | + |
| 54 | + override def upsertData(id: Id, data: Data): IO[Unit] = |
| 55 | + mapRef(id).update(_ => Some(data)) |
| 56 | + } |
| 57 | + } |
| 58 | +} |
| 59 | +``` |
0 commit comments