abpframework/abp · error · IndexOutOfRangeException
targetIndex should be between 0 and {source.Count - 1}
Error message
targetIndex should be between 0 and {source.Count - 1} What it means
Thrown by AbpListExtensions.MoveItem when targetIndex is outside [0, source.Count - 1]. MoveItem relocates the element matching selector to targetIndex via RemoveAt + Insert, so an out-of-range index is rejected up front with IndexOutOfRangeException. An empty list makes the valid range [0, -1], so any targetIndex throws.
Source
Thrown at framework/src/Volo.Abp.Core/System/Collections/Generic/AbpListExtensions.cs:155
}
public static void ReplaceOne<T>(this IList<T> source, T item, T replaceWith)
{
for (int i = 0; i < source.Count; i++)
{
if (Comparer<T>.Default.Compare(source[i], item) == 0)
{
source[i] = replaceWith;
return;
}
}
}
public static void MoveItem<T>(this List<T> source, Predicate<T> selector, int targetIndex)
{
if (!targetIndex.IsBetween(0, source.Count - 1))
{
throw new IndexOutOfRangeException("targetIndex should be between 0 and " + (source.Count - 1));
}
var currentIndex = source.FindIndex(0, selector);
if (currentIndex == targetIndex)
{
return;
}
var item = source[currentIndex];
source.RemoveAt(currentIndex);
source.Insert(targetIndex, item);
}
[NotNull]
public static T GetOrAdd<T>([NotNull] this IList<T> source, Func<T, bool> selector, Func<T> factory)
{
Check.NotNull(source, nameof(source));
View on GitHub (pinned to 7ed43b1931)
Solutions
- Bound-check targetIndex before calling: targetIndex = Math.Clamp(targetIndex, 0, source.Count - 1) (only if Count > 0).
- Ensure the list is non-empty and targetIndex was computed from the current Count.
- Handle the empty-list case explicitly before attempting to move an item.
Example fix
// before list.MoveItem(x => x.Id == id, newIndex); // throws if newIndex out of range // after if (list.Count == 0) return; list.MoveItem(x => x.Id == id, Math.Clamp(newIndex, 0, list.Count - 1));
Defensive patterns
Strategy: validation
Validate before calling
// Bound-check before moving, and handle empty lists
if (source.Count > 0)
source.MoveItem(selector, Math.Clamp(targetIndex, 0, source.Count - 1)); Prevention
- Compute targetIndex from the live list Count, not a stale value.
- Guard the empty-list case before calling MoveItem.
- Use Math.Clamp to keep targetIndex in [0, Count-1].
When it happens
Trigger: Calling list.MoveItem(selector, targetIndex) with targetIndex < 0 or >= list.Count; calling on an empty list; computing targetIndex from a stale count.
Common situations: UI reorder logic that passes an index from a different-sized list; off-by-one (using Count instead of Count-1); calling MoveItem before the list is populated.
Related errors
- len argument can not be bigger than given string's length!
- Given type ({item.AssemblyQualifiedName}) should be instance
- Cyclic dependency found! Item: {item}
- {parameterName} is null!
- {parameterName} has a default value!
AI-assisted analysis of abpframework/abp@7ed43b1931 (2026-08-13).
Data as JSON: /api/errors/6f7875e34bc0c719.
Report an issue: GitHub.