Example on how to resolve project to project reference (for single solution) in team build.

Consider a simple solution (OfficeSolution.sln) that has one main project (OfficeSolution.csproj). The main project has dependency (project to project reference) on two independent sub projects (WordApplication.csproj and ExcelApplication.csproj). Note that both the sub projects also belong to the same solution. The folder structure for the sources is shown in the following diagram.

 

├───OfficeSolution

│ │ OfficeSolution.sln

│ │ OfficeSolution.vssscc

│ │

│ ├───ExcelApplication

│ │ │ ExcelApplication.csproj

│ │ │ ExcelApplication.csproj.vspscc

│ │ │ ExcelClass.cs

│ │ └───Properties

│ │ AssemblyInfo.cs

│ │

│ ├───OfficeSolution

│ │ │ OfficeSolution.csproj

│ │ │ OfficeSolution.csproj.vspscc

│ │ │ OfficeDocument.cs

│ │ └───Properties

│ │ AssemblyInfo.cs

│ │

│ └───WordApplication

│ │ WordClass.cs

│ │ WordApplication.csproj

│ │ WordApplication.csproj.vspscc

│ └───Properties

│ AssemblyInfo.cs

 

figure 1

There are two team projects (MyProj1 and My Proj2). The Excel and Word projects belong to one team project (MyProj2) and main project (OfficeSolution) is checked in different team project (MyProj1). Now we want to build this solution using team build. Based on case 1.2, recommendation 1, the directory structure of files under build directory should be identical to figure 1.

$/MyProj1

├───OfficeSolution

│ │ OfficeSolution.sln

│ │ OfficeSolution.vssscc

│ ├───OfficeSolution

│ │ │ OfficeSolution.csproj

│ │ │ OfficeSolution.csproj.vspscc

│ │ │ OfficeDocument.cs

│ │ └───Properties

│ │ AssemblyInfo.cs

$/MyProj2

├───OfficeSolution

│ ├───ExcelApplication

│ │ │ ExcelApplication.csproj

│ │ │ ExcelApplication.csproj.vspscc

│ │ │ ExcelClass.cs

│ │ └───Properties

│ │ AssemblyInfo.cs

│ └───WordApplication

│ │ WordClass.cs

│ │ WordApplication.csproj

│ │ WordApplication.csproj.vspscc

│ └───Properties

│ AssemblyInfo.cs

figure 2

User needs to modify the build type to get sources from different team project. For example you can add the following targets in the tfsbuild.proj to get files from different team project. Please note that target "AfterGet" defined in this file will override the default target “AfterGet” of file Microsoft.TeamFoundation.Build.targets.

<PropertyGroup>

<TfCommand>$(TeamBuildRefPath)\..\tf.exe</TfCommand>

</PropertyGroup>

<Target Name="CustomGet">

<!-- Delete the default workspace used to sync sources from MyProj1 -->

<Exec

Command="&quot;$(TfCommand)&quot; workspace /delete $(WorkspaceName) /s:$(TeamFoundationServerUrl)"/>

<!-- Create workspace to get files from MyProj2-->

<Exec

WorkingDirectory="$(SolutionRoot)"

Command="&quot;$(TfCommand)&quot; workspace /new

$(WorkspaceName) /s:$(TeamFoundationServerUrl)"/>

<!-- Set the folder mappings to get files from MyProj2-->

<Exec

Command="&quot;$(TfCommand)&quot; workfold /map /s:$(TeamFoundationServerUrl)

/workspace:$(WorkspaceName) $/MyProj2/OfficeSolution $(SolutionRoot)\OfficeSolution"/>

<!-- Get the files from team project MyProj2 -->

<Exec

WorkingDirectory="$(SolutionRoot)"

Command="&quot;$(TfCommand)&quot; get /r /force ."/>

</Target>

<!—Custom target to get sources from team project (MyProj2) -->

<Target Name="AfterGet"

DependsOnTargets="CustomGet;InitializeWorkspace"/>

 

<!—Assuming the second AT name is burton-tfs1 -->

<PropertyGroup>

    <TfCommand>$(TeamBuildRefPath)\..\tf.exe</TfCommand>

    <TfsName2>https://burton-tfs1:8080/</TfsName2>

</PropertyGroup>

<Target Name="AfterGet">

    <!-- Delete the default workspace -->

    <Exec

      Command="&quot;$(TfCommand)&quot; workspace /delete $(WorkspaceName) /s:$(TeamFoundationServerUrl)"/>

    <!-- Create workspace to get files from different AT (burton-tfs1)-->

    <Exec

      WorkingDirectory="$(SolutionRoot)"

      Command="&quot;$(TfCommand)&quot; workspace /new $(WorkspaceName) /s:$(TfsName2)"/>

    <!-- Set the folder mappings to get files from burton-tfs1 -->

    <Exec

      Command="&quot;$(TfCommand)&quot; workfold /map /s:$(TfsName2)

/workspace:$(WorkspaceName) $/MyProj2/OfficeSolution $(SolutionRoot)\OfficeSolution"/>

    <!-- Get the files from team project belonging to different AT-->

    <Exec

      WorkingDirectory="$(SolutionRoot)\OfficeSolution"

      Command="&quot;$(TfCommand)&quot; get /r /force ."/>

    <!-- Delete the workspace used to sync files from different AT -->

    <Exec

      Command="&quot;$(TfCommand)&quot; workspace /delete $(WorkspaceName) /s:$(TfsName2)"/>

  

    <!-- Recreate the default workspace -->

    <CreateWorkspaceTask

      Condition=" '$(SkipInitializeWorkspace)'!='true' and '$(IsDesktopBuild)'!='true' "

      Url="$(TeamFoundationServerUrl)"

      MappingFile="WorkspaceMapping.xml"

      LocalPath="$(SolutionRoot)"

      Name="$(WorkspaceName)"

      TeamProject="$(TeamProject)" />

</Target>

 

I will be talking about file references in team build in next post.