Skip to content

Enhancement: Switch all indexing to use rich - #12193

Merged
stumpylog merged 5 commits into
devfrom
feature-switch-indexing-to-rich
Mar 2, 2026
Merged

Enhancement: Switch all indexing to use rich#12193
stumpylog merged 5 commits into
devfrom
feature-switch-indexing-to-rich

Conversation

@stumpylog

@stumpylog stumpylog commented Feb 27, 2026

Copy link
Copy Markdown
Member

Proposed change

Switches the 2 indexing commands to use rich and decouple the progress bar from the core logic. Uses the same idea as #12182, where the iteration is either tracked with progress or simply just the iterable. Once things are settle more, _identity can become something shared.

Closes #(issue or discussion)

Type of change

  • Bug fix: non-breaking change which fixes an issue.
  • New feature / Enhancement: non-breaking change which adds functionality. Please read the important note above.
  • Breaking change: fix or feature that would cause existing functionality to not work as expected.
  • Documentation only.
  • Other. Please explain:

Checklist:

  • I have read & agree with the contributing guidelines.
  • If applicable, I have included testing coverage for new code in this PR, for backend and / or front-end changes.
  • If applicable, I have tested my code for breaking changes & regressions on both mobile & desktop devices, using the latest version of major browsers.
  • If applicable, I have checked that all tests pass, see documentation.
  • I have run all Git pre-commit hooks, see documentation.
  • I have made corresponding changes to the documentation as needed.
  • In the description of the PR above I have disclosed the use of AI tools in the coding of this PR.

@github-actions github-actions Bot added enhancement New feature or enhancement backend non-trivial Requires approval by several team members labels Feb 27, 2026
@codecov

codecov Bot commented Feb 27, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 76.66667% with 7 lines in your changes missing coverage. Please review.
✅ Project coverage is 98.13%. Comparing base (62efb40) to head (f49406a).
⚠️ Report is 4 commits behind head on dev.
✅ All tests successful. No failed tests found.

Files with missing lines Patch % Lines
...documents/management/commands/document_llmindex.py 0.00% 7 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##              dev   #12193      +/-   ##
==========================================
+ Coverage   98.12%   98.13%   +0.01%     
==========================================
  Files         454      454              
  Lines       25896    25903       +7     
  Branches     2259     2203      -56     
==========================================
+ Hits        25410    25420      +10     
+ Misses        486      483       -3     
Components Coverage Δ
backend 97.15% <76.66%> (+0.02%) ⬆️
frontend 99.18% <ø> (ø)
Flag Coverage Δ
backend-python-3.10 97.15% <76.66%> (+0.02%) ⬆️
backend-python-3.11 97.13% <76.66%> (+0.02%) ⬆️
backend-python-3.12 97.13% <76.66%> (+0.02%) ⬆️
frontend-node-24.x 99.18% <ø> (ø)

Flags with carried forward coverage won't be shown. Click here to find out more.

Files with missing lines Coverage Δ
...rc/documents/management/commands/document_index.py 100.00% <100.00%> (ø)
src/documents/tasks.py 97.27% <100.00%> (+0.04%) ⬆️
src/paperless/views.py 99.03% <ø> (ø)
src/paperless_ai/indexing.py 98.67% <100.00%> (+0.05%) ⬆️
...documents/management/commands/document_llmindex.py 0.00% <0.00%> (ø)

@shamoon shamoon added this to the v3.0.0 milestone Feb 28, 2026
@paperless-ngx paperless-ngx deleted a comment from ainsleff Mar 2, 2026
@stumpylog

Copy link
Copy Markdown
Member Author

Unless I'm missing something, we didn't test document_llmindex anyway. Makes sense, given it is quite basic. I could #pragma it out I suppose, but otherwise, ready to go.

@stumpylog
stumpylog marked this pull request as ready for review March 2, 2026 16:36
@stumpylog
stumpylog requested a review from a team as a code owner March 2, 2026 16:36
@shamoon

shamoon commented Mar 2, 2026

Copy link
Copy Markdown
Member

Cool, Im testing the other one now and will do this too, I'll leave the decision about e.g. copilot reviews to you

@shamoon

shamoon commented Mar 2, 2026

Copy link
Copy Markdown
Member

Oh wait, I think you said you did them already 👍

@shamoon shamoon left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This one LGTM!

