Search in sources :

Example 1 with DictionaryLiteral

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

the class DuplicateArgumentCheck method extractKeysFromDictionary.

private static Set<String> extractKeysFromDictionary(UnpackingExpression unpackingExpression) {
    if (unpackingExpression.expression().is(Tree.Kind.DICTIONARY_LITERAL)) {
        return keysInDictionaryLiteral((DictionaryLiteral) unpackingExpression.expression());
    } else if (unpackingExpression.expression().is(Tree.Kind.CALL_EXPR)) {
        return keysFromDictionaryCreation((CallExpression) unpackingExpression.expression());
    } else if (unpackingExpression.expression().is(Tree.Kind.NAME)) {
        Name name = (Name) unpackingExpression.expression();
        Symbol symbol = name.symbol();
        if (symbol == null || symbol.usages().stream().anyMatch(u -> TreeUtils.firstAncestorOfKind(u.tree(), Tree.Kind.DEL_STMT) != null)) {
            return Collections.emptySet();
        }
        Expression expression = Expressions.singleAssignedValue(name);
        if (expression != null && expression.is(Tree.Kind.CALL_EXPR)) {
            return keysFromDictionaryCreation((CallExpression) expression);
        }
        return expression != null && expression.is(Tree.Kind.DICTIONARY_LITERAL) ? keysInDictionaryLiteral((DictionaryLiteral) expression) : Collections.emptySet();
    }
    return Collections.emptySet();
}
Also used : PythonFile(org.sonar.plugins.python.api.PythonFile) RegularArgument(org.sonar.plugins.python.api.tree.RegularArgument) PythonSubscriptionCheck(org.sonar.plugins.python.api.PythonSubscriptionCheck) HashMap(java.util.HashMap) ArrayList(java.util.ArrayList) TreeUtils(org.sonar.python.tree.TreeUtils) UnpackingExpression(org.sonar.plugins.python.api.tree.UnpackingExpression) Name(org.sonar.plugins.python.api.tree.Name) Map(java.util.Map) QualifiedExpression(org.sonar.plugins.python.api.tree.QualifiedExpression) TokenLocation(org.sonar.python.TokenLocation) PythonPunctuator(org.sonar.python.api.PythonPunctuator) Expression(org.sonar.plugins.python.api.tree.Expression) Path(java.nio.file.Path) Nullable(javax.annotation.Nullable) SymbolUtils(org.sonar.python.semantic.SymbolUtils) KeyValuePair(org.sonar.plugins.python.api.tree.KeyValuePair) SymbolUtils.pathOf(org.sonar.python.semantic.SymbolUtils.pathOf) Set(java.util.Set) StringLiteral(org.sonar.plugins.python.api.tree.StringLiteral) SubscriptionContext(org.sonar.plugins.python.api.SubscriptionContext) ClassSymbol(org.sonar.plugins.python.api.symbols.ClassSymbol) Collectors(java.util.stream.Collectors) FunctionSymbolImpl(org.sonar.python.semantic.FunctionSymbolImpl) List(java.util.List) CallExpression(org.sonar.plugins.python.api.tree.CallExpression) Argument(org.sonar.plugins.python.api.tree.Argument) Optional(java.util.Optional) Tree(org.sonar.plugins.python.api.tree.Tree) Rule(org.sonar.check.Rule) LocationInFile(org.sonar.plugins.python.api.LocationInFile) DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) Collections(java.util.Collections) FunctionSymbol(org.sonar.plugins.python.api.symbols.FunctionSymbol) Symbol(org.sonar.plugins.python.api.symbols.Symbol) DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) UnpackingExpression(org.sonar.plugins.python.api.tree.UnpackingExpression) QualifiedExpression(org.sonar.plugins.python.api.tree.QualifiedExpression) Expression(org.sonar.plugins.python.api.tree.Expression) CallExpression(org.sonar.plugins.python.api.tree.CallExpression) ClassSymbol(org.sonar.plugins.python.api.symbols.ClassSymbol) FunctionSymbol(org.sonar.plugins.python.api.symbols.FunctionSymbol) Symbol(org.sonar.plugins.python.api.symbols.Symbol) CallExpression(org.sonar.plugins.python.api.tree.CallExpression) Name(org.sonar.plugins.python.api.tree.Name)

Example 2 with DictionaryLiteral

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

