docs: align guides with 0.7.33 screen-process architecture + recent feature coverage - #105
Merged
Conversation
…emantics navigation.md still described tab_bar/drawer as rendering native chrome (UITabBarController / NavigationBar) — since 0.7.33 the runtime backs the declaration with real per-stack state but draws no chrome; switching is programmatic. New 'Tabs and multi-stack state' section documents lazy materialization, parking, independent histories, back-at-secondary-root, the orphan stack, and the MOB-115/116/117 gaps. Directional-reset docs gain the ArgumentError validation and transition-survives-coalescing behavior (#100/#103). screen_lifecycle.md gains crash/restart semantics (per-screen isolation, restart cap, re-mount + load_state), per-screen self() and message delivery, terminate/2 reality (pop stops the leaving screen only), and multi-stack system-back. Mob.App.tab_bar/1 and drawer/1 docstrings no longer claim chrome that is not drawn. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
…nt screen_pid/1 The testing guide never mentioned Mob.ScreenCase (#44), the blessed in-BEAM unit-test path — it now leads the guide. The old sync-point advice referenced Mob.Test.screen_pid/1, which does not exist, and :sys.get_state on :mob_screen, which stopped being sufficient when rendering moved to Mob.Sender (MOB-110) and :mob_screen became the navigation owner (MOB-112); both are replaced with Mob.Test.settle/2 and an explanation of the three processes it drains. Unit-test examples updated for the process model (dispatch is synchronous; get_socket is the natural sync point after send). Mob.Test's moduledoc claimed tap/2 goes through handle_event/3; it sends {:tap, tag} to handle_info/2 like a real native tap. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
components.md had no coverage of Mob.UI.sheet/2 (0.7.29) or intrinsic
content detents (0.7.32) beyond the surface-matrix row — new ':sheet'
section documents presence-is-presentation, detents including
[:content] / [{:content, max_height: n}], exactly-once {:dismiss, tag},
and the iOS scrim limitation. New 'Handle limits' section covers the
256-handle tap pool and the 256-slot native component pool with
{:error, :component_slots_exhausted} (0.7.28 behavior). :text gains the
font prop (named font tokens, 0.7.25).
theming.md never mentioned fonts — adds the fonts:/font_fallback: token
type with a pointer to Styling → Custom fonts.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>README and several guides showed UI taps handled by
handle_event("tap", %{"tag" => ...}) — a real tap delivers
{:tap, tag} to handle_info/2, so those example screens would never
respond on a device. README's diagram and testing snippet updated for
the per-screen process model and Mob.ScreenCase. getting_started
referenced Mob.Nav.push/2, which does not exist (Mob.Socket.push_screen
is the API). event_audit's list-select re-emitter is Mob.Screen.Server
since MOB-113.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>…ctices Part 1 (Working with one agent) keeps the existing content in order and adds: verify effects not exit codes (assert the app answers after a deploy), the honesty contract (success = a handler ran — assert on state change after a tap, settle-window caveat), match the evidence to the question (frames for layout, screenshots-with-tolerance for appearance, recordings for motion), lifecycle-event simulation recipes (simctl push .apns, adb broadcast / cmd notification post), and environment discipline (complete .tool-versions incl. zig/JDK, the MOB_DIR/MOB_DEV_DIR/MOB_NEW_DIR override chain). Part 2 (Working with agent teams) is new: one driver per device with lease discipline (humans outrank agents), unique node names per session (mob.connect --name), per-task git worktrees, the mob.push/mob.watch fan-out hazard (they reach every live node, no device scoping — fleets deploy per device or push over their own dist connection), and durable artifacts as the handoff medium between context windows. The standard agent loop gains a settle/2 step before native-side reads. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Mob.Router joins Navigation; Mob.Screen.Server, Mob.Listener and Mob.Sender get a Runtime Processes group; Mob.ScreenCase joins Testing & Debugging. All five were shipping ungrouped. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Written minutes before #80 merged, the honesty-contract and evidence-matching sections claimed no pixel-sampling API existed and leaned solely on state-change assertions. Now that tap_xy/3 reports observed effect, both guides document the contract: :ok only when an event reached the BEAM within 300ms, else {:error, :no_view_at_point | :no_element_at_point | :no_effect} — plus the platform limits that make :no_effect legitimate (SwiftUI on_tap containers, physical-device injection) and the serial-harness assumption the 300ms window shares with state-change checks. Evidence matching now splits exact-color decisions (sample_color/2: real pixels, dominant/average as 0xAARRGGBB, iOS debug-build only) from holistic visual parity (screenshots with tolerance). testing.md gains matching sections. No change needed for #77: push_notifications.md already described tap-to-open from a killed app, which that fix made true. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
GenericJamforce-pushed
the
docs/refresh-0733
branch
from
August 30, 2026 07:15
84dff64 to
6c19649CompareUh oh!
There was an error while loading. Please reload this page.
GenericJam
commented
Aug 30, 2026
OwnerAuthor
Review record: spot-verified the highest-consequence claims against master source (Mob.Nav is the state struct — no push/2 navigation API ever existed; screen_pid/1 absent; taps deliver {:tap, tag} to handle_info; tab_bar/1 layout draws no chrome while the :tab_bar widget path renders MobTabView — the guide's distinction is exactly right). Structure matches the requested single-agent/agent-teams split. Gates green on the rebased tree. Merged. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for freeto join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Audit of every guide, the README, and the public moduledocs against current master (0.7.34 + #103). The moduledocs written alongside MOB-108–114 were already accurate; the drift was concentrated in the guides and a few docstrings that predate the work. Sections marked rewrite replaced a wrong model; everything else is a surgical edit.
Per-doc changes
guides/navigation.md
UITabBarController/NavigationBar/ModalNavigationDrawer) that is not drawn — now describe the multi-stack runtime honestly, with the:tab_barwidget +switch_tab/2as the interim chrome path.switch_tab/2semantics (first visit mounts root, no-op cases, no animation); directional resets gain theArgumentErrorvalidation (incl. why:noneis rejected) and the transition-survives-coalescing behavior (feat(navigation): allow directional resets #100/fix(navigation): preserve initial transition #103).handle_event("tap", %{"tag" => ...})tohandle_info({:tap, tag})— the shape a real tap delivers.guides/screen_lifecycle.md (edits — the process-model intro was already updated by #101)
load_state/2, per-screenself()and message delivery.terminate/2: when it actually runs, persisted-state dump, pop stops only the leaving screen.guides/testing.md
Mob.ScreenCase(Mob.ScreenCase: blessed in-BEAM screen testing (+ contract check, device backend) #44) — previously undocumented in any guide.Mob.Test.screen_pid/1(does not exist) and the:sys.get_state(:mob_screen)sync-point advice (insufficient since MOB-110/112); replaced withMob.Test.settle/2and an explanation of the three processes it drains.dispatch/3for navigation;get_socket/1as the natural sync point aftersend).guides/components.md
:sheetsection:Mob.UI.sheet/2/<Sheet>(0.7.29), presence-is-presentation, intrinsic[:content]detents (0.7.32), exactly-once{:dismiss, tag}, iOS scrim limitation. Only the surface-matrix row covered sheets before.{:error, :component_slots_exhausted}) — 0.7.28 behavior.:textgains thefontprop row (named font tokens, 0.7.25).guides/theming.md — fonts were absent entirely; adds the
fonts:/font_fallback:token type (0.7.25) with a pointer to Styling → Custom fonts (which already covered the mechanics).guides/agentic_coding.md (restructure into two halves, existing content order preserved)
simctl push.apns,adbbroadcast /cmd notification post), environment discipline (.tool-versionscompleteness,MOB_DIR/MOB_DEV_DIR/MOB_NEW_DIR). The standard loop gains asettle/2step; the worked example'shandle_eventslip fixed.mob.connect --name), per-task worktrees, themob.push/mob.watchfan-out hazard (verified: no device scoping — switches are--all/--cookieonly), durable artifacts.README.md — counter example handled taps in
handle_event("tap", ...), which a device tap never reaches; nowhandle_info({:tap, :increment})with a sentence on delivery. Diagram node updated toMob.Screen.Server(one per live screen). Testing snippet moved toMob.ScreenCase.guides/device_capabilities.md — four
handle_event("tap", ...)examples →handle_info({:tap, ...}).guides/getting_started.md — referenced
Mob.Nav.push/2, which does not exist; nowMob.Socket.push_screen/2,3.guides/event_audit.md — list-select re-emitter is
Mob.Screen.Serversince MOB-113.lib/mob/app.ex —
tab_bar/1/drawer/1docstrings no longer claim chrome that is not drawn.lib/mob/test.ex — moduledoc claimed
tap/2goes throughhandle_event/3; it sends{:tap, tag}tohandle_info/2.mix.exs —
Mob.Router,Mob.Screen.Server,Mob.Listener,Mob.Sender,Mob.ScreenCasewere shipping ungrouped in the hexdocs sidebar.Deliberately not documented
Mob.Sender.activate/2's one-shot transition reservation (fix(navigation): preserve initial transition #103) and other sender/listener internals — user-visible effect ("a navigation's animation survives coalescing") is stated in navigation.md; the mechanism lives in the moduledocs/ADRs.Tap-honesty error tuples — iOS harness: stop tap_xy reporting phantom successes; add pixel sampling for colour #80 has not mergedUpdated after iOS harness: stop tap_xy reporting phantom successes; add pixel sampling for colour #80 and fix: cold-start launch notifications dropped before nif_load (Android + iOS) #77 merged and the branch was rebased onto them: the honesty-contract section now documentstap_xy/3/tap_id/2's observed-effect contract (:okonly when an event reached the BEAM within 300 ms;{:error, :no_view_at_point | :no_element_at_point | :no_effect}otherwise, with the platform limits that make:no_effectlegitimate), and the evidence-matching guidance now points exact-color decisions atMob.Test.sample_color/2(real pixels,:dominant/:averageas0xAARRGGBB, iOS debug-build only) with screenshots-with-tolerance reserved for holistic visual parity. testing.md gains matching sections. fix: cold-start launch notifications dropped before nif_load (Android + iOS) #77 required no doc change: push_notifications.md already described tap-to-open from a killed app, which that fix made true.Gates
mix docs— clean build; reference warnings 103 → 99 (removed the nonexistentMob.Nav.push/2refs; the rest pre-date this PR)mix format --check-formatted— cleanmix compile --warnings-as-errors— cleanmix test— 1280 passed (27 doctests), 38 excluded (re-run after rebasing onto iOS harness: stop tap_xy reporting phantom successes; add pixel sampling for colour #80/fix: cold-start launch notifications dropped before nif_load (Android + iOS) #77)mix credo --strict— no issues🤖 Generated with Claude Code