第60章 ApplicationPart自动集成整体性和独立性插件项

上章的示例把插件项的Razor展示页面定义在了Web主程序中,这样做虽然能够简化插件集成的实现,但是破坏了插件功能实现的整体性和独立性,为了保证插件项功能实现的整体性和独立性,并自动集成到Web主程序,nopCommerce程序采用的方式是通过对插件项的csproj文件进行相应的定义和配置,在整个程序执行生成操作时会把插件项的dll文件和Razor展示页面,自动复制到Web主程序的指定文件夹中,以供ApplicationPart把插件项集成到Web主程序提供支撑。下面将参照nopCommerce程序的实现方式 ,对上章的示例程序进行重构,保证集成的插件项定义实现的整体性和独立性。最终实现程序结构如下图所示:

第60章 ApplicationPart自动集成整体性和独立性插件项_第1张图片

1 自动复制插件项到Web主程序的定义配置

1.1 重构DemoPlugin1.csproj文件

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>

    <TargetFramework>net6.0TargetFramework>

    <ImplicitUsings>enableImplicitUsings>

    <Nullable>enableNullable>

     

      <OutputPath>..\WebApplicationPart\Plugins\DemoPlugin1OutputPath>

     

      <OutDir>$(OutputPath)OutDir>

      <CopyLocalLockFileAssemblies>falseCopyLocalLockFileAssemblies>

  PropertyGroup>

   

    <ItemGroup>

        <Content Include="Views\Plugin1\HelloWorld.cshtml">

            <CopyToOutputDirectory>PreserveNewestCopyToOutputDirectory>

        Content>

    ItemGroup>

  <ItemGroup>

    <PackageReference Include="Microsoft.AspNetCore.Mvc.NewtonsoftJson" Version="6.0.7" />

  ItemGroup>

Project>

1.2 执行生成操作自动复制插件项中的指定文件到主程序

1.2.1 生成操作执行前

第60章 ApplicationPart自动集成整体性和独立性插件项_第2张图片

1.2.2 执行生成操作

    右键单击“解决方案”,然后选择“生成解决方案”;或直接点击“生成解决方案”图标第60章 ApplicationPart自动集成整体性和独立性插件项_第3张图片

第60章 ApplicationPart自动集成整体性和独立性插件项_第4张图片

1.2.3 生成操作执行后

    由生成操作自动把插件项中的指定文件,自动复制到主程序中

第60章 ApplicationPart自动集成整体性和独立性插件项_第5张图片
   

2 重构ApplicationPart加载插件项的dll文件

    var builder = WebApplication.CreateBuilder(args);

string _pluginRootDirectoryPath = builder.Environment.ContentRootPath + @"Plugins";

string _pluginDirectoryPath = builder.Environment.ContentRootPath + @"Plugins\DemoPlugin1";

if (Directory.Exists(_pluginRootDirectoryPath) && Directory.Exists(_pluginDirectoryPath))

{

    var assembly = Assembly.LoadFile(_pluginDirectoryPath + @"\DemoPlugin1.dll");

    var mvcBuilders = builder.Services.AddMvc();

    var controllerAssemblyPart = new AssemblyPart(assembly);

    mvcBuilders.ConfigureApplicationPartManager(apm =>

    {

        apm.ApplicationParts.Add(controllerAssemblyPart);

    });

}

3 主程序通过默认路由规则映射模式渲染插件项Razor页面

    .Net(Core)6框架主程序MVC模板所提供的默认路由映射规则模式为:

    app.MapControllerRoute(

    name: "default",

    pattern: "{controller=Home}/{action=Index}/{id?}");

3.1 插件项控件器行为方法渲染插件项Razor页面

namespace DemoPlugin1.Controllers

{

    public class Plugin1Controller : Controller

    {

        public IActionResult HelloWorld()

        {

            return View();

        }

        public IActionResult LibraryPlugin1()

        {

            return View("~/Plugins/DemoPlugin1/Views/Plugin1/HelloWorld.cshtml");

        }

    }

}

