Search in sources :

Example 1 with Decorator

use of org.sonar.plugins.python.api.tree.Decorator in project sonar-python by SonarSource.

the class PythonTreeMaker method classDefStatement.

public ClassDef classDefStatement(AstNode astNode) {
    AstNode decoratorsNode = astNode.getFirstChild(PythonGrammar.DECORATORS);
    List<Decorator> decorators = Collections.emptyList();
    if (decoratorsNode != null) {
        decorators = decoratorsNode.getChildren(PythonGrammar.DECORATOR).stream().map(this::decorator).collect(Collectors.toList());
    }
    Name name = name(astNode.getFirstChild(PythonGrammar.CLASSNAME).getFirstChild(PythonGrammar.NAME));
    ArgList args = null;
    AstNode leftPar = astNode.getFirstChild(PythonPunctuator.LPARENTHESIS);
    if (leftPar != null) {
        args = argList(astNode.getFirstChild(PythonGrammar.ARGLIST));
    }
    AstNode suite = astNode.getFirstChild(PythonGrammar.SUITE);
    StatementList body = getStatementListFromSuite(suite);
    Token classToken = toPyToken(astNode.getFirstChild(PythonKeyword.CLASS).getToken());
    AstNode rightPar = astNode.getFirstChild(PythonPunctuator.RPARENTHESIS);
    Token colon = toPyToken(astNode.getFirstChild(PythonPunctuator.COLON).getToken());
    return new ClassDefImpl(decorators, classToken, name, leftPar != null ? toPyToken(leftPar.getToken()) : null, args, rightPar != null ? toPyToken(rightPar.getToken()) : null, colon, suiteNewLine(suite), suiteIndent(suite), body, suiteDedent(suite), DocstringExtractor.extractDocstring(body));
}
Also used : Decorator(org.sonar.plugins.python.api.tree.Decorator) StatementList(org.sonar.plugins.python.api.tree.StatementList) ArgList(org.sonar.plugins.python.api.tree.ArgList) Token(org.sonar.plugins.python.api.tree.Token) AstNode(com.sonar.sslr.api.AstNode) AliasedName(org.sonar.plugins.python.api.tree.AliasedName) Name(org.sonar.plugins.python.api.tree.Name) DottedName(org.sonar.plugins.python.api.tree.DottedName) ImportName(org.sonar.plugins.python.api.tree.ImportName)

Example 2 with Decorator

use of org.sonar.plugins.python.api.tree.Decorator in project sonar-python by SonarSource.

the class PythonTreeMaker method funcDefStatement.

