From fc33caa6ca7c4d000a9672b44419d93c5884d535 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 11:16:15 +0100 Subject: [PATCH 01/20] EA-34823 - RE: PyBaseElementImpl.childToPsiNotNull --- .../jetbrains/python/psi/impl/PyLambdaExpressionImpl.java | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/psi/impl/PyLambdaExpressionImpl.java b/python/src/com/jetbrains/python/psi/impl/PyLambdaExpressionImpl.java index 4e396a18a584..b8aaf4536dae 100644 --- a/python/src/com/jetbrains/python/psi/impl/PyLambdaExpressionImpl.java +++ b/python/src/com/jetbrains/python/psi/impl/PyLambdaExpressionImpl.java @@ -28,7 +28,12 @@ public class PyLambdaExpressionImpl extends PyElementImpl implements PyLambdaExp @NotNull public PyParameterList getParameterList() { - return childToPsiNotNull(PyElementTypes.PARAMETER_LIST_SET, 0); + final PyElement child = childToPsi(PyElementTypes.PARAMETER_LIST_SET, 0); + if (child == null) { + throw new RuntimeException("parameter list must not be null; text=" + getText()); + } + //noinspection unchecked + return (PyParameterList)child; } @Nullable From 14a7c8beab0bf54a4107c0e78e19cc7baa756562 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 11:36:53 +0100 Subject: [PATCH 02/20] EA-34432 - NPE: QualifiedNameResolver.fromElement --- .../python/psi/resolve/QualifiedNameResolver.java | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/python/src/com/jetbrains/python/psi/resolve/QualifiedNameResolver.java b/python/src/com/jetbrains/python/psi/resolve/QualifiedNameResolver.java index 62300efdfc5e..97eb8fbb64bf 100644 --- a/python/src/com/jetbrains/python/psi/resolve/QualifiedNameResolver.java +++ b/python/src/com/jetbrains/python/psi/resolve/QualifiedNameResolver.java @@ -11,6 +11,7 @@ import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; import com.jetbrains.django.facet.DjangoFacetType; import com.jetbrains.python.console.PydevConsoleRunner; +import com.jetbrains.python.psi.PyUtil; import com.jetbrains.python.psi.impl.PyBuiltinCache; import com.jetbrains.python.psi.impl.PyQualifiedName; import com.jetbrains.python.sdk.PythonSdkType; @@ -49,9 +50,14 @@ public class QualifiedNameResolver implements RootVisitor { } public QualifiedNameResolver fromElement(@NotNull PsiElement foothold) { - myFootholdFile = foothold.getContainingFile().getOriginalFile(); + if (foothold instanceof PsiDirectory) { + myFootholdFile = (PsiFile)PyUtil.turnDirIntoInit(foothold); + } + else { + myFootholdFile = foothold.getContainingFile().getOriginalFile(); + } myPsiManager = foothold.getManager(); - setModule(ModuleUtil.findModuleForPsiElement(myFootholdFile)); + setModule(ModuleUtil.findModuleForPsiElement(foothold)); if (PydevConsoleRunner.isInPydevConsole(foothold)) { withAllModules(); } From 924eea6de03fba6811352cafc72ef21a9456cddf Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 11:58:45 +0100 Subject: [PATCH 03/20] diagnostics for EA-30244 - assert: StatementParsing.parseSimpleStatement --- .../src/com/jetbrains/python/parsing/StatementParsing.java | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/parsing/StatementParsing.java b/python/src/com/jetbrains/python/parsing/StatementParsing.java index 682fe6437c29..a7018c9d87c4 100644 --- a/python/src/com/jetbrains/python/parsing/StatementParsing.java +++ b/python/src/com/jetbrains/python/parsing/StatementParsing.java @@ -204,8 +204,13 @@ public class StatementParsing extends Parsing implements ITokenTypeRemapper { } if (builder.getTokenType() == PyTokenTypes.EQ) { maybeExprMarker.rollbackTo(); + final int rollbackOffset = builder.getCurrentOffset(); getExpressionParser().parseExpression(false, true); - LOG.assertTrue(builder.getTokenType() == PyTokenTypes.EQ); + final int offsetAfterExpr = builder.getCurrentOffset(); + if (builder.getTokenType() != PyTokenTypes.EQ) { + LOG.error("'=' after rollback expected", builder.getTokenType() + "; " + + builder.getOriginalText().subSequence(rollbackOffset, offsetAfterExpr).toString()); + } builder.advanceLexer(); } else { From 2c8cd608c89f810c28563827012603921839bc40 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 12:04:20 +0100 Subject: [PATCH 04/20] EA-31486 - assert: PyParameterInfoHandler.updateUI --- .../com/jetbrains/python/PyParameterInfoHandler.java | 3 +-- .../com/jetbrains/python/psi/PyCallExpression.java | 12 +++--------- 2 files changed, 4 insertions(+), 11 deletions(-) diff --git a/python/src/com/jetbrains/python/PyParameterInfoHandler.java b/python/src/com/jetbrains/python/PyParameterInfoHandler.java index 571853ed0a38..3a89d9d12b37 100644 --- a/python/src/com/jetbrains/python/PyParameterInfoHandler.java +++ b/python/src/com/jetbrains/python/PyParameterInfoHandler.java @@ -110,9 +110,8 @@ public class PyParameterInfoHandler implements ParameterInfoHandler raw_params = Arrays.asList(callable.getParameterList().getParameters()); final List n_param_list = new ArrayList(raw_params.size()); diff --git a/python/src/com/jetbrains/python/psi/PyCallExpression.java b/python/src/com/jetbrains/python/psi/PyCallExpression.java index 775b9e7ee06a..e06a74f61b3b 100644 --- a/python/src/com/jetbrains/python/psi/PyCallExpression.java +++ b/python/src/com/jetbrains/python/psi/PyCallExpression.java @@ -95,7 +95,7 @@ public interface PyCallExpression extends PyExpression { * Couples function with a flag describing the way it is called. */ class PyMarkedCallee { - Callable myCallable; + @NotNull final Callable myCallable; PyFunction.Modifier myModifier; int myImplicitOffset; boolean myImplicitlyResolved; @@ -104,7 +104,7 @@ public interface PyCallExpression extends PyExpression { * Method-oriented constructor. * * @param function the method (or any other callable, but why bother then). - * @param flags result of decorators or wrapping. + * @param modifier classmethod or staticmethod modifier * @param offset implicit argument offset; parameters up to this are implicitly filled in the call. * @param implicitlyResolved value for {@link #isImplicitlyResolved()} */ @@ -115,13 +115,7 @@ public interface PyCallExpression extends PyExpression { myImplicitlyResolved = implicitlyResolved; } - public PyMarkedCallee(Callable callable, boolean implicitlyResolved) { - myCallable = callable; - myModifier = null; - myImplicitOffset = 0; - myImplicitlyResolved = implicitlyResolved; - } - + @NotNull public Callable getCallable() { return myCallable; } From 98c83da736ac01e0980fc603820f9669452c5c44 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 13:20:37 +0100 Subject: [PATCH 05/20] diagnostics for EA-34808 - assert: PyStringLiteralLexer.getTokenEnd --- .../src/com/jetbrains/python/lexer/PyStringLiteralLexer.java | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/lexer/PyStringLiteralLexer.java b/python/src/com/jetbrains/python/lexer/PyStringLiteralLexer.java index bdfdb1e6fb78..dc9262c6f54c 100644 --- a/python/src/com/jetbrains/python/lexer/PyStringLiteralLexer.java +++ b/python/src/com/jetbrains/python/lexer/PyStringLiteralLexer.java @@ -173,7 +173,9 @@ public class PyStringLiteralLexer extends LexerBase { } public int getTokenEnd() { - assert myStart < myEnd || (myStart == myEnd && myEnd == myBufferEnd); + if (!(myStart < myEnd || (myStart == myEnd && myEnd == myBufferEnd))) { + LOG.error("myStart=" + myStart + " myEnd="+ myEnd + " myBufferEnd=" + myBufferEnd + " text=" + myBuffer.subSequence(myStart, myBufferEnd)); + } return myEnd; } From abacb9632965a669acb93e49fe392988ac71cc34 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 15:23:54 +0100 Subject: [PATCH 06/20] explicit api to find parameter by name --- .../jetbrains/python/psi/PyParameterList.java | 4 ++++ .../psi/impl/PyKeywordArgumentReference.java | 8 ++++++-- .../python/psi/impl/PyParameterListImpl.java | 16 ++++++++++++++++ .../python/validation/HighlightingAnnotator.java | 5 +++-- 4 files changed, 29 insertions(+), 4 deletions(-) diff --git a/python/src/com/jetbrains/python/psi/PyParameterList.java b/python/src/com/jetbrains/python/psi/PyParameterList.java index 77a2e802e6c1..252875cc8fa4 100644 --- a/python/src/com/jetbrains/python/psi/PyParameterList.java +++ b/python/src/com/jetbrains/python/psi/PyParameterList.java @@ -18,6 +18,10 @@ public interface PyParameterList extends PyElement, StubBasedPsiElement()); if (calleeFunction != null) { - final PsiElement result = calleeFunction.getParameterList().getElementNamed(myElement.getKeyword()); + final PsiElement result = calleeFunction.getParameterList().findParameterByName(keyword); if (result != null) { resultList.add(new PsiElementResolveResult(result)); } diff --git a/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java b/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java index f7bb12ab38f2..35782df9a30e 100644 --- a/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java +++ b/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java @@ -1,6 +1,7 @@ package com.jetbrains.python.psi.impl; import com.intellij.lang.ASTNode; +import com.intellij.openapi.util.Ref; import com.intellij.psi.PsiElement; import com.intellij.psi.stubs.IStubElementType; import com.jetbrains.python.PyElementTypes; @@ -161,6 +162,21 @@ public class PyParameterListImpl extends PyBaseElementImpl return IterHelper.findName(iterateNames(), the_name); } + @Override + @Nullable + public PyNamedParameter findParameterByName(@NotNull final String name) { + final Ref result = new Ref(); + ParamHelper.walkDownParamArray(getParameters(), new ParamHelper.ParamVisitor() { + @Override + public void visitNamedParameter(PyNamedParameter param, boolean first, boolean last) { + if (name.equals(param.getName())) { + result.set(param); + } + } + }); + return result.get(); + } + public boolean mustResolveOutside() { return true; } diff --git a/python/src/com/jetbrains/python/validation/HighlightingAnnotator.java b/python/src/com/jetbrains/python/validation/HighlightingAnnotator.java index 16009aad9984..4cdc1b0c15c3 100644 --- a/python/src/com/jetbrains/python/validation/HighlightingAnnotator.java +++ b/python/src/com/jetbrains/python/validation/HighlightingAnnotator.java @@ -21,10 +21,11 @@ public class HighlightingAnnotator extends PyAnnotator { @Override public void visitPyReferenceExpression(PyReferenceExpression node) { - if (node.getQualifier() == null) { + final String referencedName = node.getReferencedName(); + if (node.getQualifier() == null && referencedName != null) { PyFunction function = PsiTreeUtil.getParentOfType(node, PyFunction.class); if (function != null) { - final PyNamedParameter element = (PyNamedParameter) function.getParameterList().getElementNamed(node.getReferencedName()); + final PyNamedParameter element = function.getParameterList().findParameterByName(referencedName); if (element != null) { Annotation annotation = getHolder().createInfoAnnotation(node, null); annotation.setTextAttributes(isSelf(element, function) ? PyHighlighter.PY_SELF_PARAMETER : PyHighlighter.PY_PARAMETER); From 67c86ba0404c075b485b0f81d73ae8bc436b8430 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 15:36:54 +0100 Subject: [PATCH 07/20] don't create stubs for parameter lists of lambdas --- .../src/com/jetbrains/python/psi/PyFileElementType.java | 2 +- .../python/psi/impl/stubs/PyParameterListElementType.java | 8 ++++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/psi/PyFileElementType.java b/python/src/com/jetbrains/python/psi/PyFileElementType.java index 46437170bf0e..bf7948e2d630 100644 --- a/python/src/com/jetbrains/python/psi/PyFileElementType.java +++ b/python/src/com/jetbrains/python/psi/PyFileElementType.java @@ -44,7 +44,7 @@ public class PyFileElementType extends IStubFileElementType { @Override public int getStubVersion() { - return 41; + return 42; } @Nullable diff --git a/python/src/com/jetbrains/python/psi/impl/stubs/PyParameterListElementType.java b/python/src/com/jetbrains/python/psi/impl/stubs/PyParameterListElementType.java index 32d934906085..4ed964b1bf31 100644 --- a/python/src/com/jetbrains/python/psi/impl/stubs/PyParameterListElementType.java +++ b/python/src/com/jetbrains/python/psi/impl/stubs/PyParameterListElementType.java @@ -51,4 +51,12 @@ public class PyParameterListElementType extends PyStubElementType Date: Tue, 20 Mar 2012 15:37:40 +0100 Subject: [PATCH 08/20] use findParameterByName() --- .../python/documentation/DocStringParameterReference.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/documentation/DocStringParameterReference.java b/python/src/com/jetbrains/python/documentation/DocStringParameterReference.java index 42cb5c3db049..0fae6c6b9925 100644 --- a/python/src/com/jetbrains/python/documentation/DocStringParameterReference.java +++ b/python/src/com/jetbrains/python/documentation/DocStringParameterReference.java @@ -46,7 +46,7 @@ public class DocStringParameterReference extends PsiReferenceBase { @Nullable private PsiElement resolveParameter(PyFunction owner) { - return owner.getParameterList().getElementNamed(getCanonicalText()); + return owner.getParameterList().findParameterByName(getCanonicalText()); } @NotNull From c33a6dada0e1363849b1f3c152b3f57e38e9319a Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 15:38:40 +0100 Subject: [PATCH 09/20] dead code --- .../impl/references/PyImportReference.java | 7 ++-- .../python/psi/resolve/PyResolveUtil.java | 32 ------------------- 2 files changed, 4 insertions(+), 35 deletions(-) diff --git a/python/src/com/jetbrains/python/psi/impl/references/PyImportReference.java b/python/src/com/jetbrains/python/psi/impl/references/PyImportReference.java index e0f084292862..b228213d0393 100644 --- a/python/src/com/jetbrains/python/psi/impl/references/PyImportReference.java +++ b/python/src/com/jetbrains/python/psi/impl/references/PyImportReference.java @@ -7,7 +7,6 @@ import com.intellij.codeInsight.lookup.LookupElementBuilder; import com.intellij.lang.ASTNode; import com.intellij.openapi.editor.Document; import com.intellij.openapi.editor.Editor; -import com.intellij.openapi.util.Condition; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; import com.intellij.psi.tree.IElementType; @@ -20,7 +19,10 @@ import com.jetbrains.python.psi.*; import com.jetbrains.python.psi.impl.PyQualifiedName; import com.jetbrains.python.psi.impl.PyReferenceExpressionImpl; import com.jetbrains.python.psi.impl.ResolveResultList; -import com.jetbrains.python.psi.resolve.*; +import com.jetbrains.python.psi.resolve.PyResolveContext; +import com.jetbrains.python.psi.resolve.QualifiedNameResolver; +import com.jetbrains.python.psi.resolve.RatedResolveResult; +import com.jetbrains.python.psi.resolve.ResolveImportUtil; import com.jetbrains.python.psi.types.PyModuleType; import com.jetbrains.python.psi.types.PyType; import com.jetbrains.python.psi.types.TypeEvalContext; @@ -187,7 +189,6 @@ public class PyImportReference extends PyReferenceImpl { public Object[] execute() { int relative_level = -1; - Condition node_filter = new PyResolveUtil.FilterNameNotIn(myNamesAlready); InsertHandler insertHandler = null; // NOTE: could use getPointInImport() diff --git a/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java b/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java index 46c6e6c65ca9..52382e6704e0 100644 --- a/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java +++ b/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java @@ -24,7 +24,6 @@ import com.jetbrains.python.psi.impl.PyQualifiedName; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; -import java.util.Collection; import java.util.LinkedList; import java.util.List; @@ -317,35 +316,4 @@ public class PyResolveUtil { } } - - /** - * Accepts only names not contained in a given collection. - */ - public static class FilterNameNotIn implements Condition { - private final Collection myNames; - - public FilterNameNotIn(Collection names) { - myNames = names; - } - - public boolean value(PsiElement target) { - if (target instanceof PsiNamedElement) { - return !myNames.contains(((PsiNamedElement)target).getName()); - } - else if (target instanceof PyReferenceExpression) { - return !myNames.contains(((PyReferenceExpression)target).getReferencedName()); - } - else if (target instanceof NameDefiner) { - NameDefiner definer = (NameDefiner)target; - for (PyElement expr : definer.iterateNames()) { - if (expr != null) { - String referencedName = expr.getName(); - if (myNames.contains(referencedName)) return false; - } - } - } - return true; // nothing failed us - } - } - } From 3242b5a9519a995e75cc2b7736a70009fdf185a0 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 15:42:05 +0100 Subject: [PATCH 10/20] PyParameterList is no longer a NameDefiner --- .../com/jetbrains/python/psi/PyParameterList.java | 2 +- .../python/psi/impl/PyParameterListImpl.java | 15 --------------- 2 files changed, 1 insertion(+), 16 deletions(-) diff --git a/python/src/com/jetbrains/python/psi/PyParameterList.java b/python/src/com/jetbrains/python/psi/PyParameterList.java index 252875cc8fa4..0207bb357d18 100644 --- a/python/src/com/jetbrains/python/psi/PyParameterList.java +++ b/python/src/com/jetbrains/python/psi/PyParameterList.java @@ -9,7 +9,7 @@ import org.jetbrains.annotations.Nullable; * Represents function parameter list. * Date: 29.05.2005 */ -public interface PyParameterList extends PyElement, StubBasedPsiElement, NameDefiner { +public interface PyParameterList extends PyElement, StubBasedPsiElement { /** * Extracts the individual parameters. diff --git a/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java b/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java index 35782df9a30e..c9272494859a 100644 --- a/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java +++ b/python/src/com/jetbrains/python/psi/impl/PyParameterListImpl.java @@ -10,8 +10,6 @@ import com.jetbrains.python.psi.stubs.PyParameterListStub; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; -import java.util.ArrayList; - /** * @author yole */ @@ -153,15 +151,6 @@ public class PyParameterListImpl extends PyBaseElementImpl //return false; } - @NotNull - public Iterable iterateNames() { - return new ArrayList(ParamHelper.collectNamedParameters(this)); - } - - public PyElement getElementNamed(final String the_name) { - return IterHelper.findName(iterateNames(), the_name); - } - @Override @Nullable public PyNamedParameter findParameterByName(@NotNull final String name) { @@ -177,10 +166,6 @@ public class PyParameterListImpl extends PyBaseElementImpl return result.get(); } - public boolean mustResolveOutside() { - return true; - } - public String getPresentableText(final boolean includeDefaultValue) { final StringBuilder target = new StringBuilder(); final String COMMA = ", "; From 96f1bca9b029ec06e769afdd3750338ddb14ac58 Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 15:44:26 +0100 Subject: [PATCH 11/20] remove parameter list from name definer tokens too --- .../src/com/jetbrains/python/PythonTokenSetContributor.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/python/src/com/jetbrains/python/PythonTokenSetContributor.java b/python/src/com/jetbrains/python/PythonTokenSetContributor.java index eae910811bc2..ccdef69cdc50 100644 --- a/python/src/com/jetbrains/python/PythonTokenSetContributor.java +++ b/python/src/com/jetbrains/python/PythonTokenSetContributor.java @@ -36,8 +36,8 @@ public class PythonTokenSetContributor implements PythonDialectsTokenSetContribu return TokenSet.create(PyElementTypes.STAR_IMPORT_ELEMENT, PyElementTypes.IMPORT_ELEMENT, PyElementTypes.CLASS_DECLARATION, PyElementTypes.GLOBAL_STATEMENT, PyElementTypes.GENERATOR_EXPRESSION, PyElementTypes.DICT_COMP_EXPRESSION, PyElementTypes.LIST_COMP_EXPRESSION, PyElementTypes.SET_COMP_EXPRESSION, PyElementTypes.WITH_STATEMENT, - PyElementTypes.FUNCTION_DECLARATION, PyElementTypes.ASSIGNMENT_STATEMENT, PyElementTypes.PARAMETER_LIST, - PyElementTypes.EXCEPT_PART, PyElementTypes.FOR_STATEMENT, + PyElementTypes.FUNCTION_DECLARATION, PyElementTypes.ASSIGNMENT_STATEMENT, PyElementTypes.EXCEPT_PART, + PyElementTypes.FOR_STATEMENT, PyElementTypes.FROM_IMPORT_STATEMENT); } From 46b088873a0259c0c47b216128c65dfbae4e071d Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 16:04:54 +0100 Subject: [PATCH 12/20] inline unused overloads of treeCrawlUp() --- .../python/psi/resolve/PyResolveUtil.java | 37 +------------------ 1 file changed, 2 insertions(+), 35 deletions(-) diff --git a/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java b/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java index 52382e6704e0..1998b6bd11a4 100644 --- a/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java +++ b/python/src/com/jetbrains/python/psi/resolve/PyResolveUtil.java @@ -145,12 +145,10 @@ public class PyResolveUtil { * * @param processor a visitor that says when the crawl is done and collects info. * @param elt element from which we start (not checked by processor); if null, the search immediately returns null. - * @param roof if not null, search continues only below the roof and including it. - * @param fromunder if true, begin search not above elt, but from a [possibly imaginary] node right below elt; so elt gets analyzed, too. * @return first element that the processor accepted. */ @Nullable - public static PsiElement treeCrawlUp(PsiScopeProcessor processor, boolean fromunder, PsiElement elt, @Nullable PsiElement roof) { + public static PsiElement treeCrawlUp(PsiScopeProcessor processor, PsiElement elt) { if (elt == null || !elt.isValid()) return null; // can't find anyway. PsiElement seeker = elt; PsiElement cap = PyUtil.getConcealingParent(elt); @@ -158,13 +156,7 @@ public class PyResolveUtil { final boolean is_outside_param_list = PsiTreeUtil.getParentOfType(elt, PyParameterList.class) == null; do { ProgressManager.checkCanceled(); - if (fromunder) { - fromunder = false; // only honour fromunder once per call - seeker = getPrevNodeOf(PsiTreeUtil.getDeepestLast(seeker), processor); - } - else { // main case - seeker = getPrevNodeOf(seeker, processor); - } + seeker = getPrevNodeOf(seeker, processor); // aren't we in the same defining assignment, global, etc? if ((seeker instanceof NameDefiner) && ((NameDefiner)seeker).mustResolveOutside() && PsiTreeUtil.isAncestor(seeker, elt, true)) { seeker = getPrevNodeOf(seeker, processor); @@ -190,8 +182,6 @@ public class PyResolveUtil { break; } // seeker is contextually under elt already } - // are we still under the roof? - if ((roof != null) && (seeker != null) && !PsiTreeUtil.isAncestor(roof, seeker, false)) return null; // maybe we're capped by a class? param lists are not capped though syntactically inside the function. if (is_outside_param_list && refersFromMethodToClass(capFunction, seeker)) continue; // names defined in a comprehension element are only visible inside it or the list comp expressions directly above it @@ -235,29 +225,6 @@ public class PyResolveUtil { return false; } - /** - * Crawls up the PSI tree, checking nodes as if crawling backwards through source lexemes. - * - * @param processor a visitor that says when the crawl is done and collects info. - * @param fromunder if true, search not above elt, but from a [possibly imaginary] node right below elt; so elt gets analyzed, too. - * @param elt element from which we start (not checked by processor); if null, the search immediately fails. - * @return first element that the processor accepted. - */ - @Nullable - public static PsiElement treeCrawlUp(PsiScopeProcessor processor, boolean fromunder, PsiElement elt) { - return treeCrawlUp(processor, fromunder, elt, null); - } - - /** - * Returns treeCrawlUp(processor, elt, false). A convenience method. - * - * @see PyResolveUtil#treeCrawlUp(com.intellij.psi.scope.PsiScopeProcessor, boolean, com.intellij.psi.PsiElement) - */ - @Nullable - public static PsiElement treeCrawlUp(PsiScopeProcessor processor, PsiElement elt) { - return treeCrawlUp(processor, false, elt); - } - /** * Unwinds a multi-level qualified expression into a path, as seen in source text, i.e. outermost qualifier first. * From e0ae1ff0ccc6df9582ced02dc3da032fd42f705a Mon Sep 17 00:00:00 2001 From: Dmitry Jemerov Date: Tue, 20 Mar 2012 16:17:13 +0100 Subject: [PATCH 13/20] dead code --- .../python/documentation/DocumentationBuilder.java | 5 +++-- python/src/com/jetbrains/python/psi/PyFile.java | 7 ------- python/src/com/jetbrains/python/psi/impl/PyFileImpl.java | 9 --------- 3 files changed, 3 insertions(+), 18 deletions(-) diff --git a/python/src/com/jetbrains/python/documentation/DocumentationBuilder.java b/python/src/com/jetbrains/python/documentation/DocumentationBuilder.java index 662ec3f18f35..a6f9583695ca 100644 --- a/python/src/com/jetbrains/python/documentation/DocumentationBuilder.java +++ b/python/src/com/jetbrains/python/documentation/DocumentationBuilder.java @@ -490,11 +490,12 @@ class DocumentationBuilder { private void addModulePath(PyFile followed) { // what to prepend to a module description? - String path = VfsUtil.urlToPath(followed.getUrl()); - if ("".equals(path)) { + final VirtualFile file = followed.getVirtualFile(); + if (file == null) { myProlog.addWith(TagSmall, $(PyBundle.message("QDOC.module.path.unknown"))); } else { + final String path = file.getPath(); RootFinder finder = new RootFinder(path); RootVisitorHost.visitRoots(followed, finder); final String root_path = finder.getResult(); diff --git a/python/src/com/jetbrains/python/psi/PyFile.java b/python/src/com/jetbrains/python/psi/PyFile.java index 5ad54deb1cd8..50d24a12cc3a 100644 --- a/python/src/com/jetbrains/python/psi/PyFile.java +++ b/python/src/com/jetbrains/python/psi/PyFile.java @@ -2,7 +2,6 @@ package com.jetbrains.python.psi; import com.intellij.psi.PsiFile; import com.jetbrains.python.codeInsight.controlflow.ScopeOwner; -import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import java.util.List; @@ -16,12 +15,6 @@ public interface PyFile extends PyElement, PsiFile, PyDocStringOwner, ScopeOwner List getTopLevelAttributes(); - /** - @return an URL of file, maybe bogus if virtual file is not present. - */ - @NotNull - String getUrl(); - @Nullable PyFunction findTopLevelFunction(String name); diff --git a/python/src/com/jetbrains/python/psi/impl/PyFileImpl.java b/python/src/com/jetbrains/python/psi/impl/PyFileImpl.java index 2558ed937891..76b614d960ae 100644 --- a/python/src/com/jetbrains/python/psi/impl/PyFileImpl.java +++ b/python/src/com/jetbrains/python/psi/impl/PyFileImpl.java @@ -69,15 +69,6 @@ public class PyFileImpl extends PsiFileBase implements PyFile, PyExpression { return "PyFile:" + getName(); } - @NotNull - public String getUrl() { - String fname; - VirtualFile vfile = getVirtualFile(); - if (vfile != null) fname = vfile.getUrl(); - else fname = "(null)://" + this.toString(); - return fname; - } - public PyFunction findTopLevelFunction(String name) { return findByName(name, getTopLevelFunctions()); } From 1136fbeaac6d56b56d5a253ed15d89ad5a229db6 Mon Sep 17 00:00:00 2001 From: Andrey Vlasovskikh Date: Tue, 20 Mar 2012 20:50:24 +0400 Subject: [PATCH 14/20] Separate error messages for missing 'pip' and 'distribute' (PY-5931) --- python/helpers/packaging_tool.py | 4 ++-- .../jetbrains/python/packaging/PyPackageManager.java | 12 ++++-------- 2 files changed, 6 insertions(+), 10 deletions(-) diff --git a/python/helpers/packaging_tool.py b/python/helpers/packaging_tool.py index 4db4e403139b..7702f72ff234 100644 --- a/python/helpers/packaging_tool.py +++ b/python/helpers/packaging_tool.py @@ -15,13 +15,13 @@ def error(message, retcode): sys.exit(retcode) def error_no_pip(): - error("Python package management tool 'pip' not found. Please install 'pip'", ERROR_NO_PACKAGING_TOOLS) + error("Python package management tool 'pip' not found. Please install 'pip' manually", ERROR_NO_PACKAGING_TOOLS) def do_list(): try: import pkg_resources except ImportError: - error("Python package management tools not found. Please install 'setuptools' or 'distribute'", ERROR_NO_PACKAGING_TOOLS) + error("Python package management tools not found. Please install 'setuptools' or 'distribute' manually", ERROR_NO_PACKAGING_TOOLS) for pkg in pkg_resources.working_set: print('\t'.join([pkg.project_name, pkg.version, pkg.location])) diff --git a/python/src/com/jetbrains/python/packaging/PyPackageManager.java b/python/src/com/jetbrains/python/packaging/PyPackageManager.java index d09a21d0fb76..080284e68dfb 100644 --- a/python/src/com/jetbrains/python/packaging/PyPackageManager.java +++ b/python/src/com/jetbrains/python/packaging/PyPackageManager.java @@ -257,16 +257,12 @@ public class PyPackageManager { } @Nullable - public PyPackage findPackage(String name) { - try { - for (PyPackage pkg : getPackages()) { - if (name.equals(pkg.getName())) { - return pkg; - } + public PyPackage findPackage(String name) throws PyExternalProcessException { + for (PyPackage pkg : getPackages()) { + if (name.equals(pkg.getName())) { + return pkg; } } - catch (PyExternalProcessException ignored) { - } return null; } From 602055eafac7aead45e46be1f8ea58a386125f79 Mon Sep 17 00:00:00 2001 From: Andrey Vlasovskikh Date: Tue, 20 Mar 2012 20:51:23 +0400 Subject: [PATCH 15/20] Cleanup --- .../src/com/jetbrains/python/packaging/PyPackageManager.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/packaging/PyPackageManager.java b/python/src/com/jetbrains/python/packaging/PyPackageManager.java index 080284e68dfb..712082a9ca39 100644 --- a/python/src/com/jetbrains/python/packaging/PyPackageManager.java +++ b/python/src/com/jetbrains/python/packaging/PyPackageManager.java @@ -17,6 +17,7 @@ import com.intellij.openapi.projectRoots.SdkAdditionalData; import com.intellij.openapi.util.Key; import com.intellij.openapi.util.Ref; import com.intellij.openapi.util.io.FileUtil; +import com.intellij.openapi.util.io.FileUtilLight; import com.intellij.openapi.util.text.StringUtil; import com.intellij.openapi.vfs.VirtualFileManager; import com.intellij.util.ArrayUtil; @@ -206,7 +207,7 @@ public class PyPackageManager { args.add("install"); final File buildDir; try { - buildDir = FileUtil.createTempDirectory("packaging", null); + buildDir = FileUtilLight.createTempDirectory("packaging", null); } catch (IOException e) { throw new PyExternalProcessException(ERROR_ACCESS_DENIED, PACKAGING_TOOL, args, "Cannot create temporary build directory"); From 5a6e5bbebf5b07a3aaa5e10a3f498bf6d5a81dd9 Mon Sep 17 00:00:00 2001 From: Andrey Vlasovskikh Date: Tue, 20 Mar 2012 22:19:26 +0400 Subject: [PATCH 16/20] Fixed stdlib type databse for 'str' and 'bytes' in Python 3 (PY-5901) --- .../stdlib/StdlibTypes3.properties | 229 ++++++++++++------ 1 file changed, 155 insertions(+), 74 deletions(-) diff --git a/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes3.properties b/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes3.properties index 0af17e58b339..b56bdb9eb152 100644 --- a/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes3.properties +++ b/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes3.properties @@ -3,311 +3,392 @@ ## 4.6. Sequence types -builtins.bytes.capitalize = \ +__builtin__.bytes.__init__ = \ :rtype: bytes \n\ -builtins.bytes.center = \ +__builtin__.bytes.__add__ = \ + :type y: bytes \n\ + :rtype: bytes \n\ + +__builtin__.bytes.__mul__ = \ + :type n: int or long \n\ + :rtype: bytes \n\ + +__builtin__.bytes.__mod__ = \ + :type y: object \n\ + :rtype: bytes \n\ + +__builtin__.bytes.__rmul__ = \ + :type n: int or long \n\ + :rtype: bytes \n\ + +__builtin__.bytes.__rmod__ = \ + :type y: object \n\ + :rtype: bytes \n\ + +__builtin__.bytes.__getitem__ = \ + :type y: int \n\ + :rtype: bytes \n\ + +__builtin__.bytes.capitalize = \ + :rtype: bytes \n\ + +__builtin__.bytes.center = \ :type width: int or long \n\ :type fillchar: bytes or None \n\ :rtype: bytes \n\ -builtins.bytes.count = \ +__builtin__.bytes.count = \ :type sub: bytes \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.bytes.decode = \ +__builtin__.bytes.decode = \ :type encoding: str \n\ :type errors: str or None \n\ :rtype: str \n\ -builtins.bytes.encode = \ +__builtin__.bytes.encode = \ :type encoding: str \n\ :type errors: str or None \n\ :rtype: bytes \n\ -builtins.bytes.endswith = \ +__builtin__.bytes.endswith = \ :type suffix: bytes \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: bool \n\ -builtins.bytes.find = \ +__builtin__.bytes.find = \ :type sub: bytes \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.bytes.index = \ +__builtin__.bytes.index = \ :type sub: bytes \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.bytes.isalnum = \ +__builtin__.bytes.isalnum = \ :rtype: bool \n\ -builtins.bytes.isalpha = \ +__builtin__.bytes.isalpha = \ :rtype: bool \n\ -builtins.bytes.isdigit = \ +__builtin__.bytes.isdigit = \ :rtype: bool \n\ -builtins.bytes.islower = \ +__builtin__.bytes.islower = \ :rtype: bool \n\ -builtins.bytes.isspace = \ +__builtin__.bytes.isspace = \ :rtype: bool \n\ -builtins.bytes.istitle = \ +__builtin__.bytes.istitle = \ :rtype: bool \n\ -builtins.bytes.isupper = \ +__builtin__.bytes.isupper = \ :rtype: bool \n\ -builtins.bytes.join = \ - :type iterable: object \n\ +__builtin__.bytes.join = \ + :type iterable: collections.Iterable of bytes \n\ :rtype: bytes \n\ -builtins.bytes.ljust = \ +__builtin__.bytes.ljust = \ :type width: int or long \n\ :type fillchar: bytes or None \n\ :rtype: bytes \n\ -builtins.bytes.lower = \ +__builtin__.bytes.lower = \ :rtype: bytes \n\ -builtins.bytes.lstrip = \ +__builtin__.bytes.lstrip = \ :type chars: bytes or None \n\ :rtype: bytes \n\ -builtins.bytes.partition = \ +__builtin__.bytes.partition = \ :type sep: bytes \n\ :rtype: (bytes, bytes, bytes) \n\ -builtins.bytes.replace = \ +__builtin__.bytes.replace = \ :type old: bytes \n\ :type new: bytes \n\ :type count: int or long \n\ :rtype: bytes \n\ -builtins.bytes.rfind = \ +__builtin__.bytes.rfind = \ :type sub: bytes \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.bytes.rindex = \ +__builtin__.bytes.rindex = \ :type sub: bytes \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.bytes.rpartition = \ +__builtin__.bytes.rpartition = \ :type sep: bytes \n\ :rtype: (bytes, bytes, bytes) \n\ -builtins.bytes.rsplit = \ +__builtin__.bytes.rsplit = \ :type sep: bytes or None \n\ :type maxsplit: int or long or None \n\ :rtype: list of bytes \n\ -builtins.bytes.rstrip = \ +__builtin__.bytes.rstrip = \ :type chars: bytes or None \n\ :rtype: bytes \n\ -builtins.bytes.split = \ +__builtin__.bytes.split = \ :type sep: bytes or None \n\ :type maxsplit: int or long or None \n\ :rtype: list of bytes \n\ -builtins.bytes.splitlines = \ +__builtin__.bytes.splitlines = \ :type keepends: bool or int or long or None \n\ :rtype: list of bytes \n\ -builtins.bytes.startswith = \ +__builtin__.bytes.startswith = \ :type prefix: bytes \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: bool \n\ -builtins.bytes.strip = \ +__builtin__.bytes.strip = \ :type chars: bytes or None \n\ :rtype: bytes \n\ -builtins.bytes.swapcase = \ +__builtin__.bytes.swapcase = \ :rtype: bytes \n\ -builtins.bytes.title = \ +__builtin__.bytes.title = \ :rtype: bytes \n\ -builtins.bytes.translate = \ +__builtin__.bytes.translate = \ :type table: object \n\ :type deletechars: bytes \n\ :rtype: bytes \n\ -builtins.bytes.upper = \ +__builtin__.bytes.upper = \ :rtype: bytes \n\ -builtins.bytes.zfill = \ +__builtin__.bytes.zfill = \ :type width: int or long \n\ :rtype: bytes \n\ -builtins.str.capitalize = \ +__builtin__.str.__init__ = \ :rtype: str \n\ -builtins.str.center = \ +__builtin__.str.__add__ = \ + :type y: str \n\ + :rtype: str \n\ + +__builtin__.str.__mul__ = \ + :type n: int or long \n\ + :rtype: str \n\ + +__builtin__.str.__mod__ = \ + :type y: object \n\ + :rtype: str \n\ + +__builtin__.str.__rmul__ = \ + :type n: int or long \n\ + :rtype: str \n\ + +__builtin__.str.__rmod__ = \ + :type y: object \n\ + :rtype: str \n\ + +__builtin__.str.__getitem__ = \ + :type y: int \n\ + :rtype: str \n\ + +__builtin__.str.capitalize = \ + :rtype: str \n\ + +__builtin__.str.center = \ :type width: int or long \n\ :type fillchar: str or None \n\ :rtype: str \n\ -builtins.str.count = \ +__builtin__.str.count = \ :type sub: str \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.str.decode = \ +__builtin__.str.decode = \ :type encoding: str \n\ :type errors: str or None \n\ :rtype: str \n\ -builtins.str.encode = \ +__builtin__.str.encode = \ :type encoding: str \n\ :type errors: str or None \n\ :rtype: bytes \n\ -builtins.str.endswith = \ +__builtin__.str.endswith = \ :type suffix: str \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: bool \n\ -builtins.str.find = \ +__builtin__.str.find = \ :type sub: str \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.str.index = \ +__builtin__.str.index = \ :type sub: str \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.str.isalnum = \ +__builtin__.str.isalnum = \ :rtype: bool \n\ -builtins.str.isalpha = \ +__builtin__.str.isalpha = \ :rtype: bool \n\ -builtins.str.isdecimal = \ +__builtin__.str.isdecimal = \ :rtype: bool \n\ -builtins.str.isdigit = \ +__builtin__.str.isdigit = \ :rtype: bool \n\ -builtins.str.islower = \ +__builtin__.str.islower = \ :rtype: bool \n\ -builtins.str.isnumeric = \ +__builtin__.str.isnumeric = \ :rtype: bool \n\ -builtins.str.isspace = \ +__builtin__.str.isspace = \ :rtype: bool \n\ -builtins.str.istitle = \ +__builtin__.str.istitle = \ :rtype: bool \n\ -builtins.str.isupper = \ +__builtin__.str.isupper = \ :rtype: bool \n\ -builtins.str.join = \ - :type iterable: object \n\ +__builtin__.str.join = \ + :type iterable: collections.Iterable of str \n\ :rtype: str \n\ -builtins.str.ljust = \ +__builtin__.str.ljust = \ :type width: int or long \n\ :type fillchar: str or None \n\ :rtype: str \n\ -builtins.str.lower = \ +__builtin__.str.lower = \ :rtype: str \n\ -builtins.str.lstrip = \ +__builtin__.str.lstrip = \ :type chars: str or None \n\ :rtype: str \n\ -builtins.str.partition = \ +__builtin__.str.partition = \ :type sep: str \n\ :rtype: (str, str, str) \n\ -builtins.str.replace = \ +__builtin__.str.replace = \ :type old: str \n\ :type new: str \n\ :type count: int or long \n\ :rtype: str \n\ -builtins.str.rfind = \ +__builtin__.str.rfind = \ :type sub: str \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.str.rindex = \ +__builtin__.str.rindex = \ :type sub: str \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: int or long \n\ -builtins.str.rpartition = \ +__builtin__.str.rpartition = \ :type sep: str \n\ :rtype: (str, str, str) \n\ -builtins.str.rsplit = \ +__builtin__.str.rsplit = \ :type sep: str or None \n\ :type maxsplit: int or long or None \n\ :rtype: list of str \n\ -builtins.str.rstrip = \ +__builtin__.str.rstrip = \ :type chars: str or None \n\ :rtype: str \n\ -builtins.str.split = \ +__builtin__.str.split = \ :type sep: str or None \n\ :type maxsplit: int or long or None \n\ :rtype: list of str \n\ -builtins.str.splitlines = \ +__builtin__.str.splitlines = \ :type keepends: bool or int or long or None \n\ :rtype: list of str \n\ -builtins.str.startswith = \ +__builtin__.str.startswith = \ :type prefix: str \n\ :type start: int or long or None \n\ :type end: int or long or None \n\ :rtype: bool \n\ -builtins.str.strip = \ +__builtin__.str.strip = \ :type chars: str or None \n\ :rtype: str \n\ -builtins.str.swapcase = \ +__builtin__.str.swapcase = \ :rtype: str \n\ -builtins.str.title = \ +__builtin__.str.title = \ :rtype: str \n\ -builtins.str.translate = \ +__builtin__.str.translate = \ :type table: object \n\ :type deletechars: str \n\ :rtype: str \n\ -builtins.str.upper = \ +__builtin__.str.upper = \ :rtype: str \n\ -builtins.str.zfill = \ +__builtin__.str.zfill = \ :type width: int or long \n\ :rtype: str \n\ + +## 15.2. io + +io.IOBase.readlines = \ + :rtype: list of bytes \n\ + +io.IOBase.writelines = \ + :type lines: collections.Iterable of bytes \n\ + +io.IOBase.__iter__ = \ + :rtype: list of bytes \n\ + +io.IOBase.next = \ + :rtype: bytes \n\ + +io._IOBase.readlines = \ + :rtype: list of bytes \n\ + +io._IOBase.writelines = \ + :type lines: collections.Iterable of bytes \n\ + +io._IOBase.__iter__ = \ + :rtype: list of bytes \n\ + +io._IOBase.next = \ + :rtype: bytes \n\ + From 39e4b735360f92cfd4bf06fb033bd9f9de423a29 Mon Sep 17 00:00:00 2001 From: Andrey Vlasovskikh Date: Tue, 20 Mar 2012 22:20:06 +0400 Subject: [PATCH 17/20] Improved detection of for-loop and context manager variable types --- .../stdlib/StdlibTypes2.properties | 6 ++++ .../psi/impl/PyTargetExpressionImpl.java | 31 ++++++++++++++----- 2 files changed, 30 insertions(+), 7 deletions(-) diff --git a/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes2.properties b/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes2.properties index 75e8ebb26525..88d0deac151f 100644 --- a/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes2.properties +++ b/python/src/com/jetbrains/python/codeInsight/stdlib/StdlibTypes2.properties @@ -1832,6 +1832,9 @@ io.open.2 = \ :type mode: bytes \n\ :rtype: io.FileIO \n\ +io.TextIOWrapper.__enter__ = \ + :rtype: io.TextIOWrapper \n\ + io.TextIOWrapper.read = \ :rtype: unicode \n\ @@ -1848,6 +1851,9 @@ io.TextIOWrapper.write = \ :type s: string \n\ :rtype: int \n\ +io.FileIO.__enter__ = \ + :rtype: io.FileIO \n\ + io.FileIO.read = \ :rtype: bytes \n\ diff --git a/python/src/com/jetbrains/python/psi/impl/PyTargetExpressionImpl.java b/python/src/com/jetbrains/python/psi/impl/PyTargetExpressionImpl.java index 246792aec487..83441ea8c7ef 100644 --- a/python/src/com/jetbrains/python/psi/impl/PyTargetExpressionImpl.java +++ b/python/src/com/jetbrains/python/psi/impl/PyTargetExpressionImpl.java @@ -283,15 +283,23 @@ public class PyTargetExpressionImpl extends PyPresentableElementImpl()); + if (iterMethodType instanceof PyCollectionType) { + final PyCollectionType collectionType = (PyCollectionType)iterMethodType; + type = collectionType.getElementType(context); } - else if (next != null) { - type = next.getReturnType(context, null); + if (type == null) { + PyFunction next = pyClass.findMethodByName(PyNames.NEXT, true); + if (next == null) { + next = pyClass.findMethodByName(PyNames.DUNDER_NEXT, true); + } + if (next != null) { + type = getContextSensitiveType(next, context, source); + } } } } @@ -307,6 +315,15 @@ public class PyTargetExpressionImpl extends PyPresentableElementImpl()); + } + return function.getReturnType(context, null); + } + @Nullable private PyType getTypeFromExcept() { PyExceptPart exceptPart = PsiTreeUtil.getParentOfType(this, PyExceptPart.class); From b4b867ff2b8e96c65d6b104255b92d68821ac309 Mon Sep 17 00:00:00 2001 From: Roman Shevchenko Date: Tue, 20 Mar 2012 20:47:32 +0100 Subject: [PATCH 18/20] util-rt module introduced --- .../com/jetbrains/python/packaging/PyPackageManager.java | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/python/src/com/jetbrains/python/packaging/PyPackageManager.java b/python/src/com/jetbrains/python/packaging/PyPackageManager.java index 712082a9ca39..d5769db00535 100644 --- a/python/src/com/jetbrains/python/packaging/PyPackageManager.java +++ b/python/src/com/jetbrains/python/packaging/PyPackageManager.java @@ -17,13 +17,14 @@ import com.intellij.openapi.projectRoots.SdkAdditionalData; import com.intellij.openapi.util.Key; import com.intellij.openapi.util.Ref; import com.intellij.openapi.util.io.FileUtil; -import com.intellij.openapi.util.io.FileUtilLight; import com.intellij.openapi.util.text.StringUtil; import com.intellij.openapi.vfs.VirtualFileManager; import com.intellij.util.ArrayUtil; import com.intellij.util.Function; import com.jetbrains.python.PythonHelpersLocator; -import com.jetbrains.python.psi.*; +import com.jetbrains.python.psi.PyExpression; +import com.jetbrains.python.psi.PyListLiteralExpression; +import com.jetbrains.python.psi.PyStringLiteralExpression; import com.jetbrains.python.remote.PyRemoteInterpreterException; import com.jetbrains.python.remote.PythonRemoteInterpreterManager; import com.jetbrains.python.remote.PythonRemoteSdkAdditionalData; @@ -32,6 +33,7 @@ import com.jetbrains.python.sdk.PySdkUtil; import com.jetbrains.python.sdk.PythonSdkType; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; +import org.jetbrains.util.rt.FileUtilRt; import javax.swing.event.HyperlinkEvent; import java.io.File; @@ -207,7 +209,7 @@ public class PyPackageManager { args.add("install"); final File buildDir; try { - buildDir = FileUtilLight.createTempDirectory("packaging", null); + buildDir = FileUtilRt.createTempDirectory("packaging", null); } catch (IOException e) { throw new PyExternalProcessException(ERROR_ACCESS_DENIED, PACKAGING_TOOL, args, "Cannot create temporary build directory"); From d66cbfeaca2cc31900697312ba0a8e45e9158516 Mon Sep 17 00:00:00 2001 From: Alexey Kudravtsev Date: Tue, 20 Mar 2012 20:04:54 +0400 Subject: [PATCH 19/20] cleanup --- python/src/com/jetbrains/python/PythonPsiManager.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/PythonPsiManager.java b/python/src/com/jetbrains/python/PythonPsiManager.java index 0da8f998159c..78febc929dce 100644 --- a/python/src/com/jetbrains/python/PythonPsiManager.java +++ b/python/src/com/jetbrains/python/PythonPsiManager.java @@ -12,6 +12,7 @@ import com.intellij.psi.impl.PsiTreeChangeEventImpl; import com.intellij.psi.impl.PsiTreeChangePreprocessor; import com.jetbrains.python.psi.PyFile; import com.jetbrains.python.psi.PyFunction; +import org.jetbrains.annotations.NotNull; /** * @author yole @@ -30,7 +31,7 @@ public class PythonPsiManager extends AbstractProjectComponent implements PsiTre myPsiManager.addTreeChangePreprocessor(this); } - public void treeChanged(PsiTreeChangeEventImpl event) { + public void treeChanged(@NotNull PsiTreeChangeEventImpl event) { if (!(event.getFile() instanceof PyFile)) return; boolean changedInsideCodeBlock = false; From a6ee9add418492c79a4b455ca4beb0fe441bdcd4 Mon Sep 17 00:00:00 2001 From: Roman Shevchenko Date: Wed, 21 Mar 2012 09:44:06 +0100 Subject: [PATCH 20/20] Move util-rt utility classes to a more familiar place --- python/src/com/jetbrains/python/packaging/PyPackageManager.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/python/src/com/jetbrains/python/packaging/PyPackageManager.java b/python/src/com/jetbrains/python/packaging/PyPackageManager.java index d5769db00535..0332625bb768 100644 --- a/python/src/com/jetbrains/python/packaging/PyPackageManager.java +++ b/python/src/com/jetbrains/python/packaging/PyPackageManager.java @@ -33,7 +33,7 @@ import com.jetbrains.python.sdk.PySdkUtil; import com.jetbrains.python.sdk.PythonSdkType; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; -import org.jetbrains.util.rt.FileUtilRt; +import com.intellij.openapi.util.io.FileUtilRt; import javax.swing.event.HyperlinkEvent; import java.io.File;