Error: Project file is not a DocProject template, even though it is

Topics: General Questions
Dec 4, 2008 at 10:42 AM
I finally managed to get DocProject 1.11 running on our Build Server. I copied the files onto the system, set the environment variable and registry path as needed, installed the assemblies (and two additional dependencies) into the GAC, and everything runs fine. Visual Studio is not installed. Note that DocProject tries to find HTML Help Workshop at %ProgramFiles%, which points to the x64 program files folder, but HHW is installed by default into the x86 program files folder. However.
The system is a Windows Server 2008 x64 installation.

When I build my properly configured DocProject project with msbuild with the following command line (as Administrator):
msbuild CodeDocumentation.csproj /t:Rebuild /p:Configuration=Release
it works fine. Takes some time, but finally completes as it should.

But when I want to build the same project from the Build Agent, it won't work. It's configured the same (only real difference is that I can choose whether to run MSBuild in x86 or x64 context, but I tried both) and just runs under a different user (SYSTEM account). Now it produces the following strange error, with the very same checkout directory:

[12:02:36]: C:\BuildTools\DocProject\bin\DaveSexton.DocProject.targets(40, 5): error MSB4018: Unerwarteter Fehler bei der BuildDocProject-Aufgabe.
System.ArgumentException: The specified project file was not created from a DocProject or DocSite template.

You must first use Visual Studio to create a new project that is based on a DocProject or DocSite template and then you can open it with this program.
Parametername: task
bei DaveSexton.DocProject.MSBuild.MSBuildDocProject..ctor(Engine engine, BuildDocProject task, String solutionPath)
bei DaveSexton.DocProject.MSBuild.BuildDocProject.get_Project()
bei DaveSexton.DocProject.MSBuild.BuildDocProject.get_Engine()
bei DaveSexton.DocProject.MSBuild.BuildDocProject.Execute()
bei Microsoft.Build.BuildEngine.TaskEngine.ExecuteInstantiatedTask(EngineProxy engineProxy, ItemBucket bucket, TaskExecutionMode howToExecuteTask, ITask task, Boolean& taskResult)
Now what's going on here? Why DocProject no longer recognizes the very same project file as a DocProject file? Something to do with the SYSTEM account?

I know that you're preparing DocProject for Continuous Integration, but since it runs from the command line on the server, it should do the same from the Build Agent :)

Thanks in Advance,
OregonGhost
Coordinator
Dec 4, 2008 at 1:10 PM
Hi,

> Note that DocProject tries to find HTML Help Workshop at %ProgramFiles%

This is configurable via the Tools > Options page for the DocProject build engines.  But since you don't have VS installed on the server, you can instead open DocProject's configuration file (typically, C:\Program Files\Dave Sexton\DocProject\bin\DaveSexton.DocProject.dll.config) and set the value of the htmlHelpWorkshop attribute manually.

> System.ArgumentException: The specified project file was not created from a DocProject or DocSite template

This is a strange one.  That error is meant for the DocProject External UI.  It indicates that the project being opened does not have an IsDocProject attribute with a value of true on the UserProperties element (usually found near the bottom of the project file, but not always).

