Search in sources :

Example 16 with TypeEvalContext

use of com.jetbrains.python.psi.types.TypeEvalContext in project intellij-community by JetBrains.

the class PyParameterInfoHandler method updateUI.

@Override
public void updateUI(@NotNull Pair<PyCallExpression, PyMarkedCallee> callAndCallee, @NotNull ParameterInfoUIContext context) {
    final PyCallExpression callExpression = callAndCallee.getFirst();
    PyPsiUtils.assertValid(callExpression);
    final TypeEvalContext typeEvalContext = TypeEvalContext.userInitiated(callExpression.getProject(), callExpression.getContainingFile());
    final PyCallExpression.PyArgumentsMapping mapping = PyCallExpressionHelper.mapArguments(callExpression, callAndCallee.getSecond(), typeEvalContext);
    final PyMarkedCallee markedCallee = mapping.getMarkedCallee();
    if (markedCallee == null)
        return;
    final List<PyParameter> parameters = PyUtil.getParameters(markedCallee.getCallable(), typeEvalContext);
    final List<PyNamedParameter> namedParameters = new ArrayList<>(parameters.size());
    // param -> hint index. indexes are not contiguous, because some hints are parentheses.
    final Map<PyNamedParameter, Integer> parameterToIndex = new HashMap<>();
    // formatting of hints: hint index -> flags. this includes flags for parens.
    final Map<Integer, EnumSet<ParameterInfoUIContextEx.Flag>> hintFlags = new HashMap<>();
    final List<String> hintsList = buildParameterListHint(parameters, namedParameters, parameterToIndex, hintFlags, typeEvalContext);
    // in Python mode, we get an offset here, not an index!
    final int currentParamOffset = context.getCurrentParameterIndex();
    // gray out enough first parameters as implicit (self, cls, ...)
    for (int i = 0; i < markedCallee.getImplicitOffset(); i++) {
        // show but mark as absent
        hintFlags.get(parameterToIndex.get(namedParameters.get(i))).add(ParameterInfoUIContextEx.Flag.DISABLE);
    }
    final List<PyExpression> flattenedArguments = PyUtil.flattenedParensAndLists(callExpression.getArguments());
    final int lastParamIndex = collectHighlights(mapping, parameters, parameterToIndex, hintFlags, flattenedArguments, currentParamOffset);
    highlightNext(markedCallee, parameters, namedParameters, parameterToIndex, hintFlags, flattenedArguments.isEmpty(), lastParamIndex);
    String[] hints = ArrayUtil.toStringArray(hintsList);
    if (context instanceof ParameterInfoUIContextEx) {
        final ParameterInfoUIContextEx pic = (ParameterInfoUIContextEx) context;
        EnumSet[] flags = new EnumSet[hintFlags.size()];
        for (int i = 0; i < flags.length; i++) flags[i] = hintFlags.get(i);
        if (hints.length < 1) {
            hints = new String[] { NO_PARAMS_MSG };
            flags = new EnumSet[] { EnumSet.of(ParameterInfoUIContextEx.Flag.DISABLE) };
        }
        //noinspection unchecked
        pic.setupUIComponentPresentation(hints, flags, context.getDefaultParameterColor());
    } else {
        // fallback, no highlight
        final StringBuilder signatureBuilder = new StringBuilder();
        if (hints.length > 1) {
            for (String s : hints) signatureBuilder.append(s);
        } else {
            signatureBuilder.append(XmlStringUtil.escapeString(NO_PARAMS_MSG));
        }
        context.setupUIComponentPresentation(signatureBuilder.toString(), -1, 0, false, false, false, context.getDefaultParameterColor());
    }
}
Also used : TypeEvalContext(com.jetbrains.python.psi.types.TypeEvalContext) PyMarkedCallee(com.jetbrains.python.psi.PyCallExpression.PyMarkedCallee)

Example 17 with TypeEvalContext

use of com.jetbrains.python.psi.types.TypeEvalContext in project intellij-community by JetBrains.

the class PyReferenceImpl method getResultsFromProcessor.

