Пример #1
0
        protected override void VisitValueExpression(
            XElement element, XAttribute attribute,
            MSBuildElementSyntax resolvedElement, MSBuildAttributeSyntax resolvedAttribute,
            ValueInfo info, MSBuildValueKind kind, ExpressionNode node)
        {
            bool allowExpressions = kind.AllowExpressions();
            bool allowLists       = kind.AllowListsOrCommaLists();

            if (node is ListExpression list)
            {
                if (!allowLists)
                {
                    Document.Diagnostics.Add(
                        CoreDiagnostics.UnexpectedList,
                        new TextSpan(list.Nodes[0].End, list.End - list.Nodes[0].End),
                        ImmutableDictionary <string, object> .Empty.Add("Name", info.Name),
                        DescriptionFormatter.GetKindNoun(info),
                        info.Name);
                }
                if (!allowExpressions)
                {
                    var expr = list.Nodes.FirstOrDefault(n => !(n is ExpressionText));
                    if (expr != null)
                    {
                        AddExpressionWarning(expr);
                    }
                }
            }
            else if (node is ExpressionText lit)
            {
                VisitPureLiteral(info, kind, lit.GetUnescapedValue(), lit.Offset);
            }
            else
            {
                if (!allowExpressions)
                {
                    AddExpressionWarning(node);
                }
            }

            foreach (var n in node.WithAllDescendants())
            {
                switch (n)
                {
                case ExpressionError err:
                    var(desc, args) = CoreDiagnostics.GetExpressionError(err, info);
                    Document.Diagnostics.Add(desc, new TextSpan(err.Offset, Math.Max(1, err.Length)), args);
                    break;

                case ExpressionMetadata meta:
                case ExpressionProperty prop:
                case ExpressionItem item:
                    //TODO: can we validate property/metadata/items refs?
                    //maybe warn if they're not used anywhere outside of this expression?
                    //TODO: deprecation squiggles in expressions
                    break;
                }
            }

            void AddExpressionWarning(ExpressionNode n)
            => Document.Diagnostics.Add(CoreDiagnostics.UnexpectedExpression,
                                        new TextSpan(n.Offset, n.Length),
                                        DescriptionFormatter.GetKindNoun(info),
                                        info.Name);
        }
        protected override void VisitValueExpression(
            XElement element, XAttribute attribute,
            MSBuildElementSyntax resolvedElement, MSBuildAttributeSyntax resolvedAttribute,
            ValueInfo info, MSBuildValueKind kind, ExpressionNode node)
        {
            bool allowExpressions = kind.AllowExpressions();
            bool allowLists       = kind.AllowListsOrCommaLists();

            if (node is ListExpression list)
            {
                if (!allowLists)
                {
                    Document.Diagnostics.Add(
                        CoreDiagnostics.UnexpectedList,
                        new TextSpan(list.Nodes[0].End, list.End - list.Nodes[0].End),
                        ImmutableDictionary <string, object> .Empty.Add("Name", info.Name),
                        DescriptionFormatter.GetKindNoun(info),
                        info.Name);
                }
                if (!allowExpressions)
                {
                    var expr = list.Nodes.FirstOrDefault(n => !(n is ExpressionText));
                    if (expr != null)
                    {
                        AddExpressionWarning(expr);
                    }
                }
            }
            else if (node is ExpressionText lit)
            {
                VisitPureLiteral(info, kind, lit.GetUnescapedValue(), lit.Offset);
            }
            else
            {
                if (!allowExpressions)
                {
                    AddExpressionWarning(node);
                }
            }

            foreach (var n in node.WithAllDescendants())
            {
                switch (n)
                {
                case ExpressionError err:
                    var(desc, args) = CoreDiagnostics.GetExpressionError(err, info);
                    Document.Diagnostics.Add(desc, new TextSpan(err.Offset, Math.Max(1, err.Length)), args);
                    break;

                case ExpressionMetadata meta:
                    var metaItem = meta.GetItemName();
                    if (!string.IsNullOrEmpty(metaItem) && !IsMetadataUsed(metaItem, meta.MetadataName, ReferenceUsage.Write))
                    {
                        Document.Diagnostics.Add(
                            CoreDiagnostics.UnwrittenMetadata,
                            meta.Span,
                            ImmutableDictionary <string, object> .Empty
                            .Add("ItemName", metaItem)
                            .Add("Name", meta.MetadataName)
                            .Add("Spans", new [] { new TextSpan(meta.MetadataNameOffset, meta.MetadataName.Length) }),
                            metaItem, meta.MetadataName
                            );
                    }
                    break;

                case ExpressionPropertyName prop:
                    if (!IsPropertyUsed(prop.Name, ReferenceUsage.Write))
                    {
                        Document.Diagnostics.Add(
                            CoreDiagnostics.UnwrittenProperty,
                            prop.Span,
                            ImmutableDictionary <string, object> .Empty
                            .Add("Name", prop.Name)
                            .Add("Spans", new[] { new TextSpan(prop.Offset, prop.Length) }),
                            prop.Name
                            );
                    }
                    break;

                case ExpressionItemName item:
                    if (!IsItemUsed(item.Name, ReferenceUsage.Write))
                    {
                        Document.Diagnostics.Add(
                            CoreDiagnostics.UnwrittenItem,
                            item.Span,
                            ImmutableDictionary <string, object> .Empty
                            .Add("Name", item.Name)
                            .Add("Spans", new[] { new TextSpan(item.Offset, item.Length) }),
                            item.Name
                            );
                    }
                    //TODO: deprecation squiggles in expressions
                    break;
                }
            }

            void AddExpressionWarning(ExpressionNode n)
            => Document.Diagnostics.Add(CoreDiagnostics.UnexpectedExpression,
                                        new TextSpan(n.Offset, n.Length),
                                        DescriptionFormatter.GetKindNoun(info),
                                        info.Name);
        }