Ошибка ссылки сборки призмы: System.Windows.Interactivity - PullRequest
12 голосов
/ 11 марта 2012

У меня есть приложение C # / WPF Prism (v4.0), в котором постоянно возникают проблемы с загрузкой / разрешением dll System.Windows.Interactivity, который поставляется с библиотекой Prism.Я работал три дня подряд, пытаясь отладить / решить эту проблему.Я многое узнал о разрешении сборки .Net, но пока мне не повезло с моей проблемой, поэтому я решил обратиться к сообществу StackOverflow с отчаянной просьбой о помощи.:)

У меня есть модуль, работающий как часть более крупного приложения Prism, который должен ссылаться на System.Windows.Interactivity для добавления поведения.Таким образом, у меня есть пользовательский элемент управления XAML, задающий пространство имен следующим образом:

<UserControl x:Class="MyApp.Modules.SourcesModule.myView"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity">

И затем я пытаюсь установить поведение дочернего элемента этого UserControl следующим образом:

<ListBox Name="myListBox">
    <i:Interaction.Triggers>
        <i:EventTrigger EventName="SelectionChanged">
            <i:InvokeCommandAction Command="{Binding SomeCommandOrOther}"/>
        </i:EventTrigger>
    </i:Interaction.Triggers>
</ListBox>

Как ни странно, проект строится нормально, и при наборе в ассоциированном файле code-behind и я даже могу получить автозаполнение Intellisense для объектов в пространстве имен System.Windows.Interactivity.

Однако, только во время выполнения , я получаю XamlParseException для вышеуказанного элемента ListBox.

Could not load file or assembly 'System.Windows.Interactivity, PublicKeyToken=31bf3856ad364e35' or one of its dependencies. The system cannot find the file specified. 

InnerException относится к типу System.IO.FileNotFoundException

"Could not load file or assembly 'System.Windows.Interactivity, PublicKeyToken=31bf3856ad364e35' or one of its dependencies. The system cannot find the file specified.":"System.Windows.Interactivity, PublicKeyToken=31bf3856ad364e35"

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

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

=== Pre-bind state information ===
LOG: User = aricebo-array\me
LOG: DisplayName = System.Windows.Interactivity, PublicKeyToken=31bf3856ad364e35
 (Partial)
WRN: Partial binding information was supplied for an assembly:
WRN: Assembly Name: System.Windows.Interactivity, PublicKeyToken=31bf3856ad364e35 | Domain ID: 1
WRN: A partial bind occurs when only part of the assembly display name is provided.
WRN: This might result in the binder loading an incorrect assembly.
WRN: It is recommended to provide a fully specified textual identity for the assembly,
WRN: that consists of the simple name, version, culture, and public key token.
WRN: See whitepaper http://go.microsoft.com/fwlink/?LinkId=109270 for more information and common solutions to this issue.
LOG: Appbase = file:///C:/Users/me/Documents/Development Projects/Desktop apps/Prism/MyApp/Src/MyApp/bin/Debug/
LOG: Initial PrivatePath = NULL
Calling assembly : PresentationFramework, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35.
===
LOG: This bind starts in default load context.
LOG: No application configuration file found.
LOG: Using host configuration file: 
LOG: Using machine configuration file from C:\Windows\Microsoft.NET\Framework\v4.0.30319\config\machine.config.
LOG: Policy not being applied to reference at this time (private, custom, partial, or location-based assembly bind).
LOG: Attempting download of new URL file:///C:/Users/me/Documents/Development Projects/Desktop apps/Prism/MyApp/Src/MyApp/bin/Debug/System.Windows.Interactivity.DLL.
LOG: Attempting download of new URL file:///C:/Users/me/Documents/Development Projects/Desktop apps/Prism/MyApp/Src/MyApp/bin/Debug/System.Windows.Interactivity/System.Windows.Interactivity.DLL.
LOG: Attempting download of new URL file:///C:/Users/me/Documents/Development Projects/Desktop apps/Prism/MyApp/Src/MyApp/bin/Debug/System.Windows.Interactivity.EXE.
LOG: Attempting download of new URL file:///C:/Users/me/Documents/Development Projects/Desktop apps/Prism/MyApp/Src/MyApp/bin/Debug/System.Windows.Interactivity/System.Windows.Interactivity.EXE.

Интересно, если яВ моем построенном проекте, использующем дизассемблер IL (ildasm.exe), System.Windows.Interactivity не указан в манифесте как одна из ссылочных сборок, хотя другие dll, на которые ссылаются Prism, отображаются там просто отлично.Например:

.assembly extern Microsoft.Practices.Prism
{
  .publickeytoken = (31 BF 38 56 AD 36 4E 35 )                         // 1.8V.6N5
  .ver 4:0:0:0
}
.assembly extern Microsoft.Practices.Unity
{
  .publickeytoken = (31 BF 38 56 AD 36 4E 35 )                         // 1.8V.6N5
  .ver 2:0:414:0
}

Эта проблема аналогична проблеме, упомянутой в этом другом вопросе StackOverflow: Ссылка на правильную dll System.Windows.Interactivity из приложения Prism .Тем не менее, я следую предписанному решению, упомянутому там (то есть, используя версию System.Windows.Interactivity для Prism), но безрезультатно.Просто для забавы, я также пытался использовать dll-файлы System.Windows.Interactivity, которые поставляются как с Expression Blend 3, так и с 4 SDK (конечно, отдельно), но и с ними тоже не повезло.

Я нечто-то изменилось в том, как я загрузил dll System.Windows.Interactivity, и как я загружал все остальные dll, которые поставляются с библиотекой Prism (все они находятся в папке / lib в моем решении, и я добавилони используют меню «Добавить ссылку»> «Обзор» в Visual Studio 2010 и указывают на те библиотеки на диске, которые все вместе в одном каталоге.)

Любые указания о том, куда обращаться дальше, будут наиболее ценными!Большое спасибо.

1 Ответ

32 голосов
/ 11 марта 2012

Наконец-то я нашел ответ!

При обращении к библиотекам DLL в модулях Prism механизм разрешения сборок .NET выполняет поиск ссылочных сборок в папке / bin приложения хостинга (т. Е. С использованием Shell и Bootstrapper), а не в каталоге bin модуля (при условии, что вы настроили свои модули как отдельные проекты в решении, как и я).

По стечению обстоятельств, мое хостинговое приложение ссылалось на все остальные библиотеки Prism, поэтому, когда модули ссылались на них, оно просто находило их в каталоге bin хост-приложения. Тем не менее, мое хостинговое приложение никогда не ссылалось на System.Windows.Interactivity, поэтому добавление его только в мой модуль означало, что в каталоге хост-приложений / bin не было найдено такой DLL. DLL фактически копируется в каталог / bin модуля, но некоторые особенности способа разрешения сборок работают с приложениями Prism, означающими, что приложение никогда не проверяет сборки в этой папке.

Итак, вкратце: ссылочные сборки в приложениях Prism, очевидно, должны находиться в папке / bin хост-приложения.

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

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