You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Prelude surface: classes, instances, and the value functions #94
Part of #76 (Phase 3). The highest-leverage library slice: 163 passing files are blocked on Prelude alone, more than every other missing module combined.
stdlib/lib/Prelude.purs is currently six declarations — pure, bind, discard, map, apply, runEffect over foreign import data Effect. The corpus expects the standard classes and instances.
Classes and instances
Show, Eq, Ord, Semigroup, Monoid, Functor, Apply, Applicative, Foldable, plus Boolean combinators, folds, and the String/Char/Number conversions the corpus uses.
Prerequisites this exposes
Each of these is Phase 2 work, and writing the library is the forcing function that finds the rest:
Every addition compiles and executes under Wasmtime, not only type-checks. A Prelude that type-checks but cannot run does not recover a single passing file.
Acceptance
Prelude carries the classes and instances above, executes under Wasmtime, and the passing files blocked on Prelude fall toward zero.
First slice landed in #128: Data.Function and the $/# application operators.
What landed
Data.Function: apply, applyFlipped, const, flip, on, plus infixr 0 apply as $ and infixl 1 applyFlipped as #.
Prelude re-exports const, flip, $, # (the official list) with an explicit export list.
Two prerequisite fixes: a re-exported operator alias no longer requires its target's name (the purs rule), and CC's partial-application adapter now converts the parameters it leaves to the caller to the declaration's shapes.
identity is deliberately not defined here: official re-exports it from Control.Category, so it belongs with the class hierarchy rather than as a private Data.Function.identity.
Measured
PSRS_ORACLE=annotations cargo test -p psrs-driver --test suite -- --ignored --nocapture
Board
Before
After
passing resolution
209/413
225/413
missing library module
62
61
P3 resolve
138
123
P10
147
155
P5 typecheck
35
40
L1 / M2 / M3 / M4 / M5 / L6
904/908, 72/72, 34/48, 34/50, 51/92, 0/413
unchanged
Board field
The Corpus cases field is now 80: the measured number of passing files whose first blocker is a Prelude class or value name (the convention counts first blocking stage, so this is the latent recovery the issue's surface owns, not a change in the first-blocker total). The largest groups are <> 15, Monad 9, identity/show/Eq 7 each, negate 5, Functor 5, otherwise/&&/<$>/add 3 each, and singles for Semiring, Show, when, append, mod, between, and >>>.
Remaining
The class hierarchy and its instances (Semigroup/<> needs a string- and array-concatenation primitive), Show/logShow (needs number formatting and Data.Show), Eq/Ord and the arithmetic classes whose surface operators are currently Int-monomorphic intrinsics, and identity/Control.Category.
Landed the first slice: Data.Semigroup and <> (PR #130).
stdlib/lib/Data/Semigroup.purs declares class Semigroup a where append :: a -> a -> a, infixr 5 append as <>, and the String, Unit, and Array a instances; Prelude re-exports class Semigroup, append, <>.
The compiler gains the arrayAppend primitive (HIR Intrinsic::ArrayAppend → Core ExprKind::ArrayAppend → CC AssignmentKind::ArrayAppend). Because the MIR ArrayNewDefault verifier enforces array-conversion invariants, a general ArrayNewSized allocator plus two element-copy loops lower it.
Tests: PSRS_REQUIRE_WASMTIME=1 cargo test -p psrs-driver --lib tests::semigroup (4 pass; Wasmtime execution for string/array append including a non-ASCII string, and right-associativity).
Measured with PSRS_ORACLE=annotations cargo test -p psrs-driver --test suite -- --ignored --nocapture (2026-10-04):
Board
Before
After
L2 passing resolution
225/413
235/413
L2 first-stage blockers
188
178
L2 P3 / P10
123 / 155
113 / 160
L6/M7 P5 typecheck / P8 / P6
40 / 11 / 3
43 / 12 / 4
L4
34/50
35/50
L5 NoInstanceFound
38/53
40/53 (aggregate 51/92)
<> was the largest single P3 name (15 cases) and append blocked 2 more; all 17 now stop on a later stage, and 10 cases resolve past L2 (5 P10, 3 P5 typecheck, 1 P8, 1 P6). The board Corpus cases for this issue drops 80 → 70.
Still open here: show/Show, Monad, Eq, identity, Functor/<$>, negate, and the rest of the class/value surface; assertEqual and logShow (shared with #95) still need Eq/Show.
Landed Data.Functor in #142 (merge commit 77c8745).
class Functor, map, and <$> live in Data.Functor, with Array, Maybe, and Either instances. Prelude re-exports them and adds the Effect instance. That instance is the old effect-only map: creating the action does not run it.
One PSRS_REQUIRE_WASMTIME=1 PSRS_ORACLE=annotations scoreboard on 2026-10-04, Wasmtime 49.0.2, purs 0.15.16:
Board
Before
After
passing resolution
270/413
276/413
L3
35/48
36/48
L4
35/50
35/50
L5
53/80
53/79
L6/M7
124/413
125/413
All 125 runtime files exit 0. The added file is passing/3549.purs. failing/3549.purs now matches KindsDoNotUnify. failing/NewtypeInstance5.purs leaves the L5 board and fails in the newtype checker. L1 stays 904/908 and L2 failing stays 72/72.
Functor and <$> are gone from the first-blocker names. Corpus cases is now 67: Monad 14, identity 9, _ 8, negate 6, Eq1 4, <<< 4, otherwise 3, && 3, when 2, mod 2, compare 2, and one each of between, P.identity, >>>, <*>, not, Apply, ||, Applicative, -, and Foo.Bar.
The 2026-10-17 scoreboard no longer has a passing file whose first blocker is a missing Prelude name. Corpus cases moves from 67 to 0.
L2 passing resolution is 403/413, with 0 missing-library blockers, reconfirmed on 2026-10-17 against the vendored corpus (PSRS_ORACLE=annotations, compiler 886cd82c). The 6 P3 files are DeclConflict, UnknownExport, ScopeConflict, and ExportConflict. This issue stays open; the field tracks the first-blocker count, and the class surface is not re-audited by this comment.
Evidence: L2 and L6/M7 in docs/design/D-04-suite-roadmap.md, recorded by #145.
The class surface this issue owns is measured complete on the corpus: the 2026-10-17 L2 board first reported no passing file blocked on a Prelude name (Corpus cases 67 → 0), reconfirmed 2026-10-18 on master f5abccda (PR #148): passing resolution 403/413 with 0 missing-library blockers, and L6/M7 287/340 with no in-scope program's first blocker inside Prelude's surface. The corpus-facing classes landed across the phase's slices: Data.Function ($/#), Data.Semigroup (<>), Data.Show, Data.Eq/Data.Ord/Data.Semiring (intrinsic layer), Data.Functor, Data.Monoid, Data.Foldable, Data.Tuple, Data.Traversable, plus the official module surface in the vendored package (e556bf2f, 313 trusted modules). Residual library-foreign work (Test.Assert.checkThrows) is #95's Blocked row; broader class/fundep solver acceptance is #97 (closed) / #98 / #100's scope. Closing on the measured evidence.
Activity
biuld commentedon Oct 3, 2026
First slice landed in #128:
Data.Functionand the$/#application operators.What landed
Data.Function:apply,applyFlipped,const,flip,on, plusinfixr 0 apply as $andinfixl 1 applyFlipped as #.Preludere-exportsconst,flip,$,#(the official list) with an explicit export list.pursrule), and CC's partial-application adapter now converts the parameters it leaves to the caller to the declaration's shapes.identityis deliberately not defined here: official re-exports it fromControl.Category, so it belongs with the class hierarchy rather than as a privateData.Function.identity.Measured
PSRS_ORACLE=annotations cargo test -p psrs-driver --test suite -- --ignored --nocapturepassingresolutionBoard field
The
Corpus casesfield is now 80: the measured number ofpassingfiles whose first blocker is aPreludeclass or value name (the convention counts first blocking stage, so this is the latent recovery the issue's surface owns, not a change in the first-blocker total). The largest groups are<>15,Monad9,identity/show/Eq7 each,negate5,Functor5,otherwise/&&/<$>/add3 each, and singles forSemiring,Show,when,append,mod,between, and>>>.Remaining
The class hierarchy and its instances (
Semigroup/<>needs a string- and array-concatenation primitive),Show/logShow(needs number formatting andData.Show),Eq/Ordand the arithmetic classes whose surface operators are currently Int-monomorphic intrinsics, andidentity/Control.Category.Merge pull request #129 from biuld/docs/phase3-corpus-cases
biuld commentedon Oct 3, 2026
Landed the first slice:
Data.Semigroupand<>(PR #130).stdlib/lib/Data/Semigroup.pursdeclaresclass Semigroup a where append :: a -> a -> a,infixr 5 append as <>, and theString,Unit, andArray ainstances;Preludere-exportsclass Semigroup,append,<>.arrayAppendprimitive (HIRIntrinsic::ArrayAppend→ CoreExprKind::ArrayAppend→ CCAssignmentKind::ArrayAppend). Because the MIRArrayNewDefaultverifier enforces array-conversion invariants, a generalArrayNewSizedallocator plus two element-copy loops lower it.PSRS_REQUIRE_WASMTIME=1 cargo test -p psrs-driver --lib tests::semigroup(4 pass; Wasmtime execution for string/array append including a non-ASCII string, and right-associativity).Measured with
PSRS_ORACLE=annotations cargo test -p psrs-driver --test suite -- --ignored --nocapture(2026-10-04):NoInstanceFound<>was the largest single P3 name (15 cases) andappendblocked 2 more; all 17 now stop on a later stage, and 10 cases resolve past L2 (5 P10, 3 P5 typecheck, 1 P8, 1 P6). The boardCorpus casesfor this issue drops 80 → 70.Still open here:
show/Show,Monad,Eq,identity,Functor/<$>,negate, and the rest of the class/value surface;assertEqualandlogShow(shared with #95) still needEq/Show.biuld commentedon Oct 4, 2026
Landed
Data.Functorin #142 (merge commit77c8745).class Functor,map, and<$>live inData.Functor, withArray,Maybe, andEitherinstances.Preludere-exports them and adds theEffectinstance. That instance is the old effect-onlymap: creating the action does not run it.One
PSRS_REQUIRE_WASMTIME=1 PSRS_ORACLE=annotationsscoreboard on 2026-10-04, Wasmtime 49.0.2,purs0.15.16:All 125 runtime files exit 0. The added file is
passing/3549.purs.failing/3549.pursnow matchesKindsDoNotUnify.failing/NewtypeInstance5.pursleaves the L5 board and fails in the newtype checker. L1 stays 904/908 and L2 failing stays 72/72.Functorand<$>are gone from the first-blocker names. Corpus cases is now 67:Monad14,identity9,_8,negate6,Eq14,<<<4,otherwise3,&&3,when2,mod2,compare2, and one each ofbetween,P.identity,>>>,<*>,not,Apply,||,Applicative,-, andFoo.Bar.#94 stays open.
Correct the first-stage blocker decomposition and close out Phase 2
Land Effect and Effect.Console, dropping 259 blocked files
Land the unit value and Test.Assert's assertion surface
Land Data.Function and the $/# application operators
Record #94's measured corpus count in the Phase 3 row
Merge pull request #129 from biuld/docs/phase3-corpus-cases
Add Data.Functor and re-export map from Prelude
Vendor the v0.15.16 core libraries into the standard library
Vendor the v0.15.16 core libraries into the standard library
biuld commentedon Oct 16, 2026
The 2026-10-17 scoreboard no longer has a
passingfile whose first blocker is a missingPreludename.Corpus casesmoves from 67 to 0.L2
passingresolution is 403/413, with 0 missing-library blockers, reconfirmed on 2026-10-17 against the vendored corpus (PSRS_ORACLE=annotations, compiler886cd82c). The 6 P3 files areDeclConflict,UnknownExport,ScopeConflict, andExportConflict. This issue stays open; the field tracks the first-blocker count, and the class surface is not re-audited by this comment.Evidence: L2 and L6/M7 in
docs/design/D-04-suite-roadmap.md, recorded by #145.biuld commentedon Oct 18, 2026
The class surface this issue owns is measured complete on the corpus: the 2026-10-17 L2 board first reported no
passingfile blocked on aPreludename (Corpus cases67 → 0), reconfirmed 2026-10-18 on masterf5abccda(PR #148): passing resolution 403/413 with 0 missing-library blockers, and L6/M7 287/340 with no in-scope program's first blocker insidePrelude's surface. The corpus-facing classes landed across the phase's slices:Data.Function($/#),Data.Semigroup(<>),Data.Show,Data.Eq/Data.Ord/Data.Semiring(intrinsic layer),Data.Functor,Data.Monoid,Data.Foldable,Data.Tuple,Data.Traversable, plus the official module surface in the vendored package (e556bf2f, 313 trusted modules). Residual library-foreign work (Test.Assert.checkThrows) is #95's Blocked row; broader class/fundep solver acceptance is #97 (closed) / #98 / #100's scope. Closing on the measured evidence.