using System; using System.Collections.Generic; using System.Linq; using AutoMapper; using Umbraco.Core; using Umbraco.Core.Logging; using Umbraco.Core.Models; using Umbraco.Core.PropertyEditors; using Umbraco.Core.Services; using Umbraco.Web.Models.ContentEditing; namespace Umbraco.Web.Models.Mapping { internal class PreValueDisplayResolver : ValueResolver> { private readonly Lazy _dataTypeService; public PreValueDisplayResolver(Lazy dataTypeService) { _dataTypeService = dataTypeService; } /// /// Maps pre-values in the dictionary to the values for the fields /// /// /// /// internal static void MapPreValueValuesToPreValueFields(PreValueFieldDisplay[] fields, IDictionary preValues, bool isDictionaryBased) { if (fields == null) throw new ArgumentNullException("fields"); if (preValues == null) throw new ArgumentNullException("preValues"); //now we need to wire up the pre-values values with the actual fields defined var currentIndex = 0; //used if the collection is non-dictionary based. foreach (var field in fields) { if (isDictionaryBased == false) { //we'll just need to wire up the values based on the order that the pre-values are stored var found = preValues.Any(x => x.Key.InvariantEquals(currentIndex.ToInvariantString())); if (found == false) { LogHelper.Warn("Could not find persisted pre-value for index " + currentIndex); continue; } field.Value = preValues.Single(x => x.Key.InvariantEquals(currentIndex.ToInvariantString())).Value.ToString(); currentIndex++; } else { var found = preValues.Any(x => x.Key.InvariantEquals(field.Key)); if (found == false) { LogHelper.Warn("Could not find persisted pre-value for field " + field.Key); continue; } field.Value = preValues.Single(x => x.Key.InvariantEquals(field.Key)).Value; } } } internal IEnumerable Convert(IDataTypeDefinition source) { PropertyEditor propEd = null; if (source.PropertyEditorAlias.IsNullOrWhiteSpace() == false) { propEd = PropertyEditorResolver.Current.GetByAlias(source.PropertyEditorAlias); if (propEd == null) { throw new InvalidOperationException("Could not find property editor with alias " + source.PropertyEditorAlias); } } //set up the defaults var dataTypeService = _dataTypeService.Value; var preVals = dataTypeService.GetPreValuesCollectionByDataTypeId(source.Id); IDictionary dictionaryVals = preVals.FormatAsDictionary().ToDictionary(x => x.Key, x => (object)x.Value); var result = Enumerable.Empty().ToArray(); //if we have a prop editor, then format the pre-values based on it and create it's fields. if (propEd != null) { result = propEd.PreValueEditor.Fields.Select(Mapper.Map).ToArray(); dictionaryVals = propEd.PreValueEditor.ConvertDbToEditor(propEd.DefaultPreValues, preVals); } MapPreValueValuesToPreValueFields(result, dictionaryVals, preVals.IsDictionaryBased); return result; } protected override IEnumerable ResolveCore(IDataTypeDefinition source) { return Convert(source); } } }