Skip to main content
Glama
JigeeshaJain

gh-review-queue-mcp

by JigeeshaJain

gh-review-queue-mcp

Ein MCP-Server, der eine Frage beantwortet: Was soll ich als Nächstes reviewen?

Er stellt genau ein Tool bereit, get_review_queue, das eine sortierte, deduplizierte Ansicht deiner GitHub-Pull-Request-Review-Warteschlange zurückgibt — Reviews, die bei dir angefragt wurden, Reviews, die bei deinen Teams angefragt wurden, und deine eigenen Pull-Requests, die auf jemand anderen warten.

Ein Tool ist eine bewusste Einschränkung. Ein Assistent, der zwischen list_prs, search_prs und get_pr_status wählen muss, verbringt seinen ersten Zug mit der Auswahl; ein Assistent mit einem Tool, das eine bereits priorisierte Liste zurückgibt, kann einfach antworten.


Was es tatsächlich tut

Wenn das Tool aufgerufen wird, passieren vier Dinge in dieser Reihenfolge.

1. Dich und deine Teams identifizieren

Der Server stellt eine GraphQL-Abfrage für viewer { login } plus die Teams, zu denen du gehörst (organizations.teams(role: MEMBER)). Die Team-Slugs sind wichtig, weil die Such-API von GitHub keinen Qualifier für „bei einem meiner Teams angefragt" hat — du musst jedes Team explizit benennen. Das ist der einzige Grund, warum das Token den Bereich read:org benötigt.

2. Aufteilen in eine gebündelte Suche

GitHub hat keine einzelne Abfrage für „alles, was meine Aufmerksamkeit braucht", also führt der Server mehrere Suchen aus und kombiniert sie. Alle gehen in einem GraphQL-Dokument mit Aliasen raus, sodass es ein HTTP-Roundtrip ist, egal bei wie vielen Teams du bist:

Alias

Suche

Wird zu Grund

requested_of_me

is:pr is:open archived:false review-requested:@me

requested_of_me

my_pr_awaiting_review

is:pr is:open archived:false author:@me

my_pr_awaiting_review

team_0, team_1, …

is:pr is:open archived:false team-review-requested:<org>/<team>

requested_of_my_teams

Suchstrings werden als GraphQL-Variablen übergeben, nie in das Abfragedokument interpoliert, sodass ein Team-Slug die Abfrage nicht umformen kann.

Dieselbeine Abfrage fragt auch nach rateLimit { remaining resetAt }, sodass jede Antwort dein verbleibendes Budget ohne einen zweiten Aufruf melden kann.

Zwei Anmerkungen zur Antwortform. Die Suche search(type: ISSUE) von GitHub gibt Issues sowie Pull-Requests zurück; da das Auswahlset ein Inline-Fragment auf PullRequest ist, kommen Issues als leere Knoten zurück und werden beim Parsen verworfen. Und statusCheckRollup wird aus commits(last: 1) gelesen — der CI-Zustand des Head-Commits, nicht die gesamte Branch-Historie.

3. Zusammenführen, deduplizieren, filtern, sortieren

Derselbe Pull-Request kommt regelmäßig aus mehreren Suchen zurück — ein PR, bei dem du direkter Reviewer und dein Team angefragt ist, erscheint in zwei Buckets. Sie werden anhand der GraphQL-Knoten-ID dedupliziert, und die Gründe sammeln sich auf einem Eintrag, sodass die Antwort „das ist aus zwei Gründen hier" sagt, statt es zweimal aufzulisten.

Dann werden deine Filter angewendet, und was übrig bleibt, wird bewertet und sortiert.

4. Serialisieren

Die sortierte Liste kommt als strukturierte Ausgabe zurück — das Tool deklariert ein vollständiges JSON-Ausgabeschema, sodass ein Client typisierte Felder bekommt, nicht Prosa, die er parsen muss.


Related MCP server: github-ops-mcp

Wie die Sortierung funktioniert

Die Sortierung ist gestuft, nicht gewichtsoptimiert. Jeder Pull-Request landet in genau einer Stufe, und die Stufe ist deutlich mehr wert als alles, was sich innerhalb einer Stufe ansammelt:

