Fix duplicate config section when writing a second key#314
Merged
Conversation
setInFile() appended a new [section] header whenever the target field was absent. Writing a second distinct key to a section that already existed (e.g. a second [cli] field) therefore produced a duplicate TOML table. TOML forbids duplicate tables, so the next config load failed with "table cli already exists", corrupting the user's config. Insert the field under the existing section header when that section is already present; only append a new header when the section is absent. Add a regression test covering a second key in an existing section.
7ef9ba4 to
a88175a
Compare
anisaoshafi
approved these changes
Jun 16, 2026
Member
Author
|
Thanks for taking a look, @anisaoshafi! 🍿 |
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.
Summary
config.Setpersists individual keys toconfig.tomlthroughsetInFile, which edits the file surgically to preserve user comments and formatting. It had a latent corruption bug: when the target field was absent, it always appended a brand-new[section]header — even when that section already existed. Writing a second, distinct key to an existing section produced a duplicate TOML table, which the parser rejects, so every subsequent config load failed.On a field-match miss,
setInFileunconditionally appended a new section:Today only
cli.update_skipped_versionis ever written, so the duplicate-header path is never hit — the bug is latent. But as soon as a second[cli]key is introduced (e.g. an update-notification cadence setting), the sequence becomes:cli.update_skipped_version→ appends[cli](first time, fine).cli.notify_cadence→ field absent → appends a second[cli]header.viper.ReadInConfig/toml.Unmarshalfails withtoml: table cli already exists.The user's
config.tomlis now unparseable and every command fails until the file is hand-repaired.Before (corrupted output):
After (fixed):
When the field is absent but the
[section]header already exists, insert the new field under the existing header instead of appending a duplicate table. A fresh[section]is appended only when the section does not yet exist. Behavior for existing single-field configs is unchanged; only the previously-broken "second field in an existing section" path differs.