Cairn · module

Cairn.Optimistic

lean/Cairn/Optimistic.lean

Optimistic values: shown at once, then confirmed or rolled back

A Table K V holds values a person changes and a server keeps, keyed by K (a post's URI, an account's DID). A change shows in the step it is made; the table then sends one write for it, and the server's answer confirms it or rolls it back (docs/optimistic.md). Nothing here knows about any particular server: the app turns the table's outputs into requests and the requests' answers into its inputs.

Per key the table keeps an Entry:

  • server, the last value the server confirmed: an acknowledged write, an authoritative read, or a view of a key never written this session;
  • want, what the person asked for last. This is what is shown (Table.shown);
  • phase: nothing outstanding (idle), a write in flight (writing v), a write whose answer was lost and a read in flight to settle it (doubt v), the same with the read failed and a retry due (waiting v), or a read checking a view that disagreed (checking);
  • seq, the number of the key's last request: answers carry it (Ticket), and an answer whose number isn't the current one is stale and ignored. So a duplicated, late or superseded answer changes nothing.

The rules (Entry.step):

  • One write in flight per key. A set while one is in flight, or in doubt, only changes want. When the write is answered, one write toward want is sent if want and server still differ (by the app's same, e.g. "liked or not, whichever record").
  • Refused rolls the key back in that step: want := server, reported as rolledBack when what is shown changes.
  • Lost (no answer: a timeout, a network failure, a 5xx) puts the key in doubt and sends a read. The read's answer settles it: the server holds the written value (acknowledged) or it doesn't (refused, Reason.notApplied). A failed read is retried on a backoff (1 s, doubling, at most 30 s, retryIn), never by writing again.
  • Views (seen) move a key only if it has never been written this session. A written key that a view disagrees with, with nothing outstanding, gets a read (checking), whose answer is authoritative. So a stale view never undoes a confirmed write.
  • Counts over a boolean value: count c v w = c − [v] + [w] (count).

Lookups and updates are O(log n) in the number of keys (Std.TreeMap).

Theorems here, for every table: shown_set (a set shows in its own step), get_feed_ne (an input touches only its key), feed_comm (inputs for different keys commute: the same table, the same outputs, in the other order), refused_rollback (a refusal shows server in its step), seen_written (a view never moves a written key), writes_le_sets (never more writes than sets, per key, for any sequence of inputs), and the count's arithmetic (count_exact, count_ge). Convergence against a server, for any order of replies, is Cairn.Optimistic.Server; the claims (cairn^1100–cairn^1114) are Cairn.Optimistic.Claims.

Imports Std.Data.TreeMap

Order

Structures 4

structure

Cairn.Optimistic.Entry

lean/Cairn/Optimistic.lean:102
Entry (V : Type) : Type

One key's state.

Fields
server : V

The last value the server confirmed.

want : V

What the person asked for last: what is shown.

written : Bool

Whether the person has set this key this session.

phase : Phase V
seq : Nat

The number of the key's last request (0: none yet).

backoff : Nat

The wait before the next retry of a failed read.

Instances

Repr

structure

Cairn.Optimistic.Ticket

lean/Cairn/Optimistic.lean:216
Ticket (K : Type) : Type

A request's ticket: the key it is about and its number among that key's requests. The app keeps its own request ids and maps each to the ticket it was sent for (docs/optimistic.md).

Fields
key : K
seq : Nat
Instances

Repr Inhabited

structure

Cairn.Optimistic.Table

lean/Cairn/Optimistic.lean:283
Table (K V : Type) [Ord K] : Type

The table. dflt is the value of a key it hasn't heard of; same a b says whether two values mean the same to the server (for a like: liked or not, whichever record). same should be an equivalence (Same); the theorems that need it say so.

Fields
entries : Std.TreeMap K (Entry V) compare
dflt : V
same : Bool
Instances

Repr BEq Inhabited

structure

Cairn.Optimistic.Same

lean/Cairn/Optimistic.lean:368
Same {V : Type} (same : V → V → Bool) : Prop

same is an equivalence.

Fields
refl : same a a = true
symm : same b a = true
trans : same a c = true

Inductive types 6

inductive

Cairn.Optimistic.Phase

lean/Cairn/Optimistic.lean:69
Phase (V : Type) : Type

What a key is waiting for.

Constructors
idle {V : Type} : Phase V

Nothing outstanding.

writing {V : Type} (v : V) : Phase V

A write of v is in flight.

doubt {V : Type} (v : V) : Phase V

The write of v got no answer; a read is in flight to learn whether it was applied.

waiting {V : Type} (v : V) : Phase V

The same, with that read failed; a retry sends the next.

checking {V : Type} : Phase V

A view disagreed with a written key; a read is in flight to check it.

Instances

Repr Inhabited

inductive

Cairn.Optimistic.Reason

lean/Cairn/Optimistic.lean:120
Reason : Type

Why a key was rolled back.

Constructors
refused (why : String) : Reason

The server refused the write (a 4xx), for the reason the app gave.

notApplied : Reason

The write's answer was lost, and the read that followed shows it wasn't applied.

Instances

Inhabited Repr

inductive

Cairn.Optimistic.Ev

lean/Cairn/Optimistic.lean:128
Ev (V : Type) : Type

What one key hears (Input without the key).

Constructors
set {V : Type} (f : V → V) : Ev V
acked {V : Type} (n : Nat) : Ev V
refused {V : Type} (n : Nat) (why : String) : Ev V
lost {V : Type} (n : Nat) : Ev V
read {V : Type} (n : Nat) (v : V) : Ev V
readFailed {V : Type} (n : Nat) : Ev V
retry {V : Type} : Ev V
seen {V : Type} (v : V) : Ev V
inductive

Cairn.Optimistic.Act

lean/Cairn/Optimistic.lean:139
Act (V : Type) : Type

What one key asks for (Out without the key).

Constructors
write {V : Type} (n : Nat) (v : V) : Act V
read {V : Type} (n : Nat) : Act V
retryIn {V : Type} (ms : Nat) : Act V
rolledBack {V : Type} (r : Reason) : Act V
Instances

Repr

inductive

Cairn.Optimistic.Input

lean/Cairn/Optimistic.lean:222
Input (K V : Type) : Type

What the table hears.

Constructors
set {K V : Type} (k : K) (f : V → V) : Input K V

The person changes key k to f of what is shown (f : V → V, so "like" on a value already liked can keep its record).

acked {K V : Type} (t : Ticket K) : Input K V

The write was applied (a 2xx).

refused {K V : Type} (t : Ticket K) (why : String) : Input K V

The write was refused and not applied (a 4xx), for why.

lost {K V : Type} (t : Ticket K) : Input K V

The write got no answer (a timeout, a network failure, a 5xx): it may or may not have been applied.

read {K V : Type} (t : Ticket K) (v : V) : Input K V

An authoritative read's answer: what the server holds for the key now.

readFailed {K V : Type} (t : Ticket K) : Input K V

A read got no usable answer.

retry {K V : Type} (k : K) : Input K V

The backoff timer retryIn asked for came due.

seen {K V : Type} (k : K) (v : V) : Input K V

A value in a view the app fetched (a list, a page), which may be stale.

inductive

Cairn.Optimistic.Out

lean/Cairn/Optimistic.lean:243
Out (K V : Type) : Type

What the table asks the app to do.

Constructors
write {K V : Type} (t : Ticket K) (v : V) : Out K V

Send a write of v for t.key, and answer it with t.

read {K V : Type} (t : Ticket K) : Out K V

Read t.key's value from the server, authoritatively, and answer with t.

retryIn {K V : Type} (k : K) (ms : Nat) : Out K V

Feed retry k in ms milliseconds (a timer).

rolledBack {K V : Type} (k : K) (r : Reason) : Out K V

k was rolled back; say so in words.

Instances

Repr

Definitions 36

def

Cairn.Optimistic.firstBackoff

lean/Cairn/Optimistic.lean:60
firstBackoff : Nat

The first retry of a failed read, in milliseconds.

def

Cairn.Optimistic.maxBackoff

lean/Cairn/Optimistic.lean:63
maxBackoff : Nat

The longest wait between retries.

def

Cairn.Optimistic.nextBackoff

lean/Cairn/Optimistic.lean:66
nextBackoff (ms : Nat) : Nat

The next wait: double, at most maxBackoff.

def

Cairn.Optimistic.Phase.isIdle

lean/Cairn/Optimistic.lean:85
isIdle {V : Type} : Phase V → Bool
def

Cairn.Optimistic.Phase.isOpen

lean/Cairn/Optimistic.lean:90
isOpen {V : Type} : Phase V → Bool

Whether a set may send a write now: nothing in flight or in doubt.

def

Cairn.Optimistic.Phase.pending

lean/Cairn/Optimistic.lean:95
pending {V : Type} : Phase V → Option V

The value of the write in flight or in doubt, if any.

def

Cairn.Optimistic.Entry.fresh

lean/Cairn/Optimistic.lean:117
fresh {V : Type} (v : V) : Entry V

A key the table hasn't heard of: v confirmed and shown.

def

Cairn.Optimistic.Entry.send

lean/Cairn/Optimistic.lean:150
send {V : Type} (e : Entry V) : Entry V × List (Act V)

Send a write of want, as request seq + 1.

def

Cairn.Optimistic.Entry.ask

lean/Cairn/Optimistic.lean:154
ask {V : Type} (e : Entry V) (ph : Phase V) : Entry V × List (Act V)

Send a read, as request seq + 1, waiting in ph.

def

Cairn.Optimistic.Entry.settle

lean/Cairn/Optimistic.lean:158
settle {V : Type} (same : V → V → Bool) (e : Entry V) :
  Entry V × List (Act V)

The server's value is known (e.server): rest if want is the same, else write toward it.

def

Cairn.Optimistic.Entry.rollback

lean/Cairn/Optimistic.lean:163
rollback {V : Type} (same : V → V → Bool) (e : Entry V)
  (r : Reason) : Entry V × List (Act V)

Show the server's value again, saying why if what is shown changes.

def

Cairn.Optimistic.Entry.step

lean/Cairn/Optimistic.lean:168
step {V : Type} (same : V → V → Bool) (e : Entry V) :
  Ev V → Entry V × List (Act V)

One key's step.

def

Cairn.Optimistic.Input.key

lean/Cairn/Optimistic.lean:257
key {K V : Type} : Input K V → K
def

Cairn.Optimistic.Input.ev

lean/Cairn/Optimistic.lean:261
ev {K V : Type} : Input K V → Ev V
def

Cairn.Optimistic.Act.out

lean/Cairn/Optimistic.lean:274
out {K V : Type} (k : K) : Act V → Out K V

An entry's action, as the table's output for key k.

def

Cairn.Optimistic.Table.empty

lean/Cairn/Optimistic.lean:292
empty {K V : Type} [Ord K] (dflt : V) (same : V → V → Bool) :
  Table K V

An empty table.

def

Cairn.Optimistic.Table.get

lean/Cairn/Optimistic.lean:295
get {K V : Type} [Ord K] (t : Table K V) (k : K) : Entry V

Key k's entry: O(log n).

def

Cairn.Optimistic.Table.shown

lean/Cairn/Optimistic.lean:298
shown {K V : Type} [Ord K] (t : Table K V) (k : K) : V

What is shown for k: want.

def

Cairn.Optimistic.Table.server

lean/Cairn/Optimistic.lean:301
server {K V : Type} [Ord K] (t : Table K V) (k : K) : V

The last value the server confirmed for k.

def

Cairn.Optimistic.Table.inFlight

lean/Cairn/Optimistic.lean:304
inFlight {K V : Type} [Ord K] (t : Table K V) (k : K) : Bool

A write for k is in flight.

def

Cairn.Optimistic.Table.inDoubt

lean/Cairn/Optimistic.lean:310
inDoubt {K V : Type} [Ord K] (t : Table K V) (k : K) : Bool

k's last write got no answer, and isn't settled yet.

def

Cairn.Optimistic.Table.settled

lean/Cairn/Optimistic.lean:316
settled {K V : Type} [Ord K] (t : Table K V) (k : K) : Bool

Nothing outstanding for k: no write in flight or in doubt, no read checking a view.

def

Cairn.Optimistic.Table.written

lean/Cairn/Optimistic.lean:319
written {K V : Type} [Ord K] (t : Table K V) (k : K) : Bool

Whether the person set k this session.

def

Cairn.Optimistic.Table.feed

lean/Cairn/Optimistic.lean:322
feed {K V : Type} [Ord K] (t : Table K V) (i : Input K V) :
  Table K V × List (Out K V)

One step: the input's key's entry steps, and its actions become outputs. O(log n).

def

Cairn.Optimistic.Table.run

lean/Cairn/Optimistic.lean:327
run {K V : Type} [Ord K] (t : Table K V) :
  List (Input K V) → Table K V × List (Out K V)

Feed inputs in order; the outputs in order.

def

Cairn.Optimistic.Table.allSettled

lean/Cairn/Optimistic.lean:335
allSettled {K V : Type} [Ord K] (t : Table K V) : Bool

Every key with nothing outstanding. O(n).

def

Cairn.Optimistic.Table.size

lean/Cairn/Optimistic.lean:338
size {K V : Type} [Ord K] (t : Table K V) : Nat

The number of keys the table holds.

def

Cairn.Optimistic.ind

lean/Cairn/Optimistic.lean:357
ind (b : Bool) : Nat

[b]: one if b.

def

Cairn.Optimistic.count

lean/Cairn/Optimistic.lean:363
count (c : Nat) (v w : Bool) : Nat

A count over a boolean key: c and v are the count and the person's own value from the latest view (the count includes the person's own exactly when v), w is what is shown: c − [v] + [w]. Never below zero (a Nat, count_ge), and exact whenever the view is consistent (count_exact).

