I’ve created classes that map to my content types (e.g. “Page”) in Contentful. I’m using the GetEntry and GetEntriesByType methods on ContentfulClient. If I use Page as the T parameter, everything works fine. But in some cases I want the metadata as well, so I am trying to pass in Entry, but the Fields property of the result is always null. (I can see in the network traffic that the fields are actually coming back from the server; the C# code just isn’t populating them.)
Using the C# code, how can I get an entry by ID and get both the content and the content type metadata?
Oh, interesting, what custom deserialization is that? Keep in mind that using JObject will not automatically resolve referenced entries. It’s almost always better to use strong types.
I have an entry ID, but I don’t know ahead of time what type of content the entry is. So when I get the JObject response, I look at sys.contentType.sys.id, and choose the type based on that. And then manually resolve the included entries/assets.
SDK-wise, it would be nice if there was a non-generic version of GetEntries that would choose the type based on the ContentTypeResolver.
Ah, sounds like what you’re looking for is the IContentTypeResolver
On the IContentfulClient you can set a ContentTypeResolver property, basically instructing the SDK how you want your different content types to be resolved. An implemented resolver could look something like this:
public class EntityResolver : IContentTypeResolver
{
public Dictionary<string, Type> _types = new Dictionary<string, Type>()
{
{ "person", typeof(Person) },
{ "product", typeof(Product) },
};
public Type Resolve(string contentTypeId)
{
return _types.TryGetValue(contentTypeId, out var type) ? type : null;
}
}
This resolver will resolve the contenttypes “person” and “product” into Person and Product respectively. All you need to do next is to give your classes some sort of marker interface, lets say IEntity and then make a call like this:
client.ContentTypeResolver = new EntityResolver();
var entities = await client.GetEntries<IEntity>();
and the entities collection would now contain both Person and Product respectively. You could then do:
var persons = entities.Where(p => p is Person);
var products = entities.Where(p => p is Product);