Code:
/ DotNET / DotNET / 8.0 / untmp / WIN_WINDOWS / lh_tools_devdiv_wpf / Windows / wcp / Build / Microsoft / Build / Tasks / Windows / GenerateTemporaryTargetAssembly.cs / 1 / GenerateTemporaryTargetAssembly.cs
//----------------------------------------------------------------------------
//
//
// Copyright (C) Microsoft Corporation. All rights reserved.
//
//
// Description: This is a MSBuild task which generates a temporary target assembly
// if current project contains a xaml file with local-type-reference.
//
// It generates a temporary project file and then call build-engine
// to compile it.
//
// The new project file will replace all the Reference Items with the
// resolved ReferenctPath, add all the generated code file into Compile
// Item list.
//
// History:
// 05/10/05: [....] Created.
//
//---------------------------------------------------------------------------
using System;
using System.IO;
using System.Collections;
using System.Globalization;
using System.Diagnostics;
using System.Reflection;
using System.Resources;
using System.Xml;
using Microsoft.Build.Framework;
using Microsoft.Build.Utilities;
using Microsoft.Build.BuildEngine;
using MS.Utility;
using MS.Internal.Tasks;
// Since we disable PreSharp warnings in this file, PreSharp warning is unknown to C# compiler.
// We first need to disable warnings about unknown message numbers and unknown pragmas.
#pragma warning disable 1634, 1691
namespace Microsoft.Build.Tasks.Windows
{
#region GenerateTemporaryTargetAssembly Task class
///
/// This task is used to generate a temporary target assembly. It generates
/// a temporary project file and then compile it.
///
/// The generated project file is based on current project file, with below
/// modification:
///
/// A: Add the generated code files (.g.cs) to Compile Item list.
/// B: Replace Reference Item list with ReferenctPath item list.
/// So that it doesn't need to rerun time-consuming tatk
/// ResolveAssemblyReference (RAR) again.
///
///
public sealed class GenerateTemporaryTargetAssembly : Task
{
//-----------------------------------------------------
//
// Constructors
//
//-----------------------------------------------------
#region Constructors
///
/// Constrcutor
///
public GenerateTemporaryTargetAssembly()
: base(SR.ResourceManager)
{
}
#endregion Constructors
//------------------------------------------------------
//
// Public Methods
//
//-----------------------------------------------------
#region Public Methods
///
/// ITask Execute method
///
///
public override bool Execute()
{
bool retValue = true;
// Verification
try
{
XmlDocument xmlProjectDoc = null;
xmlProjectDoc = new XmlDocument( );
xmlProjectDoc.Load(CurrentProject);
//
// remove all the WinFX specific item lists
// ApplicationDefinition, Page, MarkupResource and Resource
//
RemoveItemsByName(xmlProjectDoc, APPDEFNAME);
RemoveItemsByName(xmlProjectDoc, PAGENAME);
RemoveItemsByName(xmlProjectDoc, MARKUPRESOURCENAME);
RemoveItemsByName(xmlProjectDoc, RESOURCENAME);
// Replace the Reference Item list with ReferencePath
RemoveItemsByName(xmlProjectDoc, REFERENCETYPENAME);
AddNewItems(xmlProjectDoc, ReferencePathTypeName, ReferencePath);
// Add GeneratedCodeFiles to Compile item list.
AddNewItems(xmlProjectDoc, CompileTypeName, GeneratedCodeFiles);
// Create a random file name
// This can fix the problem of project cache in VS.NET environment.
//
// GetRandomFileName( ) could return any possible file name and extension, but
// some file externsion has special meaning in MSBUILD system, such as a ".sln"
// means the file is a solution file with special file format. Since the temporary
// file is just for a project, we can use a fixed extension here, but the basic
// file name is still random which can fix above VS.NET bug.
//
string randProj = Path.ChangeExtension(Path.GetRandomFileName(), TEMP_PROJ_EXT);
// Save the xmlDocument content into the temporary project file.
xmlProjectDoc.Save(randProj);
//
// Invoke MSBUILD engine to build this temporary project file.
//
Hashtable globalProperties = new Hashtable(2);
// Add AssemblyName and IntermediateOutputPath to the global property list
globalProperties[intermediateOutputPathPropertyName] = IntermediateOutputPath;
globalProperties[assemblyNamePropertyName] = AssemblyName;
retValue = BuildEngine.BuildProjectFile(randProj, new string[] { CompileTargetName }, globalProperties, null);
// Delete the random project file from disk.
File.Delete(randProj);
}
#pragma warning disable 6500
catch (Exception e)
{
Log.LogErrorFromException(e);
retValue = false;
}
#pragma warning retore 6500
return retValue;
}
#endregion Public Methods
//------------------------------------------------------
//
// Public Properties
//
//------------------------------------------------------
#region Public Properties
///
/// CurrentProject
/// The full path of current project file.
///
[Required]
public string CurrentProject
{
get { return _currentProject; }
set { _currentProject = value; }
}
///
/// MSBuild Binary Path.
/// This is required for Project to work correctly.
///
[Required]
public string MSBuildBinPath
{
get { return _msbuildBinPath; }
set { _msbuildBinPath = value; }
}
///
/// GeneratedCodeFiles
/// A list of generated code files, it could be empty.
/// The list will be added to the Compile item list in new generated project file.
///
public ITaskItem[] GeneratedCodeFiles
{
get { return _generatedCodeFiles; }
set { _generatedCodeFiles = value; }
}
///
/// CompileTypeName
/// The appropriate item name which can be accepted by managed compiler task.
/// It is "Compile" for now.
///
/// Adding this property is to make the type name configurable, if it is changed,
/// No code is required to change in this task, but set a new type name in project file.
///
[Required]
public string CompileTypeName
{
get { return _compileTypeName; }
set { _compileTypeName = value; }
}
///
/// ReferencePath
/// A list of resolved reference assemblies.
/// The list will replace the original Reference item list in generated project file.
///
public ITaskItem[] ReferencePath
{
get { return _referencePath; }
set { _referencePath = value; }
}
///
/// ReferencePathTypeName
/// The appropriate item name which is used to keep the Reference list in managed compiler task.
/// It is "ReferencePath" for now.
///
/// Adding this property is to make the type name configurable, if it is changed,
/// No code is required to change in this task, but set a new type name in project file.
///
[Required]
public string ReferencePathTypeName
{
get { return _referencePathTypeName; }
set { _referencePathTypeName = value; }
}
///
/// IntermediateOutputPath
///
/// The value which is set to IntermediateOutputPath property in current project file.
///
/// Passing this value explicitly is to make sure to generate temporary target assembly
/// in expected directory.
///
[Required]
public string IntermediateOutputPath
{
get { return _intermediateOutputPath; }
set { _intermediateOutputPath = value; }
}
///
/// AssemblyName
///
/// The value which is set to AssemblyName property in current project file.
/// Passing this value explicitly is to make sure to generate the expected
/// temporary target assembly.
///
///
[Required]
public string AssemblyName
{
get { return _assemblyName; }
set { _assemblyName = value; }
}
///
/// CompileTargetName
///
/// The msbuild target name which is used to generate assembly from source code files.
/// Usually it is "CoreCompile"
///
///
[Required]
public string CompileTargetName
{
get { return _compileTargetName; }
set { _compileTargetName = value; }
}
#endregion Public Properties
//-----------------------------------------------------
//
// Private Methods
//
//------------------------------------------------------
#region Private Methods
//
// Remove specific items from project file. Every item should be under an ItemGroup.
//
private void RemoveItemsByName(XmlDocument xmlProjectDoc, string sItemName)
{
if (xmlProjectDoc == null || String.IsNullOrEmpty(sItemName))
{
// When the parameters are not valid, simply return it, instead of throwing exceptions.
return;
}
//
// The project file format is always like below:
//
//
//
// ......
//
//
// ...
//
//
// ....
//
//
// ....
//
// ...
//
//
// ...
//
//
//
//
// The order of children nodes under Project Root element is random
//
XmlNode root = xmlProjectDoc.DocumentElement;
if (root.HasChildNodes == false)
{
// If there is no child element in this project file, just return immediatelly.
return;
}
for (int i = 0; i < root.ChildNodes.Count; i++)
{
XmlElement nodeGroup = root.ChildNodes[i] as XmlElement;
if (nodeGroup != null && String.Compare(nodeGroup.Name, ITEMGROUP_NAME, StringComparison.OrdinalIgnoreCase) == 0)
{
//
// This is ItemGroup element.
//
if (nodeGroup.HasChildNodes)
{
ArrayList itemToRemove = new ArrayList();
for (int j = 0; j < nodeGroup.ChildNodes.Count; j++)
{
XmlElement nodeItem = nodeGroup.ChildNodes[j] as XmlElement;
if (nodeItem != null && String.Compare(nodeItem.Name, sItemName, StringComparison.OrdinalIgnoreCase) == 0)
{
// This is the item that need to remove.
// Add it into the temporary array list.
// Don't delete it here, since it would affect the ChildNodes of parent element.
//
itemToRemove.Add(nodeItem);
}
}
//
// Now it is the right time to delete the elements.
//
if (itemToRemove.Count > 0)
{
foreach (object node in itemToRemove)
{
XmlElement item = node as XmlElement;
//
// Remove this item from its parent node.
// the parent node should be nodeGroup.
//
if (item != null)
{
nodeGroup.RemoveChild(item);
}
}
}
}
//
// Removed all the items with given name from this item group.
//
// Continue the loop for the next ItemGroup.
}
} // end of "for i" statement.
}
//
// Add a list of files into an Item in the project file, the ItemName is specified by sItemName.
//
private void AddNewItems(XmlDocument xmlProjectDoc, string sItemName, ITaskItem[] pItemList)
{
if (xmlProjectDoc == null || String.IsNullOrEmpty(sItemName) || pItemList == null)
{
// When the parameters are not valid, simply return it, instead of throwing exceptions.
return;
}
XmlNode root = xmlProjectDoc.DocumentElement;
// Create a new ItemGroup element
XmlNode nodeItemGroup = xmlProjectDoc.CreateElement(ITEMGROUP_NAME, root.NamespaceURI);
// Append this new ItemGroup item into the list of children of the document root.
root.AppendChild(nodeItemGroup);
for (int i = 0; i < pItemList.Length; i++)
{
// Create an element for the given sItemName
XmlElement nodeItem = xmlProjectDoc.CreateElement(sItemName, root.NamespaceURI);
// Create an Attribute "Include"
XmlAttribute attrInclude = xmlProjectDoc.CreateAttribute(INCLUDE_ATTR_NAME);
// Set the value for Include attribute.
attrInclude.Value = pItemList[i].ItemSpec;
// Add the attribute to current item node.
nodeItem.SetAttributeNode(attrInclude);
// Add current item node into the children list of ItemGroup
nodeItemGroup.AppendChild(nodeItem);
}
}
#endregion Private Methods
//-----------------------------------------------------
//
// Private Fields
//
//-----------------------------------------------------
#region Private Fields
private string _currentProject = String.Empty;
private ITaskItem[] _generatedCodeFiles;
private ITaskItem[] _referencePath;
private string _referencePathTypeName;
private string _compileTypeName;
private string _msbuildBinPath;
private string _intermediateOutputPath;
private string _assemblyName;
private string _compileTargetName;
private const string intermediateOutputPathPropertyName = "IntermediateOutputPath";
private const string assemblyNamePropertyName = "AssemblyName";
private const string REFERENCETYPENAME = "Reference";
private const string APPDEFNAME = "ApplicationDefinition";
private const string PAGENAME = "Page";
private const string MARKUPRESOURCENAME = "MarkupResource";
private const string RESOURCENAME = "Resource";
private const string ITEMGROUP_NAME = "ItemGroup";
private const string INCLUDE_ATTR_NAME = "Include";
private const string TEMP_PROJ_EXT = ".tmp_proj";
#endregion Private Fields
}
#endregion GenerateProjectForLocalTypeReference Task class
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- AudioFormatConverter.cs
- WorkflowInlining.cs
- DataKeyArray.cs
- SqlNodeAnnotations.cs
- InvokeWebService.cs
- LocationReferenceValue.cs
- CapabilitiesAssignment.cs
- SafePEFileHandle.cs
- FillRuleValidation.cs
- DataGridLength.cs
- TimeSpanHelper.cs
- GenericTypeParameterBuilder.cs
- CustomCategoryAttribute.cs
- TextTreeExtractElementUndoUnit.cs
- ClientSettings.cs
- SelectionEditor.cs
- LinqDataSourceUpdateEventArgs.cs
- BitmapFrame.cs
- ListViewDeleteEventArgs.cs
- HtmlTableRowCollection.cs
- Pair.cs
- ToolStripCustomTypeDescriptor.cs
- SafeProcessHandle.cs
- ServerType.cs
- ModelFunctionTypeElement.cs
- RequestQueryParser.cs
- CursorConverter.cs
- _SslSessionsCache.cs
- ObjectViewEntityCollectionData.cs
- WaitHandle.cs
- LoadRetryStrategyFactory.cs
- XmlName.cs
- CharacterMetricsDictionary.cs
- Socket.cs
- ProviderConnectionPoint.cs
- CustomAttributeBuilder.cs
- Helper.cs
- StringHandle.cs
- MachineKeySection.cs
- Stack.cs
- HttpInputStream.cs
- MarshalDirectiveException.cs
- ThreadAbortException.cs
- ConfigXmlCDataSection.cs
- CodeTypeParameter.cs
- AttachmentService.cs
- ImageIndexConverter.cs
- TextElement.cs
- CompilerGlobalScopeAttribute.cs
- TrackingRecord.cs
- DrawingContextWalker.cs
- ImageFormat.cs
- LineGeometry.cs
- HMACMD5.cs
- Int64Animation.cs
- DataBinding.cs
- brushes.cs
- DataObjectFieldAttribute.cs
- PasswordBoxAutomationPeer.cs
- OlePropertyStructs.cs
- KnownTypes.cs
- MembershipSection.cs
- EntityCommand.cs
- WebBrowser.cs
- xdrvalidator.cs
- InstanceNameConverter.cs
- WebControlAdapter.cs
- WebServiceTypeData.cs
- ToolStripMenuItem.cs
- KeyConverter.cs
- Multiply.cs
- ToolStripPanelCell.cs
- PriorityBinding.cs
- ChangeNode.cs
- DEREncoding.cs
- BStrWrapper.cs
- StreamAsIStream.cs
- Pens.cs
- _ListenerRequestStream.cs
- AutomationPropertyInfo.cs
- ExternalException.cs
- BaseValidator.cs
- PassportAuthenticationEventArgs.cs
- AttachedPropertyBrowsableForTypeAttribute.cs
- XmlDataDocument.cs
- ConfigsHelper.cs
- Brush.cs
- SmtpException.cs
- TableLayout.cs
- TextEditorContextMenu.cs
- ListenerConnectionDemuxer.cs
- CodeTypeMemberCollection.cs
- InlineUIContainer.cs
- FactoryGenerator.cs
- RC2.cs
- Claim.cs
- ToolboxItemFilterAttribute.cs
- OneOfScalarConst.cs
- ScriptServiceAttribute.cs
- TabRenderer.cs