Сообщений 6 Оценка 15 [+1/-4] Оценить |
Почему же столько проблем с COM+, если компоненты, и особенно клиента создавать средствами .NET Framework?
По большому счету, по двум причинам:
Итак, чтобы создать полноценное COM+-приложение, нужно:
Ниже приведены описания самых важных атрибутов и пример COM+-приложения на C#:
[assembly: Guid("49E484AE-02C4-4c77-A36E-7B4ED0BCE11F")]
|
GUID библиотеки типов (LibID)
[assembly: ApplicationActivation(ActivationOption.Server)] |
Говорит regsvcs что COM+-приложение нужно регистрировать как серверное, а не как библиотечное (по умолчанию).
[assembly: ApplicationID("49E484AE-02C4-4c77-FFFF-7B4ED0BCE11F")]
|
ApplicationID в COM+. Его можно использовать при отладке.
[assembly: AssemblyDescription("Test AssemblyDescription")]
|
Превращается в атрибут helpstring в библиотеке типов.
[assembly: ApplicationName("TestNetComPlusServer")]
|
Имя COM+-приложения.
[assembly: AssemblyVersion("1.1.100.200")]
|
Версия сборки и, по совместительству, библиотеки типов. В качестве версии библиотеки типов используются первые две цифры. В случае native-клиента используется именно [version(x.x)]. Для .NET-клиентов используется полная версия сборки (!), которая помещается в custom-атрибут с ID == 90883F05-3D28-11D2-8F17-00A0C9A6186D. Например:
[
uuid(49E484AE-02C4-4C77-A36E-7B4ED0BCE11F),
version(1.1),
helpstring("Test AssemblyDescription"),
custom(90883F05-3D28-11D2-8F17-00A0C9A6186D, TestNetComPlusServer, Version=1.1.100.200, Culture=neutral, PublicKeyToken=59079f6e6ca5a503)
]
|
Это все атрибуты, применяемые к сборке.
Здесь - System.EnterpriseServices Hierarchy - можно посмотреть список других атрибутов.
А это пример приложения, созданного на Шарпе. В нем можно увидеть применение всех атрибутов и технику описания интерфейса.
[assembly: Guid("49E484AE-02C4-4c77-A36E-7B4ED0BCE11F")] [assembly: ApplicationActivation(ActivationOption.Server)] [assembly: ApplicationID("49E484AE-02C4-4c77-FFFF-7B4ED0BCE11F")] [assembly: AssemblyDescription("Test AssemblyDescription")] [assembly: ApplicationName("TestNetComPlusServer")] // Обратите внимание на то, что версия сборки задана явно!// Т.е. без использования знака *. Это позволяет отучить VS// излишне беспокоиться о "правильности" версии сборки, // и тем самым снять проблему постоянной перерегистрации// COM+-приложения, COM+-прокси и перекомпиляции клиента. [assembly: AssemblyVersion("1.1.100.200")] [assembly: AssemblyDelaySign(false)] // Строгое имя (а именно так лучше переводить "strong name") // нужно создать утилитой Sn.exe [assembly: AssemblyKeyFile("..\\..\\TestNetComPlusServer.snk")] [assembly: AssemblyKeyName("")] using System; using System.EnterpriseServices; using System.Runtime.InteropServices; namespace TestNetComPlusServer { [GuidAttribute("FBEAA7C9-06D2-40a3-A3B7-ABC769DDA589")] // Тип интерфейса: Dual, IDispatch или IUnknown [InterfaceType(ComInterfaceType.InterfaceIsDual)] publicinterface IServer { void Method1(); }; // Переключает галочку "Component supports events and statistics",// тем самым позволяя следить за активностью компонента в Component Services [EventTrackingEnabledAttribute(true)] // CLSID. Многие думают что так задается IID default-интерфейса, // но это не так. [Guid("676C8C4F-7178-4023-863F-BC13658B8688")] [ClassInterface(ClassInterfaceType.None)] // Тут же можно задать кучу других атрибутов.//[Transaction(TransactionOption.Disabled)]publicclass Server: System.EnterpriseServices.ServicedComponent, IServer { public Server(){} // Для методов тоже можно задавать атрибуты.//[AutoComplete]void IServer.Method1() { // Метод COM-объекта.int i = 0; i = i; } } } |
Ниже приведен скрипт, регистрирующий приложение в GAC и COM+:
cd bin\Debug gacutil /i TestNetComPlusServer.dll regsvcs /tlb:TestNetComPlusServer.tlb TestNetComPlusServer.dll |
В принципе, того же эффекта можно добиться изменением опций проекта.
Вот библиотека типов (реинженирнутая с помощью OLEView), получившаяся после компиляции этого проекта:
// Generated .IDL file (by the OLE/COM Object Viewer) // // typelib filename: TestNetComPlusServer.tlb [ uuid(49E484AE-02C4-4C77-A36E-7B4ED0BCE11F), version(1.1), helpstring("Test AssemblyDescription"), custom(90883F05-3D28-11D2-8F17-00A0C9A6186D, TestNetComPlusServer, Version=1.1.100.200, Culture=neutral, PublicKeyToken=59079f6e6ca5a503) ] library TestNetComPlusServer { // TLib : // TLib : Common Language Runtime Library : {BED7F4EA-1A96-11D2-8F08-00A0C9A6186D} importlib("mscorlib.tlb"); // TLib : : {4FB2D46F-EFC8-4643-BCD0-6E5BFA6A174C} importlib("System.EnterpriseServices.tlb"); // TLib : OLE Automation : {00020430-0000-0000-C000-000000000046} importlib("stdole2.tlb"); // TLib : Common Language Runtime Execution Engine 1.0 Library : {5477469E-83B1-11D2-8B49-00A0C9B7C9C4} importlib("mscoree.tlb"); // Forward declare all types defined in this typelibinterface IServer; [ odl, uuid(FBEAA7C9-06D2-40A3-A3B7-ABC769DDA589), version(1.0), dual, oleautomation, custom(0F21F359-AB84-41E8-9A78-36D110E6D2F9, TestNetComPlusServer.IServer) ] interface IServer : IDispatch { [id(0x60020000)] HRESULT Method1(); }; [ uuid(676C8C4F-7178-4023-863F-BC13658B8688), version(1.0), custom(0F21F359-AB84-41E8-9A78-36D110E6D2F9, TestNetComPlusServer.Server) ] coclass Server { interface _Object; interface IRemoteDispatch; interface IDisposable; interface IManagedObject; interface System_EnterpriseServices_IServicedComponentInfo; [default] interface IServer; }; }; |
Обратите внимание на то, что все гуиды "наши". Они не изменятся ни при перекомпиляции, ни даже при изменении имен интерфейсов.
Сообщений 6 Оценка 15 [+1/-4] Оценить |