def

Cairn.Optimistic.Entry.writes

lean/Cairn/Optimistic.lean:489
writes {V : Type} (as : List (Act V)) : Nat

The writes among an entry's actions.

def

Cairn.Optimistic.Entry.Budget

lean/Cairn/Optimistic.lean:493
Budget {V : Type} (same : V → V → Bool) (e : Entry V) (s w : Nat) :
  Prop

Writes w within sets s; and when the write outstanding isn't what is shown, a set is yet to be written.

def

Cairn.Optimistic.Entry.Ev.sets

lean/Cairn/Optimistic.lean:497
sets {V : Type} : Ev V → Nat

How many sets an event is.

def

Cairn.Optimistic.Table.setsFor

lean/Cairn/Optimistic.lean:525
setsFor {K V : Type} [DecidableEq K] (k : K)
  (is : List (Input K V)) : Nat

The sets of k among some inputs.

def

Cairn.Optimistic.Table.writesFor

lean/Cairn/Optimistic.lean:529
writesFor {K V : Type} [DecidableEq K] (k : K)
  (os : List (Out K V)) : Nat

The writes for k among some outputs.

def

Cairn.Optimistic.Entry.Calm

lean/Cairn/Optimistic.lean:599
Calm {V : Type} (same : V → V → Bool) (e : Entry V) : Prop

