Skip to content

Issue picker walks up to root, then descends sub-issue tree#449

Merged
FidoCanCode merged 1 commit into
mainfrom
picker-walks-up-sub-issue-tree
Apr 14, 2026
Merged

Issue picker walks up to root, then descends sub-issue tree#449
FidoCanCode merged 1 commit into
mainfrom
picker-walks-up-sub-issue-tree

Conversation

@FidoCanCode
Copy link
Copy Markdown
Owner

Summary

The old picker iterated directly-assigned issues and asked "are all sub-issues closed?" — which couldn't tell whether an assigned issue was actually next in its parent's order, and couldn't claim unassigned children that should land first.

New picker:

  1. For each assigned candidate, walk upward via `.parent` (via `gh.get_issue_node`) to the root ancestor. Dedupe roots.
  2. Rank roots: milestone-present first, then creation order of the first assigned descendant.
  3. Descend each root in GitHub sub-issue order:
    • child assigned to us → recurse
    • child unassigned → claim (assign self) + recurse
    • child assigned to someone else → blocked, skip branch
    • leaf with no open children → pick it
  4. If every open child at a level is blocked, the whole subtree is blocked; move to next root.

Claiming the unassigned chain on the way down means once a leaf's PR merges, each ancestor naturally becomes the next pick as its other children close out.

Also adds a generic `_graphql_paginate` helper so GraphQL connections (issues, subIssues) walk every page instead of silently truncating at the first 30/50 nodes.

Fixes #433

New API

  • `GitHub.get_sub_issues(owner, repo, number)` — paginated children
  • `GitHub.get_issue_node(owner, repo, number)` — picker-shaped issue (number, title, state, assignees, milestone, parent, subIssues)
  • `GitHub.add_assignee(repo, number, login)` — claim an issue

Test plan

  • 1688 tests pass, 100% coverage
  • New `TestPickNextIssue` suite covers the walk-up/descend algorithm (milestone priority, blocked siblings, claim-and-descend, root dedup, reason strings, cycle protection)
  • `TestGraphQLPaginate` covers cursor propagation across pages
  • Existing `TestWorkerFindNextIssue` tests rewritten for the new semantics

no more grabbing the parent when a child should land first

Fixes #433.  The old picker iterated directly-assigned issues and
asked "are all sub-issues closed" — which couldn't tell whether an
assigned issue was actually next in its parent's order, and couldn't
claim unassigned children that should land first.

New picker:

1. For each assigned candidate, walk upward via `.parent` (via
   `gh.get_issue_node`) to the root ancestor.  Dedupe roots.
2. Rank roots: milestone-present first, then creation order of the
   first assigned descendant.
3. Descend each root in GitHub sub-issue order:
   - child assigned to us → recurse
   - child unassigned → claim (assign self) + recurse
   - child assigned to someone else → blocked, skip branch
   - leaf with no open children → pick it
4. If every open child at a level is blocked, the whole subtree is
   blocked; move to next root.

Claiming the unassigned chain on the way down means once a leaf's
PR merges, each ancestor naturally becomes the next pick as its
other children close out.

Also adds a generic `_graphql_paginate` helper so GraphQL connections
(issues, subIssues) walk every page instead of silently truncating
at the first 30/50 nodes.  `find_issues` and `get_sub_issues` now
use it; `get_issue_node` hydrates via `get_sub_issues` when the
embedded first page has more.

New API surface:
- `GitHub.get_sub_issues(owner, repo, number)` — paginated children
- `GitHub.get_issue_node(owner, repo, number)` — picker-shaped issue
- `GitHub.add_assignee(repo, number, login)` — claim an issue

100% coverage, 1688 tests passing.
@FidoCanCode FidoCanCode merged commit 0964385 into main Apr 14, 2026
2 checks passed
@FidoCanCode FidoCanCode deleted the picker-walks-up-sub-issue-tree branch April 14, 2026 05:47
FidoCanCode added a commit that referenced this pull request Apr 14, 2026
Resolves conflicts from #449 (issue picker) landing on main:
- kennel/github.py: GH class retained (collapsed-client plan),
  dropped the now-obsolete GitHub wrapper class from main.  New
  methods from #449 (find_issues with cursor pagination,
  get_sub_issues, get_issue_node, add_assignee) are already on GH.
- tests/test_github.py: dropped wrapper delegation tests for the
  removed GitHub class; kept the direct GH-class tests for the
  new methods.
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.

Issue picker should descend into sub-issues before picking up parent

2 participants