Skip to content

Fix: persistence.py function calls in main#61

Open
SIDDHANTCOOKIE wants to merge 8 commits intoStabilityNexus:mainfrom
SIDDHANTCOOKIE:fix/persistence-hardening
Open

Fix: persistence.py function calls in main#61
SIDDHANTCOOKIE wants to merge 8 commits intoStabilityNexus:mainfrom
SIDDHANTCOOKIE:fix/persistence-hardening

Conversation

@SIDDHANTCOOKIE
Copy link
Contributor

@SIDDHANTCOOKIE SIDDHANTCOOKIE commented Mar 16, 2026

Addressed Issues:

The previous pr has no function calls from persistence.py in main.py
so it was originally just dead code with no use at all
this pr fixes that and hardens persistence.py for any mid chain crashes

Screenshots/Recordings:

TODO: If applicable, add screenshots or recordings that demonstrate the interface before and after the changes.

Additional Notes:

AI Usage Disclosure:

We encourage contributors to use AI tools responsibly when creating Pull Requests. While AI can be a valuable aid, it is essential to ensure that your contributions meet the task requirements, build successfully, include relevant tests, and pass all linters. Submissions that do not meet these standards may be closed without warning to maintain the quality and integrity of the project. Please take the time to understand the changes you are proposing and their impact. AI slop is strongly discouraged and may lead to banning and blocking. Do not spam our repos with AI slop.

Check one of the checkboxes below:

  • This PR does not contain AI-generated code at all.
  • This PR contains AI-generated code. I have read the AI Usage Policy and this PR complies with this policy. I have tested the code locally and I am responsible for it.

I have used the following AI models and tools: TODO

Checklist

  • My PR addresses a single issue, fixes a single bug or makes a single improvement.
  • My code follows the project's code style and conventions
  • If applicable, I have made corresponding changes or additions to the documentation
  • If applicable, I have made corresponding changes or additions to tests
  • My changes generate no new warnings or errors
  • I have joined the Discord server and I will share a link to this PR with the project maintainers there
  • I have read the Contribution Guidelines
  • Once I submit my PR, CodeRabbit AI will automatically review it and I will address CodeRabbit's comments.
  • I have filled this PR template completely and carefully, and I understand that my PR may be closed without review otherwise.

Summary by CodeRabbit

  • New Features

    • Optional on-disk persistence for blockchain and account state via a new CLI option to specify a persistence directory.
    • Automatic restore from saved state on startup when present, and atomic save on shutdown to prevent data loss and ensure integrity.
  • Tests

    • Comprehensive persistence tests covering save/load round-trips, integrity and tampering checks, corrupted/missing-file handling, state recomputation, and post-load behavior.

aniket866 and others added 5 commits March 16, 2026 23:05
Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Mar 16, 2026

Walkthrough

Adds atomic on-disk persistence for the blockchain via a new persistence module, re-exports save/load from the package, integrates a --datadir CLI flag, loads persisted state at startup when present, and saves the chain atomically on shutdown with integrity checks and error handling.

Changes

Cohort / File(s) Summary
CLI Integration
main.py
Added --datadir CLI option; updated `run_node(..., datadir: str
Package Exports
minichain/__init__.py
Imported and re-exported save and load from minichain.persistence; updated __all__.
Persistence Core
minichain/persistence.py
New module providing save(blockchain, path) and load(path) with atomic JSON write/read (data.json), chain integrity verification, block deserialization, state restoration, locking during serialization, and fsync/atomic-rename helpers.
Tests
tests/test_persistence.py
New comprehensive test suite covering save/load round-trips, genesis-only chains, state replay, tamper/linkage detection, corrupted/missing JSON handling, and appending blocks after load.

Sequence Diagram

sequenceDiagram
    participant App as Application
    participant Persist as Persistence Module
    participant Disk as Filesystem
    participant Chain as Blockchain

    App->>Persist: load(datadir) if provided
    Persist->>Disk: read datadir/data.json
    Persist->>Persist: _verify_chain_integrity(blocks)
    Persist->>Chain: deserialize blocks & restore accounts
    Persist-->>App: return Blockchain instance

    App->>Chain: normal operations (mining, txs)

    App->>Persist: save(chain, datadir) on shutdown
    Persist->>Persist: acquire blockchain._lock & serialize snapshot
    Persist->>Disk: atomic write datadir/temp -> datadir/data.json (fsync + rename)
    Persist-->>App: persistence complete
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Suggested labels

Python Lang

Poem

🐰 I dug a tiny data hole,
Saved blocks and state to keep the whole,
Atomic writes beneath the moon,
Load at start and save at noon,
Hooray — the chain sleeps safe and droll! ✨

🚥 Pre-merge checks | ✅ 2
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'Fix: persistence.py function calls in main' accurately describes the main objective: reintroducing and wiring persistence functions into main.py that were previously unused.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
📝 Coding Plan
  • Generate coding plan for human review comments

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.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@main.py`:
- Around line 330-335: Wrap the persistence and network shutdown in a
try/except/finally so network.stop() always executes: call save(chain, datadir)
only if datadir is set, catch and log any exception from save (including
exception details) without re-raising, and then call await network.stop() in the
finally block; reference the existing save(...) call, the datadir check, and
await network.stop() to locate where to implement the try/except/finally.
- Around line 287-289: The current except block that catches (FileNotFoundError,
ValueError) and calls logger.warning should be split: only catch
FileNotFoundError and continue starting fresh (log with file path), but treat
ValueError as fatal — log the error (include exception details and the persisted
filename) and re-raise or exit non‑zero to avoid silently overwriting
corrupted/tampered data; update the block that currently uses "except
(FileNotFoundError, ValueError) as e" and the logger.warning call accordingly so
ValueError is not swallowed.

