Skip to content

feat(literalinclude): add negative line number indexing in :lines: option#14461

Open
jlaportebot wants to merge 1 commit into
sphinx-doc:masterfrom
jlaportebot:feat/literalinclude-negative-lines
Open

feat(literalinclude): add negative line number indexing in :lines: option#14461
jlaportebot wants to merge 1 commit into
sphinx-doc:masterfrom
jlaportebot:feat/literalinclude-negative-lines

Conversation

@jlaportebot
Copy link
Copy Markdown

Summary

The :lines: option of the literalinclude directive now supports negative line indices, mirroring Python's sequence indexing convention. This makes it much easier to include content relative to the end of a file without needing to know the exact line count.

Syntax

Negative indices use a double-dash to distinguish the range separator from the negative sign:

Spec Meaning
5--1 Lines 5 through the last line
-3--1 The last 3 lines
-1--1 The last line only
-3- From the 3rd-to-last line to the end
-8-5 From the 8th-to-last through line 5

A bare negative value like -5 retains its existing Sphinx meaning (lines 1 through 5) for backward compatibility. Use -5--1 to select the last five lines.

Implementation

  • Rewrote parse_line_num_spec() in sphinx/util/_lines.py with character-by-character parsing that correctly distinguishes range separator dashes from negative sign dashes
  • Added _resolve() helper to convert negative indices to 1-based positive offsets
  • Added _parse_part() for per-comma-part parsing with full negative support
  • Line number 0 is now explicitly rejected as invalid with a clear error message
  • Out-of-range negative indices raise ValueError with descriptive messages

Tests

All 47 tests in the relevant test files pass:

  • test_parse_line_num_spec — existing positive-index tests (unchanged)
  • test_parse_line_num_spec_negative_indices — core negative index tests
  • test_parse_line_num_spec_negative_edge_cases — edge cases (backward compat, out-of-range, mixed)
  • test_LiteralIncludeReader_lines_negative — directive-level negative line tests
  • test_LiteralIncludeReader_lines_negative_lineno_match — lineno-match compatibility
  • test_literal_include_negative_lines_build — full Sphinx build integration test

Existing test test_LiteralIncludeReader_lines_and_lineno_match2 updated to use valid line numbers (1,3,5 instead of 0,3,5) since 0 is now correctly rejected as an invalid line number.

Documentation

Updated doc/usage/restructuredtext/directives.rst with examples and a versionchanged:: 9.2 entry.


This PR was generated with the assistance of AI. All code has been tested locally and passes the existing test suite.

Support negative line indices in the :lines: option of the
literalinclude directive, mirroring Python's sequence indexing:

- '-1' refers to the last line, '-2' the second-to-last, etc.
- '5--1' selects lines 5 through the last line
- '-3--1' selects the last 3 lines
- '-3-' selects from the 3rd-to-last line to the end
- '-8-5' selects from the 8th-to-last through line 5

Backward compatibility is preserved: bare '-N' (e.g. '-5') retains its
existing meaning of 'lines 1 through N'. Use '-5--1' to select the
last five lines.

Line number 0 is now explicitly rejected as invalid with a clear error
message. Out-of-range negative indices raise ValueError.

Core changes:
- Rewrite parse_line_num_spec() with character-by-character parsing
  that correctly distinguishes range separator dashes from negative
  sign dashes (e.g. '5--1' = lines 5 to last, not range 5 to -1)
- Add _resolve() helper to convert negative indices to 1-based positive
- Add _parse_part() for per-comma-part parsing with full negative support
- Update docstring with negative indexing examples and semantics

Tests: 47 pass (3 new unit tests, 3 new directive tests, 1 integration
build test). Existing test for line number 0 updated to use valid
disjoint line numbers (1,3,5 instead of 0,3,5).

Co-authored-by: AI Assistant <ai@nousresearch.com>
@timhoffm
Copy link
Copy Markdown
Contributor

timhoffm commented Jun 1, 2026

For context: This tries to address #14453 but doesn't state it. Sensibility and format of the request are still under discussion, so I feel the PR is premature.

The PR seems to stem from an AI agent without human oversight.

@jdillard
Copy link
Copy Markdown
Member

jdillard commented Jun 1, 2026

There are a couple bots making PRs, in most cases this bot produces lower quality code in my opinion. Bots have already been banned from this org and wouldn't mind if this one got banned.

@jdillard jdillard linked an issue Jun 1, 2026 that may be closed by this pull request
@timhoffm
Copy link
Copy Markdown
Contributor

timhoffm commented Jun 2, 2026

@jdillard Should we add an AI policy to the project?

@jdillard
Copy link
Copy Markdown
Member

jdillard commented Jun 2, 2026

I'm not sure what that looks like exactly, but I think it's a good idea. This issue for a simple typo has 6 PRs, a lot of which aren't correct. I responded to a couple to see if there is a response.

I don't know if banning all bots is the answer, but having a human at the helm to guide the PR if there issues should be required.

edit: I created a discussion here: https://github.com/orgs/sphinx-doc/discussions/14463

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

literalinclude directive: support negative indexing

3 participants