private void PreviewTransformation()
        {
            try
            {
                this.outputTextBox.Foreground = (Brush)TextBox.ForegroundProperty.DefaultMetadata.DefaultValue;
                var input          = this.inputTextBox.Text;
                var transformation = this.transformationTextBox.Text;
                var output         = string.Empty;
                if (!string.IsNullOrWhiteSpace(input) && !string.IsNullOrWhiteSpace(transformation))
                {
                    // Perform the transformation.
                    output = WorkItemConfigurationTransformer.Transform(this.TransformationType, input, transformation);

                    // Also replace macros to complete the preview.
                    output = WorkItemConfigurationItemImportExport.ReplaceTeamProjectMacros(output, this.SelectedItem.TeamProject);
                }
                this.outputTextBox.Text = output;
            }
            catch (Exception exc)
            {
                this.outputTextBox.Foreground = Brushes.Red;
                this.outputTextBox.Text       = exc.ToString();
            }
        }
        private bool ApplyTransformation()
        {
            var transformXml = this.transformationTextBox.Text;

            try
            {
                this.outputTextBox.Foreground = (Brush)TextBox.ForegroundProperty.DefaultMetadata.DefaultValue;
                this.outputTextBox.Text       = string.Empty;

                // First try to apply the transformation to all items.
                var transformations = new Dictionary <WorkItemConfigurationItemExport, XmlDocument>();
                foreach (var item in this.Items)
                {
                    this.outputTextBox.Text += "Applying transformation to {0} ({1})...".FormatCurrent(item.Item.DisplayName, item.TeamProject.Name);
                    this.outputTextBox.ScrollToEnd();
                    var result = WorkItemConfigurationTransformer.Transform(this.TransformationType, item.Item.XmlDefinition, transformXml);
                    transformations.Add(item, result);
                }

                // Only commit if everything succeeded.
                foreach (var item in this.Items)
                {
                    item.Item.XmlDefinition = transformations[item];
                }

                return(true);
            }
            catch (Exception exc)
            {
                // Don't close but show the exception.
                this.outputTextBox.Foreground = Brushes.Red;
                this.outputTextBox.Text      += Environment.NewLine + exc.ToString();
                this.outputTextBox.ScrollToEnd();
                return(false);
            }
        }
        private void ApplyTransformations(object argument)
        {
            var simulate = this.Simulate;
            var saveCopy = this.SaveCopy;

            if (!simulate)
            {
                var result = MessageBox.Show("This will apply the specified transformations to all selected Team Projects. Are you sure you want to continue?", "Confirm Transformation", MessageBoxButton.YesNo, MessageBoxImage.Warning);
                if (result != MessageBoxResult.Yes)
                {
                    return;
                }
            }
            var teamProjects    = this.SelectedTeamProjects.ToList();
            var transformations = this.Transformations.ToList();
            var task            = new ApplicationTask("Transforming work item configuration", teamProjects.Count, true);

            PublishStatus(new StatusEventArgs(task));
            var step   = 0;
            var worker = new BackgroundWorker();

            worker.DoWork += (sender, e) =>
            {
                var tfs   = GetSelectedTfsTeamProjectCollection();
                var store = tfs.GetService <WorkItemStore>();
                var numTransformations = 0;

                foreach (var teamProject in teamProjects)
                {
                    task.SetProgress(step++, string.Format(CultureInfo.CurrentCulture, "Processing Team Project \"{0}\"", teamProject.Name));
                    try
                    {
                        var project = store.Projects[teamProject.Name];

                        // Apply the transformations only if everything succeeded for the Team Project; cache them in the mean time.
                        var transformedItems = new List <WorkItemConfigurationItem>();
                        foreach (var transformation in transformations)
                        {
                            if (transformation.WorkItemConfigurationItemType == WorkItemConfigurationItemType.WorkItemType)
                            {
                                // Apply work item type definition transformation, which can apply to multiple work item type definitions (semicolon separated).
                                // If no work item type names are specified, apply to all work item types in the project.
                                var workItemTypeNames = (string.IsNullOrEmpty(transformation.WorkItemTypeNames) ? project.WorkItemTypes.Cast <WorkItemType>().Select(w => w.Name) : transformation.WorkItemTypeNames.Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries));
                                foreach (var workItemTypeName in workItemTypeNames)
                                {
                                    // If the work item type has already been processed before, continue with that version.
                                    var itemToTransform = transformedItems.FirstOrDefault(w => string.Equals(w.Name, workItemTypeName, StringComparison.OrdinalIgnoreCase));
                                    if (itemToTransform == null)
                                    {
                                        // If the work item type wasn't processed yet, find the one with the specified name (if it exists).
                                        var wit = project.WorkItemTypes.Cast <WorkItemType>().FirstOrDefault(w => string.Equals(w.Name, workItemTypeName, StringComparison.OrdinalIgnoreCase));
                                        if (wit != null)
                                        {
                                            itemToTransform = WorkItemTypeDefinition.FromXml(wit.Export(false));
                                        }
                                    }
                                    if (itemToTransform != null)
                                    {
                                        task.Status = "Transforming " + itemToTransform.DisplayName;
                                        var transformed = WorkItemConfigurationTransformer.Transform(transformation.TransformationType, itemToTransform.XmlDefinition, transformation.TransformationXml);
                                        if (string.Equals(itemToTransform.XmlDefinition.DocumentElement.OuterXml, transformed.DocumentElement.OuterXml))
                                        {
                                            task.Status = "The transformation was applied but did not result in any changes, skipping.";
                                        }
                                        else
                                        {
                                            itemToTransform.XmlDefinition = transformed;
                                            transformedItems.Add(itemToTransform);
                                        }
                                    }
                                    else
                                    {
                                        task.Status = "Skipping \"{0}\": a work item type with this name was not found in the Team Project".FormatCurrent(workItemTypeName);
                                    }
                                }
                            }
                            else if (transformation.WorkItemConfigurationItemType == WorkItemConfigurationItemType.Categories)
                            {
                                var itemToTransform = transformedItems.FirstOrDefault(w => w.Type == WorkItemConfigurationItemType.Categories);
                                if (itemToTransform == null)
                                {
                                    itemToTransform = WorkItemConfigurationItemImportExport.GetCategories(project);
                                }
                                task.Status = "Transforming " + itemToTransform.DisplayName;
                                var transformed = WorkItemConfigurationTransformer.Transform(transformation.TransformationType, itemToTransform.XmlDefinition, transformation.TransformationXml);
                                if (string.Equals(itemToTransform.XmlDefinition.DocumentElement.OuterXml, transformed.DocumentElement.OuterXml))
                                {
                                    task.Status = "The transformation was applied but did not result in any changes, skipping.";
                                }
                                else
                                {
                                    itemToTransform.XmlDefinition = transformed;
                                    transformedItems.Add(itemToTransform);
                                }
                            }
                            else if (transformation.WorkItemConfigurationItemType == WorkItemConfigurationItemType.AgileConfiguration)
                            {
                                var itemToTransform = transformedItems.FirstOrDefault(w => w.Type == WorkItemConfigurationItemType.AgileConfiguration);
                                if (itemToTransform == null)
                                {
                                    itemToTransform = WorkItemConfigurationItemImportExport.GetAgileConfiguration(project);
                                }
                                if (itemToTransform != null)
                                {
                                    task.Status = "Transforming " + itemToTransform.DisplayName;
                                    var transformed = WorkItemConfigurationTransformer.Transform(transformation.TransformationType, itemToTransform.XmlDefinition, transformation.TransformationXml);
                                    if (string.Equals(itemToTransform.XmlDefinition.DocumentElement.OuterXml, transformed.DocumentElement.OuterXml))
                                    {
                                        task.Status = "The transformation was applied but did not result in any changes, skipping.";
                                    }
                                    else
                                    {
                                        itemToTransform.XmlDefinition = transformed;
                                        transformedItems.Add(itemToTransform);
                                    }
                                }
                            }
                            else if (transformation.WorkItemConfigurationItemType == WorkItemConfigurationItemType.CommonConfiguration)
                            {
                                var itemToTransform = transformedItems.FirstOrDefault(w => w.Type == WorkItemConfigurationItemType.CommonConfiguration);
                                if (itemToTransform == null)
                                {
                                    itemToTransform = WorkItemConfigurationItemImportExport.GetCommonConfiguration(project);
                                }
                                if (itemToTransform != null)
                                {
                                    task.Status = "Transforming " + itemToTransform.DisplayName;
                                    var transformed = WorkItemConfigurationTransformer.Transform(transformation.TransformationType, itemToTransform.XmlDefinition, transformation.TransformationXml);
                                    if (string.Equals(itemToTransform.XmlDefinition.DocumentElement.OuterXml, transformed.DocumentElement.OuterXml))
                                    {
                                        task.Status = "The transformation was applied but did not result in any changes, skipping.";
                                    }
                                    else
                                    {
                                        itemToTransform.XmlDefinition = transformed;
                                        transformedItems.Add(itemToTransform);
                                    }
                                }
                            }
                            else if (transformation.WorkItemConfigurationItemType == WorkItemConfigurationItemType.ProcessConfiguration)
                            {
                                var itemToTransform = transformedItems.FirstOrDefault(w => w.Type == WorkItemConfigurationItemType.ProcessConfiguration);
                                if (itemToTransform == null)
                                {
                                    itemToTransform = WorkItemConfigurationItemImportExport.GetProcessConfiguration(project);
                                }
                                if (itemToTransform != null)
                                {
                                    task.Status = "Transforming " + itemToTransform.DisplayName;
                                    var transformed = WorkItemConfigurationTransformer.Transform(transformation.TransformationType, itemToTransform.XmlDefinition, transformation.TransformationXml);
                                    if (string.Equals(itemToTransform.XmlDefinition.DocumentElement.OuterXml, transformed.DocumentElement.OuterXml))
                                    {
                                        task.Status = "The transformation was applied but did not result in any changes, skipping.";
                                    }
                                    else
                                    {
                                        itemToTransform.XmlDefinition = transformed;
                                        transformedItems.Add(itemToTransform);
                                    }
                                }
                            }
                            else
                            {
                                throw new ArgumentException("The Work Item Configuration Item Type is unknown: " + transformation.WorkItemConfigurationItemType.ToString());
                            }
                            if (task.IsCanceled)
                            {
                                break;
                            }
                        }

                        // Only apply the transformations if they all succeeded (i.e. there was no exception).
                        if (task.IsCanceled)
                        {
                            break;
                        }
                        else
                        {
                            var teamProjectsWithConfigurationItems = new Dictionary <TeamProjectInfo, List <WorkItemConfigurationItem> >()
                            {
                                { teamProject, transformedItems }
                            };
                            var options = ImportOptions.None;
                            if (simulate)
                            {
                                options |= ImportOptions.Simulate;
                            }
                            if (saveCopy)
                            {
                                options |= ImportOptions.SaveCopy;
                            }
                            WorkItemConfigurationItemImportExport.Import(this.Logger, task, false, store, teamProjectsWithConfigurationItems, options);
                        }
                        numTransformations += transformedItems.Count;
                    }
                    catch (Exception exc)
                    {
                        task.SetWarning(string.Format(CultureInfo.CurrentCulture, "An error occurred while processing Team Project \"{0}\"", teamProject.Name), exc);
                    }
                    if (task.IsCanceled)
                    {
                        task.Status = "Canceled";
                        break;
                    }
                }
                e.Result = numTransformations;
            };
            worker.RunWorkerCompleted += (sender, e) =>
            {
                if (e.Error != null)
                {
                    Logger.Log("An unexpected exception occurred while transforming work item configuration", e.Error);
                    task.SetError(e.Error);
                    task.SetComplete("An unexpected exception occurred");
                }
                else
                {
                    var numTransformations = (int)e.Result;
                    task.SetComplete("Applied transformation to " + numTransformations.ToCountString("work item configuration item"));
                }
            };
            worker.RunWorkerAsync();
        }