Как вызывать статические методы в сборке внутри AppDomain

У меня есть следующий класс (сокращенный для удобства чтения)

public class Connection
{
    Guid _id;
    AppDomain _appDomain;
    Type _coreApp;

    public string ConnectionName
    {
        get
        {
            this._coreApp.InvokeMember("_some_property_", BindingFlags.GetProperty, null, null, null).ToString();
        }
    }

    public Connection(string username, string password)
    {
        this._id = Guid.NewGuid();
        this._appDomain = AppDomain.CreateDomain(this._id.ToString());
        Assembly asm = this._appDomain.Load("_some_dll_");
        this._coreApp = asm.GetExportedTypes().First(t => t.Name == "_some_type_");
        this._coreApp.InvokeMember("_some_method_", BindingFlags.InvokeMethod, null, null, new object[] { username, password });
    } 
}

У меня также есть следующий код

public class Main()
{
    public Main()
    {
        Connection connOne = new Connection("_some_user_1_", "_some_pw_1_");
        Connection connTwo = new Connection("_some_user_2_", "_some_pw_2_");

        string nameOne = connOne.ConnectionName;
        string nameTwo = connTwo.ConnectionName;
    }
}

Я также получил эти факты:

  • DLL, которую я загружаю в AppDomain, является сторонней.
  • _some_method_ и _some_property_ являются статическими
  • ConnectionName должно возвращать разные значения для обоих экземпляров, поскольку параметры не совпадают.

И последняя проблема, с которой я столкнулся:

Я работал в предположении, что вызов статического метода из типа в DLL в его собственном AppDomain изолирует этот вызов от других к тому же статическому методу в той же DLL в отдельном AppDomain, но по какой-то причине это не так. дело. Если бы я запустил такой код, я бы, например, получил обе строки как «результат_1», а инвертирование параметров установило бы для обеих строк значение «результат_2».

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

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


person PedroC88    schedule 30.04.2015    source источник
comment
Можете ли вы показать, где вы загружаете тип в отдельный AppDomain?   -  person Ron Beyer    schedule 30.04.2015
comment
Разве строка this._appDomain = AppDomain.CreateDomain(this._id.ToString()); не создает один AppDomain для этого экземпляра Connection? И тогда не является ли this._coreApp = asm.GetExportedTypes().First(t => t.Name == _some_type);_ созданием экземпляра типа из ЭТОГО AppDomain?   -  person PedroC88    schedule 30.04.2015
comment
Извините, пропустил эти строки при сканировании поздно ночью.   -  person Ron Beyer    schedule 30.04.2015
comment
см. это: stackoverflow.com/questions/4298913/static-fields-in -домен приложения   -  person Ron Beyer    schedule 30.04.2015
comment
@RonBeyer не стесняйтесь добавлять этот комментарий в качестве ответа, так как я нашел там то, что искал, спасибо.   -  person PedroC88    schedule 30.04.2015
comment
Я бы, если бы мог, но вопрос закрыт как дубликат. Рад, что ты понял.   -  person Ron Beyer    schedule 30.04.2015


Ответы (1)


Я согласен с @RonBeyer. Весь ваш код и вызовы вашего метода/свойства выполняются в том же AppDomain, что и ваш основной класс. Просто тот факт, что вы создаете экземпляр нового AppDomain и выполняете AppDomain.Load, не означает, что теперь вы запускаете код внутри этого другого AppDomain, который вы создали. В конечном счете, все, что вам нужно сделать, это получить экспортированные типы из сборки, а затем вызвать свойство/метод для одного из этих типов. Но нигде вы не указываете, что вызов должен происходить в другом AppDomain.

См. эти сообщения для получения некоторой информации о вызовах между доменами приложений:

Самый простой способ сделать междоменный вызов?

Вызов Cross AppDomain выполняется в вызывающем домене

person Rajeev Goel    schedule 30.04.2015
comment
Спасибо @Rajeev, хотя они не ответили на мой конкретный вопрос, они очень помогли понять мою проблему. - person PedroC88; 30.04.2015