<li class="nav-item">

<a class="nav-link text-dark" asp-area="" asp-controller="Plugin1" asp-action="LibraryPlugin1">插件项控件器行为方法渲染a>

第60章 ApplicationPart自动集成整体性和独立性插件项_第6张图片
li>

3.2 主程序控件器行为方法渲染插件项Razor页面

namespace WebApplicationPart.Controllers

{

    public class HomeController : Controller

    {

        private readonly ILogger _logger;

        public HomeController(ILogger logger)

        {

            _logger = logger;

        }

        public IActionResult Index()

        {

            return View();

        }

        public IActionResult WebPlugin1()

        {

            return View("~/Plugins/DemoPlugin1/Views/Plugin1/HelloWorld.cshtml");

        }

    }

}

<li class="nav-item">

<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="WebPlugin1">主程序控件器行为方法渲染a>

第60章 ApplicationPart自动集成整体性和独立性插件项_第7张图片
li>

    注意:本人建议通过默认路由映射规则模式,来让主程序在浏览器渲染插件项Razor页面,毕竟这种实现方式相对简单。

对以上功能更为具体实现和注释见:22-07-31-059_WebApplicationPart(默认路由规则映射模式渲染插件项Razor页面)。

4 主程序通过自定义配置路由规则映射模式渲染插件项Razor页面

    1、自定义和配置插件项控件器行为方法与Razor页面的映射规则:

    //参照MVC默认"Aaers"映射规则,自定义和配置插件项控件器行为方法与Razor页面的映射规则,以主程序能够通过配置插件项控件器行为方法,在浏览器中渲染出插件项的Razor页面。

builder.Services.Configure(o =>

{

    //o.AreaViewLocationFormats.Add("/Plugins/{2}/{1}/Views/{0}" + RazorViewEngine.ViewExtension);

    o.AreaViewLocationFormats.Add("/Plugins/{2}/Views/{1}/{0}.cshtml" /*+ RazorViewEngine.ViewExtension=“.cshtml”*/);

});

///MVC模板自定义路由映射规则模式,该映射规则模型实际上是对"Aaers"默认映射模式的参考,也可以理解"Aaers"默认映射模式的变种,第1种被注释掉模式也是可以被正常被使用的。

//app.MapControllerRoute(

//    name: "PluginsArea",

//    pattern: "plugins/{area=DemoPlugin1}/{controller=Home}/{action=Index}/{id?}");

app.MapControllerRoute(

    name: "PluginsArea",

    pattern: "plugins/{area:exists}/{controller=Home}/{action=Index}/{id?}");

   

2、重构控件器类:DemoPlugin1.Controllers.Plugin1Controller

     [Area("DemoPlugin1")]

    public class Plugin1Controller : Controller

    {

        public IActionResult HelloWorld()

        {

            return View();

        }

        public IActionResult LibraryPlugin1()

        {

            return View("~/Plugins/DemoPlugin1/Views/Plugin1/HelloWorld.cshtml");

        }

}

第60章 ApplicationPart自动集成整体性和独立性插件项_第8张图片

3、删除Web主程序中的“Plugins”文件夹。

4、更新执行程序的生成操作在Web主程序中重新生成“Plugins”文件夹及其文件。

5、按F5执行程序,在浏览器地址栏输入:https://localhost:7239/plugins/DemoPlugin1/Plugin1/HelloWorld。

6、注意: 默认自定义路由映射规则模式,来让主程序在浏览器渲染插件项Razor页面,这种实现方式需要更加复杂的配置定义,但是却省掉了额外的控制器行为方法。

7、更多、更详细技术实现见:“https://www.cnblogs.com/lwqlun/p/11260750.html”。

8、对以上功能更为具体实现和注释见:22-07-31-060_WebApplicationPart(自定义路由规则映射模式渲染插件项Razor页面)。 

你可能感兴趣的:(ApplicationPart,插件项集成,路由映射规则)