public override SyntaxNode VisitIdentifierName(IdentifierNameSyntax node) { // This method handles NameColonSyntax as well as regular references to parameter // Considers: // foo(a: 1); -> foo(b: 1); // int c = a; -> int c = b; // Get related symbol CommonSymbolInfo symbolInfo = this.model.GetSymbolInfo(node, this.cancellationToken); ISymbol referencedSymbol = symbolInfo.Symbol; if (referencedSymbol != null) { // Verify does the name refer to searched symbol if (referencedSymbol.Equals(this.parameterSymbol)) { // Rename the identifier token SyntaxToken identifierToken = node.Identifier; return(node.WithIdentifier(Syntax.Identifier(identifierToken.LeadingTrivia, this.newName, identifierToken.TrailingTrivia))); } } // Perform default behavior return(base.VisitIdentifierName(node)); }
public override SyntaxNode VisitIdentifierName(IdentifierNameSyntax node) { // Get related symbol CommonSymbolInfo symbolInfo = this.model.GetSymbolInfo(node, this.cancellationToken); ISymbol referencedSymbol = symbolInfo.Symbol; // Do not consider identifiers within NameColonSyntax! if (referencedSymbol != null && !(node.Parent is NameColonSyntax)) { // Verify does the name refer to any of compressed parameters if (this.symbols.Contains(referencedSymbol)) { // Replace parameter reference with reference via ParameterObject // Considers: // int a = b; -> int a = parameterObject.b; MemberAccessExpressionSyntax accessExpression = Syntax.MemberAccessExpression( SyntaxKind.MemberAccessExpression, Syntax.IdentifierName(this.parameterObjectName), Syntax.IdentifierName(node.Identifier.WithLeadingTrivia()) ) .WithLeadingTrivia(node.GetLeadingTrivia()) .WithTrailingTrivia(node.GetTrailingTrivia()); return(accessExpression); } } // Perform default behavior return(base.VisitIdentifierName(node)); }
public override SyntaxNode VisitObjectCreationExpression(ObjectCreationExpressionSyntax node) { TypeSyntax typeSyntax = node.Type; CommonSymbolInfo constructorSymbolInfo = this.model.GetSymbolInfo(typeSyntax); INamedTypeSymbol classTypeSymbol = constructorSymbolInfo.Symbol.ContainingType; if (classTypeSymbol.Equals(this.classSymbol)) { // Replace with Instance access // Considers: // new A() -> A.Instance() return(Syntax.InvocationExpression( Syntax.MemberAccessExpression( SyntaxKind.MemberAccessExpression , Syntax.ParseName(this.classSymbol.ToMinimalDisplayString(node.GetLocation(), model)) , Syntax.IdentifierName("Instance") ) ) .WithLeadingTrivia(node.GetLeadingTrivia()) .WithTrailingTrivia(node.GetTrailingTrivia())); } else { return(base.VisitObjectCreationExpression(node)); } }
private List <string> GetNamespaces(bool appendDefaultNamespaces, CommonSymbolInfo namespaceSymbolInfo) { var namespaces = new List <string>(); if (appendDefaultNamespaces) { namespaces.AddRange(NamespaceToDllMap.Map.Keys); } //NuGet namespaces namespaces.AddRange(GetAssemblyNameSpaces(this.NuGetDllReferences)); if (namespaceSymbolInfo.Symbol != null && namespaceSymbolInfo.Symbol.Kind == CommonSymbolKind.Namespace) { var symbolNameSpaces = new List <string>(); symbolNameSpaces.AddRange( GetAssemblyNameSpaces( ((INamespaceSymbol)namespaceSymbolInfo.Symbol).ConstituentNamespaces.Select( n => n.ContainingAssembly.Identity.Location))); symbolNameSpaces.AddRange(namespaces); namespaces = symbolNameSpaces.Distinct() .Where(n => n != null && n.StartsWith(namespaceSymbolInfo.Symbol.ToDisplayString())) .ToList(); } return(namespaces); }
public CodeRefactoring GetRefactoring(IDocument document, TextSpan textSpan, CancellationToken cancellationToken) { string newName = "newVariableName"; SyntaxNode root = (SyntaxNode)document.GetSyntaxRoot(cancellationToken); SyntaxToken token = root.FindToken(textSpan.Start, findInsideTrivia: true); // Verify is the selected token an identifier if (token.Kind == SyntaxKind.IdentifierToken && token.Span.Start <= textSpan.End && textSpan.End <= token.Span.End) { ISemanticModel model = document.GetSemanticModel(cancellationToken); ISymbol symbol = null; CommonSyntaxNode parentNode = token.Parent; // Local variable node-reference can be either IdentifierName node or VariableDeclarator node if (parentNode is IdentifierNameSyntax) { CommonSymbolInfo symbolInfo = model.GetSymbolInfo(parentNode, cancellationToken); symbol = symbolInfo.Symbol; } else if (parentNode is VariableDeclaratorSyntax) { symbol = model.GetDeclaredSymbol(parentNode, cancellationToken); } if (symbol == null) { return(null); } // Verify is the symbol of local variable kind if (symbol.Kind != CommonSymbolKind.Local) { return(null); } // Verify is there any other local variable of the same name IList <ISymbol> visibleSymbols = model.LookupSymbols(token.Span.Start, name: newName, container: symbol.ContainingType); bool isNameReserved = visibleSymbols .Any(otherSymbol => (otherSymbol.Kind == CommonSymbolKind.Local || otherSymbol.Kind == CommonSymbolKind.Parameter) && !otherSymbol.Equals(symbol)); if (!isNameReserved) { return(new CodeRefactoring( new[] { new RenameLocalAction(document, token, symbol, newName) }, token.Span)); } } return(null); }
private List<string> GetNamespaces(bool appendDefaultNamespaces, CommonSymbolInfo namespaceSymbolInfo) { var namespaces = new List<string>(); if (appendDefaultNamespaces) namespaces.AddRange(NamespaceToDllMap.Map.Keys); //NuGet namespaces namespaces.AddRange(GetAssemblyNameSpaces(this.NuGetDllReferences)); if (namespaceSymbolInfo.Symbol != null && namespaceSymbolInfo.Symbol.Kind == CommonSymbolKind.Namespace) { var symbolNameSpaces = new List<string>(); symbolNameSpaces.AddRange( GetAssemblyNameSpaces( ((INamespaceSymbol) namespaceSymbolInfo.Symbol).ConstituentNamespaces.Select( n => n.ContainingAssembly.Identity.Location))); symbolNameSpaces.AddRange(namespaces); namespaces = symbolNameSpaces.Distinct() .Where(n => n != null && n.StartsWith(namespaceSymbolInfo.Symbol.ToDisplayString())) .ToList(); } return namespaces; }
public override SyntaxNode VisitInvocationExpression(InvocationExpressionSyntax node) { ExpressionSyntax expression = node.Expression; CommonSymbolInfo methodSymbolInfo = this.model.GetSymbolInfo(expression); MethodSymbol visitedMethodSymbol = methodSymbolInfo.Symbol as MethodSymbol; // Verify does the invocation refer to searched method if (visitedMethodSymbol != null && visitedMethodSymbol.Equals(this.methodSymbol)) { if (expression.Kind == SyntaxKind.MemberAccessExpression) { MemberAccessExpressionSyntax memberAccess = (MemberAccessExpressionSyntax)expression; // Move all from the beginning (except for the method name) to parameter // Considers: // a.b.foo(47); -> B.foo(a.b, 47); ArgumentListSyntax argumentsList = node.ArgumentList; ArgumentSyntax newArgument = Syntax.Argument(memberAccess.Expression); SeparatedSyntaxList <ArgumentSyntax> arguments = argumentsList.Arguments.Insert(0, newArgument); argumentsList = Syntax.ArgumentList(arguments).WithAdditionalAnnotations(CodeAnnotations.Formatting); InvocationExpressionSyntax newInvocation = node.WithArgumentList(argumentsList); // Replace invocation expression with qualified (class) name TypeSyntax typeSyntax = Syntax.ParseTypeName(this.methodSymbol.ContainingType.ToMinimalDisplayString(expression.GetLocation(), this.model)) .WithLeadingTrivia(memberAccess.Expression.GetLeadingTrivia()); newInvocation = newInvocation.WithExpression(Syntax.MemberAccessExpression(SyntaxKind.MemberAccessExpression, typeSyntax, memberAccess.Name)); return(newInvocation); } else if (expression.Kind == SyntaxKind.IdentifierName) { IdentifierNameSyntax identifierName = (IdentifierNameSyntax)expression; // Unqualified reference, `this' should be passed as first parameter // Considers: // foo(47); -> B.foo(this, 47); ArgumentListSyntax argumentsList = node.ArgumentList; ArgumentSyntax newArgument = Syntax.Argument(Syntax.ThisExpression()); SeparatedSyntaxList <ArgumentSyntax> arguments = argumentsList.Arguments.Insert(0, newArgument); argumentsList = Syntax.ArgumentList(arguments).WithAdditionalAnnotations(CodeAnnotations.Formatting); InvocationExpressionSyntax newInvocation = node.WithArgumentList(argumentsList); // Replace invocation expression with qualified (class) name TypeSyntax typeSyntax = Syntax.ParseTypeName(this.methodSymbol.ContainingType.ToMinimalDisplayString(expression.GetLocation(), this.model)) .WithLeadingTrivia(identifierName.GetLeadingTrivia()); newInvocation = newInvocation.WithExpression(Syntax.MemberAccessExpression(SyntaxKind.MemberAccessExpression, typeSyntax, identifierName)); return(newInvocation); } } return(base.VisitInvocationExpression(node)); }