the class StringFormatCorrectnessCheck method checkPrintfStyle.

@Override
protected void checkPrintfStyle(SubscriptionContext ctx, BinaryExpression modulo, StringLiteral literal) {
    Optional<StringFormat> formatOptional = StringFormat.createFromPrintfStyle(IGNORE_SYNTAX_ERRORS, literal.trimmedQuotesValue());
    if (!formatOptional.isPresent()) {
        // The string format contains invalid syntax.
        return;
    }
    StringFormat format = formatOptional.get();
    if (!isInterestingDictLiteral(modulo.rightOperand())) {
        return;
    }
    DictionaryLiteral dict = (DictionaryLiteral) modulo.rightOperand();
    List<String> allNames = format.replacementFields().stream().filter(StringFormat.ReplacementField::isNamed).map(StringFormat.ReplacementField::name).collect(Collectors.toList());
    dict.elements().stream().map(KeyValuePair.class::cast).map(kv -> (StringLiteral) kv.key()).filter(key -> !allNames.contains(key.trimmedQuotesValue())).forEach(key -> ctx.addIssue(key, "Remove this unused argument or add a replacement field."));
}
Also used : DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) IntStream(java.util.stream.IntStream) Arrays(java.util.Arrays) BinaryExpression(org.sonar.plugins.python.api.tree.BinaryExpression) KeyValuePair(org.sonar.plugins.python.api.tree.KeyValuePair) RegularArgument(org.sonar.plugins.python.api.tree.RegularArgument) Set(java.util.Set) StringLiteral(org.sonar.plugins.python.api.tree.StringLiteral) Token(org.sonar.plugins.python.api.tree.Token) SubscriptionContext(org.sonar.plugins.python.api.SubscriptionContext) Collectors(java.util.stream.Collectors) HashSet(java.util.HashSet) List(java.util.List) CallExpression(org.sonar.plugins.python.api.tree.CallExpression) Name(org.sonar.plugins.python.api.tree.Name) QualifiedExpression(org.sonar.plugins.python.api.tree.QualifiedExpression) Optional(java.util.Optional) Expression(org.sonar.plugins.python.api.tree.Expression) Tree(org.sonar.plugins.python.api.tree.Tree) Rule(org.sonar.check.Rule) DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) Symbol(org.sonar.plugins.python.api.symbols.Symbol) DictionaryLiteralElement(org.sonar.plugins.python.api.tree.DictionaryLiteralElement)

Example 3 with DictionaryLiteral

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

the class DictionaryDuplicateKeyCheck method initialize.

@Override
public void initialize(Context context) {
    context.registerSyntaxNodeConsumer(Tree.Kind.DICTIONARY_LITERAL, ctx -> {
        DictionaryLiteral dictionaryLiteral = (DictionaryLiteral) ctx.syntaxNode();
        Set<Integer> issueIndexes = new HashSet<>();
        if (dictionaryLiteral.elements().size() > SIZE_THRESHOLD) {
            return;
        }
        for (int i = 0; i < dictionaryLiteral.elements().size(); i++) {
            if (!dictionaryLiteral.elements().get(i).is(Tree.Kind.KEY_VALUE_PAIR) || issueIndexes.contains(i)) {
                continue;
            }
            Expression key = ((KeyValuePair) dictionaryLiteral.elements().get(i)).key();
            List<Tree> duplicateKeys = findIdenticalKeys(i, dictionaryLiteral.elements(), issueIndexes);
            if (!duplicateKeys.isEmpty()) {
                PreciseIssue issue = ctx.addIssue(key, "Change or remove duplicates of this key.");
                duplicateKeys.forEach(d -> issue.secondary(d, "Duplicate key"));
            }
        }
    });
}
Also used : DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) KeyValuePair(org.sonar.plugins.python.api.tree.KeyValuePair) Expression(org.sonar.plugins.python.api.tree.Expression) Tree(org.sonar.plugins.python.api.tree.Tree) HashSet(java.util.HashSet)

Example 4 with DictionaryLiteral

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

the class PythonTreeMakerTest method dictionary_literal.