With no write in flight or in doubt (idle, or checking a view), what is shown is the server's last confirmed value (by same).

def

Cairn.Optimistic.Table.Calm

lean/Cairn/Optimistic.lean:615
Calm {K V : Type} [Ord K] (t : Table K V) : Prop

Every key at rest shows the server's last confirmed value.

Theorems 25

theorem

Cairn.Optimistic.Same.beq

provedlean/Cairn/Optimistic.lean:374
beq {V : Type} [BEq V] [LawfulBEq V] : Same fun a b => a == b

Equality, as same.

theorem

Cairn.Optimistic.count_exact

provedlean/Cairn/Optimistic.lean:378
count_exact (c : Nat) (v w : Bool) (h : ind v ≤ c) :
  ↑(count c v w) = ↑c - ↑(ind v) + ↑(ind w)
theorem

Cairn.Optimistic.count_ge

provedlean/Cairn/Optimistic.lean:382
count_ge (c : Nat) (v w : Bool) : ind w ≤ count c v w
theorem

Cairn.Optimistic.count_view

provedlean/Cairn/Optimistic.lean:388
count_view (o : Nat) (v r : Bool) : count (o + ind v) v r = o + ind r

Counts once settled. A view's count is other people's o plus the person's own [v]. When the key shows the server's value r (a settled key does, Server.converges), the count shown is o + [r]: exactly the server's count when no one else acted since the view.