Stufe

Bedingung

Basis

3

Eigener PR mit fehlgeschlagenem CI

300

2

Eigener PR mit angefragten Änderungen

200

1

Ein direkt bei dir angefragtes Review

100

0

Eine Team-Anfrage oder ein eigener PR, der einfach wartet

0

Innerhalb einer Stufe gelten zwei kleinere Signale:

  • Alter — 2 Punkte pro Tag seit dem Öffnen des PR, gedeckelt bei 20. Alte Review-Anfragen tauchen auf, aber ein sechs Monate alter PR kann nicht für immer dominieren.

  • Kleiner Diff — ein pauschaler Bonus von 8 Punkten für Diffs von 100 Zeilen oder weniger, nach der Theorie, dass ein kleines Review, das du jetzt abschließen kannst, besser ist als ein großes, das du aufschieben wirst.

Die Obergrenze ist der Kern. Das Maximum, das sich innerhalb einer Stufe ansammeln kann, ist 20 + 8 = 28, deutlich unter der Stufenschrittweite von 100, also gilt Stufendominanz per Konstruktion: Eine brandneue direkte Anfrage übertrifft immer eine uralte Team-Anfrage, und keine zukünftige Gewichtsoptimierung kann das still umdrehen. Wenn du ein Bewertungssignal hinzufügst, halte die Summe innerhalb der Stufe unter 100, sonst bricht diese Garantie.

Gleichstände werden nach der letzten Aktivität (updatedAt) aufgelöst, sodass eine aktive Diskussion einen gleichwertigen, aber stillstehenden Eintrag übertrifft.

Jedes Element trägt priority_reasons — menschenlesbare Strings wie ["my PR, CI failing", "3 days old"] — sodass die Sortierung dir erklärt werden kann, statt als unerklärte Zahl anzukommen.


Installation

Erfordert Python 3.11+ und uv.

git clone <this repo>
cd ReviewQueueMcp
uv sync

Token

Der Server liest ein persönliches Zugriffstoken von GitHub aus GITHUB_TOKEN:

cp .env.example .env      # then edit it
export GITHUB_TOKEN=ghp_...

Benötigte Bereiche:

  • repo — Pull-Requests in privaten Repositories lesen

  • read:org — deine Teammitgliedschaften lesen, für die team-review-requested-Suchen

Ein klassisches PAT ist am einfachsten. Feingranulare Tokens funktionieren, wenn „Pull requests: read" plus Organisationsmitglied-Lesezugriff gewährt wird. Erstelle eines unter https://github.com/settings/tokens.

GITHUB_GRAPHQL_URL überschreibt optional den Endpunkt für GitHub Enterprise Server.

Das Token wird pro Tool-Aufruf gelesen, nicht beim Start — der Server startet sauber ohne eines und gibt bei einem Aufruf einen umsetzbaren Fehler zurück, statt während des MCP-Handshakes zu sterben, wo der Client nur eine unterbrochene Pipe sehen würde.


Ausführen

uv run gh-review-queue-mcp

Es spricht MCP über stdio und erwartet einen Client am anderen Ende; direkt ausgeführt, wartet es einfach.

Mit MCP Inspector

npx @modelcontextprotocol/inspector uv --directory /absolute/path/to/ReviewQueueMcp run gh-review-queue-mcp

Öffne die gedruckte URL, verbinde dich, und das Tool erscheint unter Tools mit seinem generierten Eingabeschema.

Mit Claude Desktop

Füge zu claude_desktop_config.json hinzu — auf macOS unter ~/Library/Application Support/Claude/claude_desktop_config.json:

{
  "mcpServers": {
    "gh-review-queue": {
      "command": "uv",
      "args": [
        "--directory",
        "/absolute/path/to/ReviewQueueMcp",
        "run",
        "gh-review-queue-mcp"
      ],
      "env": {
        "GITHUB_TOKEN": "ghp_..."
      }
    }
  }
}

