-
Notifications
You must be signed in to change notification settings - Fork 387
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
Concurrency issue with the UnitValueAbbreviationLookup #919
Comments
|
Right, there are 3 options that I can see (yours being the second):
I personally don't think we should store the passed-in string at all: this would leave us with the following tradeoff - lock-on-read-and-across-the-board-thread-safety-guarantee vs no-thread-safety-guarantees (+ the code size difference) In summary, if we say that late-bound mappings on UnitAbbreviationCache.Default should be avoided (especially ones setting the default abbreviation), then I'd say that option 1 is the way to go (+ maybe using a SortedSet) |
Correction: I was thinking of LinkedHashSet when talking about SortedSet, but anyways- I believe even the HashSet preserves the insert order (until you start removing stuff). PS: Ok, that's wouldn't be an ideal solution cause you'd have to re-create the whole set when setting a default abbreviation, but still better than doing Distinct().ToList() every time.. PS2 Is there any actual need for Distinct().ToList() : it seems to me like the Add method already discards any duplicates |
Gotcha. No, I agree, it seems like a flaw that we store the passed in abbreviation if there is a miss. |
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions. |
Faced this problem.
If I call the endpoints one by one, then everything works fine. |
I think there were no more reports about this bug, because my case is quite specific. If you are wonder, I'll clarify my case detailly. To bypass this limitation, I reproduced the |
Thanks for the details. At any rate, there are two things going wrong here:
|
Fixes #919 Duplicates #924 Do not update collection on get. Co-authored-by: lipchev <[email protected]>
Refs #919 Use `ConcurrentDictionary` for lookups. Use `IReadOnlyList` and treat list instances as immutable. Reduce `ToList()` allocations. Use `Lazy` to compute all abbreviations.
I tried on version 5.0.0-rc004, everything works fine 👍 |
Describe the bug
There is a possible concurrency issue with adding the missing abbreviation here (likely applicable to the overloads as well).
To Reproduce
Expected behavior
The GetMethod simply returns the empty list (I don't know if it's worth storing every single string that is passed in the method).
As for the actual mapping vs getting - it is very unlikely that someone would actually MapUnitAbbreviations while at same time parsing in a another thread, using the same AbbreviationCache, but I could see a use case where abbreviations are added asynchronously so I don't know I guess we could use a Concurrent collection instead..
See, now that I think about it- even if mapping inside a static constructor (as I do) there is always the possibility for somebody (unknowingly) launching an asynchronous operation that does any string-related operation that crashes the whole thing because it is reading some abbreviation while my InitializeCustomAbbreviations is still executing.
The text was updated successfully, but these errors were encountered: