2016-05-11 2 views
0

Я получаю зависание Automapper в приложении ASP.NET MVC 5 с целью сопоставления модели домена с ViewModel. Существует случай, когда я до сих пор не знаю, как решить: когда объект ViewModel (destination) имеет свойство не в модели домена (источник).Как использовать Automapper для назначения значений для полей в целевой модели, но не в исходной модели?

Два дополнительных свойства в ViewModel - это IEnumerables, которые мне нужно заполнить в контроллере.

Как я объясняю в комментариях в блоке Контроллер (показано ниже), модель домена является источником и будет подана в таблицу View. Дополнительные два IEnumerables в ViewModel будут заполнять DropDownLists в блоке HTML.BeginForm().

Примеры, которые я видел с помощью .CreateMap<>().ForMember(), касаются вычислений или преобразований свойств в исходной модели, а не в этом случае, когда я определяю что-то в контроллере на основе параметров Action.

Мой вопрос заключается в том, как сопоставить оставшиеся IEnumerables, как определено в контроллере?

Mapping Config в App_Start

public static class MappingConfig 
{ 
    public static void RegisterMaps() 
    { 
     AutoMapper.Mapper.Initialize(config => 
      { 
       config.CreateMap<StudentRoster, StudentRosterViewModel>(); 
      }); 
    } 
} 

модели и ViewModel:

[Table("StudentRoster")] 
public partial class StudentRoster 
{ 
    public int ID { get; set; } 

    [Required] 
    [StringLength(3)] 
    public string Campus { get; set; } 

    [Required] 
    [StringLength(4)] 
    public string FiscalYear { get; set; } 

    [Required] 
    [StringLength(50)] 
    public string StudentName { get; set; } 

    public int StudentID { get; set; }    

} 

// ViewModel 

public partial class StudentRosterViewModel 
{ 
    // Automapper successfully mappped the first five fields 
    // to the parent class 
    public int ID { get; set; } 

    public string Campus { get; set; } 

    public string FiscalYear { get; set; } 

    public string StudentName { get; set; } 

    public int StudentID { get; set; }  


    // These two fields are not in the parent class 
    public IEnumerable<SelectListItem> CampusListSelect { get; set; } 
    public IEnumerable<SelectListItem> FiscalYearSelect { get; set; } 
} 

Index Действие в контроллере:

// GET: StudentRosterViewModels 
public ActionResult Index(string campus = "MRA", string fy="FY16") 
{ 
    IEnumerable<StudentRoster> query = db.StudentRosters.Where(m=>m.Campus==campus).ToList(); 

    // This successfully maps the domain model to the viewmodel 
    // This IEnumerable will display in the "Table" 
    IEnumerable<StudentRosterViewModel> mappedQuery = 
     AutoMapper.Mapper.Map<IEnumerable<StudentRoster>, IEnumerable<StudentRosterViewModel>>(query); 

    // The two remaining IEnumerables need to be mapped to 'mappedQuery' 
    // CampusListSelect and FiscalYearSelect 
    // These two IEnumerables will populate the dropdownlists in Html.BeginForm() 
    IEnumerable<SelectListItem> CampusList = new SelectList(new List<string> { "CRA", "DRA", "MRA", "PRA" }, campus); 
    IEnumerable<SelectListItem> FiscalYearList = new SelectList(new List<string> { "FY12", "FY13", "FY14", "FY15", "FY16" }, fy);     

    return View(mappedQuery.ToList()); 
} 
+0

Я думаю, что это может помочь вам http://stackoverflow.com/questions/21413273/automapper-convert-from-multiple-sources#answer-21413828 – FabioG

+0

Возможно, я не понимаю, но похоже, что это Сообщение SO имеет дело с отображением из более чем одной исходной модели. Я имею дело с моделью назначения с двумя свойствами, которые _not_ в исходной модели. –

+0

Итак, исправьте меня, если я ошибаюсь, но вы хотите заполнить каждый элемент в 'mappedQuery'' CampusList' и 'FiscalYearList' (все элементы по тем же спискам)? – MaKCbIMKo

ответ

1

Вы можете попытаться использовать DynamicMap для заполнения ваших элементов, не создавая дополнительных классов для сопоставления.

В случае, если вы используете старую версию AutoMapper (4.1 или ниже) вы можете попробовать что-то следующее:

// GET: StudentRosterViewModels 
public ActionResult Index(string campus = "MRA", string fy="FY16") 
{ 
    IEnumerable<StudentRoster> query = db.StudentRosters.Where(m=>m.Campus==campus).ToList(); 

    // This successfully maps the domain model to the viewmodel 
    // This IEnumerable will display in the "Table" 
    IEnumerable<StudentRosterViewModel> mappedQuery = 
     AutoMapper.Mapper.Map<IEnumerable<StudentRoster>, IEnumerable<StudentRosterViewModel>>(query); 

    // The two remaining IEnumerables need to be mapped to 'mappedQuery' 
    // CampusListSelect and FiscalYearSelect 
    // These two IEnumerables will populate the dropdownlists in Html.BeginForm() 
    IEnumerable<SelectListItem> CampusList = new SelectList(new List<string> { "CRA", "DRA", "MRA", "PRA" }, campus); 
    IEnumerable<SelectListItem> FiscalYearList = new SelectList(new List<string> { "FY12", "FY13", "FY14", "FY15", "FY16" }, fy);     

    var objForDynamicMapping = new 
    { 
     CampusListSelect = CampusList, 
     FiscalYearListSelect = FiscalYearList 
    }; 

    foreach(var mappedItem in mappedQuery) 
    { 
     // will create the mapping configuration dynamically 
     AutoMapper.Mapper.DynamicMap(objForDynamicMapping, mappedItem); 
    } 

    return View(mappedQuery.ToList()); 
} 

В случае, если вы используете AutoMapper 4.2 или высоко.

Тогда вам просто нужно поставить эту строку:

var config = new MapperConfiguration(cfg => cfg.CreateMissingTypeMaps = true); 

в месте, где вы создаете конфигурацию картографа, а затем просто использовать метод Map как:

mapper.Map(objForDynamicMapping, mappedItem); 

вместо DynamicMap.

Надеюсь, это поможет.

+0

Я катился до AutoMapper 4.1.1, но два Ienumerables равны нулю. –

Смежные вопросы