I have implemented the RavenDB Denormalized Reference pattern. I am struggling to wire together the static index and the patch update request required to ensure that my denormal
Try changing your line:
RavenSessionProvider.UpdateByIndex(indexName, //etc
to
db.Advanced.DatabaseCommands.UpdateByIndex(indexName, //etc
This will ensure that the Update command is issued on the same (Fake) document store that you are using in your unit tests.
Answer to edit 2:
There's no automatic way to wait for non-stale results when using UpdateByIndex. You have a couple of choices in your SetUserName
method:
1 - Change your datastore to always update indexes immediately like this (NOTE: this may adversely affect performance):
store.Conventions.DefaultQueryingConsistency = ConsistencyOptions.MonotonicRead;
2 - Run a query against your index, just before the UpdateByIndex call, specifying the WaitForNonStaleResults
option:
var dummy = session.Query("Relationships_ByMentorId")
.Customize(x => x.WaitForNonStaleResultsAsOfLastWrite())
.ToArray();
3 - Catch the exception throw when the index is stale, do a Thread.Sleep(100)
and retry.
Answer to edit 3:
I've finally figured it out, and have a passing test... can't believe it, but it seems to just have been a caching issue. When you re-load your docs for asserting against, you need to use a different session... e.g.
using (var db = Fake.Db())
{
const string userName = "updated-mentor-username";
var mentor = Fake.Mentor(db);
var mentee = Fake.Mentee(db);
var relationship = Fake.Relationship(mentor, mentee, db);
db.Store(mentor);
db.Store(mentee);
db.Store(relationship);
db.SaveChanges();
MentorService.SetUserName(db, mentor, userName);
}
using (var db = Fake.Db())
{
relationship = db
.Include("Mentor.Id")
.Load(relationship.Id);
//etc...
}
Can't believe I didn't spot this sooner, sorry.