@Test
public void dictionary_literal() {
    setRootRule(PythonGrammar.ATOM);
    DictionaryLiteral tree = (DictionaryLiteral) parse("{'key': 'value'}", treeMaker::expression);
    assertThat(tree.firstToken().value()).isEqualTo("{");
    assertThat(tree.lastToken().value()).isEqualTo("}");
    assertThat(tree.getKind()).isEqualTo(Tree.Kind.DICTIONARY_LITERAL);
    assertThat(tree.elements()).hasSize(1);
    KeyValuePair keyValuePair = (KeyValuePair) tree.elements().iterator().next();
    assertThat(keyValuePair.getKind()).isEqualTo(Tree.Kind.KEY_VALUE_PAIR);
    assertThat(keyValuePair.key().getKind()).isEqualTo(Tree.Kind.STRING_LITERAL);
    assertThat(keyValuePair.colon().value()).isEqualTo(":");
    assertThat(keyValuePair.value().getKind()).isEqualTo(Tree.Kind.STRING_LITERAL);
    assertThat(tree.children()).hasSize(3).containsExactly(tree.lCurlyBrace(), tree.elements().get(0), tree.rCurlyBrace());
    tree = (DictionaryLiteral) parse("{'key': 'value', 'key2': 'value2'}", treeMaker::expression);
    assertThat(tree.elements()).hasSize(2);
    assertThat(tree.children()).hasSize(5).containsExactly(tree.lCurlyBrace(), tree.elements().get(0), tree.commas().get(0), tree.elements().get(1), tree.rCurlyBrace());
    tree = (DictionaryLiteral) parse("{** var}", treeMaker::expression);
    assertThat(tree.elements()).hasSize(1);
    UnpackingExpression dictUnpacking = (UnpackingExpression) tree.elements().iterator().next();
    assertThat(dictUnpacking.expression().getKind()).isEqualTo(Tree.Kind.NAME);
    assertThat(dictUnpacking.starToken().value()).isEqualTo("**");
    tree = (DictionaryLiteral) parse("{** var, key: value}", treeMaker::expression);
    assertThat(tree.elements()).hasSize(2);
}
Also used : DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) UnpackingExpression(org.sonar.plugins.python.api.tree.UnpackingExpression) KeyValuePair(org.sonar.plugins.python.api.tree.KeyValuePair) Test(org.junit.Test) RuleTest(org.sonar.python.parser.RuleTest)

Example 5 with DictionaryLiteral

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

the class HttpOnlyCookieCheck method dictionarySessionCookieHttponlyCheck.

private void dictionarySessionCookieHttponlyCheck(SubscriptionContext ctx) {
    DictionaryLiteral dict = (DictionaryLiteral) ctx.syntaxNode();
    Optional<Expression> falsySetting = searchForFalsySessionCookieHttponlyInDictionary(dict);
    falsySetting.ifPresent(expression -> ctx.addIssue(expression, message()));
}
Also used : DictionaryLiteral(org.sonar.plugins.python.api.tree.DictionaryLiteral) CallExpression(org.sonar.plugins.python.api.tree.CallExpression) SubscriptionExpression(org.sonar.plugins.python.api.tree.SubscriptionExpression) Expression(org.sonar.plugins.python.api.tree.Expression)

Aggregations

DictionaryLiteral (org.sonar.plugins.python.api.tree.DictionaryLiteral)6 Expression (org.sonar.plugins.python.api.tree.Expression)5 CallExpression (org.sonar.plugins.python.api.tree.CallExpression)4 KeyValuePair (org.sonar.plugins.python.api.tree.KeyValuePair)4 Tree (org.sonar.plugins.python.api.tree.Tree)3 UnpackingExpression (org.sonar.plugins.python.api.tree.UnpackingExpression)3 HashSet (java.util.HashSet)2 List (java.util.List)2 Optional (java.util.Optional)2 Set (java.util.Set)2 Collectors (java.util.stream.Collectors)2 Rule (org.sonar.check.Rule)2 SubscriptionContext (org.sonar.plugins.python.api.SubscriptionContext)2 Symbol (org.sonar.plugins.python.api.symbols.Symbol)2 Name (org.sonar.plugins.python.api.tree.Name)2 QualifiedExpression (org.sonar.plugins.python.api.tree.QualifiedExpression)2 RegularArgument (org.sonar.plugins.python.api.tree.RegularArgument)2 StringLiteral (org.sonar.plugins.python.api.tree.StringLiteral)2 Path (java.nio.file.Path)1 ArrayList (java.util.ArrayList)1