private ProjectItemElement MergeWithExistingItemsWithACondition(
            ProjectItemElement item,
            ProjectItemGroupElement destinationItemGroup)
        {
            // This logic only applies to conditionless items
            if (item.ConditionChain().Any() || destinationItemGroup.ConditionChain().Any())
            {
                return(item);
            }

            var existingItemsWithACondition =
                FindExistingItemsWithACondition(item, destinationItemGroup.ContainingProject, destinationItemGroup);

            MigrationTrace.Instance.WriteLine(String.Format(
                                                  LocalizableStrings.ItemTransformApplicatorMergingItemWithExistingItems,
                                                  nameof(ItemTransformApplicator),
                                                  existingItemsWithACondition.Count()));

            foreach (var existingItem in existingItemsWithACondition)
            {
                if (!string.IsNullOrEmpty(item.Include))
                {
                    MergeOnIncludesWithExistingItemsWithACondition(item, existingItem, destinationItemGroup);
                }

                if (!string.IsNullOrEmpty(item.Update))
                {
                    MergeOnUpdatesWithExistingItemsWithACondition(item, existingItem, destinationItemGroup);
                }
            }

            return(item);
        }
Beispiel #2
0
        private ProjectItemElement MergeWithExistingItemsWithNoCondition(ProjectItemElement item, ProjectItemGroupElement destinationItemGroup)
        {
            // This logic only applies to items being placed into a condition
            if (!item.ConditionChain().Any() && !destinationItemGroup.ConditionChain().Any())
            {
                return(item);
            }

            var existingItemsWithNoCondition =
                FindExistingItemsWithNoCondition(item, destinationItemGroup.ContainingProject, destinationItemGroup);

            MigrationTrace.Instance.WriteLine($"{nameof(ItemTransformApplicator)}: Merging Item with {existingItemsWithNoCondition.Count()} existing items with a different condition chain.");

            // Handle the item being placed inside of a condition, when it is overlapping with a conditionless item
            // If it is not definining new metadata or excludes, the conditioned item can be merged with the
            // conditionless item
            foreach (var existingItem in existingItemsWithNoCondition)
            {
                var encompassedIncludes = existingItem.GetEncompassedIncludes(item);
                if (encompassedIncludes.Any())
                {
                    MigrationTrace.Instance.WriteLine($"{nameof(ItemTransformApplicator)}: encompassed includes {string.Join(", ", encompassedIncludes)}");
                    item.RemoveIncludes(encompassedIncludes);
                    if (!item.Includes().Any())
                    {
                        MigrationTrace.Instance.WriteLine($"{nameof(ItemTransformApplicator)}: Ignoring Item {{ ItemType: {existingItem.ItemType}, Condition: {existingItem.Condition}, Include: {existingItem.Include}, Exclude: {existingItem.Exclude} }}");
                        return(null);
                    }
                }
            }

            // If we haven't returned, and there are existing items with a separate condition, we need to
            // overwrite with those items inside the destinationItemGroup by using a Remove
            if (existingItemsWithNoCondition.Any())
            {
                // Merge with the first remove if possible
                var existingRemoveItem = destinationItemGroup.Items
                                         .Where(i =>
                                                string.IsNullOrEmpty(i.Include) &&
                                                string.IsNullOrEmpty(i.Exclude) &&
                                                !string.IsNullOrEmpty(i.Remove))
                                         .FirstOrDefault();

                if (existingRemoveItem != null)
                {
                    existingRemoveItem.Remove += ";" + item.Include;
                }
                else
                {
                    var clearPreviousItem = _projectElementGenerator.CreateItemElement(item.ItemType);
                    clearPreviousItem.Remove = item.Include;

                    AddItemToItemGroup(clearPreviousItem, destinationItemGroup);
                }
            }

            return(item);
        }