public FunctionDef funcDefStatement(AstNode astNode) {
    AstNode decoratorsNode = astNode.getFirstChild(PythonGrammar.DECORATORS);
    List<Decorator> decorators = Collections.emptyList();
    if (decoratorsNode != null) {
        decorators = decoratorsNode.getChildren(PythonGrammar.DECORATOR).stream().map(this::decorator).collect(Collectors.toList());
    }
    Name name = name(astNode.getFirstChild(PythonGrammar.FUNCNAME).getFirstChild(PythonGrammar.NAME));
    ParameterList parameterList = null;
    AstNode typedArgListNode = astNode.getFirstChild(PythonGrammar.TYPEDARGSLIST);
    if (typedArgListNode != null) {
        List<AnyParameter> arguments = typedArgListNode.getChildren(PythonGrammar.TFPDEF, PythonPunctuator.MUL, PythonPunctuator.DIV).stream().map(this::parameter).filter(Objects::nonNull).collect(Collectors.toList());
        List<Token> commas = punctuators(typedArgListNode, PythonPunctuator.COMMA);
        parameterList = new ParameterListImpl(arguments, commas);
    }
    AstNode suite = astNode.getFirstChild(PythonGrammar.SUITE);
    StatementList body = getStatementListFromSuite(suite);
    AstNode defNode = astNode.getFirstChild(PythonKeyword.DEF);
    Token asyncToken = null;
    AstNode defPreviousSibling = defNode.getPreviousSibling();
    if (defPreviousSibling != null && defPreviousSibling.getToken().getValue().equals("async")) {
        asyncToken = toPyToken(defPreviousSibling.getToken());
    }
    Token lPar = toPyToken(astNode.getFirstChild(PythonPunctuator.LPARENTHESIS).getToken());
    Token rPar = toPyToken(astNode.getFirstChild(PythonPunctuator.RPARENTHESIS).getToken());
    TypeAnnotation returnType = null;
    AstNode returnTypeNode = astNode.getFirstChild(PythonGrammar.FUN_RETURN_ANNOTATION);
    if (returnTypeNode != null) {
        List<AstNode> children = returnTypeNode.getChildren();
        returnType = new TypeAnnotationImpl(toPyToken(children.get(0).getToken()), toPyToken(children.get(1).getToken()), expression(children.get(2)));
    }
    Token colon = toPyToken(astNode.getFirstChild(PythonPunctuator.COLON).getToken());
    return new FunctionDefImpl(decorators, asyncToken, toPyToken(defNode.getToken()), name, lPar, parameterList, rPar, returnType, colon, suiteNewLine(suite), suiteIndent(suite), body, suiteDedent(suite), isMethodDefinition(astNode), DocstringExtractor.extractDocstring(body));
}
Also used : TypeAnnotation(org.sonar.plugins.python.api.tree.TypeAnnotation) Token(org.sonar.plugins.python.api.tree.Token) AliasedName(org.sonar.plugins.python.api.tree.AliasedName) Name(org.sonar.plugins.python.api.tree.Name) DottedName(org.sonar.plugins.python.api.tree.DottedName) ImportName(org.sonar.plugins.python.api.tree.ImportName) Decorator(org.sonar.plugins.python.api.tree.Decorator) StatementList(org.sonar.plugins.python.api.tree.StatementList) ParameterList(org.sonar.plugins.python.api.tree.ParameterList) AnyParameter(org.sonar.plugins.python.api.tree.AnyParameter) AstNode(com.sonar.sslr.api.AstNode)

Example 3 with Decorator

use of org.sonar.plugins.python.api.tree.Decorator in project sonar-python by SonarSource.

the class PythonTreeMakerTest method funcdef_statement.