In `@minichain/persistence.py`:
- Around line 151-153: The write currently uses os.fdopen(fd) and json.dump then
os.replace(tmp_path, filepath) but doesn't fsync, risking loss on crash; update
the write path around the with-block that uses fd/tmp_path/filepath so that
after json.dump you call f.flush() and os.fsync(f.fileno()) (or os.fsync(fd))
before closing/replacing, then after os.replace() open the containing directory
(os.path.dirname(filepath) or '.' if empty) and call os.fsync(dir_fd) on that
directory file descriptor (then close it) to ensure the rename is durable across
crashes.
- Around line 52-53: The two separate calls to _atomic_write_json for
_CHAIN_FILE and _STATE_FILE can produce a torn snapshot if a crash occurs
between them; modify the save procedure to perform a snapshot-id handshake:
write chain and state to their temp/atomic files including a common snapshot_id
(or write them then create a single atomic marker file containing snapshot_id),
then atomically publish the marker (or snapshot_id) only after both writes
succeed; update load() to read the marker and verify the snapshot_id matches in
both _CHAIN_FILE and _STATE_FILE (reject or retry if mismatched). Use the
existing _atomic_write_json and the constants _CHAIN_FILE and _STATE_FILE and
add a single-marker file (or embedded snapshot_id field) to guarantee both files
belong to the same snapshot before accepting them.

In `@tests/test_persistence.py`:
- Around line 104-119: The test test_state_recomputed_from_blocks currently only
round-trips state and won't detect if load() trusts a persisted state file;
modify the test so after calling save(bc, path=self.tmpdir) you explicitly
tamper the persisted state file (e.g., open the saved state JSON under
self.tmpdir and change Alice/Bob balances to bogus values) and write it back,
then call restored = load(path=self.tmpdir) and assert
restored.state.get_account(...) equals bc.state.get_account(...) (not the
tampered file values), ensuring replay-from-blocks behavior is validated while
keeping the test name.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 47ed40aa-4d9e-4404-b721-939b57e5e120

📥 Commits

Reviewing files that changed from the base of the PR and between 715a904 and 9447621.

📒 Files selected for processing (4)
  • main.py
  • minichain/__init__.py
  • minichain/persistence.py
  • tests/test_persistence.py

Comment on lines +104 to +119
def test_state_recomputed_from_blocks(self):
"""Balances must be recomputed by replaying blocks, not from a file."""
bc, alice_pk, bob_pk = self._chain_with_tx()
save(bc, path=self.tmpdir)

restored = load(path=self.tmpdir)
# Alice started with 100, sent 30 → 70
self.assertEqual(
restored.state.get_account(alice_pk)["balance"],
bc.state.get_account(alice_pk)["balance"],
)
# Bob received 30
self.assertEqual(
restored.state.get_account(bob_pk)["balance"],
bc.state.get_account(bob_pk)["balance"],
)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Test intent and assertions are mismatched.

Line 105 says state must be recomputed from blocks, but this test only checks round-trip equality with persisted state. It won’t catch regressions where loader trusts a tampered state.json.

Suggested correction
-    def test_state_recomputed_from_blocks(self):
-        """Balances must be recomputed by replaying blocks, not from a file."""
+    def test_state_round_trip_preserved(self):
+        """Balances should round-trip correctly through persistence."""