Beispiel #3
0
        private ProjectItemElement MergeWithExistingItemsWithDifferentCondition(ProjectItemElement item, ProjectItemGroupElement destinationItemGroup)
        {
            var existingItemsWithDifferentCondition =
                FindExistingItemsWithDifferentCondition(item, destinationItemGroup.ContainingProject, destinationItemGroup);

            MigrationTrace.Instance.WriteLine($"{nameof(TransformApplicator)}: Merging Item with {existingItemsWithDifferentCondition.Count()} existing items with a different condition chain.");

            foreach (var existingItem in existingItemsWithDifferentCondition)
            {
                var encompassedIncludes = existingItem.GetEncompassedIncludes(item);
                if (encompassedIncludes.Any())
                {
                    MigrationTrace.Instance.WriteLine($"{nameof(TransformApplicator)}: encompassed includes {string.Join(", ", encompassedIncludes)}");
                    item.RemoveIncludes(encompassedIncludes);
                    if (!item.Includes().Any())
                    {
                        MigrationTrace.Instance.WriteLine($"{nameof(TransformApplicator)}: Ignoring Item {{ ItemType: {existingItem.ItemType}, Condition: {existingItem.Condition}, Include: {existingItem.Include}, Exclude: {existingItem.Exclude} }}");
                        return(null);
                    }
                }
            }

            // If we haven't returned, and there are existing items with a separate condition, we need to
            // overwrite with those items inside the destinationItemGroup by using a Remove
            // Unless this is a conditionless item, in which case this the conditioned items should be doing the
            // overwriting.
            if (existingItemsWithDifferentCondition.Any() &&
                (item.ConditionChain().Count() > 0 || destinationItemGroup.ConditionChain().Count() > 0))
            {
                // Merge with the first remove if possible
                var existingRemoveItem = destinationItemGroup.Items
                                         .Where(i =>
                                                string.IsNullOrEmpty(i.Include) &&
                                                string.IsNullOrEmpty(i.Exclude) &&
                                                !string.IsNullOrEmpty(i.Remove))
                                         .FirstOrDefault();

                if (existingRemoveItem != null)
                {
                    existingRemoveItem.Remove += ";" + item.Include;
                }
                else
                {
                    var clearPreviousItem = _projectElementGenerator.CreateItemElement(item.ItemType);
                    clearPreviousItem.Remove = item.Include;

                    Execute(clearPreviousItem, destinationItemGroup);
                }
            }

            return(item);
        }
Beispiel #4
0
        private ProjectItemElement MergeWithExistingItemsWithACondition(ProjectItemElement item, ProjectItemGroupElement destinationItemGroup)
        {
            // This logic only applies to conditionless items
            if (item.ConditionChain().Any() || destinationItemGroup.ConditionChain().Any())
            {
                return(item);
            }

            var existingItemsWithACondition =
                FindExistingItemsWithACondition(item, destinationItemGroup.ContainingProject, destinationItemGroup);

            MigrationTrace.Instance.WriteLine($"{nameof(ItemTransformApplicator)}: Merging Item with {existingItemsWithACondition.Count()} existing items with a different condition chain.");

            foreach (var existingItem in existingItemsWithACondition)
            {
                // If this item is encompassing items in a condition, remove the encompassed includes from the existing item
                var encompassedIncludes = item.GetEncompassedIncludes(existingItem);
                if (encompassedIncludes.Any())
                {
                    MigrationTrace.Instance.WriteLine($"{nameof(ItemTransformApplicator)}: encompassed includes {string.Join(", ", encompassedIncludes)}");
                    existingItem.RemoveIncludes(encompassedIncludes);
                }

                // continue if the existing item is now empty
                if (!existingItem.Includes().Any())
                {
                    MigrationTrace.Instance.WriteLine($"{nameof(ItemTransformApplicator)}: Removing Item {{ ItemType: {existingItem.ItemType}, Condition: {existingItem.Condition}, Include: {existingItem.Include}, Exclude: {existingItem.Exclude} }}");
                    existingItem.Parent.RemoveChild(existingItem);
                    continue;
                }

                // If we haven't continued, the existing item may have includes
                // that need to be removed before being redefined, to avoid duplicate includes
                // Create or merge with existing remove
                var remainingIntersectedIncludes = existingItem.IntersectIncludes(item);

                if (remainingIntersectedIncludes.Any())
                {
                    var existingRemoveItem = destinationItemGroup.Items
                                             .Where(i =>
                                                    string.IsNullOrEmpty(i.Include) &&
                                                    string.IsNullOrEmpty(i.Exclude) &&
                                                    !string.IsNullOrEmpty(i.Remove))
                                             .FirstOrDefault();

                    if (existingRemoveItem != null)
                    {
                        var removes = new HashSet <string>(existingRemoveItem.Remove.Split(';'));
                        foreach (var include in remainingIntersectedIncludes)
                        {
                            removes.Add(include);
                        }
                        existingRemoveItem.Remove = string.Join(";", removes);
                    }
                    else
                    {
                        var clearPreviousItem = _projectElementGenerator.CreateItemElement(item.ItemType);
                        clearPreviousItem.Remove = string.Join(";", remainingIntersectedIncludes);

                        AddItemToItemGroup(clearPreviousItem, existingItem.Parent as ProjectItemGroupElement);
                    }
                }
            }

            return(item);
        }