def testIsMultilineString(self):
        tok = format_token.FormatToken(pytree.Leaf(token.STRING,
                                                   '"""hello"""'))
        self.assertTrue(tok.is_multiline_string)

        tok = format_token.FormatToken(
            pytree.Leaf(token.STRING, 'r"""hello"""'))
        self.assertTrue(tok.is_multiline_string)
  def testSimple(self):
    tok = format_token.FormatToken(pytree.Leaf(token.STRING, "'hello world'"))
    self.assertEqual("FormatToken(name=STRING, value='hello world', lineno=0)",
                     str(tok))
    self.assertTrue(tok.is_string)

    tok = format_token.FormatToken(pytree.Leaf(token.COMMENT, '# A comment'))
    self.assertEqual('FormatToken(name=COMMENT, value=# A comment, lineno=0)',
                     str(tok))
    self.assertTrue(tok.is_comment)
Exemple #3
0
    def AppendNode(self, node):
        """Convenience method to append a pytree node directly.

    Wraps the node with a FormatToken.

    Arguments:
      node: the node to append
    """
        self.AppendToken(format_token.FormatToken(node))
Exemple #4
0
    def DefaultLeafVisit(self, leaf):
        """Default visitor for tree leaves.

    A tree leaf is always just gets appended to the current logical line.

    Arguments:
      leaf: the leaf to visit.
    """
        if leaf.type in _WHITESPACE_TOKENS:
            self._StartNewLine()
        elif leaf.type != grammar_token.COMMENT or leaf.value.strip():
            # Add non-whitespace tokens and comments that aren't empty.
            self._cur_logical_line.AppendToken(format_token.FormatToken(leaf))
Exemple #5
0
def _SingleOrMergedLines(uwlines):
    """Generate the lines we want to format.

  Arguments:
    uwlines: (list of unwrapped_line.UnwrappedLine) Lines we want to format.

  Yields:
    Either a single line, if the current line cannot be merged with the
    succeeding line, or the next two lines merged into one line.
  """
    index = 0
    last_was_merged = False
    while index < len(uwlines):
        if uwlines[index].disable:
            uwline = uwlines[index]
            index += 1
            while index < len(uwlines):
                column = uwline.last.column + 2
                if uwlines[index].lineno != uwline.lineno:
                    break
                if uwline.last.value != ':':
                    leaf = pytree.Leaf(type=token.SEMI,
                                       value=';',
                                       context=('', (uwline.lineno, column)))
                    uwline.AppendToken(format_token.FormatToken(leaf))
                for tok in uwlines[index].tokens:
                    uwline.AppendToken(tok)
                index += 1
            yield uwline
        elif line_joiner.CanMergeMultipleLines(uwlines[index:],
                                               last_was_merged):
            # TODO(morbo): This splice is potentially very slow. Come up with a more
            # performance-friendly way of determining if two lines can be merged.
            next_uwline = uwlines[index + 1]
            for tok in next_uwline.tokens:
                uwlines[index].AppendToken(tok)
            if (len(next_uwline.tokens) == 1
                    and next_uwline.first.is_multiline_string):
                # This may be a multiline shebang. In that case, we want to retain the
                # formatting. Otherwise, it could mess up the shell script's syntax.
                uwlines[index].disable = True
            yield uwlines[index]
            index += 2
            last_was_merged = True
        else:
            yield uwlines[index]
            index += 1
            last_was_merged = False
Exemple #6
0
def _CreateLogicalLines(tokens):
    """Separate tokens into logical lines.

  Arguments:
    tokens: (list of tokenizer.TokenInfo) Tokens generated by tokenizer.

  Returns:
    A list of LogicalLines.
  """
    logical_lines = []
    cur_logical_line = []
    prev_tok = None
    depth = 0

    for tok in tokens:
        tok = py3compat.TokenInfo(*tok)
        if tok.type == tokenize.NEWLINE:
            # End of a logical line.
            logical_lines.append(
                logical_line.LogicalLine(depth, cur_logical_line))
            cur_logical_line = []
            prev_tok = None
        elif tok.type == tokenize.INDENT:
            depth += 1
        elif tok.type == tokenize.DEDENT:
            depth -= 1
        elif tok.type not in {tokenize.NL, tokenize.ENDMARKER}:
            if (prev_tok and prev_tok.line.rstrip().endswith('\\')
                    and prev_tok.start[0] < tok.start[0]):
                # Insert a token for a line continuation.
                ctok = py3compat.TokenInfo(type=CONTINUATION,
                                           string='\\',
                                           start=(prev_tok.start[0],
                                                  prev_tok.start[1] + 1),
                                           end=(prev_tok.end[0],
                                                prev_tok.end[0] + 2),
                                           line=prev_tok.line)
                ctok.lineno = ctok.start[0]
                ctok.column = ctok.start[1]
                ctok.value = '\\'
                cur_logical_line.append(
                    format_token.FormatToken(ctok, 'CONTINUATION'))
            tok.lineno = tok.start[0]
            tok.column = tok.start[1]
            tok.value = tok.string
            cur_logical_line.append(
                format_token.FormatToken(tok, token.tok_name[tok.type]))
        prev_tok = tok

    # Link the FormatTokens in each line together to for a doubly linked list.
    for line in logical_lines:
        previous = line.first
        bracket_stack = [previous] if previous.OpensScope() else []
        for tok in line.tokens[1:]:
            tok.previous_token = previous
            previous.next_token = tok
            previous = tok

            # Set up the "matching_bracket" attribute.
            if tok.OpensScope():
                bracket_stack.append(tok)
            elif tok.ClosesScope():
                bracket_stack[-1].matching_bracket = tok
                tok.matching_bracket = bracket_stack.pop()

    return logical_lines
def _MakeFormatTokenLeaf(token_type, token_value):
  return format_token.FormatToken(pytree.Leaf(token_type, token_value))
  def testIsImportStatement(self):
    tok = format_token.FormatToken(pytree.Leaf(token.NAME, 'import'))
    self.assertTrue(tok.is_import_keyword)

    tok = format_token.FormatToken(pytree.Leaf(token.STRING, "'import'"))
    self.assertFalse(tok.is_import_keyword)