Pfade müssen absolut sein — Claude Desktop startet keine Server aus deiner Shell, hat also kein Arbeitsverzeichnis oder exportierte Umgebung, die es erben könnte. Starte Claude Desktop nach der Bearbeitung neu. Frag es dann: „Was soll ich heute reviewen?"


Tool-Referenz

get_review_queue

Alle Argumente sind optional.

Argument

Typ

Standard

Bedeutung

include

Array aus requested_of_me | requested_of_my_teams | my_pr_awaiting_review

alle drei

Welche Gründe einbezogen werden. Ein Element überlebt, wenn irgendeiner seiner Gründe enthalten ist.

exclude_drafts

boolean

true

Entwürfe verwerfen. Sie werden ausgeschlossen, nicht herabgestuft — ein Entwurf ist noch nicht reviewbar.

max_age_days

integer

keine

PRs verwerfen, die vor mehr als dieser Anzahl von Tagen geöffnet wurden. Inklusiv an der Grenze.

repos

Array von owner/name

keine

Auf diese Repositories beschränken. Exakte Übereinstimmung.

limit

integer 1–100

25

Maximale Anzahl zurückgegebener Elemente. total_matching meldet weiterhin die Gesamtzahl.

Antwort:

{
  "viewer": "octocat",
  "generated_at": "2026-08-20T12:00:00Z",
  "returned": 5,
  "total_matching": 5,
  "rate_limit_remaining": 4712,
  "warnings": [],
  "items": [
    {
      "repository": "acme/payments-api",
      "number": 4830,
      "title": "Add idempotency keys",
      "url": "https://github.com/acme/payments-api/pull/4830",
      "author": "octocat",
      "reasons": ["my_pr_awaiting_review"],
      "priority_score": 306.0,
      "priority_reasons": ["my PR, CI failing", "3 days old"],
      "age_days": 3.0,
      "diff_size": 374,
      "changed_files": 12,
      "is_draft": false,
      "review_decision": "REVIEW_REQUIRED",
      "ci_status": "FAILURE"
    }
  ]
}

returned vs. total_matching unterscheidet „hier sind 25" von „es gibt viele" — ohne das ist eine begrenzte Antwort nicht von einer vollständigen zu unterscheiden.

warnings trägt GraphQL-Teilfehler. GitHub kann brauchbare Daten zusammen mit Fehlern zurückgeben (eine Org nicht lesbar, eine Suche fehlschlagend); anstatt die gesamte Warteschlange zu verwerfen, werden diese zu Warnungen herabgestuft und der Rest der Ergebnisse kommt trotzdem zurück.


Architektur

Vier Module unter src/gh_review_queue/, und die Grenzen sind tragend:

server.py    MCP wiring. Parse arguments -> call client -> domain layer -> serialize.
   |         Deliberately thin; its docstring sets a ~120-line budget.
   v
github.py    The only module that touches the network. Builds GraphQL, handles HTTP
   |         and GraphQL errors, returns domain objects. Never ranks or filters.
   v
queue.py     Pure functions: merge -> apply_filters -> rank/score, via build_queue.
   |         Input is a snapshot and a clock. Nothing else.
   v
models.py    Frozen pydantic value objects. The only place GitHub's nested GraphQL
             shape is flattened. No network types.

Der Gewinn ist queue.py: Da es ein QueueSnapshot und ein datetime und sonst nichts nimmt, wird jede Sortierregel mit einfachen Daten getestet und ohne Mocks, ohne Netzwerk und ohne Uhren-Patching. Das ist der Grund für die Aufteilung und warum ein httpx-Import es nie erreichen darf.

Herabstufen statt Fehlschlagen

Unbekannte Enum-Werte von GitHub — ein neues reviewDecision, ein neuer CI-Rollup-Zustand — werden auf None abgebildet, statt einen Fehler zu werfen. Ein Zustand, der auf GitHub-Seite hinzugefügt wird, sollte nie deine gesamte Warteschlange brechen. Derselbe Instinkt zieht sich durch die Parsing-Schicht: Fehlende Autoren werden zu ghost (GitHubs eigene Konvention für gelöschte Konten), Nicht-PR-Suchergebnisse werden verworfen, und fehlende Zeitstempel sind der einzige wirklich nicht wiederherstellbare Fall, der einen Fehler wirft.