@Test
public void funcdef_statement() {
    setRootRule(PythonGrammar.FUNCDEF);
    AstNode astNode = p.parse("def func(): pass");
    FunctionDef functionDef = treeMaker.funcDefStatement(astNode);
    assertThat(functionDef.name()).isNotNull();
    assertThat(functionDef.name().name()).isEqualTo("func");
    assertThat(functionDef.body().statements()).hasSize(1);
    assertThat(functionDef.body().statements().get(0).is(Tree.Kind.PASS_STMT)).isTrue();
    assertThat(functionDef.children()).hasSize(6);
    assertThat(functionDef.parameters()).isNull();
    assertThat(functionDef.isMethodDefinition()).isFalse();
    assertThat(functionDef.docstring()).isNull();
    assertThat(functionDef.decorators()).isEmpty();
    assertThat(functionDef.asyncKeyword()).isNull();
    assertThat(functionDef.returnTypeAnnotation()).isNull();
    assertThat(functionDef.colon().value()).isEqualTo(":");
    assertThat(functionDef.defKeyword().value()).isEqualTo("def");
    assertThat(functionDef.leftPar().value()).isEqualTo("(");
    assertThat(functionDef.rightPar().value()).isEqualTo(")");
    functionDef = parse("def func(x): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.parameters().all()).hasSize(1);
    functionDef = parse("async def func(x): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.asyncKeyword().value()).isEqualTo("async");
    functionDef = parse("def func(x) -> string : pass", treeMaker::funcDefStatement);
    TypeAnnotation returnType = functionDef.returnTypeAnnotation();
    assertThat(returnType.getKind()).isEqualTo(Tree.Kind.RETURN_TYPE_ANNOTATION);
    assertThat(returnType.expression().getKind()).isEqualTo(Tree.Kind.NAME);
    functionDef = parse("@foo\ndef func(x): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.decorators()).hasSize(1);
    Decorator decoratorTree = functionDef.decorators().get(0);
    assertThat(decoratorTree.getKind()).isEqualTo(Tree.Kind.DECORATOR);
    assertThat(decoratorTree.atToken().value()).isEqualTo("@");
    assertThat(decoratorTree.name().names().get(0).name()).isEqualTo("foo");
    assertThat(decoratorTree.leftPar()).isNull();
    assertThat(decoratorTree.arguments()).isNull();
    assertThat(decoratorTree.rightPar()).isNull();
    functionDef = parse("@foo()\n@bar(1)\ndef func(x): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.decorators()).hasSize(2);
    Decorator decoratorTree1 = functionDef.decorators().get(0);
    assertThat(decoratorTree1.leftPar().value()).isEqualTo("(");
    assertThat(decoratorTree1.arguments()).isNull();
    assertThat(decoratorTree1.rightPar().value()).isEqualTo(")");
    Decorator decoratorTree2 = functionDef.decorators().get(1);
    assertThat(decoratorTree2.arguments().arguments()).extracting(arg -> ((RegularArgument) arg).expression().getKind()).containsExactly(Tree.Kind.NUMERIC_LITERAL);
    functionDef = parse("def func(x, y): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.parameters().all()).hasSize(2);
    functionDef = parse("def func(x = 'foo', y): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.parameters().all()).isEqualTo(functionDef.parameters().nonTuple());
    List<Parameter> parameters = functionDef.parameters().nonTuple();
    assertThat(parameters).hasSize(2);
    Parameter parameter1 = parameters.get(0);
    assertThat(parameter1.name().name()).isEqualTo("x");
    assertThat(parameter1.equalToken().value()).isEqualTo("=");
    assertThat(parameter1.defaultValue().is(Tree.Kind.STRING_LITERAL)).isTrue();
    assertThat(parameter1.children()).doesNotContainNull();
    Parameter parameter2 = parameters.get(1);
    assertThat(parameter2.equalToken()).isNull();
    assertThat(parameter2.defaultValue()).isNull();
    assertThat(parameter2.children()).doesNotContainNull();
    functionDef = parse("def func(p1, *p2, **p3): pass", treeMaker::funcDefStatement);
    parameters = functionDef.parameters().nonTuple();
    assertThat(parameters).extracting(p -> p.name().name()).containsExactly("p1", "p2", "p3");
    assertThat(parameters).extracting(p -> p.starToken() == null ? null : p.starToken().value()).containsExactly(null, "*", "**");
    Parameter parameter = parameters.get(2);
    assertThat(parameter.children()).containsExactly(parameter.starToken(), parameter.name());
    assertThat(parameter.firstToken()).isSameAs(parameter.starToken());
    assertThat(parameter.lastToken()).isSameAs(parameter.name().lastToken());
    functionDef = parse("def func(x : int, y): pass", treeMaker::funcDefStatement);
    parameters = functionDef.parameters().nonTuple();
    assertThat(parameters).hasSize(2);
    TypeAnnotation annotation = parameters.get(0).typeAnnotation();
    assertThat(annotation.getKind()).isEqualTo(Tree.Kind.PARAMETER_TYPE_ANNOTATION);
    assertThat(((Name) annotation.expression()).name()).isEqualTo("int");
    assertThat(annotation.children()).hasSize(2);
    assertThat(parameters.get(1).typeAnnotation()).isNull();
    functionDef = parse("def func(a, ((b, c), d)): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.parameters().all()).hasSize(2);
    assertThat(functionDef.parameters().all()).extracting(Tree::getKind).containsExactly(Tree.Kind.PARAMETER, Tree.Kind.TUPLE_PARAMETER);
    TupleParameter tupleParam = (TupleParameter) functionDef.parameters().all().get(1);
    assertThat(tupleParam.openingParenthesis().value()).isEqualTo("(");
    assertThat(tupleParam.closingParenthesis().value()).isEqualTo(")");
    assertThat(tupleParam.parameters()).extracting(Tree::getKind).containsExactly(Tree.Kind.TUPLE_PARAMETER, Tree.Kind.PARAMETER);
    assertThat(tupleParam.commas()).extracting(Token::value).containsExactly(",");
    assertThat(tupleParam.children()).hasSize(5);
    functionDef = parse("def func(x : int, y):\n  \"\"\"\n" + "This is a function docstring\n" + "\"\"\"\n  pass", treeMaker::funcDefStatement);
    assertThat(functionDef.docstring().stringElements().get(0).value()).isEqualTo("\"\"\"\n" + "This is a function docstring\n" + "\"\"\"");
    assertThat(functionDef.children()).hasSize(10);
    functionDef = parse("def __call__(self, *, manager):\n  pass", treeMaker::funcDefStatement);
    assertThat(functionDef.parameters().all()).hasSize(3);
    functionDef = parse("def __call__(*):\n  pass", treeMaker::funcDefStatement);
    assertThat(functionDef.parameters().all()).extracting(Tree::getKind).containsExactly(Kind.PARAMETER);
    functionDef = parse("def f(a, /): pass", treeMaker::funcDefStatement);
    assertThat(functionDef.parameters().all()).extracting(Tree::getKind).containsExactly(Kind.PARAMETER, Kind.PARAMETER);
    assertThat(((Parameter) functionDef.parameters().all().get(1)).starToken().value()).isEqualTo("/");
    assertThat(funcDef("def func(): ...").parameters()).isNull();
    assertThat(funcDef("def func(a): ...").parameters().all()).hasSize(1);
    assertThat(funcDef("def func(a, b): ...").parameters().all()).hasSize(2);
    assertThat(funcDef("def func(a, *args): ...").parameters().all()).hasSize(2);
    assertThat(funcDef("def func(a, **kwargs): ...").parameters().all()).hasSize(2);
    assertThat(funcDef("def func(a, *args, **kwargs): ...").parameters().all()).hasSize(3);
    assertThat(funcDef("def func(*args): ...").parameters().all()).hasSize(1);
    assertThat(funcDef("def func(**kwargs): ...").parameters().all()).hasSize(1);
    assertThat(funcDef("def func(*args, **kwargs): ...").parameters().all()).hasSize(2);
    assertThat(funcDef("def func(*args, a, **kwargs): ...").parameters().all()).hasSize(3);
    assertThat(funcDef("def func(*): ...").parameters().all()).hasSize(1);
    assertThat(funcDef("def func(*, a): ...").parameters().all()).hasSize(2);
    assertThat(funcDef("def func(a, b, *, c): ...").parameters().all()).hasSize(4);
    assertThat(funcDef("def func(a, b, /): ...").parameters().all()).hasSize(3);
    assertThat(funcDef("def func(a, b, /, c): ...").parameters().all()).hasSize(4);
    assertThat(funcDef("def func(a, b, /, c, *args): ...").parameters().all()).hasSize(5);
    assertThat(funcDef("def func(a, b, /, c, **kwargs): ...").parameters().all()).hasSize(5);
    assertThat(funcDef("def func(a, b, /, *args): ...").parameters().all()).hasSize(4);
    assertThat(funcDef("def func(a, b, /, **kwargs): ...").parameters().all()).hasSize(4);
}
Also used : Decorator(org.sonar.plugins.python.api.tree.Decorator) AstNode(com.sonar.sslr.api.AstNode) Arrays(java.util.Arrays) CompoundAssignmentStatement(org.sonar.plugins.python.api.tree.CompoundAssignmentStatement) ReprExpression(org.sonar.plugins.python.api.tree.ReprExpression) NonlocalStatement(org.sonar.plugins.python.api.tree.NonlocalStatement) IfStatement(org.sonar.plugins.python.api.tree.IfStatement) IsExpression(org.sonar.plugins.python.api.tree.IsExpression) ExceptClause(org.sonar.plugins.python.api.tree.ExceptClause) AliasedName(org.sonar.plugins.python.api.tree.AliasedName) Kind(org.sonar.plugins.python.api.tree.Tree.Kind) AssertStatement(org.sonar.plugins.python.api.tree.AssertStatement) Decorator(org.sonar.plugins.python.api.tree.Decorator) ImportFrom(org.sonar.plugins.python.api.tree.ImportFrom) Name(org.sonar.plugins.python.api.tree.Name) ReturnStatement(org.sonar.plugins.python.api.tree.ReturnStatement) Map(java.util.Map) QualifiedExpression(org.sonar.plugins.python.api.tree.QualifiedExpression) MatchStatement(org.sonar.plugins.python.api.tree.MatchStatement) Statement(org.sonar.plugins.python.api.tree.Statement) ExecStatement(org.sonar.plugins.python.api.tree.ExecStatement) TupleParameter(org.sonar.plugins.python.api.tree.TupleParameter) ContinueStatement(org.sonar.plugins.python.api.tree.ContinueStatement) SliceItem(org.sonar.plugins.python.api.tree.SliceItem) PythonTokenType(org.sonar.python.api.PythonTokenType) StringLiteral(org.sonar.plugins.python.api.tree.StringLiteral) ListLiteral(org.sonar.plugins.python.api.tree.ListLiteral) StandardCharsets(java.nio.charset.StandardCharsets) DelStatement(org.sonar.plugins.python.api.tree.DelStatement) CallExpression(org.sonar.plugins.python.api.tree.CallExpression) ExpressionList(org.sonar.plugins.python.api.tree.ExpressionList) Assertions.fail(org.assertj.core.api.Assertions.fail) EllipsisExpression(org.sonar.plugins.python.api.tree.EllipsisExpression) FormattedExpression(org.sonar.plugins.python.api.tree.FormattedExpression) Trivia(org.sonar.plugins.python.api.tree.Trivia) ForStatement(org.sonar.plugins.python.api.tree.ForStatement) RegularArgument(org.sonar.plugins.python.api.tree.RegularArgument) PythonGrammar(org.sonar.python.api.PythonGrammar) YieldStatement(org.sonar.plugins.python.api.tree.YieldStatement) WithStatement(org.sonar.plugins.python.api.tree.WithStatement) ArgList(org.sonar.plugins.python.api.tree.ArgList) UnpackingExpression(org.sonar.plugins.python.api.tree.UnpackingExpression) NoneExpression(org.sonar.plugins.python.api.tree.NoneExpression) GlobalStatement(org.sonar.plugins.python.api.tree.GlobalStatement) PythonPunctuator(org.sonar.python.api.PythonPunctuator) YieldExpression(org.sonar.plugins.python.api.tree.YieldExpression) FormatSpecifier(org.sonar.plugins.python.api.tree.FormatSpecifier) BinaryExpression(org.sonar.plugins.python.api.tree.BinaryExpression) KeyValuePair(org.sonar.plugins.python.api.tree.KeyValuePair) Files(java.nio.file.Files) IOException(java.io.IOException) Test(org.junit.Test) File(java.io.File) ImportName(org.sonar.plugins.python.api.tree.ImportName) UnaryExpression(org.sonar.plugins.python.api.tree.UnaryExpression) TryStatement(org.sonar.plugins.python.api.tree.TryStatement) SliceExpression(org.sonar.plugins.python.api.tree.SliceExpression) SubscriptionExpression(org.sonar.plugins.python.api.tree.SubscriptionExpression) Tree(org.sonar.plugins.python.api.tree.Tree) TypeAnnotation(org.sonar.plugins.python.api.tree.TypeAnnotation) DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) ImportStatement(org.sonar.plugins.python.api.tree.ImportStatement) DictCompExpression(org.sonar.plugins.python.api.tree.DictCompExpression) Assertions.assertThat(org.assertj.core.api.Assertions.assertThat) AssignmentExpression(org.sonar.plugins.python.api.tree.AssignmentExpression) FunctionDef(org.sonar.plugins.python.api.tree.FunctionDef) AssignmentStatement(org.sonar.plugins.python.api.tree.AssignmentStatement) AnnotatedAssignment(org.sonar.plugins.python.api.tree.AnnotatedAssignment) ElseClause(org.sonar.plugins.python.api.tree.ElseClause) SetLiteral(org.sonar.plugins.python.api.tree.SetLiteral) Expression(org.sonar.plugins.python.api.tree.Expression) List(java.util.List) FileInput(org.sonar.plugins.python.api.tree.FileInput) Tuple(org.sonar.plugins.python.api.tree.Tuple) ComprehensionExpression(org.sonar.plugins.python.api.tree.ComprehensionExpression) ParenthesizedExpression(org.sonar.plugins.python.api.tree.ParenthesizedExpression) PassStatement(org.sonar.plugins.python.api.tree.PassStatement) NumericLiteral(org.sonar.plugins.python.api.tree.NumericLiteral) InExpression(org.sonar.plugins.python.api.tree.InExpression) HashMap(java.util.HashMap) ExpressionStatement(org.sonar.plugins.python.api.tree.ExpressionStatement) ComprehensionFor(org.sonar.plugins.python.api.tree.ComprehensionFor) ClassDef(org.sonar.plugins.python.api.tree.ClassDef) PrintStatement(org.sonar.plugins.python.api.tree.PrintStatement) RuleTest(org.sonar.python.parser.RuleTest) RecognitionException(com.sonar.sslr.api.RecognitionException) AwaitExpression(org.sonar.plugins.python.api.tree.AwaitExpression) Parameter(org.sonar.plugins.python.api.tree.Parameter) WithItem(org.sonar.plugins.python.api.tree.WithItem) RaiseStatement(org.sonar.plugins.python.api.tree.RaiseStatement) ComprehensionIf(org.sonar.plugins.python.api.tree.ComprehensionIf) StringElement(org.sonar.plugins.python.api.tree.StringElement) GenericTokenType(com.sonar.sslr.api.GenericTokenType) ConditionalExpression(org.sonar.plugins.python.api.tree.ConditionalExpression) StatementList(org.sonar.plugins.python.api.tree.StatementList) Token(org.sonar.plugins.python.api.tree.Token) WhileStatement(org.sonar.plugins.python.api.tree.WhileStatement) LambdaExpression(org.sonar.plugins.python.api.tree.LambdaExpression) BreakStatement(org.sonar.plugins.python.api.tree.BreakStatement) TypeAnnotation(org.sonar.plugins.python.api.tree.TypeAnnotation) TupleParameter(org.sonar.plugins.python.api.tree.TupleParameter) FunctionDef(org.sonar.plugins.python.api.tree.FunctionDef) TupleParameter(org.sonar.plugins.python.api.tree.TupleParameter) Parameter(org.sonar.plugins.python.api.tree.Parameter) AstNode(com.sonar.sslr.api.AstNode) AliasedName(org.sonar.plugins.python.api.tree.AliasedName) Name(org.sonar.plugins.python.api.tree.Name) ImportName(org.sonar.plugins.python.api.tree.ImportName) Test(org.junit.Test) RuleTest(org.sonar.python.parser.RuleTest)

Example 4 with Decorator

use of org.sonar.plugins.python.api.tree.Decorator in project sonar-python by SonarSource.

the class PythonTreeMakerTest method decorators.

@Test
public void decorators() {
    FunctionDef functionDef = funcDef("@foo()\n@bar(1)\ndef func(x): pass");
    List<Decorator> decorators = functionDef.decorators();
    assertThat(decorators).hasSize(2);
    Decorator decorator = decorators.get(0);
    assertThat(decorator.name().names().get(0).name()).isEqualTo("foo");
    assertThat(TreeUtils.decoratorNameFromExpression(decorator.expression())).isEqualTo("foo");
    assertThat(decorator.expression().is(Kind.CALL_EXPR)).isTrue();
    functionDef = funcDef("@foo.bar(1)\ndef func(x): pass");
    decorators = functionDef.decorators();
    assertThat(decorators).hasSize(1);
    decorator = decorators.get(0);
    assertThat(decorator.name().names().get(0).name()).isEqualTo("foo");
    assertThat(decorator.name().names().get(1).name()).isEqualTo("bar");
    assertThat(TreeUtils.decoratorNameFromExpression(decorator.expression())).isEqualTo("foo.bar");
    assertThat(decorator.expression().is(Kind.CALL_EXPR)).isTrue();
    functionDef = funcDef("@buttons[\"hello\"].clicked.connect\ndef func(x): pass");
    decorators = functionDef.decorators();
    assertThat(decorators).hasSize(1);
    decorator = decorators.get(0);
    assertThat(decorator.name().names()).isEmpty();
    assertThat(TreeUtils.decoratorNameFromExpression(decorator.expression())).isNull();
    assertThat(decorator.expression().is(Kind.QUALIFIED_EXPR)).isTrue();
    functionDef = funcDef("@hello() or bye()\ndef func(x): pass");
    decorators = functionDef.decorators();
    assertThat(decorators).hasSize(1);
    decorator = decorators.get(0);
    assertThat(decorator.expression().getKind()).isEqualTo(Kind.OR);
    BinaryExpression binaryExpression = (BinaryExpression) decorator.expression();
    assertThat(binaryExpression.leftOperand().getKind()).isEqualTo(Kind.CALL_EXPR);
    assertThat(binaryExpression.rightOperand().getKind()).isEqualTo(Kind.CALL_EXPR);
    functionDef = funcDef("@b:=some_decorator\ndef func(x): pass");
    decorators = functionDef.decorators();
    assertThat(decorators).hasSize(1);
    decorator = decorators.get(0);
    assertThat(decorator.expression().getKind()).isEqualTo(Kind.ASSIGNMENT_EXPRESSION);
}
Also used : Decorator(org.sonar.plugins.python.api.tree.Decorator) BinaryExpression(org.sonar.plugins.python.api.tree.BinaryExpression) FunctionDef(org.sonar.plugins.python.api.tree.FunctionDef) Test(org.junit.Test) RuleTest(org.sonar.python.parser.RuleTest)

Example 5 with Decorator

use of org.sonar.plugins.python.api.tree.Decorator in project sonar-python by SonarSource.

the class PythonTreeMakerTest method classdef_statement.

@Test
public void classdef_statement() {
    setRootRule(PythonGrammar.CLASSDEF);
    AstNode astNode = p.parse("class clazz(Parent): pass");
    ClassDef classDef = treeMaker.classDefStatement(astNode);
    assertThat(classDef.name()).isNotNull();
    assertThat(classDef.docstring()).isNull();
    assertThat(classDef.classKeyword().value()).isEqualTo("class");
    assertThat(classDef.leftPar().value()).isEqualTo("(");
    assertThat(classDef.rightPar().value()).isEqualTo(")");
    assertThat(classDef.colon().value()).isEqualTo(":");
    assertThat(classDef.name().name()).isEqualTo("clazz");
    assertThat(classDef.body().statements()).hasSize(1);
    assertThat(classDef.body().statements().get(0).is(Tree.Kind.PASS_STMT)).isTrue();
    assertThat(classDef.args().is(Tree.Kind.ARG_LIST)).isTrue();
    assertThat(classDef.args().children()).hasSize(1);
    assertThat(classDef.args().arguments().get(0).is(Tree.Kind.REGULAR_ARGUMENT)).isTrue();
    assertThat(classDef.decorators()).isEmpty();
    classDef = parse("class clazz: pass", treeMaker::classDefStatement);
    assertThat(classDef.leftPar()).isNull();
    assertThat(classDef.rightPar()).isNull();
    assertThat(classDef.args()).isNull();
    classDef = parse("class clazz(): pass", treeMaker::classDefStatement);
    assertThat(classDef.leftPar().value()).isEqualTo("(");
    assertThat(classDef.rightPar().value()).isEqualTo(")");
    assertThat(classDef.args()).isNull();
    astNode = p.parse("@foo.bar\nclass clazz: pass");
    classDef = treeMaker.classDefStatement(astNode);
    assertThat(classDef.decorators()).hasSize(1);
    Decorator decorator = classDef.decorators().get(0);
    assertThat(decorator.name().names()).extracting(Name::name).containsExactly("foo", "bar");
    astNode = p.parse("class clazz:\n  def foo(): pass");
    classDef = treeMaker.classDefStatement(astNode);
    FunctionDef funcDef = (FunctionDef) classDef.body().statements().get(0);
    assertThat(funcDef.isMethodDefinition()).isTrue();
    astNode = p.parse("class clazz:\n  if True:\n    def foo(): pass");
    classDef = treeMaker.classDefStatement(astNode);
    funcDef = (FunctionDef) ((IfStatement) classDef.body().statements().get(0)).body().statements().get(0);
    assertThat(funcDef.isMethodDefinition()).isTrue();
    astNode = p.parse("class ClassWithDocstring:\n" + "\t\"\"\"This is a docstring\"\"\"\n" + "\tpass");
    classDef = treeMaker.classDefStatement(astNode);
    assertThat(classDef.docstring().stringElements()).hasSize(1);
    assertThat(classDef.docstring().stringElements().get(0).value()).isEqualTo("\"\"\"This is a docstring\"\"\"");
    assertThat(classDef.children()).hasSize(7);
}
Also used : Decorator(org.sonar.plugins.python.api.tree.Decorator) IfStatement(org.sonar.plugins.python.api.tree.IfStatement) ClassDef(org.sonar.plugins.python.api.tree.ClassDef) FunctionDef(org.sonar.plugins.python.api.tree.FunctionDef) AstNode(com.sonar.sslr.api.AstNode) Test(org.junit.Test) RuleTest(org.sonar.python.parser.RuleTest)

Aggregations

Decorator (org.sonar.plugins.python.api.tree.Decorator)8 AstNode (com.sonar.sslr.api.AstNode)4 CallExpression (org.sonar.plugins.python.api.tree.CallExpression)4 Expression (org.sonar.plugins.python.api.tree.Expression)4 FunctionDef (org.sonar.plugins.python.api.tree.FunctionDef)4 Name (org.sonar.plugins.python.api.tree.Name)4 Arrays (java.util.Arrays)3 List (java.util.List)3 Test (org.junit.Test)3 AliasedName (org.sonar.plugins.python.api.tree.AliasedName)3 ArgList (org.sonar.plugins.python.api.tree.ArgList)3 ClassDef (org.sonar.plugins.python.api.tree.ClassDef)3 ImportName (org.sonar.plugins.python.api.tree.ImportName)3 ListLiteral (org.sonar.plugins.python.api.tree.ListLiteral)3 QualifiedExpression (org.sonar.plugins.python.api.tree.QualifiedExpression)3 RegularArgument (org.sonar.plugins.python.api.tree.RegularArgument)3 StatementList (org.sonar.plugins.python.api.tree.StatementList)3 StringLiteral (org.sonar.plugins.python.api.tree.StringLiteral)3 SubscriptionExpression (org.sonar.plugins.python.api.tree.SubscriptionExpression)3 Token (org.sonar.plugins.python.api.tree.Token)3