theorem

Cairn.Optimistic.Table.get_insert

provedlean/Cairn/Optimistic.lean:394
get_insert {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (k j : K) (e : Entry V) :
  { entries := t.entries.insert k e, dflt := t.dflt, same := t.same }.get j =
    if k = j then e else t.get j
theorem

Cairn.Optimistic.Table.get_feed

provedlean/Cairn/Optimistic.lean:404
get_feed {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (i : Input K V) (k : K) :
  (t.feed i).fst.get k =
    if i.key = k then (Entry.step t.same (t.get i.key) i.ev).fst else t.get k

What feed does to any key: the input's key steps; every other key is as it was.

theorem

Cairn.Optimistic.Table.get_feed_self

provedlean/Cairn/Optimistic.lean:408
get_feed_self {K V : Type} [Ord K] [Std.TransOrd K]
  [Std.LawfulEqOrd K] [DecidableEq K] (t : Table K V) (i : Input K V) :
  (t.feed i).fst.get i.key = (Entry.step t.same (t.get i.key) i.ev).fst
theorem

Cairn.Optimistic.Table.get_feed_ne

provedlean/Cairn/Optimistic.lean:413
get_feed_ne {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (i : Input K V) {k : K} (h : i.key ≠ k) :
  (t.feed i).fst.get k = t.get k

An input touches only its key.

theorem

Cairn.Optimistic.Table.feed_same

provedlean/Cairn/Optimistic.lean:417
feed_same {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (i : Input K V) : (t.feed i).fst.same = t.same
theorem

Cairn.Optimistic.Table.feed_dflt

provedlean/Cairn/Optimistic.lean:418
feed_dflt {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (i : Input K V) : (t.feed i).fst.dflt = t.dflt
theorem

Cairn.Optimistic.Table.feed_out

provedlean/Cairn/Optimistic.lean:420
feed_out {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (i : Input K V) :
  (t.feed i).snd = List.map (Act.out i.key) (Entry.step t.same (t.get i.key) i.ev).snd
theorem

Cairn.Optimistic.Table.shown_set

provedlean/Cairn/Optimistic.lean:424
shown_set {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (k : K) (f : V → V) :
  (t.feed (Input.set k f)).fst.shown k = f (t.shown k)

A set shows in its own step: after set k f, k shows f of what it showed.

theorem

Cairn.Optimistic.Table.feed_comm

provedlean/Cairn/Optimistic.lean:434
feed_comm {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (i j : Input K V) (h : i.key ≠ j.key) :
  (∀ (k : K), ((t.feed i).fst.feed j).fst.get k = ((t.feed j).fst.feed i).fst.get k) ∧
    ((t.feed i).fst.feed j).snd = (t.feed j).snd ∧
      ((t.feed j).fst.feed i).snd = (t.feed i).snd

Inputs for different keys commute: in either order the table is the same at every key, and each input's outputs are the ones it gives alone, so the two orders' outputs are the same two lists, swapped.

theorem

Cairn.Optimistic.Table.refused_rollback

provedlean/Cairn/Optimistic.lean:451
refused_rollback {K V : Type} [Ord K] [Std.TransOrd K]
  [Std.LawfulEqOrd K] [DecidableEq K] (t : Table K V) (k : K) (n : Nat) (why : String)
  (w : V) (hp : (t.get k).phase = Phase.writing w) (hn : n = (t.get k).seq) :
  (t.feed (Input.refused { key := k, seq := n } why)).fst.shown k = t.server k ∧
    (t.feed (Input.refused { key := k, seq := n } why)).fst.server k = t.server k ∧
      (t.feed (Input.refused { key := k, seq := n } why)).fst.settled k = true

A refusal rolls back in its step: when k's write n is in flight, refused for it leaves k showing the server's value, which is unchanged.

theorem

Cairn.Optimistic.Table.seen_written

provedlean/Cairn/Optimistic.lean:464
seen_written {K V : Type} [Ord K] [Std.TransOrd K]
  [Std.LawfulEqOrd K] [DecidableEq K] (t : Table K V) (k : K) (v : V)
  (hw : t.written k = true) :
  (t.feed (Input.seen k v)).fst.shown k = t.shown k ∧
    (t.feed (Input.seen k v)).fst.server k = t.server k

A view never moves a written key: seen leaves what a key written this session shows, and the server value it holds, as they were.

theorem

Cairn.Optimistic.Table.feed_ext

provedlean/Cairn/Optimistic.lean:475
feed_ext {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t u : Table K V) (h : ∀ (k : K), t.get k = u.get k)
  (hs : t.same = u.same) (i : Input K V) :
  (∀ (k : K), (t.feed i).fst.get k = (u.feed i).fst.get k) ∧ (t.feed i).snd = (u.feed i).snd

feed reads the table only through get, same and dflt: tables equal at every key step alike. (TreeMaps holding the same entries can differ in shape; nothing here sees it.)

theorem

Cairn.Optimistic.Entry.budget_step

provedlean/Cairn/Optimistic.lean:501
budget_step {V : Type} (same : V → V → Bool) (hs : Same same)
  (e : Entry V) (s w : Nat) (h : Budget same e s w) (ev : Ev V) :
  Budget same (step same e ev).fst (s + Ev.sets ev) (w + writes (step same e ev).snd)
theorem

Cairn.Optimistic.Table.writesFor_map

provedlean/Cairn/Optimistic.lean:532
writesFor_map {K V : Type} [Ord K] [Std.TransOrd K]
  [Std.LawfulEqOrd K] [DecidableEq K] (k j : K) (as : List (Act V)) :
  writesFor k (List.map (Act.out j) as) = if j = k then Entry.writes as else 0
theorem

Cairn.Optimistic.Table.budget_feed

provedlean/Cairn/Optimistic.lean:543
budget_feed {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (hs : Same t.same) (s w : K → Nat)
  (h : ∀ (k : K), Entry.Budget t.same (t.get k) (s k) (w k)) (i : Input K V) (k : K) :
  Entry.Budget t.same ((t.feed i).fst.get k) (s k + setsFor k [i])
    (w k + writesFor k (t.feed i).snd)
theorem

Cairn.Optimistic.Table.budget_run

provedlean/Cairn/Optimistic.lean:560
budget_run {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (is : List (Input K V)) (t : Table K V) (s w : K → Nat) :
  Same t.same →
    (∀ (k : K), Entry.Budget t.same (t.get k) (s k) (w k)) →
      ∀ (k : K),
        Entry.Budget t.same ((t.run is).fst.get k) (s k + setsFor k is)
          (w k + writesFor k (t.run is).snd)
theorem

Cairn.Optimistic.Table.writes_le_sets

provedlean/Cairn/Optimistic.lean:581
writes_le_sets {K V : Type} [Ord K] [Std.TransOrd K]
  [Std.LawfulEqOrd K] [DecidableEq K] (dflt : V) (same : V → V → Bool) (hs : Same same)
  (is : List (Input K V)) (k : K) :
  writesFor k ((empty dflt same).run is).snd ≤ setsFor k is

Never more writes than sets. From an empty table, for any sequence of inputs (any answers, in any order, duplicated or stale), the writes the table asks for k never outnumber the person's sets of k.

theorem

Cairn.Optimistic.Entry.calm_step

provedlean/Cairn/Optimistic.lean:601
calm_step {V : Type} (same : V → V → Bool) (hs : Same same)
  (e : Entry V) (h : Calm same e) (ev : Ev V) : Calm same (step same e ev).fst
theorem

Cairn.Optimistic.Table.calm_empty

provedlean/Cairn/Optimistic.lean:617
calm_empty {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (dflt : V) (same : V → V → Bool) (hs : Same same) : (empty dflt same).Calm
theorem

Cairn.Optimistic.Table.calm_feed

provedlean/Cairn/Optimistic.lean:624
calm_feed {K V : Type} [Ord K] [Std.TransOrd K] [Std.LawfulEqOrd K]
  [DecidableEq K] (t : Table K V) (hs : Same t.same) (h : t.Calm) (i : Input K V) :
  (t.feed i).fst.Calm

At rest, a key shows the server's value, after any input.

theorem

Cairn.Optimistic.Table.Calm.settled

provedlean/Cairn/Optimistic.lean:633
settled {K V : Type} [Ord K] [Std.TransOrd K]
  [Std.LawfulEqOrd K] [DecidableEq K] {t : Table K V} (h : t.Calm) {k : K}
  (hk : t.settled k = true) : t.same (t.shown k) (t.server k) = true

A settled key shows what the table last heard from the server.

Instances 18

instance

Cairn.Optimistic.instDecidableEqPhase

lean/Cairn/Optimistic.lean:80
instDecidableEqPhase {V✝ : Type} [DecidableEq V✝] : DecidableEq (Phase V✝)
instance

Cairn.Optimistic.instReprPhase

lean/Cairn/Optimistic.lean:80
instReprPhase {V✝ : Type} [Repr V✝] : Repr (Phase V✝)
instance

Cairn.Optimistic.instInhabitedPhase

lean/Cairn/Optimistic.lean:80
instInhabitedPhase {a✝ : Type} : Inhabited (Phase a✝)
instance

Cairn.Optimistic.instDecidableEqEntry

lean/Cairn/Optimistic.lean:114
instDecidableEqEntry {V✝ : Type} [DecidableEq V✝] : DecidableEq (Entry V✝)
instance

Cairn.Optimistic.instReprEntry

lean/Cairn/Optimistic.lean:114
instReprEntry {V✝ : Type} [Repr V✝] : Repr (Entry V✝)
instance

Cairn.Optimistic.instDecidableEqReason

lean/Cairn/Optimistic.lean:125
instDecidableEqReason : DecidableEq Reason
instance

Cairn.Optimistic.instInhabitedReason

lean/Cairn/Optimistic.lean:125
instInhabitedReason : Inhabited Reason
instance

Cairn.Optimistic.instReprReason

lean/Cairn/Optimistic.lean:125
instReprReason : Repr Reason
instance

Cairn.Optimistic.instDecidableEqAct

lean/Cairn/Optimistic.lean:144
instDecidableEqAct {V✝ : Type} [DecidableEq V✝] : DecidableEq (Act V✝)
instance

Cairn.Optimistic.instReprAct

lean/Cairn/Optimistic.lean:144
instReprAct {V✝ : Type} [Repr V✝] : Repr (Act V✝)
instance

Cairn.Optimistic.instDecidableEqTicket

lean/Cairn/Optimistic.lean:219
instDecidableEqTicket {K✝ : Type} [DecidableEq K✝] :
  DecidableEq (Ticket K✝)
instance

Cairn.Optimistic.instReprTicket

lean/Cairn/Optimistic.lean:219
instReprTicket {K✝ : Type} [Repr K✝] : Repr (Ticket K✝)
instance

Cairn.Optimistic.instInhabitedTicket

lean/Cairn/Optimistic.lean:219
instInhabitedTicket {a✝ : Type} [Inhabited a✝] : Inhabited (Ticket a✝)
instance

Cairn.Optimistic.instReprOut

lean/Cairn/Optimistic.lean:252
instReprOut {K✝ V✝ : Type} [Repr K✝] [Repr V✝] : Repr (Out K✝ V✝)
instance

Cairn.Optimistic.instDecidableEqOut

lean/Cairn/Optimistic.lean:252
instDecidableEqOut {K✝ V✝ : Type} [DecidableEq K✝] [DecidableEq V✝] :
  DecidableEq (Out K✝ V✝)
instance

Cairn.Optimistic.Table.instRepr

lean/Cairn/Optimistic.lean:340
instRepr {K V : Type} [Ord K] [Repr K] [Repr V] : Repr (Table K V)
instance

Cairn.Optimistic.Table.instBEqOfDecidableEq

lean/Cairn/Optimistic.lean:345
instBEqOfDecidableEq {K V : Type} [Ord K] [BEq K] [DecidableEq V] :
  BEq (Table K V)

Two tables are == when they hold the same entries and default; same is a function and isn't compared. So an app's state that holds a table can derive BEq for its tests.

instance

Cairn.Optimistic.Table.instInhabited

lean/Cairn/Optimistic.lean:350
instInhabited {K V : Type} [Ord K] [Inhabited V] :
  Inhabited (Table K V)

An empty table of defaults, with every value the same as every other: for deriving Inhabited. A real table is Table.empty.