protected List<RatedResolveResult> getResultsFromProcessor(@NotNull String referencedName, @NotNull PyResolveProcessor processor, @Nullable PsiElement realContext, @Nullable PsiElement resolveRoof) {
    boolean unreachableLocalDeclaration = false;
    boolean resolveInParentScope = false;
    final ResolveResultList resultList = new ResolveResultList();
    final ScopeOwner referenceOwner = ScopeUtil.getScopeOwner(realContext);
    final TypeEvalContext typeEvalContext = myContext.getTypeEvalContext();
    ScopeOwner resolvedOwner = processor.getOwner();
    if (resolvedOwner != null && !processor.getResults().isEmpty()) {
        final Collection<PsiElement> resolvedElements = processor.getElements();
        final Scope resolvedScope = ControlFlowCache.getScope(resolvedOwner);
        if (!resolvedScope.isGlobal(referencedName)) {
            if (resolvedOwner == referenceOwner) {
                final List<Instruction> instructions = PyDefUseUtil.getLatestDefs(resolvedOwner, referencedName, realContext, false, true);
                // TODO: Use the results from the processor as a cache for resolving to latest defs
                final ResolveResultList latestDefs = resolveToLatestDefs(instructions, realContext, referencedName, typeEvalContext);
                if (!latestDefs.isEmpty()) {
                    return latestDefs;
                } else if (resolvedOwner instanceof PyClass || instructions.isEmpty() && allInOwnScopeComprehensions(resolvedElements)) {
                    resolveInParentScope = true;
                } else if (PyiUtil.isInsideStubAnnotation(myElement)) {
                    for (PsiElement element : resolvedElements) {
                        resultList.poke(element, getRate(element, typeEvalContext));
                    }
                    return resultList;
                } else {
                    unreachableLocalDeclaration = true;
                }
            } else if (referenceOwner != null) {
                final Scope referenceScope = ControlFlowCache.getScope(referenceOwner);
                if (referenceScope.containsDeclaration(referencedName)) {
                    unreachableLocalDeclaration = true;
                }
            }
        }
    }
    if (!unreachableLocalDeclaration) {
        if (resolveInParentScope) {
            processor = new PyResolveProcessor(referencedName);
            resolvedOwner = ScopeUtil.getScopeOwner(resolvedOwner);
            if (resolvedOwner != null) {
                PyResolveUtil.scopeCrawlUp(processor, resolvedOwner, referencedName, resolveRoof);
            }
        }
        for (Map.Entry<PsiElement, PyImportedNameDefiner> entry : processor.getResults().entrySet()) {
            final PsiElement resolved = entry.getKey();
            final PyImportedNameDefiner definer = entry.getValue();
            if (resolved != null) {
                if (typeEvalContext.maySwitchToAST(resolved) && isInnerComprehension(realContext, resolved)) {
                    continue;
                }
                if (skipClassForwardReferences(referenceOwner, resolved)) {
                    continue;
                }
                if (definer == null) {
                    resultList.poke(resolved, getRate(resolved, typeEvalContext));
                } else {
                    resultList.poke(definer, getRate(definer, typeEvalContext));
                    resultList.add(new ImportedResolveResult(resolved, getRate(resolved, typeEvalContext), definer));
                }
            } else if (definer != null) {
                resultList.add(new ImportedResolveResult(null, RatedResolveResult.RATE_LOW, definer));
            }
        }
        if (!resultList.isEmpty()) {
            return resultList;
        }
    }
    return resolveByReferenceResolveProviders();
}
Also used : Instruction(com.intellij.codeInsight.controlflow.Instruction) TypeEvalContext(com.jetbrains.python.psi.types.TypeEvalContext) ScopeOwner(com.jetbrains.python.codeInsight.controlflow.ScopeOwner) Scope(com.jetbrains.python.codeInsight.dataflow.scope.Scope)

Example 18 with TypeEvalContext

use of com.jetbrains.python.psi.types.TypeEvalContext in project intellij-community by JetBrains.

the class PyOperatorReference method resolveMember.

@NotNull
private List<RatedResolveResult> resolveMember(@Nullable PyExpression object, @Nullable String name) {
    final ArrayList<RatedResolveResult> results = new ArrayList<>();
    if (object != null && name != null) {
        final TypeEvalContext typeEvalContext = myContext.getTypeEvalContext();
        PyType type = typeEvalContext.getType(object);
        typeEvalContext.trace("Side text is %s, type is %s", object.getText(), type);
        if (type instanceof PyClassLikeType) {
            if (((PyClassLikeType) type).isDefinition()) {
                type = ((PyClassLikeType) type).getMetaClassType(typeEvalContext, true);
            }
        }
        if (type != null) {
            List<? extends RatedResolveResult> res = type.resolveMember(name, object, AccessDirection.of(myElement), myContext);
            if (res != null && res.size() > 0) {
                results.addAll(res);
            } else if (typeEvalContext.tracing()) {
                VirtualFile vFile = null;
                if (type instanceof PyClassType) {
                    final PyClass pyClass = ((PyClassType) type).getPyClass();
                    vFile = pyClass.getContainingFile().getVirtualFile();
                }
                type.resolveMember(name, object, AccessDirection.of(myElement), myContext);
                typeEvalContext.trace("Could not resolve member %s in type %s from file %s", name, type, vFile);
            }
        }
    }
    return results;
}
Also used : VirtualFile(com.intellij.openapi.vfs.VirtualFile) PyClassType(com.jetbrains.python.psi.types.PyClassType) PyType(com.jetbrains.python.psi.types.PyType) ArrayList(java.util.ArrayList) PyClassLikeType(com.jetbrains.python.psi.types.PyClassLikeType) RatedResolveResult(com.jetbrains.python.psi.resolve.RatedResolveResult) TypeEvalContext(com.jetbrains.python.psi.types.TypeEvalContext) NotNull(org.jetbrains.annotations.NotNull)