If the attribute does exist in your project file and DocProject isn't reading it, then presumably it can't see any of the attributes on that element, which of course is a problem.  Please verify whether your DocProject project file contains XML attributes similar to the following (note that there are usually additional XML elements for a DocSite project that aren't included here):

<ProjectExtensions>

  <VisualStudio>

    <UserProperties Sandcastle_PresentationName="Visual Studio 2005" Sandcastle_Version="2.4.10520.1"

                    BuildEngineProviderName="Sandcastle" DocProjectVersion="1.11.0.0" IsDocProject="true"

                    ProcessComponentTypeName="Your_Project_Namespace.BuildProcess" />

  </VisualStudio>

</ProjectExtensions>

<!--EndFragment-->
If your project has the IsDocProject attribute, which I suspect that it does since it builds fine on the command-line, then I must assume that DocProject is not loading the correct project file to begin with.  So which project file could it be loading?

In your DocProject project file, try overriding the BeforeBuildHelp task and add a Message task that outputs the full project path that DocProject sees:

<Target Name="BeforeBuildHelp">

  <Message Text="Current DocProject Path: $(MSBuildProjectFullPath)"/>

</Target>

<!--EndFragment-->
Place the Target at the bottom of the project file.  Then build on the command-line and check the build output for something like the following.  Then build using the build agent and check for the same.

    Target BeforeBuildHelp:
        Current DocProject Path: [full path to your DocProject project file]

You should see the path to the DocProject project file that is being built, and the file should have the IsDocProject attribute set to true as shown above.

> Something to do with the SYSTEM account?

I doubt that the System account has anything to do with it.  The only relationship that I could see would be if you created the DocProjectPath environment variable as a user variable instead of as a system variable.  But even then I would expect a different error altogether.  (You may want to verify that you're using a system environment variable anyway :)

- Dave
Dec 4, 2008 at 4:22 PM
Edited Dec 4, 2008 at 4:25 PM
Thanks for the quick reply.
I added the Message element to output the full path, and the path when run from the Build Agent is:
[...]\CodeDocumentation.csproj.teamcity.patch.tcprojx
In other words, TeamCity (our CIS) obviously creates a temporary project file with some patched data. The file, like other temporary build scripts generated by TeamCity, unfortunately vanishes when the build completes (or fails), so I can't see what's exactly in it. But I guess the UserProperties[@IsDocProject] thing is no longer in it. So, it does not seem to be a DocProject problem, unless you could make it work without the UserProperties :)
I'll try to examine the temporary file and ask the TC guys what they're doing to my project file. Or, maybe I get it to work if I run the solution (instead of the project) with only the Documentation project as an active target. Or a special build configuration.

Thanks for your help,
OregonGhost
Coordinator
Dec 4, 2008 at 4:46 PM
Hi,

At my job I'm using TeamCity with SVN.  I've set it up to automatically build our DocSites along with their solutions and deploy them to our staging server.

Our setup uses an MSBuild runner that points to a Build/Server.targets file.  (It's the same for all of our projects.)  The build target string is usually similar to, "Staging Docs".  Those targets look like this: 

<Target Name="Staging">
    <ItemGroup>
        <Property Include="Configuration=Staging"/>
        ... additional properties ...
    </ItemGroup>
    <MSBuild Projects="$(Solution)" Targets="Rebuild" Properties="@(Property)"/>
</Target>

<Target Name="Docs">
    <ItemGroup>
        <Property Include="Configuration=Release"/>
        ... additional properties ...
    </ItemGroup>
    <MSBuild Projects="$(DocSite)" Targets="Rebuild" Properties="@(Property)"/>
</Target>

At the top of the Server.targets file we add the following properties:

<PropertyGroup>
    <Solution>..\[Name].sln</Solution>
    <DocSite>..\Documentation\[Name].Docs\[Name].Docs.csproj</DocSite>
</PropertyGroup>

Hope that helps :)

- Dave

Dec 5, 2008 at 9:48 AM
I guess that would help if I'd understand how to use it :)

For now, I added a "Docs" build configuration to the solution, switched to the sln2008 build runner and it works fine this way.

I don't really understand your solution though. I'm new to automated builds, so I'm likely missing something.

So you say I setup a common Server.targets file with the target "Docs" (and "Staging" if needed, does currently not apply to us) that would build the DocProject project at $(DocSite). Correct up to this point? :)

And then you say I should add the actual solution file name as a property to the Server.targets file? In the common targets file? Or did I just misunderstand you and I should create a msbuild file that would reference the targets file and set the properties, which would more sense to me? :)

Thanks for your help so far,
OregonGhost
Coordinator
Dec 5, 2008 at 11:38 AM
Hi,

Well I'm glad to hear that you've found a solution.

The solution that I offerred consists of only a single file, Server.targets.  The last property group I mentioned at the end of my post must be in the same file, before all of the other Target elements.  It uses relative paths to identify the main .sln file and the DocSite project file that will be built by the Targets.

> So you say I setup a common Server.targets file with the target "Docs" that would build the DocProject project at $(DocSite). Correct up to this point? :)

Yes.

> And then you say I should add the actual solution file name as a property to the Server.targets file?

Yes, at the top of the file you would add a new PropertyGroup as shown above.  In the property group add a DocSite element and specify the path relative from the Server.targets file.

> In the common targets file? Or did I just misunderstand you [snip]

No, and no, I don't think so :)

Why do you feel that the PropertyGroup should not be in the Server.targets file?

- Dave
Coordinator
Dec 5, 2008 at 11:44 AM
Hi,

I just realized your confusion...

I had written that, "It's the same for all of our projects".  I didn't mean that there's one common Server.targets file for all of our projects.  I meant that I copy the same exact file, albeit sometimes wtih subtle modifications, to each of our projects.

Root
    [Product].sln
    Build
        Server.targets
    Documentation
        [Product].Docs
            [Product].Docs.csproj
    Source
        [Product]
            [Product].csproj
        ...
    ...

- Dave
Dec 5, 2008 at 1:05 PM
Hi,
now I understand what you meant ;)
I'll look into this when I prepare the next project that uses DocProject (we have many non-.NET projects, so that may take a while). But for now, I'm quite happy with the sln approach.

Regards,
OregonGhost