forked from gohugoio/hugo
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Avoid sticky errors in subsequent *Init.Do calls
When *Init.Do executes the *Init's f function, it stores the error in the *Init's err field and returns ini.err. If we call an *Init's Do method again, and there is no error in the subsequent call, ini.err remains unchanged, and *Init.Do returns it again. This becomes an issue for the "hugo server" command, which calls h.init.data.Do within *HugoSites.Data every time the site is rebuilt. If "hugo server" is started with a valid data file, and that data file is edited to make it invalid (e.g., with poorly formatted JSON), then any attempt to fix the data file only causes Hugo to return the same error. The fix is to ensure that *Init.Do resets ini.err to nil with each call. The err field of lazy.Init is not used outside of *Init.Do, so I removed it in order to simplify the code slightly and ensure that errors would not be part of an *Init's state. Instead, this change declares an error variable at the top of *Init.Do and assigns it in place of ini.err. After making this change, the go race detector began reporting a race in TestImageOps between one goroutine created in *Site.renderPages: ```go go pageRenderer(ctx, s, pages, results, wg) ``` ...and another goroutine created in *Init.withTimeout: ```go go func(cv chan verr) { v, err := f(ctx) c <- verr{v: v, err: err} }(c) ``` The race affected *pageContentOutput.content. To prevent this race, I added getter and setter methods for pageContentOutput.content that make use of a sync.RWMutex. Otherwise, this field is assigned/read directly by multiple goroutines. I made other changes in order to refactor the code and prevent unintentional memory sharing: - Removed lazy.AddWithTimeout and its tests. This function is not called anywhere, and removing it makes it slightly easier to make sense of the lazy package. - Edited the *Init.withTimeout to remove a redundant select statement. - Edited *onceMore.Do to return an error, making it a bit more straightforward to share errors between its function argument and its caller without risking unintentional memory sharing. Fixes gohugoio#7043
- Loading branch information
Showing
4 changed files
with
68 additions
and
84 deletions.
There are no files selected for viewing
This file contains 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
This file contains 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
This file contains 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
This file contains 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