EllanJiang/GameFramework · error · GameFrameworkException

Release object filter callback is invalid.

Error message

Release object filter callback is invalid.

What it means

ObjectPool<T>.Release(int toReleaseCount, ReleaseObjectFilterCallback<T>) requires a filter callback to decide which objects may be released. Passing a null delegate is rejected with this GameFrameworkException before any release logic runs.

Solutions

  1. Pass a real filter, e.g. (obj) => true to release any candidate.
  2. Use the parameterless Release() or Release(int) overloads when no custom filtering is needed.
  3. Ensure the callback field is initialized before the release call.

Example fix

// before
pool.Release(5, null);
// after
pool.Release(5, internalObject => internalObject.Priority < 10);
Defensive patterns

Strategy: validation

Validate before calling

if (releaseObjectFilterCallback != null)
{
    pool.Release(toReleaseCount, releaseObjectFilterCallback);
}
else
{
    pool.Release(toReleaseCount); // default behavior
}

Try / catch

try { pool.Release(count, filter); }
catch (GameFrameworkException) { /* filter was null; fall back to pool.Release(count) */ }

Prevention

When it happens

Trigger: Calling Release(count, null); a filter delegate variable that was never assigned or was cleared; invoking the count-based overload intending to use the parameterless default-filter path.

Common situations: Refactoring from Release() (no-arg) or Release(count) to the filtered overload and forgetting the callback; conditional callback assignment that left it null.

Related errors


AI-assisted analysis of EllanJiang/GameFramework@d0c010b051 (2026-09-15). Data as JSON: /api/errors/47a6e734bf809976. Report an issue: GitHub.

Appendix: source

Thrown at GameFramework/ObjectPool/ObjectPoolManager.ObjectPool.cs:477

            /// <summary>
            /// 释放对象池中的可释放对象。
            /// </summary>
            /// <param name="releaseObjectFilterCallback">释放对象筛选函数。</param>
            public void Release(ReleaseObjectFilterCallback<T> releaseObjectFilterCallback)
            {
                Release(Count - m_Capacity, releaseObjectFilterCallback);
            }

            /// <summary>
            /// 释放对象池中的可释放对象。
            /// </summary>
            /// <param name="toReleaseCount">尝试释放对象数量。</param>
            /// <param name="releaseObjectFilterCallback">释放对象筛选函数。</param>
            public void Release(int toReleaseCount, ReleaseObjectFilterCallback<T> releaseObjectFilterCallback)
            {
                if (releaseObjectFilterCallback == null)
                {
                    throw new GameFrameworkException("Release object filter callback is invalid.");
                }

                if (toReleaseCount < 0)
                {
                    toReleaseCount = 0;
                }

                DateTime expireTime = DateTime.MinValue;
                if (m_ExpireTime < float.MaxValue)
                {
                    expireTime = DateTime.UtcNow.AddSeconds(-m_ExpireTime);
                }

                m_AutoReleaseTime = 0f;
                GetCanReleaseObjects(m_CachedCanReleaseObjects);
                List<T> toReleaseObjects = releaseObjectFilterCallback(m_CachedCanReleaseObjects, toReleaseCount, expireTime);
                if (toReleaseObjects == null || toReleaseObjects.Count <= 0)
                {

View on GitHub (pinned to d0c010b051)