dev.constructive.eo.laws.eo

Laws specific to eo's composition machinery rather than any single optic (ComposeLaws):

  • capability-keyed compose-coherence — get / getOption / foldMap / reverseGet each distribute through andThen (Composed*Laws), stated once per capability and reused across every family and cross-family cell that admits it;
  • andThen associativity for modify (and get on total-read carriers) (ComposeAssociativityLaws) — the identity unit law is intentionally absent because core ships no identity-optic constructor to compose against;
  • the per-family pair laws (LensComposeLaws / IsoComposeLaws / PrismComposeLaws / OptionalComposeLaws), which now delegate their shared members to the capability layer;

plus fold/traverse consistency, modifyA coherence, reverse/transform round-trips, and Morph faithfulness.

Attributes

Members list

Packages

Discipline RuleSet bundles for the composition-machinery laws in dev.constructive.eo.laws.eo.

Discipline RuleSet bundles for the composition-machinery laws in dev.constructive.eo.laws.eo.

Attributes

Type members

Classlikes

trait ComposeAssociativityLaws[S, A, F[_, _]]

Associativity of andThen: the two bracketings of a three-optic chain behave identically. The spec materialises both leftNested = (a ∘ b) ∘ c and rightNested = a ∘ (b ∘ c) because the law trait can't call .andThen itself (the carrier's leftover X is abstract here — the same reason dev.constructive.eo.laws.typeclass.AssociativeFunctorLaws takes a materialised composed).

Associativity of andThen: the two bracketings of a three-optic chain behave identically. The spec materialises both leftNested = (a ∘ b) ∘ c and rightNested = a ∘ (b ∘ c) because the law trait can't call .andThen itself (the carrier's leftover X is abstract here — the same reason dev.constructive.eo.laws.typeclass.AssociativeFunctorLaws takes a materialised composed).

  • associativeModify holds for any ForgetfulFunctor[F] carrier.
  • associativeGet additionally requires Accessor[F] (a total-read carrier).

No andThen identity unit law (o ∘ id == o == id ∘ o) is stated: core ships no identity-optic constructor (no Iso.id / Optic.id), so there is nothing lawful to compose against. Add the unit law here if such a constructor lands.

Attributes

Source
ComposeLaws.scala
Supertypes
class Object
trait Matchable
class Any
trait ComposedFoldMapLaws[S, A, B]

Compose-coherence for folding. For composed = outer.andThen(inner), composed.foldMap(f)(s) == outer.foldMap(a => inner.foldMap(f)(a))(s) — folding the whole chain equals folding each outer focus through the inner fold. Keyed by CanFold on all three legs (every readable family; the primary surface of Fold and Traversal).

Compose-coherence for folding. For composed = outer.andThen(inner), composed.foldMap(f)(s) == outer.foldMap(a => inner.foldMap(f)(a))(s) — folding the whole chain equals folding each outer focus through the inner fold. Keyed by CanFold on all three legs (every readable family; the primary surface of Fold and Traversal).

Attributes

Source
ComposeLaws.scala
Supertypes
class Object
trait Matchable
class Any
trait ComposedGetLaws[S, A, B]

Compose-coherence for total read. For composed = outer.andThen(inner), composed.get(s) == inner.get(outer.get(s)) — reading through the whole chain equals reading the outer focus, then the inner. Keyed by CanGet on all three legs (Lens / Iso / Getter and their total-read composites).

Compose-coherence for total read. For composed = outer.andThen(inner), composed.get(s) == inner.get(outer.get(s)) — reading through the whole chain equals reading the outer focus, then the inner. Keyed by CanGet on all three legs (Lens / Iso / Getter and their total-read composites).

Attributes

Source
ComposeLaws.scala
Supertypes
class Object
trait Matchable
class Any
Known subtypes
trait IsoComposeLaws[S, A, B]
trait LensComposeLaws[S, A, B]
trait ComposedGetOptionLaws[S, A, B]

Compose-coherence for partial read. For composed = outer.andThen(inner), composed.getOption(s) == outer.getOption(s).flatMap(inner.getOption) — the Kleisli law over Option. Keyed by CanGetOption on all three legs (Prism / Optional / AffineFold and their partial-read composites).

Compose-coherence for partial read. For composed = outer.andThen(inner), composed.getOption(s) == outer.getOption(s).flatMap(inner.getOption) — the Kleisli law over Option. Keyed by CanGetOption on all three legs (Prism / Optional / AffineFold and their partial-read composites).

Attributes

Source
ComposeLaws.scala
Supertypes
class Object
trait Matchable
class Any
Known subtypes
trait OptionalComposeLaws[S, A, B]
trait PrismComposeLaws[S, A, B]
trait ComposedReverseGetLaws[S, A, B]

Compose-coherence for building. For composed = outer.andThen(inner), composed.reverseGet(c) == outer.reverseGet(inner.reverseGet(c)) — building through the chain equals building the inner focus, then re-homing it via the outer. Keyed by CanReverseGet on all three legs (Iso / Prism / Review and their build composites).

Compose-coherence for building. For composed = outer.andThen(inner), composed.reverseGet(c) == outer.reverseGet(inner.reverseGet(c)) — building through the chain equals building the inner focus, then re-homing it via the outer. Keyed by CanReverseGet on all three legs (Iso / Prism / Review and their build composites).

