Используйте интерфейс COM-объекта по Reflection - PullRequest
0 голосов
/ 26 ноября 2018

У меня проблемы с динамическим использованием COM-объекта без добавления сборки в качестве ссылки в моем проекте.

Дело в том, что я буду использовать свое приложение на некоторых компьютерах, на которых не обязательно установлены эти сборки, и их необходимо загружать с сервера, поскольку они являются приложениями COM +.Итак, для этого я использую следующий код:

  Type _ObjectType;
        Type ObjectType
        {
            get
            {

                _ObjectType= Type.GetTypeFromProgID(APP_NAME, server);
                if (_ObjectType!= null)
                    return _ObjectType;


                _ObjectType= Type.GetTypeFromCLSID(new Guid(CLSID), server);
                if (_ObjectType!= null)
                    return _ObjectType;


                throw new Exception("Error al obtener instancia de " + APP_NAME + " en " + server);
            }
        }


         object _InstanceObject;
         object InstanceObject
        {
            get
            {


                if (ObjectType!= null)
                {
                    _InstanceObject= Activator.CreateInstance(ObjectType);
                }


                if (_InstanceObject!= null)
                    return _InstanceObject;
                else
                    throw new Exception("Error al obtener instancia de Object");
            }
        }

На данный момент у меня есть экземпляр этой COM + Aplication без добавления этих сборок в качестве ссылки на мой проект, и я могу вызывать и потреблятьМетоды этих примеров, использующих отражение, выглядят следующим образом:

//The method I'm calling have two arguments, one ByVal and one ByRef
 object[] args = new object[]
                     {
                         arg1,
                        arg2
                     };

ParameterModifier modifier = new ParameterModifier(2);

                modifier[0] = false;
                modifier[1] = false;


ParameterModifier[] mods = { modifier };

dynamic Result = (dynamic)ObjectType.InvokeMember("MyMethod", BindingFlags.InvokeMethod, null, InstanceObject, args, mods, null, null);

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

НО, тут возникает проблема.

Приложение COM + имеет интерфейс, и у этого интерфейса есть некоторые методы, которые мне нужно вызывать, но, используя предыдущий подход, я не могу этого сделать, яУ меня следующая ошибка:

  • $ exception {"Неизвестное имя. (Исключение из HRESULT: 0x80020006 (DISP_E_UNKNOWNNAME)))"} System.Runtime.InteropServices.COMException

Итак, я думаю, может быть, этот интерфейс не является общедоступным или что-то подобное, и я не могу получить доступ таким образом, поэтому я пытаюсь добавить сборку в качестве ссылкиd создать традиционный экземпляр интерфейса COM-объекта:

        MySpaceName.IMyInterface ComInterfaceInstance = new MySpaceName.IMyInterface();
        ComInterfaceInstance.MyMethod(arg1, ref arg2);

Но C # сообщает мне, что произошла ошибка:

Невозможно создать экземпляр класса или абстрактного интерфейса'IMyInterface'

Поэтому я пытаюсь создать экземпляр основного объекта COM +, а затем привести этот объект в качестве интерфейса, который имеет нужный мне метод, например:

 MySpaceName.MyObject a = new  MySpaceName.MyObject();

string param1 = "Param1";
object parm2 = new object();

((MySpaceName.IMyInterface)a).MyInterfaceMehthod(param1, ref parm2 );

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

Мне нужно пояснить, что эти приложения COM + являются библиотеками Delphi, а не сборками .NET.

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

Что-то вроде:

dynamic Result = (dynamic)ObjectType.InvokeMember("IMyInterface.MyMethod", BindingFlags.InvokeMethod, null, InstanceObject, args, mods, null, null);

или что-то, что позволяет мне вызывать метод интерфейса?

Кто-нибудь может мне помочь?

Хорошо, спасибо зачтение,

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