Sagar Beeravelly
Sagar Beeravelly

Reputation: 1

Glass Mapper -ERROR Failed to render field

I'm running into the below error message when I open the sitecore page in edit mode. Any idea what seems to be the problem.

I was using Glass mapper fluent configuration and it's working fine for a few other classes. The issue seem to be with just one class and I wasn't able to find out what is causing the problem. Any help would be appreciated.

8384 13:46:48 ERROR Failed to render field at System.RuntimeMethodHandle.InvokeMethod(Object target, Object[] arguments, Signature sig, Boolean constructor) at System.Reflection.RuntimeMethodInfo.UnsafeInvokeInternal(Object obj, Object[] parameters, Object[] arguments) at System.Reflection.RuntimeMethodInfo.Invoke(Object obj, BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture) at System.Reflection.RuntimePropertyInfo.GetValue(Object obj, Object[] index) at Glass.Mapper.Sc.Configuration.SitecoreTypeConfiguration.ResolveItem(Object target, Database database) at Glass.Mapper.Sc.GlassHtml.MakeEditable[T](Expression1 field, Expression1 standardOutput, T model, Object parameters, Context context, Database database, TextWriter writer) `

Nested Exception Exception: System.Collections.Generic.KeyNotFoundException Message: The given key was not present in the dictionary. Source: Sitecore.ContentSearch at Sitecore.ContentSearch.SearchTypes.SearchResultItem.get_Item(String key) at Sitecore.ContentSearch.SearchTypes.SearchResultItem.get_Version()

Code that is causing the problem.

View rendering:

@using Glass.Mapper.Sc.Web.Mvc
@inherits GlassView<_RegionsCMS.Presentation.Models.InsightBaseModel>

<div class="nav-container">
<div class="page-nav" role="navigation">
    <h1 class="article-title">@Editable(model => model.Insight.Title)</h1>
</div>

Controller Definition:

 var insight = _sitecoreContext.GetCurrentItem<Insights>();
        var model = new InsightBaseModel
        {
            Insight = insight
        };

        return View(model);

Insights Class Definition:

  public class Insights : SearchResultItem    {
    //Basic Information
    public virtual string Title { get; set; }}

Fluent Configuration:

public static IConfigurationLoader[] GlassLoaders(){
var attributes = new AttributeConfigurationLoader("Glass.Mapper.Sc"); 
var loader = new SitecoreFluentConfigurationLoader(); 
var config = loader.Add().AutoMap(); 
config.Id(x => x.ItemId); 
config.Info(x => x.Language).InfoType(SitecoreInfoType.Language); 
config.Info(x => x.Version).InfoType(SitecoreInfoType.Version); 
config.Info(x => x.Url).InfoType(SitecoreInfoType.Url); 
return new IConfigurationLoader[] {attributes ,loader }; 
}

Upvotes: 0

Views: 1672

Answers (2)

Taras Alenin
Taras Alenin

Reputation: 8592

Looks like you are trying to read from the index, not the database. Note that not all fields are stored in the index. You should also note that the field names in the index do not always match the names in sitecore, therefore you need to decorate them correctly with [IndexField("<index field name>")] and possibly [TypeConverter(typeof(IndexFieldGuidValueConverter .. etc.))] attributes.

You've mentioned you're using the fluid Glass configuration, I guess the above solution is a declarative mapper configuration rather then fluid, so you would need to port it to fluid based configuration if you want to persist with that approach. Please note the the IndexField is Sitecore native decorator it has noting to do with Glass, but I have successful mixed them on my POCO objects to read data from both Index and DB using the same models. I prefer to generate my POCO classes based on serialised items and decorate them declaratively.

I find disassembler is one of the fastest ways to find out what is happening. Based on the below decompile of the method, in your stack dump, that throws and exception Glass mapper is trying to read a field that does not exist in the index.

// Sitecore.ContentSearch.SearchTypes.SearchResultItem
public virtual string this[string key]
{
    get
    {
        if (key == null)
        {
            throw new ArgumentNullException("key");
        }
        return this.fields[key.ToLowerInvariant()].ToString();
    }
    set
    {
        if (key == null)
        {
            throw new ArgumentNullException("key");
        }
        this.fields[key.ToLowerInvariant()] = value;
    }
}

I'm sure with some source analysis you should be able to identify the offending field. Try removing them one by one until it works. A good tool to look inside a Lucene index is Luke. Its ugly but very efficient.

Upvotes: 0

Sagar Beeravelly
Sagar Beeravelly

Reputation: 1

I was able to fix the problem. Thanks to Big T for the helping tip. After I update the code to read the object from database instead of index, it solved the problem.

   var insight = _sitecoreContext.GetCurrentItem<Insights>();
        var result = _Broker.GetInsightItem(insight);

GetInsightItem method defination would like like this:

var index = ContentSearchManager.GetIndex((SitecoreIndexableItem)ItemReferences.RootItem);
        var sitecoreService = new SitecoreService(Sitecore.Context.Database.Name);

        using (var context = index.CreateSearchContext())
        {
            var result = context.GetQueryable<Insights>()
                .FirstOrDefault(item => item.ItemId == insights.ItemId);
            sitecoreService.Map(result);
            return result;
        }

Upvotes: 0

Related Questions