stride3d/stride · error · InvalidOperationException
Cannot serialize an object of type
Error message
Cannot serialize an object of type {partType.Name} as an asset part reference: the type does not implement {typeof(IIdentifiable).Name} What it means
IdentifiableAssetPartReference.GenerateProxyPart materializes a proxy instance of the given part type and assigns the stored Id to it. It requires the type to implement IIdentifiable; otherwise the generated instance cannot receive the Id and InvalidOperationException is thrown. Like FillFromPart, this enforces the identifiable contract on both ends of the reference round-trip.
Solutions
- Make the part type implement IIdentifiable (derive from Identifiable) so GenerateProxyPart can assign the Id.
- Pass the correct part Type — the identifiable one associated with the reference — to GenerateProxyPart.
- Check typeof(IIdentifiable).IsAssignableFrom(partType) before calling and handle non-identifiable types separately.
- Return null gracefully by ensuring Id == Guid.Empty only for intentionally empty references; fix the type for real parts.
Example fix
// before
var part = (AssetPart)reference.GenerateProxyPart(typeof(PlainPart));
// after
class PlainPart : Identifiable { ... } // or use the identifiable part type
var part = (AssetPart)reference.GenerateProxyPart(typeof(IdentifiablePart)); Defensive patterns
Strategy: type-guard
Validate before calling
if (!typeof(IIdentifiable).IsAssignableFrom(partType))
throw new ArgumentException($"{partType.Name} must implement IIdentifiable", nameof(partType)); Type guard
bool IsIdentifiablePartType(Type t) => typeof(IIdentifiable).IsAssignableFrom(t);
Try / catch
try { return reference.GenerateProxyPart(partType); }
catch (InvalidOperationException) { log.Error($"Cannot proxy non-identifiable type {partType.Name}"); return null; } Prevention
- Ensure every part type used in references implements IIdentifiable
- Check IsAssignableFrom before proxy generation
- Keep part base classes stable across refactorings
- Test deserialization of assets containing custom part types
When it happens
Trigger: Calling GenerateProxyPart(typeof(T)) where typeof(T) does not implement IIdentifiable — e.g. registering a reference for a part type that is not identifiable, or passing the wrong Type during proxy generation of a deserialized asset.
Common situations: Custom asset part types missing the IIdentifiable implementation on the deserialization side; refactorings that changed a part's base class; mismatched part types between the reference descriptor and the actual asset model.
Understand the failure class
Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.
Related errors
- Cannot serialize an object of type
- Unable to extract asset reference from object
- Unable to extract url reference from object
- The given container does not match the expected type.
- Unexpected arguments
AI-assisted analysis of stride3d/stride@96fad776d2 (2026-09-14).
Data as JSON: /api/errors/86c898ac9ec8c64b.
Report an issue: GitHub.
Appendix: source
Thrown at sources/assets/Stride.Core.Assets/Serializers/IdentifiableAssetPartReference.cs:44
public override string ToString()
{
return $"{{AssetPartReference: {Id}}}";
}
/// <inheritdoc/>
public void FillFromPart(object assetPart)
{
if (assetPart is not IIdentifiable identifiable)
throw new InvalidOperationException($"Cannot serialize an object of type {assetPart.GetType().Name} as an asset part reference: the type does not implement {typeof(IIdentifiable).Name}");
Id = identifiable?.Id ?? Guid.Empty;
}
/// <inheritdoc/>
public object? GenerateProxyPart(Type partType)
{
if (!typeof(IIdentifiable).IsAssignableFrom(partType))
throw new InvalidOperationException($"Cannot serialize an object of type {partType.Name} as an asset part reference: the type does not implement {typeof(IIdentifiable).Name}");
if (Id == Guid.Empty)
return null;
var assetPart = (IIdentifiable)Activator.CreateInstance(partType)!;
assetPart.Id = Id;
return assetPart;
}
}
View on GitHub (pinned to 96fad776d2)