Beispiel #1
0
def pyls_lint(config: Config, workspace: Workspace, document: Document,
              is_saved: bool) -> List[Dict[str, Any]]:
    """
    Lints.

    Parameters
    ----------
    config : Config
        The pyls config.
    workspace : Workspace
        The pyls workspace.
    document : Document
        The document to be linted.
    is_saved : bool
        Weather the document is saved.

    Returns
    -------
    List[Dict[str, Any]]
        List of the linting data.

    """
    settings = config.plugin_settings('pyls_mypy')
    live_mode = settings.get('live_mode', True)
    args = settings.get('args', [])
    args.extend([
        '--incremental', '--show-column-numbers', '--follow-imports', 'silent'
    ])

    global tmpFile
    if live_mode and not is_saved and tmpFile:
        tmpFile = open(tmpFile.name, "w")
        tmpFile.write(document.source)
        tmpFile.close()
        args.extend(['--shadow-file', document.path, tmpFile.name])
    elif not is_saved:
        return []

    if mypyConfigFile:
        args.append('--config-file')
        args.append(mypyConfigFile)
    args.append(document.path)
    if settings.get('strict', False):
        args.append('--strict')

    report, errors, _ = mypy_api.run(args)

    diagnostics = []
    for line in report.splitlines():
        diag = parse_line(line, document)
        if diag:
            diagnostics.append(diag)

    return diagnostics
Beispiel #2
0
def pyls_document_symbols(config: Config, workspace: Workspace,
                          document: Document) -> List[Dict]:
    """Cell and block comment extraction."""

    settings = config.plugin_settings('pyls_spyder')
    group_cells = settings.get('group_cells', True)
    enable_block_comments = settings.get('enable_block_comments', True)
    lines = document.lines
    cells = []
    blocks = []

    cell_stack = []
    unnamed_cell = 1
    unnamed_block = 1

    for line_num, line in enumerate(lines):
        cell_rule, cell_match = CELL_REGEX.match(line)
        block_rule, block_match = BLOCK_REGEX.match(line)

        if cell_match is not None:
            percentages = cell_match.group(1)
            cell_name = cell_match.group(2).strip()

            if cell_name == '':
                cell_name = 'Unnamed cell {0}'.format(unnamed_cell)
                unnamed_cell += 1

            if not group_cells or cell_rule != CELL_PERCENTAGE:
                cells.append(
                    create_symbol(cell_name, document, line_num, line_num + 1))
            else:
                current_line, current_level, current_name = peek_symbol(
                    cell_stack)
                cell_level = len(percentages) - 1
                if cell_level > current_level:
                    cell_stack.insert(0, (line_num, cell_level, cell_name))
                else:
                    while current_level >= cell_level:
                        cell_stack.pop(0)
                        cells.append(
                            create_symbol(current_name, document, current_line,
                                          line_num))
                        (current_line, current_level,
                         current_name) = peek_symbol(cell_stack)
                    cell_stack.insert(0, (line_num, cell_level, cell_name))
        elif block_match is not None and enable_block_comments:
            block_name = block_match.group(1).strip()
            if block_name == '':
                block_name = 'Unnamed comment {0}'.format(unnamed_block)
                unnamed_block += 1
            blocks.append(
                create_symbol(block_name, document, line_num, line_num + 1,
                              False))

    for line, _, name in cell_stack:
        cells.append(create_symbol(name, document, line, line_num + 1))

    spyder_symbols = cells + blocks
    spyder_symbols = sorted(
        spyder_symbols, key=lambda x: x['location']['range']['start']['line'])
    return spyder_symbols
Beispiel #3
0
def pyls_lint(config: Config, workspace: Workspace, document: Document,
              is_saved: bool) -> List[Dict[str, Any]]:
    """
    Lints.

    Parameters
    ----------
    config : Config
        The pyls config.
    workspace : Workspace
        The pyls workspace.
    document : Document
        The document to be linted.
    is_saved : bool
        Weather the document is saved.

    Returns
    -------
    List[Dict[str, Any]]
        List of the linting data.

    """
    settings = config.plugin_settings('mypy-ls')
    log.info(
        "lint settings = %s document.path = %s is_saved = %s",
        settings,
        document.path,
        is_saved
    )

    live_mode = settings.get('live_mode', True)
    dmypy = settings.get("dmypy", False)

    if dmypy and live_mode:
        # dmypy can only be efficiently run on files that have been saved, see:
        # https://github.com/python/mypy/issues/9309
        log.warning("live_mode is not supported with dmypy, disabling")
        live_mode = False

    args = ['--show-column-numbers']

    prepend = settings.get('prepend')
    if prepend:
        args = prepend + args

    modified_time = os.path.getmtime(document.path)

    global tmpFile
    if live_mode and not is_saved and tmpFile:
        log.info("live_mode tmpFile = %s", live_mode)
        tmpFile = open(tmpFile.name, "w")
        tmpFile.write(document.source)
        tmpFile.close()
        args.extend(['--shadow-file', document.path, tmpFile.name])
    elif (
        not is_saved
        and document.path in last_diagnostics
        and last_updated[document.path] == modified_time
    ):
        # On-launch the document isn't marked as saved, so fall through and run
        # the diagnostics anyway even if the file contents may be out of date.
        log.info(
            "non-live, returning cached diagnostics len(cached) = %s",
            last_diagnostics[document.path]
        )
        return last_diagnostics[document.path]

    last_updated[document.path] = modified_time

    if mypyConfigFile:
        args.append('--config-file')
        args.append(mypyConfigFile)

    args.append(document.path)

    if settings.get('strict', False):
        args.append('--strict')

    if not dmypy:
        args.extend([
            "--incremental",
            "--follow-imports",
            "silent"
        ])

        log.info(f"executing mypy {args=}")
        report, errors, _ = mypy_api.run(args)
    else:
        args = ["run", "--"] + args

        log.info(f"executing dmypy {args=}")
        report, errors, _ = mypy_api.run_dmypy(args)

    log.debug("report: \n" + report)
    log.debug("errors: \n" + errors)

    diagnostics = []
    for line in report.splitlines():
        log.debug(f"parsing: {line=}")
        diag = parse_line(line, document)
        if diag:
            diagnostics.append(diag)

    logging.info("mypy-ls len(diagnostics) = %s", len(diagnostics))

    last_diagnostics[document.path] = diagnostics
    return diagnostics