В настоящее время я создаю новый раздел отчетов для одного из наших продуктов на работе и занимаюсь этой же проблемой. Решение, которое я придумала до сих пор, хотя оно еще не было реализовано, так что это все еще в стадии разработки, соответствует этому.
Будет класс, который будет представлять фильтр отчета, который будет содержать некоторую базовую информацию, такую как текст метки и список значений параметров.
public enum DisplayStyle
{
DropDown,
ListBox,
RadioList,
CheckList,
TextBox
}
public class FilterOption
{
public string Name { get; set; }
public string Value { get; set; }
public bool Selected { get; set; }
}
public class ReportFilter
{
public string Title { get; set; }
public DisplayStyle Style { get; set; }
public List<FilterOption> Options { get; set; }
}
И тогда моя модель будет содержать список этих классов опций, которые будут сгенерированы на основе потребностей каждого отчета. У меня также есть базовый класс отчета, от которого унаследуется каждый отчет, чтобы я мог обрабатывать построение списков опций для каждого отчета и использовать одно представление для их обработки.
public class ReportModel
{
public string Name { get; set; }
public List<ReportFilter> Filters { get; set; }
public DateTime StartDate { get; set; }
public DateTime EndDate { get; set; }
}
Тогда внутри моих представлений у меня будут некоторые вспомогательные методы, которые будут принимать эти классы опций и создавать для меня фактические элементы управления.
public static string ReportFilter(this HtmlHelper htmlHelper, DisplayStyle displayStyle, FilterOption filterOption)
{
switch (displayStyle)
{
case DisplayStyle.TextBox:
return string.Format("<input type=\"text\"{0}>", filterOption.Selected ? (" value=\"" + filterOption.Value + "\"") : string.Empty);
break;
...
}
}
Мой маршрут будет выглядеть так
Reports/{reportID}/start/{startDate}/end/{endDate}/{*pathInfo}
Все отчеты имеют дату начала и окончания, а затем дополнительные фильтры. Параметр catchall будет иметь списки значений фильтра в форме «Клиент / 1,4,7 / Программа / 45,783». Так что это будет похоже на пару ключ / значение в форме списка. Затем, когда контроллер загружается, он анализирует эти значения во что-то более значимое.
public static Dictionary<string, string> RouteParams(string pathInfo)
{
if (string.IsNullOrEmpty(pathInfo))
{
return new Dictionary<string, string>();
}
var values = new Dictionary<string, string>();
// split out params and add to the dictionary object
return values;
}
Затем он передает их классу отчета и проверяет их, чтобы убедиться, что они верны для этого отчета. Затем при загрузке параметров для этого отчета все, что было установлено в URL-адресе, будет установлено в значение «Выбрано» в классе ReportOption, чтобы можно было поддерживать их состояние. Затем список фильтров и другие данные отчета будут добавлены в модель.
Для моей настройки некоторые фильтры изменятся при изменении выбора другого фильтра, поэтому здесь будет некоторое количество AJAX для публикации данных и получения обновленных параметров фильтра. Развертывание будет работать подобно параметрам поиска в amazon или newegg, когда вы сузите критерии поиска.
Я надеюсь, что все это имеет смысл для кого-то, кроме меня. И если у кого-то есть вклад в его улучшение, я буду рад это услышать.