Indexing documents... ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 63/63 0:00:00 0:00:00
Indexing documents... ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 63/63 0:00:01 0:00:00

(llmindex looks exactly the same as regular one =)

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR transitions the document and LLM indexing flows away from tqdm and toward rich progress output, by injecting progress tracking via an iterable wrapper instead of coupling progress bars to the core indexing loops.

Changes:

  • Replace tqdm usage in indexing loops with an iter_wrapper callable that can either track progress (CLI) or act as a no-op (tasks/API).
  • Update the document_index and document_llmindex management commands to use PaperlessCommand.track() (rich) for progress display.
  • Update call sites to match the new indexing/task function signatures (remove progress_bar_disable).

Reviewed changes

Copilot reviewed 5 out of 5 changed files in this pull request and generated no comments.

Show a summary per file
File Description
src/paperless_ai/indexing.py Adds a generic iterable wrapper hook to update_llm_index and removes tqdm usage.
src/paperless/views.py Updates the async LLM index trigger call to match the updated task signature.
src/documents/tasks.py Adds iterable wrapper hooks to reindexing and LLM indexing task flow; removes tqdm usage in reindexing.
src/documents/management/commands/document_llmindex.py Switches to PaperlessCommand and uses self.track() to provide rich progress for LLM indexing.
src/documents/management/commands/document_index.py Switches to PaperlessCommand and uses self.track() to provide rich progress for Whoosh reindexing.
Comments suppressed due to low confidence (3)

src/documents/tasks.py:610

  • llmindex_index is a Celery task, but it now exposes an iter_wrapper parameter that is meant to be a Python callable. With the current Celery pickle serializer, only certain callables are picklable (typically top-level functions); lambdas/closures/bound methods (like self.track) won’t serialize reliably, so passing this via .delay() would likely break at runtime. Consider keeping the task signature strictly serializable and moving iter_wrapper to a non-task helper (task calls helper with _identity, management commands call helper with self.track).
def llmindex_index(
    *,
    iter_wrapper: IterWrapper[Document] = _identity,
    rebuild=False,
    scheduled=True,
    auto=False,
) -> None:

src/paperless_ai/indexing.py:40

  • IterWrapper/_identity are introduced here, but the same generic wrapper + identity function are also defined in src/documents/tasks.py. Duplicating these utilities across modules increases the chance they’ll drift (e.g., different typing/behavior). Consider moving this type alias + helper into a small shared module (or re-exporting from one place) so both indexing paths use the same definition.
_T = TypeVar("_T")
IterWrapper = Callable[[Iterable[_T]], Iterable[_T]]


def _identity(iterable: Iterable[_T]) -> Iterable[_T]:
    return iterable

src/documents/tasks.py:82

  • IterWrapper and _identity are now defined in this module, but equivalent definitions were also added in paperless_ai/indexing.py. To avoid divergence over time (typing tweaks, behavior changes), consider centralizing this wrapper type + identity function in a shared utility module and importing it in both places.
_T = TypeVar("_T")
IterWrapper = Callable[[Iterable[_T]], Iterable[_T]]


if settings.AUDIT_LOG_ENABLED:
    from auditlog.models import LogEntry
logger = logging.getLogger("paperless.tasks")


def _identity(iterable: Iterable[_T]) -> Iterable[_T]:
    return iterable


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

@stumpylog
stumpylog force-pushed the feature-switch-indexing-to-rich branch from 3dd4064 to f49406a Compare March 2, 2026 18:28
@sonarqubecloud

sonarqubecloud Bot commented Mar 2, 2026

Copy link
Copy Markdown

@stumpylog
stumpylog merged commit 20a9cd4 into dev Mar 2, 2026
31 checks passed
@stumpylog
stumpylog deleted the feature-switch-indexing-to-rich branch March 2, 2026 18:41
@shamoon shamoon changed the title Feature: Switch all indexing to use rich Enhancement: Switch all indexing to use rich Mar 4, 2026
@github-actions

github-actions Bot commented Apr 4, 2026

Copy link
Copy Markdown
Contributor

This pull request has been automatically locked since there has not been any recent activity after it was closed. Please open a new discussion or issue for related concerns. See our contributing guidelines for more details.

@github-actions github-actions Bot locked as resolved and limited conversation to collaborators Apr 4, 2026
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

backend enhancement New feature or enhancement non-trivial Requires approval by several team members

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants