-
Notifications
You must be signed in to change notification settings - Fork 0
Make stream representation deterministic #39
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
|
Important Review skippedAuto incremental reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the You can disable this status message by setting the WalkthroughThe changes introduce a global stream ID counter that assigns unique numeric identifiers to each Stream instance, replacing pointer-based identity. Stream comparison and WriteTerm output now use these IDs, with a new exported ResetStreamIDCounter() function for test determinism. Tests are updated across three files to accommodate the new ID system and refactor error handling patterns. Changes
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25–30 minutes
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Codecov Report✅ All modified and coverable lines are covered by tests. @@ Coverage Diff @@
## main #39 +/- ##
==========================================
+ Coverage 98.05% 98.27% +0.21%
==========================================
Files 24 24
Lines 7917 7053 -864
==========================================
- Hits 7763 6931 -832
+ Misses 122 90 -32
Partials 32 32
... and 22 files with indirect coverage changes 🚀 New features to boost your workflow:
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Nitpick comments (5)
engine/stream.go (2)
13-31: Global stream ID counter and Reset API look sound; consider constraining Reset to testsThe atomic counter and
nextStreamID()/ResetStreamIDCounter()implementation are correct and safe for concurrent stream creation. The only concern is thatResetStreamIDCountermutates global ordering and seems to exist purely for test determinism; exporting it makes it easy for callers to reset IDs in production and silently change comparison/log ordering.If you want to keep the public surface minimal and avoid surprising global state changes, consider either:
- Making
ResetStreamIDCounterunexported and calling it only from tests in the same package, or- Leaving it exported but documenting explicitly that it is intended for testing and should not be used in normal code paths.
Also applies to: 33-37
52-62: Deterministic IDs in constructors, WriteTerm, and Compare align with the PR goalAssigning
idvianextStreamID()in allNew*Streamconstructors, printing<stream>(alias)whenaliasis set, and ordering streams byidinComparegive you stable, deterministic behavior and remove pointer-address dependence. This matches the stated objective and keepsCompareAtomicsemantics intact.One nuance: Streams constructed manually as
&Stream{...}(without going throughNew*Stream) will keep the defaultid == 0and thus all compare equal among themselves and sort before any constructor-created stream. That’s still deterministic and consistent, but if you ever rely on uniqueness for such manually created streams, you may want to either:
- Route all production code through the constructors, or
- Lazily assign an ID in
WriteTerm/Comparewhenid == 0.Given current usage, this can remain as-is, just something to be aware of.
Also applies to: 64-98, 100-107, 110-122
engine/builtin_test.go (1)
4454-4529: PutChar tests correctly handle stream-dependent errors with the new factory patternThe refactor of
TestPutCharto:
- Reset the global stream ID counter once at the start, and
- Use
streamOrAlias func() (Term, func(*testing.T))pluserr func(Term) erroris a solid way to keep tests deterministic while still building expected errors from the actual
sOrAterm passed toPutChar. This avoids brittle coupling to internal details of how streams are represented while still verifying the exactExceptionstructure.If you want to make intent slightly clearer, you could name the
Termparameter of error factories_ Termin cases where it’s ignored (e.g., simpleInstantiationError(nil)), but the current implementation is functionally fine.engine/stream_test.go (2)
16-26: Constructor tests updated for deterministic IDs and stream types look correctCalling
ResetStreamIDCounter()at the start of each constructor test and assertingid: 1plus the appropriatemode,eofAction, andstreamTypematches the new contract of theNew*Streamfunctions. This gives strong coverage that each constructor wires fields correctly and no longer relies on pointer addresses.If you want slightly stronger guards, you could also assert
reposition: falseexplicitly in these expected structs, but that’s optional since the zero value already enforces it.Also applies to: 28-38, 40-62
64-97: Stream.WriteTerm tests validate ID and alias behavior; consider simplifying the “registered” setupThe updated
TestStream_WriteTerm:
- Resets the ID counter so the first two
NewInputTextStream(nil)calls get IDs 1 and 2, and- Checks that streams without aliases render as
<stream>(0x1)/<stream>(0x2)while an aliased stream renders as<stream>(foo),accurately captures the new
WriteTermbehavior.Note that in the
"registered"case,prepareadds the stream to a localVM’sstreamsset but never assignss.vm, andWriteTermdoes not consultvmat all. As a result, that registration work has no observable effect on the assertion; the case effectively just verifies the second auto-assigned ID.You could either:
- Drop the VM registration from
"registered"to keep the test minimal, or- If the intent is to cover VM/stream integration, also set
s.vm = &vmand assert on VM state separately.Functionally it’s fine as-is; this is mostly about avoiding implied dependencies that aren’t actually exercised.
📜 Review details
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (3)
engine/builtin_test.go(3 hunks)engine/stream.go(7 hunks)engine/stream_test.go(5 hunks)
🧰 Additional context used
🧠 Learnings (1)
📚 Learning: 2024-11-24T08:47:15.195Z
Learnt from: ccamel
Repo: axone-protocol/prolog PR: 21
File: engine/builtin_test.go:40-45
Timestamp: 2024-11-24T08:47:15.195Z
Learning: In `engine/builtin_test.go`, the function `do_not_call_misc_error` intentionally panics with a non-string, non-error value (e.g., `panic(42)`) as part of the test. Do not suggest changing this code to panic with an error value.
Applied to files:
engine/builtin_test.go
🧬 Code graph analysis (2)
engine/stream.go (4)
engine/vm.go (1)
VM(122-152)engine/builtin.go (1)
Compare(883-906)engine/term.go (2)
Term(12-15)CompareAtomic(95-106)engine/env.go (1)
Env(27-32)
engine/builtin_test.go (4)
engine/stream.go (2)
ResetStreamIDCounter(29-31)NewOutputTextStream(77-86)engine/atom.go (1)
NewAtom(204-206)engine/exception.go (1)
InstantiationError(33-35)engine/variable.go (1)
NewVariable(30-38)
🔇 Additional comments (1)
engine/stream_test.go (1)
99-121: Stream.Compare tests now align with id-based orderingInitializing
sswith explicitidvalues{1, 2, 3}and using those in the comparison table ties the expectations directly to the newStream.Comparesemantics (ordering byidviaCompareAtomic). The test matrix (s > X,s = s,s < s, etc.) still exercises the same ordering cases and remains valid under the new implementation.
70ab2eb to
c080c33
Compare
Fixes #14 : make stream representation deterministic by replacing pointer-based output with IDs, provided by an atomic counter that assigns unique IDs to every stream at creation time.
Before:
<stream>(0x140001d2210)(pointer address - non-deterministic - very bad)After:
<stream>(0x1)(deterministic - very good)This is of course critical in the Axone blockchain context where deterministic behavior is essential for consensus.