diff --git a/jedi/parser/diff.py b/jedi/parser/diff.py index ee0e87eb..ea0860fd 100644 --- a/jedi/parser/diff.py +++ b/jedi/parser/diff.py @@ -12,7 +12,7 @@ from collections import namedtuple from jedi._compatibility import use_metaclass from jedi import settings from jedi.common import splitlines -from jedi.parser import ParserWithRecovery +from jedi.parser.python.parser import ParserWithRecovery, _remove_last_newline from jedi.parser.python.tree import EndMarker from jedi.parser.utils import parser_cache from jedi import debug @@ -183,7 +183,7 @@ class DiffParser(object): self._nodes_stack.close() if self._added_newline: - self._parser._remove_last_newline() + _remove_last_newline(self._parser.get_root_node()) self._parser.source = ''.join(lines_new) diff --git a/jedi/parser/python/__init__.py b/jedi/parser/python/__init__.py index 886a1039..5e936ffe 100644 --- a/jedi/parser/python/__init__.py +++ b/jedi/parser/python/__init__.py @@ -5,7 +5,8 @@ import os from jedi._compatibility import FileNotFoundError from jedi.parser.pgen2.pgen import generate_grammar -from jedi.parser.python.parser import Parser, ParserWithRecovery +from jedi.parser.python.parser import Parser, ParserWithRecovery, \ + _remove_last_newline from jedi.parser.tokenize import source_tokens @@ -82,6 +83,6 @@ def parse(code, grammar=None, error_recovery=True, start_symbol='file_input'): p = parser(grammar, code, start_parsing=False, **kwargs) module = p.parse(tokens=tokens) if added_newline: - p._remove_last_newline() + _remove_last_newline(module) return module diff --git a/jedi/parser/python/parser.py b/jedi/parser/python/parser.py index 08344206..5b82a231 100644 --- a/jedi/parser/python/parser.py +++ b/jedi/parser/python/parser.py @@ -69,7 +69,7 @@ class Parser(BaseParser): ) if self._added_newline: - self._remove_last_newline() + _remove_last_newline(node) return node def get_root_node(self): @@ -114,31 +114,32 @@ class Parser(BaseParser): else: return tree.Operator(value, start_pos, prefix) - def _remove_last_newline(self): - endmarker = self._parsed.children[-1] - # The newline is either in the endmarker as a prefix or the previous - # leaf as a newline token. - prefix = endmarker.prefix - if prefix.endswith('\n'): - endmarker.prefix = prefix = prefix[:-1] - last_end = 0 - if '\n' not in prefix: - # Basically if the last line doesn't end with a newline. we - # have to add the previous line's end_position. - previous_leaf = endmarker.get_previous_leaf() - if previous_leaf is not None: - last_end = previous_leaf.end_pos[1] - last_line = re.sub('.*\n', '', prefix) - endmarker.start_pos = endmarker.line - 1, last_end + len(last_line) - else: - newline = endmarker.get_previous_leaf() - if newline is None: - return # This means that the parser is empty. - assert newline.value.endswith('\n') - newline.value = newline.value[:-1] - endmarker.start_pos = \ - newline.start_pos[0], newline.start_pos[1] + len(newline.value) +def _remove_last_newline(node): + endmarker = node.children[-1] + # The newline is either in the endmarker as a prefix or the previous + # leaf as a newline token. + prefix = endmarker.prefix + if prefix.endswith('\n'): + endmarker.prefix = prefix = prefix[:-1] + last_end = 0 + if '\n' not in prefix: + # Basically if the last line doesn't end with a newline. we + # have to add the previous line's end_position. + previous_leaf = endmarker.get_previous_leaf() + if previous_leaf is not None: + last_end = previous_leaf.end_pos[1] + last_line = re.sub('.*\n', '', prefix) + endmarker.start_pos = endmarker.line - 1, last_end + len(last_line) + else: + newline = endmarker.get_previous_leaf() + if newline is None: + return # This means that the parser is empty. + + assert newline.value.endswith('\n') + newline.value = newline.value[:-1] + endmarker.start_pos = \ + newline.start_pos[0], newline.start_pos[1] + len(newline.value) class ParserWithRecovery(Parser):