【问题标题】:Visual Studio Multi Project Template : Project Reference IssuesVisual Studio 多项目模板:项目参考问题
【发布时间】:2014-08-17 06:07:23
【问题描述】:

上下文:我目前正在开发一个 VB.NET 多项目模板,它们之间有交叉引用,几乎可以正常工作。

问题: VS 为每个生成的项目生成新的 GUID,并将它们更新到新的 .sln 和每个新的 .vbproj,但绝不会以相同的方式将项目引用更新到 .vbproj。

这是一个 .vbproj 示例:

<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
  <PropertyGroup>
    <ProductVersion>
    </ProductVersion>
    <SchemaVersion>
    </SchemaVersion>
    <ProjectGuid>{_NewGUIDGeneratedByVS_}</ProjectGuid>
    <OutputType>Library</OutputType>
    <RootNamespace>Template.DataModel</RootNamespace>
    <AssemblyName>Template.DataModel</AssemblyName>
    <FileAlignment>512</FileAlignment>
    <MyType>Windows</MyType>
    <TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
  </PropertyGroup>

...在另一个生成的 .vbproj 中进一步引用之前的项目:

<ProjectReference Include="..\Template.DataModel\Template.DataModel.vbproj">
          <Project>{_OldBoringGUID_}</Project>
          <Name>Template.DataModel</Name>
        </ProjectReference>

一些线索:我已经尝试在我的 IWizard Root 和 Child 派生类中通过 replacementsDictionary 强制替换特定的 GUID,但 VS 一直在替换旧的 GUID:

这里,$Sguid6$ 标签将被 VS 忽略,并将被新的闪亮 GUID 替换!

<ProductVersion>8.0.50727</ProductVersion>
    <SchemaVersion>2.0</SchemaVersion>
    <ProjectGuid>{$Sguid6$}</ProjectGuid>
    <OutputType>WinExe</OutputType>
    <StartupObject>$safeprojectname$.My.MyApplication</StartupObject>        <RootNamespace>$safeprojectname$</RootNamespace>
    <AssemblyName>$safeprojectname$</AssemblyName>

然后再次在另一个 .vbproj 中:$Sguid6$ 将采用我告诉他接受我的replacementsDictionary 的 GUID,正如预期的那样。

<ProjectReference Include="..\$safeprojectname$.DataModel\$safeprojectname$.DataModel.vbproj">
  <Project>{$Sguid6$}</Project>
  <Name>$safeprojectname$.DataModel</Name>
  <Private>True</Private>
</ProjectReference>

问题:我怎样才能告诉 VS 正确地交换所有这些 GUID,或者至少不改变它们?

【问题讨论】:

    标签: visual-studio-2010 visual-studio templates msbuild multi-project


    【解决方案1】:

    我找到了一个替代方案:我们需要通过IWizard 手动设置项目引用。只需在 RootIWizard 中添加/编辑您的 ProjectFinishedGenerating 方法:

        public void ProjectFinishedGenerating(EnvDTE.Project project)
        {
            // will store all references related to the template
            Dictionary<String, Project> lReferences = new Dictionary<string, Project>();
    
            foreach (Project p in pDTE.Solution.Projects.Cast<Project>())
            {
                lReferences.Add(p.Name, p);
            }
    
            // will add all needed references for each specific project invoked from the template
            foreach (Project p in pDTE.Solution.Projects)
            {
                VSLangProj80.VSProject2 vsproj = (VSLangProj80.VSProject2)p.Object;
    
                if (p.Name.IsMatchProjectName("Services"))
                {
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("DataModel")).Value);
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("WS")).Value);
                }
                else if (p.Name.IsMatchProjectName("Web"))
                {
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("DataModel")).Value);
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("WS")).Value);
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("Services")).Value);
                }
                else if (p.Name.IsMatchProjectName("WinForms"))
                {
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("DataModel")).Value);
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("WS")).Value);
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.IsMatchProjectName("Services")).Value);
                    vsproj.References.AddProject(lReferences.Single(f => f.Key.Contains("SortableBindingList")).Value);
                }
    
                vsproj.Refresh();
                vsproj.Project.Save();
            }
    
            pDTE.Solution.SolutionBuild.Build(true);
        }
    

    【讨论】:

      【解决方案2】:

      我也遇到了这个问题(但使用 C#!),我只是通过删除模板项目文件中 &lt;ProjectReference&gt; 标记中的 &lt;Project&gt;{GUID}&lt;/Project&gt; 来解决它。

      引用由路径和名称解析。

      更多讨论可以在这里找到:MSDN 其中还指出,&lt;Project&gt; 无关紧要。然而,正如另一位用户所说,它似乎不适用于 Azure 项目。

      【讨论】:

        猜你喜欢
        • 2011-05-17
        • 1970-01-01
        • 1970-01-01
        • 2012-04-05
        • 2011-10-06
        • 2010-12-22
        • 1970-01-01
        • 2017-09-01
        • 1970-01-01
        相关资源
        最近更新 更多