dotnet/wpf · error · InvalidOperationException
SR.ExpectedResourceDictionaryTarget
Error message
SR.ExpectedResourceDictionaryTarget
What it means
Inside ConvertFrom, after obtaining IProvideValueTarget, the converter checks that the target object receiving the deferred content is a ResourceDictionary. Deferred content is only meaningful inside a ResourceDictionary; if the value target is any other object the converter throws InvalidOperationException.
Solutions
- Only use DeferrableContentConverter for values that live inside a ResourceDictionary (e.g. deferred BAML entries of a .xaml resource dictionary)
- Remove a custom DeferringLoader/ValueSerializer assignment from types that are not ResourceDictionary content
- If building a test harness, register an IProvideValueTarget whose TargetObject is a real ResourceDictionary instance
Example fix
// before
typeDescriptorContext.GetService(typeof(IProvideValueTarget)) as IProvideValueTarget
// returns a target that is not a ResourceDictionary
// after
var ipvt = (IProvideValueTarget)provider.GetService(typeof(IProvideValueTarget));
if (ipvt.TargetObject is ResourceDictionary) { /* safe to proceed */ } Defensive patterns
Strategy: type-guard
Validate before calling
var ipvt = provider.GetService(typeof(IProvideValueTarget)) as IProvideValueTarget;
if (ipvt?.TargetObject is not ResourceDictionary)
throw new InvalidOperationException("DeferrableContentConverter may only target a ResourceDictionary."); Type guard
static bool TargetsResourceDictionary(IServiceProvider p) =>
(p.GetService(typeof(IProvideValueTarget)) as IProvideValueTarget)?.TargetObject is ResourceDictionary; Try / catch
try { return (DeferrableContent)converter.ConvertFrom(ctx, culture, value); }
catch (InvalidOperationException ex) when (ex.Message.Contains("ResourceDictionary")) { /* handle non-dictionary target */ } Prevention
- Only attach the WPF deferring loader to types consumed inside ResourceDictionary
- In custom pipelines, verify IProvideValueTarget.TargetObject type before invoking the converter
- Don't reuse DeferrableContentConverter for generic deferred content scenarios
When it happens
Trigger: Invoking DeferrableContentConverter.ConvertFrom when the IProvideValueTarget.TargetObject returned by the service provider is not a ResourceDictionary — i.e. the deferral loader is being applied outside a dictionary, such as directly in a control's property or in a non-dictionary resource scope.
Common situations: Manually constructing a service provider for a ValueSerializer/TypeConverter test, copying a DeferringLoader attribute onto a type not used inside ResourceDictionary, or WPF internals changed by a framework version mismatch so the target is typed differently.
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
- SR.KeyCollectionHasInvalidKey
- SR.NamesNotSupportedInsideResourceDictionary
- SR.ResourceDictionaryDeferredContentFailure
- SR.ResourceDictionaryDuplicateDeferredContent
- SR.SharedAttributeInLooseXaml
AI-assisted analysis of dotnet/wpf@81131a70a4 (2026-09-14).
Data as JSON: /api/errors/b0bf9dae527a0504.
Report an issue: GitHub.
Appendix: source
Thrown at src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/DeferrableContentConverter.cs:49
XamlSchemaContext xamlSchemaContext =
RequireService<IXamlSchemaContextProvider>(context).SchemaContext;
Baml2006SchemaContext schemaContext = xamlSchemaContext as Baml2006SchemaContext;
if (schemaContext == null)
{
throw new InvalidOperationException(SR.ExpectedBamlSchemaContext);
}
IXamlObjectWriterFactory objectWriterFactory =
RequireService<IXamlObjectWriterFactory>(context);
IProvideValueTarget ipvt =
RequireService<IProvideValueTarget>(context);
IRootObjectProvider rootObjectProvider =
RequireService<IRootObjectProvider>(context);
ResourceDictionary dictionary = ipvt.TargetObject as ResourceDictionary;
if (dictionary == null)
{
throw new InvalidOperationException(SR.ExpectedResourceDictionaryTarget);
}
Stream stream = value as Stream;
if (stream == null)
{
byte[] bytes = value as byte[];
if (bytes != null)
{
stream = new MemoryStream(bytes);
}
}
if (stream == null)
{
throw new InvalidOperationException(SR.ExpectedBinaryContent);
}
// we shouldn't pass around the service provider
DeferrableContent deferrableContext = new DeferrableContent(stream, schemaContext,View on GitHub (pinned to 81131a70a4)