2013-10-15 4 views
1

У меня есть ситуация, когда я хотел бы создавать представления стиля MVC во время выполнения, используя их шаблоны EditorFor/DisplayFor (или что-то подобное).Запись и изменение кода во время выполнения

В идеале наше приложение позволит пользователю выбрать, какие поля они хотят в своем пользовательском интерфейсе (чтобы они могли добавлять/удалять любые по своему усмотрению), с этой целью я считаю, что было бы удобно создавать класс openmodel classess во время выполнения и добавить к ним различные атрибуты dataannotation в зависимости от того, какой пользователь выбирает (т. е. stringlength, required и т. д.).

Одна вещь, которую я должен иметь возможность поддерживать, - это смена созданных классов во время выполнения, не затрагивая других пользователей или необходимость выполнять полный iisreset.

Чтобы сделать это, я провел небольшое исследование, и, похоже, могут быть три разных подхода: CodeDom, RunSharp/Relfection.Emit, Roslyn.

Из того, что я могу сказать reflection.Emit/Runsharp позволит мне создавать классы и добавлять аттрибуты и свойства к ним во время выполнения и, возможно, также модифицировать их, когда мне нужно без неблагоприятных эффектов.

Я не уверен, что Roslyn разрешил бы это, я не смог отследить любые простые примеры создания класса со свойствами или атрибутами в нем, и я видел несколько упоминаний о выходе Roslyn поэтому я не уверен, что это позволяет мне изменить его позже, без неблагоприятных последствий.

В общем, из того, что я видел, большинство людей не рекомендуют CodeDom, поэтому я не совсем уверен, не должен ли я беспокоиться о том, чтобы спуститься по этому маршруту.

Может ли кто-нибудь дать мне представление о том, какое из этих направлений может быть жизнеспособным для меня?

+0

Вы действительно хотите создать тип во время выполнения? Не будет ли что-то вроде 'Dictionary ' достаточно? – svick

ответ

1

Итак, ни одно из этих решений не будет работать, и, честно говоря, генерировать тип во время выполнения действительно не то, что вы хотите здесь.

Когда дело доходит до CLR, как только у вас есть тип с полями и методами, вы не сможете добавлять новых членов или изменять членов во время выполнения. Самое близкое, что мы делаем, это функции редактирования и продолжения в Visual Studio, мы очень ограничены тем, какие изменения мы можем внести. Мы часто «обманываем», не добавляя методы или атрибуты, которые, по вашему мнению, они добавили, но мы спрячем их где-то в другом месте и испускаем IL, который ссылается на это секретное место, когда вы делаете редактирование. Сумасшедшие вещи, такие как удаление членов, полностью неподдерживаются. Даже если он был поддержан, много кода любит предполагать, что делать someObject.GetType().GetMembers() возвращает то же самое снова и снова.

Что касается Roslyn, то, когда мы говорим, что результаты являются «неизменными», мы не имеем в виду, что предъявляет любые требования к любому IL, которые вы можете сгенерировать с ним. Скорее, когда вы попросите Roslyn разобрать что-либо или проанализировать исходный код, объекты (деревья синтаксиса, информация о типе и т. Д.) Неизменяемы. Тем не менее, это не имеет значения, поскольку вы не можете изменять типы в CLR, как только они существуют.

Я с svick в его комментарии - это не то, что вы хотите сделать. Используйте некоторые подходящие структуры данных для представления вашей информации во время выполнения, вместо того, чтобы думать об этом как о конкретном классе, который каким-то образом может быть изменен.

+0

interesting, да, поскольку я делал больше исследований, это начинало думать об этом, если бы мы не требовали, чтобы пользователь мог изменять типы во время выполнения, тогда у меня бы были свои собственные готовые классы в коде, поэтому мой идея заключалась в том, чтобы попытаться воспроизвести это как можно больше, динамически создав все классы, а затем я мог бы использовать такие вещи, как отражение MVC над объектами для шаблонов, и использовать RavenDB для их сохранения без особых изменений. –

+0

Если вам нужны динамические материалы , просто используйте словарь в своих типах и не беспокойтесь о безопасности типов в традиционном смысле. –

+0

Да, я думаю, что я собираюсь с классом, который имеет свойство Key (string) и Value (object), в основном из-за некоторых проблем со связями со словарем в MVC, я понял, что мне все равно, что тип до тех пор, пока я могу сказать это через отражение, которое я могу с этим подходом –