Entwicklung

uv run pytest                       # all tests
uv run pytest tests/test_queue.py   # one file
uv run pytest -k "rank or score"    # by name
uv run ruff check .                 # lint
uv run ruff format .                # format
uv run mypy                         # typecheck (strict)

Führe mypy nackt aus — es nimmt seine Ziele aus [tool.mypy] files in pyproject.toml, also prüft das Übergeben eines Pfads weniger als beabsichtigt.

Testansatz

Tests laufen mit tests/fixtures/queue_response.json, einer erfassten GraphQL-Antwort, die die schwierigen Fälle enthält: einen PR, der in zwei Buckets erscheint, einen Entwurf, einen sehr alten PR, einen PR des Viewers mit fehlgeschlagenem CI und einen Null-Status-Rollup.

test_rank_orders_the_fixture_the_way_a_reviewer_would_read_it prüft exakte Punktzahlen gegen eine feste Uhr. Es ist der Kanarienvogel für Sortieränderungen — wenn es fehlschlägt, entscheide, ob die neue Reihenfolge wirklich besser ist, bevor du die Zahlen aktualisierst.


Status

Phase

Umfang

Zustand

1

Gerüst, Paketierung, Tooling

erledigt

2

models.py, queue.py, Domänentests

erledigt

3

github.py GraphQL-Client, echte server.py

erledigt

4

Client- und Server-Tests

nicht gestartet

5

Dokumentation

diese Datei

Phase 3 ist Ende-zu-Ende verifiziert — ein echter MCP-stdio-Handshake, Tool-Erkennung und ein Tool-Aufruf — aber tests/test_server.py ist noch ein Platzhalter. Die Fehlerpfade des Clients (401, 403, partielle GraphQL-Fehler, nicht erreichbarer Host) sind geschrieben, aber noch nicht durch automatisierte Tests abgedeckt.# gh-review-queue-mcp

Ein MCP-Server, der eine Frage beantwortet: Was soll ich als Nächstes reviewen?

Er stellt genau ein Tool bereit, get_review_queue, das eine sortierte, deduplizierte Ansicht deiner GitHub-Pull-Request-Review-Warteschlange zurückgibt — Reviews, die bei dir angefragt wurden, Reviews, die bei deinen Teams angefragt wurden, und deine eigenen Pull-Requests, die auf jemand anderen warten.

Ein Tool ist eine bewusste Einschränkung. Ein Assistent, der zwischen list_prs, search_prs und get_pr_status wählen muss, verbringt seinen ersten Zug mit der Auswahl; ein Assistent mit einem Tool, das eine bereits priorisierte Liste zurückgibt, kann einfach antworten.


Was es tatsächlich tut

Wenn das Tool aufgerufen wird, passieren vier Dinge in dieser Reihenfolge.

1. Dich und deine Teams identifizieren

Der Server stellt eine GraphQL-Abfrage für viewer { login } plus die Teams, zu denen du gehörst (organizations.teams(role: MEMBER)). Die Team-Slugs sind wichtig, weil die Such-API von GitHub keinen Qualifier für „bei einem meiner Teams angefragt" hat — du musst jedes Team explizit benennen. Das ist der einzige Grund, warum das Token den Bereich read:org benötigt.

2. Aufteilen in eine gebündelte Suche

GitHub hat keine einzelne Abfrage für „alles, was meine Aufmerksamkeit braucht", also führt der Server mehrere Suchen aus und kombiniert sie. Alle gehen in einem GraphQL-Dokument mit Aliasen raus, sodass es ein HTTP-Roundtrip ist, egal bei wie vielen Teams du bist:

Alias

Suche

Wird zu Grund

requested_of_me

is:pr is:open archived:false review-requested:@me

requested_of_me

my_pr_awaiting_review

is:pr is:open archived:false author:@me

my_pr_awaiting_review

team_0, team_1, …

is:pr is:open archived:false team-review-requested:<org>/<team>

requested_of_my_teams

Suchstrings werden als GraphQL-Variablen übergeben, nie in das Abfragedokument interpoliert, sodass ein Team-Slug die Abfrage nicht umformen kann.

