egametang/ET · error · Exception

cant convert to entityref, entity instanceid == 0!

Error message

cant convert to entityref, entity instanceid == 0!

What it means

Thrown by the EntityWeakRef<T> constructor when wrapping an entity with InstanceId==0. Even a weak reference requires a live (InstanceId!=0) target so the dereference can validate liveness; wrapping a disposed entity is rejected.

Source

Thrown at Packages/cn.etetet.core/Scripts/Core/Share/Entity/EntityRef.cs:146

    public struct EntityWeakRef<T>: IDisposable, IEquatable<EntityWeakRef<T>> where T: Entity
    {
        private long instanceId;
        // 使用WeakReference,这样不会导致entity dispose了却无法gc的问题
        // 不过暂时没有测试WeakReference的性能
        private readonly WeakReference<T> weakRef;

        private EntityWeakRef(T t)
        {
            if (t == null)
            {
                this.instanceId = 0;
                this.weakRef = null;
                return;
            }

            if (t.InstanceId == 0)
            {
                throw new Exception("cant convert to entityref, entity instanceid == 0!");
            }
            this.instanceId = t.InstanceId;
            this.weakRef = new WeakReference<T>(t);
        }
        
        public void Dispose()
        {
            T t = this.Entity;
            
            if (t == null)
            {
                return;
            }

            t.Dispose();
        }
        
        public T Entity

View on GitHub (pinned to 5cab01f7a8)

Solutions

  1. Validate `t != null && t.InstanceId != 0` before constructing EntityWeakRef.
  2. Drop cache entries whose InstanceId is 0 before they are wrapped.
  3. Avoid constructing refs inside cleanup paths where the entity may already be disposed.

Example fix

// before
var wr = new EntityWeakRef<T>(entity);

// after
if (entity == null || entity.InstanceId == 0) return;
var wr = new EntityWeakRef<T>(entity);
Defensive patterns

Strategy: type-guard

Validate before calling

if (entity != null && entity.InstanceId != 0)
{
    var wr = new EntityWeakRef<T>(entity);
}

Type guard

static bool IsLive<T>(T e) where T : Entity
    => e != null && e.InstanceId != 0;

Prevention

When it happens

Trigger: Constructing EntityWeakRef on a disposed entity; building a weak cache entry for an entity that was already recycled; capturing disposed entities into a weak reference list.

Common situations: Weak caches populated from entities that get disposed before insertion; deferred callbacks building weak refs for senders that died.

Related errors


AI-assisted analysis of egametang/ET@5cab01f7a8 (2026-08-13). Data as JSON: /api/errors/8c47a2d277bb0422. Report an issue: GitHub.