fix(start-sdk): drop undefined keys an onWrite transformer produces - #4067
Merged
Merged
Conversation
#3874 moved the undefined-key filter from the INI writer into serialize(), which runs before a file model's onWrite transformer. Keys the transformer itself leaves undefined then reach the writer, and INI.stringify renders them as the word: Bitcoin's bitcoin.conf model, whose onWrite maps its form onto every conf key, wrote `rpcuser=undefined`, `connect=undefined` and 15 more on its first write, and its next read failed validation on `connect=undefined`. The env writer had the same gap with a transformer before #3874. rawTransformed now filters the transformer's output too. Helix-Harness: claude-code Helix-Model: claude-opus-5-5
…mat serializer serialize() filtered the data before any onWrite transformer ran, and the transformed writer filtered again after it. Each writer now filters exactly once, on whatever reaches toFile: after onWrite for the format helpers, and on the data itself for FileHelper.raw. This is where the INI writer filtered before #3874 moved it up. Helix-Harness: claude-code Helix-Model: claude-opus-5-5
dr-bonez
approved these changes
Sep 23, 2026
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 free
to 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.
What changes
A file model with an
onWritetransformer drops the keys that transformer leavesundefined, instead of writing them out as the wordundefined.filterUndefinednow runs exactly once per write, on whatever reaches the format'stoFile:rawTransformed), it runs afteronWrite, or on the data itself when there is no transformer.FileHelper.raw, it runs on the data, just before the caller's writer.The filter is removed from
serialize(), which no longer exists:writeFileandmergecallwriteDatadirectly.rawTransformedbuilds itsFileHelperImpldirectly, so the filter is not wrapped twice.Why
Before #3874, the INI writer filtered in exactly this spot:
INI.stringify(filterUndefined(inData)), after any transformer. #3874 moved the filter intoserialize()so that the env writer got it too. Butserialize()runs before the transformer, so a key the transformer itself sets toundefinedreachedINI.stringifyand was rendered as the word.Found while testing Bitcoin on SDK 3.0, on a VM built from the #4062 head. Bitcoin's
bitcoin.confmodel maps its form onto every conf key inonWrite(formToFile). On its first write after an upgrade it wrote 17 such lines, including:The next read turned
connect=undefinedinto connect-only to a peer named "undefined", which fails that field's address pattern, and init aborted:The same round trip on SDK 2.0.9 writes none of those lines.
onWritenow receives the data as given,undefinedkeys included, as it did before #3874. Bitcoin'sformToFile/stringifyPrimitivespass anundefinedvalue through unchanged, so the filter after them drops it.Changelog
No entry. #3874's entry already describes the intended behaviour under the unreleased 3.0.0, and the INI regression never shipped.
Verification
onWritethat sets a key toundefined. Without the fix, theenvandinicases fail.FileHelper.rawhands its writer no key merged asundefined.make checkand the full jest suite (136 tests) pass. Prettier 3.8.3 passes on both files.