Dieselbe Abfrage fragt auch nach rateLimit { remaining resetAt }, sodass jede Antwort dein verbleibendes Budget ohne einen zweiten Aufruf melden kann.

Zwei Anmerkungen zur Antwortform. GitHubs search(type: ISSUE) gibt Issues sowie Pull-Requests zurück; da das Auswahlset ein Inline-Fragment auf PullRequest ist, kommen Issues als leere Knoten zurück und werden beim Parsen verworfen. Und statusCheckRollup wird aus commits(last: 1) gelesen — der CI-Zustand des Head-Commits, nicht die gesamte Branch-Historie.

3. Zusammenführen, deduplizieren, filtern, sortieren

Derselbe Pull-Request kommt regelmäßig aus mehreren Suchen zurück — ein PR, bei dem du direkter Reviewer und dein Team angefragt ist, erscheint in zwei Buckets. Sie werden anhand der GraphQL-Knoten-ID dedupliziert, und die Gründe sammeln sich auf einem Eintrag, sodass die Antwort sagt „das ist hier aus zwei Gründen" statt es zweimal aufzulisten.

Dann werden deine Filter angewendet, und was übrig bleibt, wird bewertet und sortiert.

4. Serialisieren

Die sortierte Liste kommt als strukturierte Ausgabe zurück — das Tool deklariert ein vollständiges JSON-Ausgabeschema, sodass ein Client typisierte Felder bekommt, nicht Prosa, die er parsen muss.


Wie die Sortierung funktioniert

Die Sortierung ist gestuft, nicht gewichtsoptimiert. Jeder Pull-Request landet in genau einer Stufe, und die Stufe ist deutlich mehr wert als alles, was sich innerhalb einer Stufe ansammelt:

Stufe

Bedingung

Basis

3

Eigener PR mit fehlgeschlagenem CI

300

2

Eigener PR mit angefragten Änderungen

200

1

Ein direkt bei dir angefragtes Review

100

0

Eine Team-Anfrage oder ein eigener PR, der einfach wartet

0

Innerhalb einer Stufe gelten zwei kleinere Signale:

  • Alter — 2 Punkte pro Tag seit dem Öffnen des PR, gedeckelt bei 20. Alte Review-Anfragen tauchen auf, aber ein sechs Monate alter PR kann nicht für immer dominieren.

  • Kleiner Diff — ein flacher 8-Punkte-Bonus für Diffs von 100 Zeilen oder weniger, nach der Theorie, dass ein kleines Review, das du jetzt abschließen kannst, ein großes schlägt, das du aufschieben wirst.

Die Obergrenze ist der Kern. Das Maximum, das sich innerhalb einer Stufe ansammeln kann, ist 20 + 8 = 28, deutlich unter der Stufenschrittweite von 100, also Stufendominanz gilt per Konstruktion: Eine brandneue direkte Anfrage übertrifft immer eine uralte Team-Anfrage, und keine zukünftige Gewichtsoptimierung kann das stillschweigend umkehren. Wenn du ein Bewertungssignal hinzufügst, halte die Summe innerhalb der Stufe unter 100, sonst bricht diese Garantie.

Gleichstände werden nach der neuesten Aktivität (updatedAt) aufgelöst, sodass eine aktive Diskussion einen gleichzeitig gestoppten Stand übertrifft.

Jedes Element trägt priority_reasons — menschenlesbare Strings wie ["my PR, CI failing", "3 days old"] — sodass die Sortierung dir erklärt werden kann, statt als unerklärte Zahl anzukommen.

Installation

Erfordert Python 3.11+ und uv.

git clone <this repo>
cd ReviewQueueMcp
uv sync

Token

Der Server liest ein persönliches Zugriffstoken von GitHub aus GITHUB_TOKEN:

cp .env.example .env      # then edit it
export GITHUB_TOKEN=ghp_...

Benötigte Bereiche:

  • repo — Pull-Requests in privaten Repositories lesen

  • read:org — deine Teammitgliedschaften lesen, für die Team-Review-Anfragen-Suchen

Ein klassisches PAT ist am einfachsten. Feingranulare Tokens funktionieren, wenn „Pull requests: read“ plus Organisationsmitglied-Lesezugriff gewährt wird. Erstelle eines unter https://github.com/settings/tokens.

GITHUB_GRAPHQL_URL überschreibt optional den Endpunkt für GitHub Enterprise Server.

Das Token wird pro Tool-Aufruf gelesen, nicht beim Start — der Server startet sauber ohne eines und gibt einen umsetzbaren Fehler zurück, wenn er aufgerufen wird, statt während des MCP-Handshakes zu sterben, wo der Client nur eine unterbrochene Verbindung sehen würde.

Ausführen

uv run gh-review-queue-mcp

Es spricht MCP über stdio und erwartet einen Client am anderen Ende; direkt ausgeführt, wartet es einfach.

Mit MCP Inspector

npx @modelcontextprotocol/inspector uv --directory /absolute/path/to/ReviewQueueMcp run gh-review-queue-mcp

Öffne die gedruckte URL, verbinde dich, und das Tool erscheint unter Tools mit seinem generierten Eingabeschema.

Mit Claude Desktop

Füge zu claude_desktop_config.json hinzu — auf macOS unter ~/Library/Application Support/Claude/claude_desktop_config.json:

{
  "mcpServers": {
    "gh-review-queue": {
      "command": "uv",
      "args": [
        "--directory",
        "/absolute/path/to/ReviewQueueMcp",
        "run",
        "gh-review-queue-mcp"
      ],
      "env": {
        "GITHUB_TOKEN": "ghp_..."
      }
    }
  }
}

Pfade müssen absolut sein — Claude Desktop startet keine Server aus deiner Shell, hat also kein Arbeitsverzeichnis oder exportierte Umgebung, die es erben kann. Starte Claude Desktop nach der Bearbeitung neu. Frag es dann: „Was soll ich heute reviewen?"

Tool-Referenz

get_review_queue

Alle Argumente sind optional.

Argument

Typ

Standard

Bedeutung

include

Array von requested_of_me | requested_of_my_teams | my_pr_awaiting_review

alle drei

Welche Gründe einbezogen werden. Ein Element überlebt, wenn irgendeiner seiner Gründe enthalten ist.

exclude_drafts

boolean

true

Entwürfe verwerfen. Sie werden ausgeschlossen, nicht herabgestuft — ein Entwurf ist noch nicht reviewbar.

max_age_days

integer

keine

PRs verwerfen, die vor mehr als dieser Anzahl von Tagen geöffnet wurden. Inklusiv an der Grenze.

repos

Array von owner/name

keine

Auf diese Repositories beschränken. Exakte Übereinstimmung.

limit

integer 1–100

25

Maximale Anzahl zurückgegebener Elemente. total_matching meldet weiterhin die Gesamtzahl.

Antwort:

{
  "viewer": "octocat",
  "generated_at": "2026-08-20T12:00:00Z",
  "returned": 5,
  "total_matching": 5,
  "rate_limit_remaining": 4712,
  "warnings": [],
  "items": [
    {
      "repository": "acme/payments-api",
      "number": 4830,
      "title": "Add idempotency keys",
      "url": "https://github.com/acme/payments-api/pull/4830",
      "author": "octocat",
      "reasons": ["my_pr_awaiting_review"],
      "priority_score": 306.0,
      "priority_reasons": ["my PR, CI failing", "3 days old"],
      "age_days": 3.0,
      "diff_size": 374,
      "changed_files": 12,
      "is_draft": false,
      "review_decision": "REVIEW_REQUIRED",
      "ci_status": "FAILURE"
    }
  ]
}

returned vs. total_matching unterscheidet „hier sind 25“ von „es gibt viele“ — ohne das ist eine begrenzte Antwort nicht von einer vollständigen zu unterscheiden.

warnings trägt GraphQL-Teilfehler. GitHub kann brauchbare Daten neben Fehlern zurückgeben (eine Org nicht lesbar, eine Suche fehlschlagend); anstatt die gesamte Warteschlange zu verwerfen, werden diese zu Warnungen herabgestuft und der Rest der Ergebnisse kommt trotzdem zurück.

Architektur

Vier Module unter src/gh_review_queue/, und die Grenzen sind tragend:

server.py    MCP wiring. Parse arguments -> call client -> domain layer -> serialize.
   |         Deliberately thin; its docstring sets a ~120-line budget.
   v
github.py    The only module that touches the network. Builds GraphQL, handles HTTP
   |         and GraphQL errors, returns domain objects. Never ranks or filters.
   v
queue.py     Pure functions: merge -> apply_filters -> rank/score, via build_queue.
   |         Input is a snapshot and a clock. Nothing else.
   v
models.py    Frozen pydantic value objects. The only place GitHub's nested GraphQL
             shape is flattened. No network types.

Der Gewinn ist queue.py: Da es ein QueueSnapshot und ein datetime und sonst nichts nimmt, wird jede Sortierregel mit einfachen Daten getestet und ohne Mocks, ohne Netzwerk und ohne Uhren-Patching. Das ist der Grund für die Aufteilung und warum ein httpx-Import es nie erreichen darf.

Herabstufen statt Fehlschlagen

Unbekannte Enum-Werte von GitHub — ein neues reviewDecision, ein neuer CI-Rollup-Zustand — werden auf None abgebildet, statt einen Fehler zu werfen. Ein Zustand, der auf GitHubs Seite hinzugefügt wird, sollte nie deine gesamte Warteschlange brechen. Derselbe Instinkt durchläuft die Parsing-Schicht: Fehlende Autoren werden zu ghost (GitHubs eigene Konvention für gelöschte Konten), Nicht-PR-Suchergebnisse werden verworfen, und fehlende Zeitstempel sind der einzige wirklich nicht wiederherstellbare Fall, der einen Fehler wirft.

Entwicklung

uv run pytest                       # all tests
uv run pytest tests/test_queue.py   # one file
uv run pytest -k "rank or score"    # by name
uv run ruff check .                 # lint
uv run ruff format .                # format
uv run mypy                         # typecheck (strict)

Führe mypy nackt aus — es nimmt seine Ziele aus [tool.mypy] files in pyproject.toml, also prüft das Übergeben eines Pfads weniger als beabsichtigt.

Testansatz

Tests laufen mit tests/fixtures/queue_response.json, einer erfassten GraphQL-Antwort, die die schwierigen Fälle enthält: einen PR, der in zwei Buckets erscheint, einen Entwurf, einen sehr alten PR, einen PR des Viewers mit fehlgeschlagenem CI und einen Null-Status-Rollup.

test_rank_orders_the_fixture_the_way_a_reviewer_would_read_it prüft exakte Punktzahlen gegen eine feste Uhr. Es ist der Kanarienvogel für Sortieränderungen — wenn es fehlschlägt, entscheide, ob die neue Reihenfolge wirklich besser ist, bevor du die Zahlen aktualisierst.

Status

Phase

Umfang

Zustand

1

Gerüst, Paketierung, Tooling

erledigt

2

models.py, queue.py, Domänentests

erledigt

3

github.py GraphQL-Client, echte server.py

erledigt

4

Client- und Server-Tests

nicht gestartet

5

Dokumentation

diese Datei

Phase 3 ist Ende-zu-Ende verifiziert — ein echter MCP-stdio-Handshake, Tool-Erkennung und ein Tool-Aufruf — aber tests/test_server.py ist noch ein Platzhalter. Die Fehlerpfade des Clients (401, 403, partielle GraphQL-Fehler, unerreichbarer Host) sind geschrieben, aber noch nicht durch automatisierte Tests abgedeckt.

F
license - not found
Not graded
quality - not tested
C
maintenance

Maintenance

Maintainers
Response time
Release cycle
Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Servers

View all related MCP servers

Related MCP Connectors

  • A Model Context Protocol (MCP) application for automated GitHub PR analysis and issue management.…

  • An MCP server that gives your AI access to the source code and docs of all public github repos

  • A MCP server built for developers enabling Git based project management with project and personal…

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/JigeeshaJain/ReviewQueueMcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server