diff --git a/osu.Game/Database/Live.cs b/osu.Game/Database/Live.cs
index 7d607a4637..f4882ae325 100644
--- a/osu.Game/Database/Live.cs
+++ b/osu.Game/Database/Live.cs
@@ -14,7 +14,7 @@ namespace osu.Game.Database
///
///
/// To consume this as a live instance, the live object should be stored and accessed via each time.
- /// To consume this as a detached instance, assign to a variable of type . The implicit conversion will handle detaching an instance.
+ /// To consume this as a detached instance, assign to a variable of type . The implicit conversion will handle detaching an instance.
///
/// The underlying object type. Should be a with a primary key provided via .
public class Live : IEquatable>, IHasGuidPrimaryKey
@@ -33,24 +33,34 @@ namespace osu.Game.Database
private readonly ThreadLocal threadValues;
+ private readonly T original;
+
private readonly IRealmFactory contextFactory;
- public Live(T original, IRealmFactory contextFactory)
+ public Live(T item, IRealmFactory contextFactory)
{
this.contextFactory = contextFactory;
- Guid = original.Guid;
- var originalContext = original.Realm;
+ original = item;
+ Guid = item.Guid;
- threadValues = new ThreadLocal(() =>
- {
- var context = this.contextFactory.Get();
+ threadValues = new ThreadLocal(getThreadLocalValue);
- if (context == null || originalContext?.IsSameInstance(context) != false)
- return original;
+ // the instance passed in may not be in a managed state.
+ // for now let's immediately retrieve a managed object on the current thread.
+ // in the future we may want to delay this until the first access (only populating the Guid at construction time).
+ if (!item.IsManaged)
+ original = Get();
+ }
- return context.Find(Guid);
- });
+ private T getThreadLocalValue()
+ {
+ var context = contextFactory.Get();
+
+ // only use the original if no context is available or the source realm is the same.
+ if (context == null || original.Realm?.IsSameInstance(context) == true) return original;
+
+ return context.Find(ID);
}
///