-
-
Notifications
You must be signed in to change notification settings - Fork 213
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
Fix: Collection was modified exception #331
Conversation
Codecov Report
@@ Coverage Diff @@
## master #331 +/- ##
=======================================
Coverage 80.08% 80.08%
=======================================
Files 111 111
Lines 4423 4423
=======================================
Hits 3542 3542
Misses 881 881
Continue to review full report at Codecov.
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you take a look ?
@@ -39,7 +39,7 @@ public IEnumerable<LogEntry> FindLogEntries([NotNull] params IRequestMatcher[] m | |||
{ | |||
var results = new Dictionary<LogEntry, RequestMatchResult>(); | |||
|
|||
foreach (var log in _options.LogEntries) | |||
foreach (var log in _options.LogEntries.ToList()) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it's even better to just use the property LogEntries
here (that property is already made safe...)
Also in the DeleteLogEntry()
method, it's safer to use the LogEntries
property.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it's even better to just use the property LogEntries here (that property is already made safe...)
Adding/Removing/Setting/Clearing is thread safe for the LogEntries
property (due to https://github.com/WireMock-Net/WireMock.Net/blob/master/src/WireMock.Net/Util/ConcurrentObservableCollection.cs) but enumerating is not.
In my case we have thread 1 calling FindLogEntries
and thread 2 calling a mocked http api.
Since the foreach
loop above does not hold a lock, the log entry for the call made by thread 2 is added to the LogEntries
property. This causes the enumerator in the foreach
loop to throw an exception.
I hope that explanation makes sense?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Also in the DeleteLogEntry() method, it's safer to use the LogEntries property
Yup in that method LogEntries
is perfect, since the Remove
method on LogEntries
is thread safe.
Thanks for this PR, can you take a look at my comments? |
hi guys, I'm using version 1.0.30-ci11848 and still getting this error: HttpStatusCode set to 500 System.InvalidOperationException: Collection was modified; enumeration operation may not execute. at System.Collections.Generic.List Is it the same as in this bug? |
@gregoks A new fix is required I think. |
@gregoks Can you please try: |
Problem
We are using wiremock as part of our tests and we found that if we have tests running in parallel we sometimes get an error when calling the
FindLogEntries
method.Error
Potential Solution
This is my quick attempt at fixing the above issue. By convert the collection into a new list it shouldn't throw an error if the
LogEntries
collection is updated.From a quick google around the
ToList
method itself isn't thread safe either though. So its possible that while theToList
method is creating a copy, it fails due to the original collection getting changed.Thoughts?
@StefH