Or keep the current name and add tamper logic to assert replay behavior explicitly.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
def test_state_recomputed_from_blocks(self):
"""Balances must be recomputed by replaying blocks, not from a file."""
bc, alice_pk, bob_pk = self._chain_with_tx()
save(bc, path=self.tmpdir)
restored = load(path=self.tmpdir)
# Alice started with 100, sent 30 → 70
self.assertEqual(
restored.state.get_account(alice_pk)["balance"],
bc.state.get_account(alice_pk)["balance"],
)
# Bob received 30
self.assertEqual(
restored.state.get_account(bob_pk)["balance"],
bc.state.get_account(bob_pk)["balance"],
)
def test_state_round_trip_preserved(self):
"""Balances should round-trip correctly through persistence."""
bc, alice_pk, bob_pk = self._chain_with_tx()
save(bc, path=self.tmpdir)
restored = load(path=self.tmpdir)
# Alice started with 100, sent 30 → 70
self.assertEqual(
restored.state.get_account(alice_pk)["balance"],
bc.state.get_account(alice_pk)["balance"],
)
# Bob received 30
self.assertEqual(
restored.state.get_account(bob_pk)["balance"],
bc.state.get_account(bob_pk)["balance"],
)
🧰 Tools
🪛 Ruff (0.15.6)

[warning] 111-111: Use a regular assert instead of unittest-style assertEqual

Replace assertEqual(...) with assert ...

(PT009)


[warning] 116-116: Use a regular assert instead of unittest-style assertEqual

Replace assertEqual(...) with assert ...

