我正在尝试将 Microsoft 可扩展性框架 (MEF) 实现到基于 MVC 的示例 Web 应用程序中。我在MEF 概述页面上使用 SimpleCalculator 示例解决方案。我的目标是一个可以从另一个项目动态加载 DLL 扩展以扩展模型功能的应用程序,本质上我希望 MVC 应用程序成为其他扩展插件的框架。首先我的设置:
项目 1(MVC 应用程序,MEF 组件主机):
我将模型中的元素装饰如下:
using System.ComponentModel.Composition;
using System.ComponentModel.Composition.Hosting;
namespace ExpressionParserPOC.Models
{
public class ExpressionModel
{
private CompositionContainer _container;
[ImportMany]
IEnumerable<Lazy<IExtensions,IExtensionName>> extensions { get; set; }
public ExpressionModel()
{
var catalog = new AggregateCatalog();
catalog.Catalogs.Add(new DirectoryCatalog("C:\\local_visual_studio\\ExpressionParserPOC\\ExpressionParserPOC\\Extensions"));
//Create the CompositionContainer with the parts in the catalog
_container = new CompositionContainer(catalog);
_container.ComposeParts(_container);
//TEST: Can we access the extensions?
if (extensions != null)//<--NULL WHEN CONSTRUCTOR IS CALLED WHY? Expected GetMatrix() Function from DLL to be exposed
{
foreach (Lazy<IExtensions, IExtensionName> i in extensions)
{
Lazy<IExtensions, IExtensionName> foo = i;
}
}
}
}
public interface IExtensions
{
double[][] GetMatrix(string matrix);
}
public interface IExtensionName
{
Char Symbol { get; }
}
}
现在要测试,我只是从控制器调用模型的构造函数:
namespace ExpressionParserPOC.Controllers
{
public class HomeController : Controller
{
public ActionResult Index()
{
ViewBag.Message = "Enter an Expression for Octave to evaluate";
//Instantiate an ExpressionModel composed of extensible parts
var model = new ExpressionModel();
return View(model);
}
}
}
项目 2(DLL 项目,MEF 组件):
//PROJECT BUILD OUTPUTS TO THE EXTENSIONS DIRECTORY IN PROJECT 1 ABOVE
using System.ComponentModel.Composition;
namespace MyExtensions
{
//Project 1 already added as a reference
[Export(typeof(ExpressionParserPOC.Models.IExtensions))]
[ExportMetadata("Symbol", 'o')]
public class Octave : MyExtensions.IExtensions
{
//Other class properties, constructors, functions, etc.
#region FUNCTIONS
public double[][] GetMatrix(string matrix)
{
double[][] mat = new double[][];
//Do Stuff
return mat;
}
#endregion
}
public interface IExtensions : ExpressionParserPOC.Models.IExtensions
{
}
}
问题是当我从同一个项目中的控制器调用模型构造函数时,主机 MVC 应用程序项目中的扩展列表永远不会被填充。我是 MEF 开发的新手,不确定我做错了什么,因为我正在使用 MVC 应用程序,所以我需要考虑一些额外的事情吗?为什么没有填写 Project 1 扩展列表?我的接口定义错了吗?示例计算器应用程序是一个简单的命令行项目,似乎工作正常,我看到的唯一区别是外部 DLL 项目位于同一解决方案空间中,而在我的示例中,解决方案空间是独立的。