Attributes

Source
ComposeLaws.scala
Supertypes
class Object
trait Matchable
class Any
Known subtypes
trait IsoComposeLaws[S, A, B]
trait PrismComposeLaws[S, A, B]
trait FoldMapHomomorphismLaws[S, A, F[_, _]]

E1 — optic.foldMap is a Monoid homomorphism on the target monoid (tested at Int with additive Monoid[Int], which is enough to witness the law).

E1 — optic.foldMap is a Monoid homomorphism on the target monoid (tested at Int with additive Monoid[Int], which is enough to witness the law).

Attributes

Source
FoldAndTraverseLaws.scala
Supertypes
class Object
trait Matchable
class Any
trait IsoComposeLaws[S, A, B] extends ComposedGetLaws[S, A, B], ComposedReverseGetLaws[S, A, B]

C3/C4 — Iso ∘ Iso composition laws. Both composedGet and composedReverseGet are inherited from the capability layer.

C3/C4 — Iso ∘ Iso composition laws. Both composedGet and composedReverseGet are inherited from the capability layer.

Attributes

Source
ComposeLaws.scala
Supertypes
trait ComposedReverseGetLaws[S, A, B]
trait ComposedGetLaws[S, A, B]
class Object
trait Matchable
class Any
trait LensComposeLaws[S, A, B] extends ComposedGetLaws[S, A, B]

C1/C2 — Lens ∘ Lens composition laws. composedGet is inherited from ComposedGetLaws; composedReplace is the Lens-specific write-seam law.

C1/C2 — Lens ∘ Lens composition laws. composedGet is inherited from ComposedGetLaws; composedReplace is the Lens-specific write-seam law.

Attributes

Source
ComposeLaws.scala
Supertypes
trait ComposedGetLaws[S, A, B]
class Object
trait Matchable
class Any
trait ModifyAConstLaws[S, A, F[_, _]]

D3 — optic.modifyA[Const[M, *]] is pointwise equal to optic.foldMap on the same function, with M = Int (additive).

D3 — optic.modifyA[Const[M, *]] is pointwise equal to optic.foldMap on the same function, with M = Int (additive).

Attributes

Source
ModifyALaws.scala
Supertypes
class Object
trait Matchable
class Any
trait ModifyAIdLaws[S, A, F[_, _]]

D1 — optic.modifyA[Id] is pointwise equal to optic.modify.

D1 — optic.modifyA[Id] is pointwise equal to optic.modify.

Attributes

Source
ModifyALaws.scala
Supertypes
class Object
trait Matchable
class Any
trait MorphLaws[S, A, F[_, _], G[_, _]]

Laws that pin down Optic.morph — EO's carrier-coercion extension.

Laws that pin down Optic.morph — EO's carrier-coercion extension.

A1/I1. Morph preserves modify: reshaping the carrier does not change what the optic does to the focus.

A2. Morph preserves get: for any carriers F / G that both expose Accessor, reshaping preserves the read path as well.

These two laws are the foundation of EO's "write once, reuse everywhere" claim about optics. If they failed, a user could not safely convert a Lens to an Optional or a Getter to a Fold without changing observable behaviour.

Attributes

Source
MorphLaws.scala
Supertypes
class Object
trait Matchable
class Any
trait OptionalComposeLaws[S, A, B] extends ComposedGetOptionLaws[S, A, B]

Optional ∘ Optional composition laws. composedGetOption is inherited from the capability layer; composedModifyIdentity is the Optional-specific write-seam law.

Optional ∘ Optional composition laws. composedGetOption is inherited from the capability layer; composedModifyIdentity is the Optional-specific write-seam law.

Attributes

Source
ComposeLaws.scala
Supertypes
trait ComposedGetOptionLaws[S, A, B]
class Object
trait Matchable
class Any
trait PrismComposeLaws[S, A, B] extends ComposedGetOptionLaws[S, A, B], ComposedReverseGetLaws[S, A, B]

C5 — Prism ∘ Prism composition laws. Both composedGetOption and composedReverseGet are inherited from the capability layer.

C5 — Prism ∘ Prism composition laws. Both composedGetOption and composedReverseGet are inherited from the capability layer.

Attributes

Source
ComposeLaws.scala
Supertypes
trait ComposedReverseGetLaws[S, A, B]
trait ComposedGetOptionLaws[S, A, B]
class Object
trait Matchable
class Any
trait PutIsReverseGetLaws[S, A]

H3 — Iso put is the curried reverseGet ∘ pure.

H3 — Iso put is the curried reverseGet ∘ pure.

Attributes

Source
ReverseAndTransformLaws.scala
Supertypes
class Object
trait Matchable
class Any
trait ReverseInvolutionLaws[S, A]

B1 — Iso reverse is involutive on both get and reverseGet.

B1 — Iso reverse is involutive on both get and reverseGet.

Attributes

Source
ReverseAndTransformLaws.scala
Supertypes
class Object
trait Matchable
class Any
trait TransformLaws[S, A, X0]

H1/H2/H4 — Lens transform / place / transfer mutually agree.

H1/H2/H4 — Lens transform / place / transfer mutually agree.

Attributes

Source
ReverseAndTransformLaws.scala
Supertypes
class Object
trait Matchable
class Any