Как динамически определить класс в C # PowerShell Cmdlet - PullRequest
7 голосов
/ 18 марта 2011

У меня есть некоторые данные, которые я получаю из источника данных, который представляет собой набор пар имя / значение, которые я храню в словаре.

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

Я вижу пример этого с Get-WmiObject.Он возвращает экземпляры ManagementObject (который является в основном универсальной сумкой свойств), но пользователь может напрямую обращаться к свойствам и вызывать методы для него (т.е. без необходимости вызывать методы GetPropertyValue / InvokeMethod для ManagementObject).

PS C:\temp> $comp = Get-WmiObject Win32_ComputerSystem
PS C:\temp> $comp | Get-Member

   TypeName: System.Management.ManagementObject#root\cimv2\Win32_ComputerSystem

Name                        MemberType   Definition
----                        ----------   ----------
JoinDomainOrWorkgroup       Method       System.Management.ManagementBaseObject JoinDomainO
Rename                      Method       System.Management.ManagementBaseObject Rename(Syst
SetPowerState               Method       System.Management.ManagementBaseObject SetPowerSta
UnjoinDomainOrWorkgroup     Method       System.Management.ManagementBaseObject UnjoinDomai
AdminPasswordStatus         Property     System.UInt16 AdminPasswordStatus {get;set;}
AutomaticManagedPagefile    Property     System.Boolean AutomaticManagedPagefile {get;set;}
AutomaticResetBootOption    Property     System.Boolean AutomaticResetBootOption {get;set;}
... etc ...

Как мне сделать это с моими собственными объектами?

ОБНОВЛЕНИЕ

Принятие ответа Кейта, который представляет собой общий подход .NET Framework для динамической генерации кода.Это должно работать для моего сценария, хотя я думаю, что это может быть излишним.

Я надеялся, что кто-нибудь предоставит наглядный пример этого, используя возможности, предоставляемые PowerShell.Кажется, должен быть способ динамического создания класса путем расширения классов PSObject , PSProperty и PSMethod , описанных в Powershell SDK .

К сожалению, документация вокруг этого кажется довольно скудной, с множеством нелепых утверждений, таких как ". Хотя этот класс можно извлечь из этого класса, не существует установленного сценария для этого и любой попытки сделать это.это может привести к неожиданному поведению."

Хуже всего то, что все ссылки в MSDN, объясняющие систему расширенных типов PowerShell, кажутся плохими!И единственные примеры, которые я видел в Интернете, - это как сделать это из сценария PowerShell, а не для людей, разрабатывающих командлеты с использованием C # и SDK.

Здравствуйте, кто-нибудь из команды PowerShell слушает?

Ответы [ 3 ]

6 голосов
/ 18 марта 2011

Возможность определять свои собственные новые классы - это то, что они добавили в PowerShell v2. Вот образец:

PS C:\> $def = @"
public class MyClass {
  public string MyProperty;
}
"@

PS C:\> Add-Type -TypeDefinition $def
PS C:\> $obj = New-Object MyClass
PS C:\> $obj.MyProperty = "Hello"
PS C:\> $obj

MyProperty
----------
Hello

Если вам не нужно что-то слишком сложное, вы можете воспользоваться преимуществами «сплаттинга» - обычно это для создания пар имя / значение для передачи командлетам или функциям, но это может работать как универсальный Сортировочный объект тоже:

PS C:\> $splat = @{
  Name = "goyuix"
  Site = "stackoverflow.com"
  Tag = "powershell"
}

PS H:\> $splat

Name    Value
----    -----
Name    Goyuix
Site    stackoverflow.com
Tag     powershell
3 голосов
/ 20 марта 2011

Взгляните на пространство имен System.Reflection.Emit . Это позволит вам генерировать код во время выполнения. System.AppDomain имеет ряд перегрузок, называемых DefineDynamicAssembly, которые обычно начинаются с этого места. Это возвращает AssemblyBuilder, и оттуда вы используете такие типы, как TypeBuilder, PropertyBuilder, MethodBuilder и т. Д. Эта статья CodeProject - хороший пример создания динамических типов с отражением emit.

0 голосов
/ 29 ноября 2014

Я работаю над улучшением реализации PSClass.

Источник реализации: https://github.com/ghostsquad/AetherClass/blob/master/functions/New-PSClass.ps1

Тесты с использованием: https://github.com/ghostsquad/AetherClass/blob/master/test/New-PSClass.Tests.ps1

Существует также функциональность для моделирования psclasses, то есть вы получаете все изящные функциональные возможности Moq с динамическим psobject.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...