Example 19 with TypeEvalContext

use of com.jetbrains.python.psi.types.TypeEvalContext in project intellij-community by JetBrains.

the class PyTypeTest method testReturnTypeOfTypeForInstance.

// PY-7058
public void testReturnTypeOfTypeForInstance() {
    PyExpression expr = parseExpr("class C(object):\n" + "    pass\n" + "\n" + "x = C()\n" + "expr = type(x)\n");
    assertNotNull(expr);
    for (TypeEvalContext context : getTypeEvalContexts(expr)) {
        PyType type = context.getType(expr);
        assertInstanceOf(type, PyClassType.class);
        assertTrue("Got instance type instead of class type", ((PyClassType) type).isDefinition());
    }
}
Also used : PyType(com.jetbrains.python.psi.types.PyType) PyExpression(com.jetbrains.python.psi.PyExpression) TypeEvalContext(com.jetbrains.python.psi.types.TypeEvalContext)

Example 20 with TypeEvalContext

use of com.jetbrains.python.psi.types.TypeEvalContext in project intellij-community by JetBrains.

the class PyStaticCallHierarchyUtil method createFindUsageHandler.

/**
   * @see {@link com.jetbrains.python.findUsages.PyFindUsagesHandlerFactory#createFindUsagesHandler(com.intellij.psi.PsiElement, boolean) createFindUsagesHandler}
   */
@Nullable
private static FindUsagesHandler createFindUsageHandler(@NotNull final PsiElement element) {
    if (element instanceof PyFunction) {
        final TypeEvalContext context = TypeEvalContext.userInitiated(element.getProject(), null);
        final Collection<PsiElement> superMethods = PySuperMethodsSearch.search((PyFunction) element, true, context).findAll();
        if (superMethods.size() > 0) {
            final PsiElement next = superMethods.iterator().next();
            if (next instanceof PyFunction && !isInObject((PyFunction) next)) {
                List<PsiElement> allMethods = Lists.newArrayList();
                allMethods.add(element);
                allMethods.addAll(superMethods);
                return new PyFunctionFindUsagesHandler(element, allMethods);
            }
        }
        return new PyFunctionFindUsagesHandler(element);
    }
    if (element instanceof PyClass) {
        return new PyClassFindUsagesHandler((PyClass) element);
    }
    return null;
}
Also used : PyFunctionFindUsagesHandler(com.jetbrains.python.findUsages.PyFunctionFindUsagesHandler) PyClassFindUsagesHandler(com.jetbrains.python.findUsages.PyClassFindUsagesHandler) TypeEvalContext(com.jetbrains.python.psi.types.TypeEvalContext) PsiElement(com.intellij.psi.PsiElement) Nullable(org.jetbrains.annotations.Nullable)

Aggregations

TypeEvalContext (com.jetbrains.python.psi.types.TypeEvalContext)44 PyType (com.jetbrains.python.psi.types.PyType)15 PsiElement (com.intellij.psi.PsiElement)13 NotNull (org.jetbrains.annotations.NotNull)10 Nullable (org.jetbrains.annotations.Nullable)8 PyResolveContext (com.jetbrains.python.psi.resolve.PyResolveContext)6 PyClassLikeType (com.jetbrains.python.psi.types.PyClassLikeType)5 ArrayList (java.util.ArrayList)5 ScopeOwner (com.jetbrains.python.codeInsight.controlflow.ScopeOwner)4 com.jetbrains.python.psi (com.jetbrains.python.psi)4 TextRange (com.intellij.openapi.util.TextRange)3 PsiTreeUtil (com.intellij.psi.util.PsiTreeUtil)3 XmlStringUtil (com.intellij.xml.util.XmlStringUtil)3 PyNames (com.jetbrains.python.PyNames)3 PyFunction (com.jetbrains.python.psi.PyFunction)3 PyClassType (com.jetbrains.python.psi.types.PyClassType)3 Lists (com.google.common.collect.Lists)2 Instruction (com.intellij.codeInsight.controlflow.Instruction)2 LookupElement (com.intellij.codeInsight.lookup.LookupElement)2 ASTNode (com.intellij.lang.ASTNode)2