(四)学习了解OrchardCore笔记——将模块的名字添加到程序集的ModuleName

  关于若何将模块名添加到程序集的ModuleName说简朴吧也简朴,说不简朴吧也不简朴。

  简朴的原因是代码只有几行,不简朴的原因是这些都不是c#,都是MSbuild的代码。这可真难为我了,以是这个地方我卡了两个星期。

  首先我们来看下解决方案的目录:

(四)学习了解OrchardCore笔记——将模块的名字添加到程序集的ModuleName

  都知道这些文件夹都是解决方案文件夹,然则build解决方案文件夹里放的是什么,居然不是项目?不是项目若何挪用呢,这可触及我的知识盲点。经由多方查阅资料和博问上提问,我重于搞清楚了。

  首先,这两个.yml文件删了也无所谓,我第一次见到yml文件照样在docker的设置上,也就是一个跟我们常用的json一样的设置文件(用缩进取代json内里那堆括号,有人以为这样对照利便)。最先我还以为是通过其它程序靠yml设置文件注入模块,被误导了很久,这两个设置文件就是连续集成的设置文件(没进过大厂不懂这些被虚耗很久),也就是项目公布到github会自动帮你build等等。

  其次,就是剩下的文件是靠Directory.Build.props和Directory.Build.targets挪用到项目里的。这就是我的第二个知识盲点了。我们打开文件夹(直接打开资源管理器的,不是visual studio的),可以发现src源码文件夹下的OrchardCore、OrchardCore.Modules和OrchardCore.Themes三个文件夹都有Directory.Build.props和Directory.Build.targets这两个文件。这意味着另有文件不在项目里?这又怎么用呢?我真是快溃逃了!经由查找资料,主要明了:在MSBuild15以后新增一个功效就是让开发者可以自己界说项目信息放在一个文件,这个文件会在Microsoft.Common.props和Microsoft.Common.target引用,而且会在csproj项目文件所在的文件夹最先寻找,只要找到存在Directory.Build.props和Directory.Build.target文件就会自动导入内里的内容。也就是从项目的csproj当前项目最先自动向上寻找Directory.Build.props和Directory.Build.target,直到解决方法根目录,只要找到立刻住手。这就是意味着每个项目编译的时刻会把这些文件给包罗进来。

图计算黑科技:打开中文词嵌入训练实践新模式

  好了,明了了这些后,最先按顺序领会模块的加载历程。

  我是从启动项目OrchardCore.Cms.Web最先看,它项目引用了OrchardCore.Application.Cms.Core.Targets,而这个项目又引用了OrchardCore.Application.Targets,这下Targets项目都在OrchardCore文件夹下,也就是编译的时刻会包罗上面说的Directory.Build.props和Directory.Build.targets文件。

  OrchardCore.Application.Targets内里只有一个OrchardCore.Application.Targets.targets文件,打开如下:

<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">

  <!-- 
    This file is packaged with "OrchardCore.Application.Targets.nupkg" in "./build" such that any
    Application that references it will embed in its assembly a list of the referenced modules.
  -->

  <Target Name="ResolveModuleProjectReferences" AfterTargets="AfterResolveReferences">
    <MSBuild
      Targets="GetModuleProjectName"
      BuildInParallel="$(BuildInParallel)"
      Projects="@(_MSBuildProjectReferenceExistent)"
      Condition="'@(_MSBuildProjectReferenceExistent)' != ''"
      SkipNonexistentTargets="true"
      ContinueOnError="true">

      <Output ItemName="ModuleProjectNames" TaskParameter="TargetOutputs" />
    </MSBuild>

    <ItemGroup>
      <ModuleNames Include="@(ModulePackageNames);@(ModuleProjectNames)" />
    </ItemGroup>

    <ItemGroup>
      <AssemblyAttribute Include="OrchardCore.Modules.Manifest.ModuleNameAttribute" Condition="'@(ModuleNames)' != ''">
        <_Parameter1>%(ModuleNames.Identity)</_Parameter1>
      </AssemblyAttribute>
    </ItemGroup>
  </Target>

  <Target Name="NoWarnOnRazorViewImportedTypeConflicts" BeforeTargets="RazorCoreCompile">
    <PropertyGroup>
      <NoWarn>$(NoWarn);0436</NoWarn>
    </PropertyGroup>
  </Target>

</Project>

   看到AssemblyAttribute元素了吧,没错,这就是程序集的属性啊,在看看它内里有啥?OrchardCore.Modules.Manifest.ModuleNameAttribute,没错,这个就是上篇反射找到的ModuleName,那么怎么来的呢,有个Condition=”‘@(ModuleNames)’ != ””,显著这个条件就是ModuleNames元素不为空,然后获取ModuleNames元素的Identity。那么我们顺着往上看就可以看到上个ItemGroup元素内里就包罗ModuleNames,然则没有Identity属性啊,只能查阅资料了,谁叫我MSbuild两眼一抹黑呢,凭据msdn先容明了Identity就是Include属性中指定的项,人人也可以看看msdn。那么我们接着看INclude,@(ModulePackageNames);@(ModuleProjectNames),分号距离符,距离而已,继续看看第二个ModuleProjectNames,上面的MSBuid的Oupt就是了,而义务呢,就是MSBuild的GetModuleProjectName。这个义务在哪呢,感受很无厘头是不是,纰谬,前面不是先容了Directory.Build.props和Directory.Build.targets吗,没错,往内里找,打开Directory.Build.targets看看

<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">

  <Import Project="..\OrchardCore.Build\OrchardCore.Commons.targets" />
  <Import Project="..\OrchardCore\OrchardCore.Module.Targets\OrchardCore.Module.Targets.targets" />

  <PropertyGroup>
    <AllowedOutputExtensionsInPackageBuildOutputFolder>$(AllowedOutputExtensionsInPackageBuildOutputFolder);.pdb</AllowedOutputExtensionsInPackageBuildOutputFolder>
  </PropertyGroup>

</Project>

  看到内里包罗了的OrchardCore.Module.Targets.targets文件没有,打开接着看(这个有点长直接看最后部门):

 

<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">

  ...

  <Target Name="GetModuleProjectName" Returns="@(ModuleProjectName)">
    <ItemGroup>
      <ModuleProjectName Include="$(AssemblyName)" />
    </ItemGroup>
  </Target>

</Project>

  看到Name为GetModuleProjectName的Target义务了吧,请注意这个文件的位置,在..\OrchardCore\OrchardCore.Module.Targets\OrchardCore.Module.Targets.targets,没错就在OrchardCore.Module.Targets项目里,而所有模块都是以用这个项目,也就是说所有应用这个项目的项目名都市加到程序集的ModuleName上!

原创文章,作者:admin,如若转载,请注明出处:https://www.2lxm.com/archives/22258.html