(PT009)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/test_persistence.py` around lines 104 - 119, The test
test_state_recomputed_from_blocks currently only round-trips state and won't
detect if load() trusts a persisted state file; modify the test so after calling
save(bc, path=self.tmpdir) you explicitly tamper the persisted state file (e.g.,
open the saved state JSON under self.tmpdir and change Alice/Bob balances to
bogus values) and write it back, then call restored = load(path=self.tmpdir) and
assert restored.state.get_account(...) equals bc.state.get_account(...) (not the
tampered file values), ensuring replay-from-blocks behavior is validated while
keeping the test name.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

♻️ Duplicate comments (1)
tests/test_persistence.py (1)

103-118: ⚠️ Potential issue | 🟡 Minor

Test intent and assertions are still mismatched.

The name/docstring says “recomputed from blocks,” but this only checks round-trip equality from persisted state; it does not verify replay behavior.

Proposed adjustment
-    def test_state_recomputed_from_blocks(self):
-        """Balances must be recomputed by replaying blocks, not from a file."""
+    def test_state_round_trip_preserved(self):
+        """Balances should round-trip correctly through persistence."""
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/test_persistence.py` around lines 103 - 118, The test
test_state_recomputed_from_blocks currently only checks round-trip equality;
change it to assert that state is recomputed from blocks by tampering with or
removing the persisted state before calling load and verifying restored.state
equals bc.state (the recomputed state from blocks) and not the tampered-on-disk
state; specifically, use the existing helpers _chain_with_tx,
save(path=self.tmpdir) and load(path=self.tmpdir), alter the saved state file in
self.tmpdir (or delete it) to an incorrect value, then call load and assert
restored.state.get_account(alice_pk)["balance"] ==
bc.state.get_account(alice_pk)["balance"] and similarly for bob_pk, ensuring the
test proves replay-from-blocks rather than trusting persisted state.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@minichain/persistence.py`:
- Around line 165-170: The code opens a directory descriptor into dir_fd with
os.open and calls os.fsync(dir_fd) but if os.fsync raises the current except
block skips os.close(dir_fd) and leaks the descriptor; wrap the fsync/close in a
try/finally (or use contextlib.closing) so os.close(dir_fd) always runs (e.g.,
set dir_fd = os.open(...); try: os.fsync(dir_fd) finally: os.close(dir_fd)) and
keep the existing OSError handling around the whole open/fsync/close sequence.
- Around line 48-55: The snapshot code currently does a shallow copy of
blockchain.state.accounts after releasing the lock, which allows nested account
dicts to be mutated and produce inconsistent snapshots; while holding
blockchain._lock, replace the shallow copy (blockchain.state.accounts.copy())
with a deep copy (e.g., use copy.deepcopy(blockchain.state.accounts) after
importing copy) so the snapshot's "state" is fully frozen at the same point in
time as chain_data (chain derived from [block.to_dict() for block in
blockchain.chain]); ensure the deep copy happens inside the with
blockchain._lock block before constructing the snapshot.

In `@tests/test_persistence.py`:
- Around line 182-187: The test signs tx2 with the wrong private key; ensure the
transaction is signed with the private key that corresponds to tx2.sender (the
new keypair from _make_keypair()). Replace the current unpack and sign usage so
you capture the private key for the new public key (e.g., new_sk, new_pk =
_make_keypair()) and call tx2.sign(new_sk) instead of tx2.sign(alice_sk),
referencing _make_keypair, new_pk, alice_sk, and tx2.sign to locate the change.

---

Duplicate comments:
In `@tests/test_persistence.py`:
- Around line 103-118: The test test_state_recomputed_from_blocks currently only
checks round-trip equality; change it to assert that state is recomputed from
blocks by tampering with or removing the persisted state before calling load and
verifying restored.state equals bc.state (the recomputed state from blocks) and
not the tampered-on-disk state; specifically, use the existing helpers
_chain_with_tx, save(path=self.tmpdir) and load(path=self.tmpdir), alter the
saved state file in self.tmpdir (or delete it) to an incorrect value, then call
load and assert restored.state.get_account(alice_pk)["balance"] ==
bc.state.get_account(alice_pk)["balance"] and similarly for bob_pk, ensuring the
test proves replay-from-blocks rather than trusting persisted state.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 66b9fa6c-5388-4a5d-92ea-caa14f4b719b

📥 Commits

Reviewing files that changed from the base of the PR and between 9447621 and 1ccae68.

📒 Files selected for processing (3)
  • main.py
  • minichain/persistence.py
  • tests/test_persistence.py

@aniket866
Copy link
Contributor

@Zahnentferner and @SIDDHANTCOOKIE
This is Duplicate of #56 Check that out

@SIDDHANTCOOKIE
Copy link
Contributor Author

@Zahnentferner and @SIDDHANTCOOKIE This is Duplicate of #56 Check that out

image image why are you deleting and re-commenting the same thing

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

♻️ Duplicate comments (1)
tests/test_persistence.py (1)

103-119: ⚠️ Potential issue | 🟡 Minor

Test name and docstring don't match actual behavior.

The test is named test_state_recomputed_from_blocks with docstring claiming "Balances must be recomputed by replaying blocks, not from a file." However:

  1. The load() implementation directly assigns raw_accounts from the file (line 105 in persistence.py)
  2. This test only verifies round-trip equality, not replay behavior

Either rename the test to test_state_round_trip_preserved or implement actual tamper detection by modifying the saved state and verifying it's recomputed from blocks.

📝 Suggested rename
-    def test_state_recomputed_from_blocks(self):
-        """Balances must be recomputed by replaying blocks, not from a file."""
+    def test_state_round_trip_preserved(self):
+        """Account balances should round-trip correctly through persistence."""
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/test_persistence.py` around lines 103 - 119, The test name and
docstring are misleading: update the test function
test_state_recomputed_from_blocks to reflect its actual behavior (round-trip
equality) by renaming it to test_state_round_trip_preserved and change the
docstring to state that balances are preserved across save/load; also adjust any
references to the old name in the test suite. Alternatively, if you want to
enforce recomputation from blocks instead, modify the load() logic (where
raw_accounts is assigned) to ignore or validate raw_accounts and then implement
a tamper test that alters the saved raw_accounts before loading and asserts
balances are recomputed from blocks; reference the test function
test_state_recomputed_from_blocks, the load() function, and the raw_accounts
variable when making changes.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@minichain/persistence.py`:
- Around line 4-6: The module docstring is out of sync with the implementation:
it describes separate files `blockchain.json` and `state.json` but the code uses
a single `_DATA_FILE = "data.json"`. Update the top-level docstring in
minichain/persistence.py to accurately describe the single-file design (that
`_DATA_FILE` stores both the serialized chain and the accounts/state) and
mention any format/keys used, referencing the `_DATA_FILE` constant and the
persistence class or functions (e.g., Persistence or load/save methods) so
maintainers can find where the file is read/written.
- Around line 122-125: The genesis block validation only checks genesis.index
and genesis.hash but misses genesis.previous_hash; update the check around the
genesis variable (in minichain/persistence.py where genesis = blocks[0]) to also
assert genesis.previous_hash == "0" (or "0" * 64 if the codebase represents it
as 64 zeros) and raise a ValueError with a clear message (e.g., "Invalid genesis
block: bad previous_hash") when this condition fails so malformed genesis blocks
are rejected.
- Around line 184-188: Remove the TOCTOU-prone os.path.exists() check from the
_read_json function and rely on opening the file directly; if open() raises
FileNotFoundError (or other IO errors) let it propagate or catch-and-re-raise
with a clearer message, but do not perform the separate existence check before
calling open() in _read_json.
- Around line 104-105: Validate and deep-copy raw_accounts before assigning to
blockchain.state.accounts: ensure raw_accounts is a dict, iterate its items
(account IDs → account data) and verify required fields like "balance" and
"nonce" exist and are of the expected types, reject or sanitize malformed
entries, then assign a deep copy (e.g., via copy.deepcopy) to
blockchain.state.accounts to avoid sharing the parsed JSON object; perform this
check/assignment in the restore logic where raw_accounts is currently assigned
directly to blockchain.state.accounts.
- Around line 213-215: When loading blocks, avoid overwriting the computed
merkle_root from Block.__init__ with a None from legacy data; change the
assignment using data.get("merkle_root") so that block.merkle_root is only set
when the stored value exists and is not None (e.g., check "merkle_root" in data
and data["merkle_root"] is not None) instead of unconditionally assigning; this
ensures _verify_chain_integrity continues to use the computed merkle_root for
older blocks.

---

Duplicate comments:
In `@tests/test_persistence.py`:
- Around line 103-119: The test name and docstring are misleading: update the
test function test_state_recomputed_from_blocks to reflect its actual behavior
(round-trip equality) by renaming it to test_state_round_trip_preserved and
change the docstring to state that balances are preserved across save/load; also
adjust any references to the old name in the test suite. Alternatively, if you
want to enforce recomputation from blocks instead, modify the load() logic
(where raw_accounts is assigned) to ignore or validate raw_accounts and then
implement a tamper test that alters the saved raw_accounts before loading and
asserts balances are recomputed from blocks; reference the test function
test_state_recomputed_from_blocks, the load() function, and the raw_accounts
variable when making changes.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 0b00e318-1baf-41ec-985b-4f5c81a75927

📥 Commits

Reviewing files that changed from the base of the PR and between 1ccae68 and 71fa281.

📒 Files selected for processing (2)
  • minichain/persistence.py
  • tests/test_persistence.py

Comment on lines +4 to +6
Design:
- blockchain.json holds the full list of serialised blocks
- state.json holds the accounts dict (includes off-chain credits)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Docstring describes two-file design but implementation uses single file.

The docstring mentions blockchain.json and state.json as separate files, but the implementation uses a single _DATA_FILE = "data.json" containing both chain and state. This inconsistency could confuse future maintainers.

📝 Proposed fix to update docstring
 Design:
-  - blockchain.json  holds the full list of serialised blocks
-  - state.json       holds the accounts dict (includes off-chain credits)
+  - data.json  holds both the serialised blocks and account state in a single
+               atomic snapshot to prevent torn writes on crash
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@minichain/persistence.py` around lines 4 - 6, The module docstring is out of
sync with the implementation: it describes separate files `blockchain.json` and
`state.json` but the code uses a single `_DATA_FILE = "data.json"`. Update the
top-level docstring in minichain/persistence.py to accurately describe the
single-file design (that `_DATA_FILE` stores both the serialized chain and the
accounts/state) and mention any format/keys used, referencing the `_DATA_FILE`
constant and the persistence class or functions (e.g., Persistence or load/save
methods) so maintainers can find where the file is read/written.

@aniket866
Copy link
Contributor

@Zahnentferner and @SIDDHANTCOOKIE This is Duplicate of #56 Check that out

image image why are you deleting and re-commenting the same thing

That was by mistake I thought. but the last one is actual.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@minichain/persistence.py`:
- Around line 101-105: The load() function currently constructs a fresh
Blockchain() and then assigns blockchain.chain and blockchain.state.accounts
without holding blockchain._lock; to fix, acquire the instance's lock
(blockchain._lock) before replacing blockchain.chain and
blockchain.state.accounts (or otherwise ensure the returned instance is
documented as not safe for concurrent use during load); update the load()
implementation to lock around the assignments so they are atomic with respect to
add_block() and mirror the save() locking discipline used elsewhere.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: dccf5429-61c8-414d-bffe-a3fb2723ffc2

📥 Commits

Reviewing files that changed from the base of the PR and between 71fa281 and 0931f43.

📒 Files selected for processing (1)
  • minichain/persistence.py

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants