Skip to content

feat: use graphql for querying#73

Open
MiyakoMeow wants to merge 7 commits intoScoopInstaller:mainfrom
MiyakoMeow:feat-use-graphql
Open

feat: use graphql for querying#73
MiyakoMeow wants to merge 7 commits intoScoopInstaller:mainfrom
MiyakoMeow:feat-use-graphql

Conversation

@MiyakoMeow
Copy link
Copy Markdown

@MiyakoMeow MiyakoMeow commented Mar 3, 2026

Summary by CodeRabbit

  • New Features
    • GraphQL-first fetching with retries and REST fallback, plus parallel GraphQL query execution for faster multi-request operations.
  • Bug Fixes / Behavior
    • Safer PR and branch workflow: check branch protection, prefer creating PRs when needed, otherwise push fixes directly; PR selection now considers title and base branch.
  • Improvements
    • Improved logging, rate-limit handling, and conservative fallbacks for reliable operation.

@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Mar 3, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review

Walkthrough

Adds GraphQL client functions to the GitHub module and updates the Issue action to prefer GraphQL (with REST fallback) for fetching default branch, open PRs, and rate-limit data; adds guarded branch-protection checks and adjusts branch/PR creation versus direct pushes.

Changes

Cohort / File(s) Summary
GraphQL API Layer
src/Github.psm1
Added Invoke-GithubGraphQL (GraphQL query, retries, auth, rate-limit/backoff, request counting) and Invoke-GithubGraphQLParallel (parallel runspace queries, aggregated results/errors). Exported both functions via Export-ModuleMember.
Issue Processing Integration
src/Action/Issue.psm1
Imported Github.psm1; replaced REST-first repo/PR retrieval with GraphQL-first (with parallel attempts) and REST fallback; introduced GraphQL-driven hash-mismatch flow; updated PR selection to filter by title and baseRefName; added guarded branch-protection check and conditional flow to create branch+PR only when default branch is protected (otherwise push directly); preserved hash verification and issue commenting.

Sequence Diagram(s)

sequenceDiagram
    participant Issue as Issue Handler
    participant GQL as Invoke-GithubGraphQL
    participant GitHubGQL as GitHub GraphQL API
    participant REST as GitHub REST API

    Issue->>GQL: Query defaultBranchRef, open PRs, rateLimit (parallel)
    activate GQL
    GQL->>GitHubGQL: Send GraphQL request(s)
    activate GitHubGQL

    alt GraphQL success
        GitHubGQL-->>GQL: Repo data, PRs, rateLimit
        GQL-->>Issue: Return data
    else GraphQL failure / partial
        GitHubGQL-->>GQL: Error(s)
        GQL-->>Issue: Indicate fallback
        Issue->>REST: Fetch default_branch, PRs, branch protection
        REST-->>Issue: REST responses
    end
    deactivate GitHubGQL
    deactivate GQL
Loading
sequenceDiagram
    participant Issue as Issue Handler
    participant Git as Git operations
    participant REST as GitHub REST API

    Issue->>Issue: Determine masterBranch & PRs (GQL or REST)
    alt Existing PR found (title + baseRefName)
        Issue->>REST: Update PR body/labels/comments
    else No PR found
        Issue->>REST: Check branch protection (guarded)
        alt Default branch protected
            Issue->>Git: Create branch & push fixes
            Git->>REST: Create PR from branch
        else Default branch unprotected
            Issue->>Git: Push fixes directly to default branch
        end
    end
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Poem

🐇 I nibbled at GraphQL rails tonight,
Parallel hops and retries took flight.
When queries wobble, REST lends a paw,
Branches stitched, PRs in awe.
A carrot commit — hop, push, delight!

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'feat: use graphql for querying' accurately describes the main changes: introducing GraphQL querying functionality alongside REST APIs with fallback patterns across Issue.psm1 and Github.psm1.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 5

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/Action/Issue.psm1`:
- Around line 4-40: The Invoke-GithubGraphQLQuery function duplicates existing
Invoke-GithubGraphQL (from Github.psm1) and lacks its retry/rate-limit handling;
remove Invoke-GithubGraphQLQuery and update all local callers to call
Invoke-GithubGraphQL instead, ensuring Helpers.psm1 (which imports/exports
Invoke-GithubGraphQL) is available in this module; verify parameter names/shape
match (pass the same $Query and $Variables, and JSON body handling) and preserve
the original return semantics (response object and GH_REQUEST_COUNTER increment)
or rely on the shared function's counter behavior so you don't lose
retry/rate-limit logic.
- Line 148: The pull request listing call in Invoke-GithubRequest is using the
wrong query parameter name "sorting"; update the request URL in the
Invoke-GithubRequest invocation that assigns $prs so the query uses
"sort=updated" (e.g.
"repos/$REPOSITORY/pulls?state=open&base=$masterBranch&sort=updated") to ensure
GitHub respects the sort order; keep the same variables ($REPOSITORY,
$masterBranch) and the rest of the ConvertFrom-Json handling unchanged.

In `@src/Github.psm1`:
- Around line 500-501: The Export-ModuleMember line uses a backtick for line
continuation but has a trailing space after the backtick which escapes the space
instead of continuing the line; edit the Export-ModuleMember declaration (the
line containing Export-ModuleMember -Function Invoke-GithubRequest,
Invoke-GithubGraphQL, Invoke-GithubGraphQLParallel, Add-Comment,
Get-AllChangedFilesInPR, New-Issue, Close-Issue, ` Add-Label, Remove-Label,
Get-RateLimit, Get-JobID, Get-LogURL) and remove the whitespace after the
backtick so the backtick is the final character on the line (or alternatively
remove the backtick and place a comma at the end of the first line and continue
on the next), ensuring proper PowerShell line continuation.
- Around line 18-24: Remove the unused parameter $UseFallback from the
param(...) list (or implement its fallback logic if intended), and ensure
pipeline input is handled by wrapping the function body in a process { ... }
block so items passed via ValueFromPipeline on the [String] $Query parameter are
processed per-item; alternatively, if pipeline behavior is not desired, remove
ValueFromPipeline from the [String] $Query declaration instead.
- Around line 145-151: The per-runspace increment of $env:GH_REQUEST_COUNTER
inside the Invoke-WebRequest try/catch block won’t affect the parent process;
remove the line that increments $env:GH_REQUEST_COUNTER from inside that
scriptblock (the try where Invoke-WebRequest `@parameters` is called) and instead,
after all runspaces/jobs complete, aggregate results (e.g., count successful
responses from the collected results array) and update the parent environment
variable once: set $env:GH_REQUEST_COUNTER = ([int]$env:GH_REQUEST_COUNTER) +
$successfulCount. Ensure the returned objects from the runspaces still include
Success so you can sum them before updating the counter.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 31b5ce6 and a8b0427.

📒 Files selected for processing (2)
  • src/Action/Issue.psm1
  • src/Github.psm1

Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 3

♻️ Duplicate comments (2)
src/Github.psm1 (2)

19-23: ⚠️ Potential issue | 🟡 Minor

Handle pipeline input correctly for Query.

Query is declared with ValueFromPipeline but there is no process {} block, so piped input is not processed per-item (see Line [19]). Either add process or remove ValueFromPipeline.

Suggested fix
 param(
-    [Parameter(Mandatory, ValueFromPipeline)]
+    [Parameter(Mandatory)]
     [String] $Query,
     [Hashtable] $Variables,
     [Int] $MaxRetries = 3
 )
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Github.psm1` around lines 19 - 23, The parameter $Query is marked
ValueFromPipeline but the function lacks a process block, so piped values won't
be handled per-item; either remove ValueFromPipeline from the [Parameter()] for
$Query or add a process { ... } block to handle each piped input (set local
$Query from $_ or $PSBoundParameters['Query'] and run the existing logic per
item). Update the function that declares the parameters (the function containing
[String] $Query, [Hashtable] $Variables, [Int] $MaxRetries) accordingly so
pipeline input is processed correctly.

11-12: ⚠️ Potential issue | 🟡 Minor

Comment-based help is stale (UseFallback).

.PARAMETER UseFallback is documented but the parameter does not exist in this function signature, so Get-Help is now misleading.

Suggested fix
-    .PARAMETER UseFallback
-        If set, falls back to REST API on GraphQL failure.
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Github.psm1` around lines 11 - 12, The comment-based help in Github.psm1
documents a non-existent parameter `.PARAMETER UseFallback`; remove that
`.PARAMETER UseFallback` entry from the help block (or alternatively add a real
parameter named UseFallback and wire it into the function logic if fallback
behavior is intended) so Get-Help matches the function signature; search for the
comment-based help block in Github.psm1 and either delete the UseFallback
parameter stanza or implement a UseFallback parameter and its handling where the
function (the GitHub-related function in this module) performs GraphQL and
should fall back to REST.
🧹 Nitpick comments (1)
src/Github.psm1 (1)

160-178: Always dispose runspacePool even if aggregation fails.

If EndInvoke() throws during job collection, execution can exit before Line [177]-Line [178]. Wrap collection/counter update in an outer try/finally for guaranteed cleanup.

Suggested refactor
-foreach ($job in $jobs) {
-    try {
-        $result = $job.PowerShell.EndInvoke($job.AsyncResult)
-        if ($result.Success) {
-            $results += $result.Data
-        } else {
-            Write-Log "Parallel query failed: $($result.Error)"
-            $errors += @{ Query = $job.Query; Error = $result.Error }
-        }
-    } finally {
-        $job.PowerShell.Dispose()
-    }
-}
-
-# Update parent process counter after all runspaces complete
-$env:GH_REQUEST_COUNTER = ([int]$env:GH_REQUEST_COUNTER) + $results.Count
-
-$runspacePool.Close()
-$runspacePool.Dispose()
+try {
+    foreach ($job in $jobs) {
+        try {
+            $result = $job.PowerShell.EndInvoke($job.AsyncResult)
+            if ($result.Success) {
+                $results += $result.Data
+            } else {
+                Write-Log "Parallel query failed: $($result.Error)"
+                $errors += @{ Query = $job.Query; Error = $result.Error }
+            }
+        } finally {
+            $job.PowerShell.Dispose()
+        }
+    }
+
+    # Update parent process counter after all runspaces complete
+    $env:GH_REQUEST_COUNTER = ([int]$env:GH_REQUEST_COUNTER) + $results.Count
+}
+finally {
+    $runspacePool.Close()
+    $runspacePool.Dispose()
+}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Github.psm1` around lines 160 - 178, The current job collection loop can
throw from $job.PowerShell.EndInvoke which may skip calling
$runspacePool.Close() and $runspacePool.Dispose(); wrap the entire aggregation
phase (the foreach loop that calls $job.PowerShell.EndInvoke and the update to
$env:GH_REQUEST_COUNTER) in an outer try/finally so that $runspacePool.Close()
and $runspacePool.Dispose() are always executed in the finally block regardless
of errors; ensure you still dispose each $job.PowerShell in its inner finally
and preserve collecting $results and $errors as before.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/Action/Issue.psm1`:
- Around line 140-145: The catch block that handles failures from
Invoke-GithubRequest currently forces $isProtected = $false which allows direct
pushes; change it so failures assume the branch is protected: in the catch for
the Invoke-GithubRequest call (the block that logs via Write-Log), set
$isProtected = $true (or another sentinel treated as protected) and adjust the
log message to reflect that protection status is unknown and we will default to
protected to enforce PR-based flow; ensure any downstream checks that read
$isProtected (and variable masterBranch) treat this default as protected.
- Around line 77-83: The GraphQL pullRequests node must include the base branch
field and the PR selection must also verify that base branch matches the target;
add baseRefName to the pullRequests nodes in the GraphQL query and update the
filter that selects $prs (the Where-Object that currently checks $_.title -eq
$titleToBePosted) to require both title equality and that the PR base equals
$masterBranch by checking either $_.baseRefName or the existing $_.base.ref
against $masterBranch.

In `@src/Github.psm1`:
- Around line 144-149: Remove the unreachable duplicate "return @{ Success =
$true; Data = $response }" and add GraphQL error handling after
Invoke-WebRequest: parse $response.Content as JSON and if it contains a
non-empty "errors" array set and return @{ Success = $false; Error = <serialize
errors> } (and populate/merge into the existing $errors used by the parallel
worker) instead of marking success for any HTTP 200; keep the existing catch to
return @{ Success = $false; Error = $_.Exception.Message } for transport errors.

---

Duplicate comments:
In `@src/Github.psm1`:
- Around line 19-23: The parameter $Query is marked ValueFromPipeline but the
function lacks a process block, so piped values won't be handled per-item;
either remove ValueFromPipeline from the [Parameter()] for $Query or add a
process { ... } block to handle each piped input (set local $Query from $_ or
$PSBoundParameters['Query'] and run the existing logic per item). Update the
function that declares the parameters (the function containing [String] $Query,
[Hashtable] $Variables, [Int] $MaxRetries) accordingly so pipeline input is
processed correctly.
- Around line 11-12: The comment-based help in Github.psm1 documents a
non-existent parameter `.PARAMETER UseFallback`; remove that `.PARAMETER
UseFallback` entry from the help block (or alternatively add a real parameter
named UseFallback and wire it into the function logic if fallback behavior is
intended) so Get-Help matches the function signature; search for the
comment-based help block in Github.psm1 and either delete the UseFallback
parameter stanza or implement a UseFallback parameter and its handling where the
function (the GitHub-related function in this module) performs GraphQL and
should fall back to REST.

---

Nitpick comments:
In `@src/Github.psm1`:
- Around line 160-178: The current job collection loop can throw from
$job.PowerShell.EndInvoke which may skip calling $runspacePool.Close() and
$runspacePool.Dispose(); wrap the entire aggregation phase (the foreach loop
that calls $job.PowerShell.EndInvoke and the update to $env:GH_REQUEST_COUNTER)
in an outer try/finally so that $runspacePool.Close() and
$runspacePool.Dispose() are always executed in the finally block regardless of
errors; ensure you still dispose each $job.PowerShell in its inner finally and
preserve collecting $results and $errors as before.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between a8b0427 and 1328263.

📒 Files selected for processing (2)
  • src/Action/Issue.psm1
  • src/Github.psm1

Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 3

♻️ Duplicate comments (3)
src/Action/Issue.psm1 (2)

143-146: ⚠️ Potential issue | 🟠 Major

Remove contradictory assignment in branch-protection fail-safe path.

Line 145 immediately overrides the safe default from Line 144. On API check failure, this currently behaves as unprotected.

Suggested fix
 } catch {
     Write-Log "Failed to check branch protection status: $($_.Exception.Message). Assuming branch is protected for safety."
     $isProtected = $true
-    $isProtected = $false
 }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Action/Issue.psm1` around lines 143 - 146, The catch/fail-safe in the
branch protection check currently logs the error then sets $isProtected = $true
and immediately overrides it with $isProtected = $false; remove the
contradictory assignment so the fail-safe leaves $isProtected = $true. Locate
the catch block containing Write-Log and the two $isProtected assignments and
delete the line that sets $isProtected = $false, ensuring the safe default
remains true.

119-119: ⚠️ Potential issue | 🟠 Major

Make PR filtering compatible with both GraphQL and REST fallback payloads.

Line 119 filters only by baseRefName. After REST fallback (Line 113), PRs use base.ref, so existing matching PRs can be missed.

Suggested fix
-$prs = $prs | Where-Object { $_.title -eq $titleToBePosted -and $_.baseRefName -eq $masterBranch }
+$prs = $prs | Where-Object {
+    $_.title -eq $titleToBePosted -and (($_.baseRefName -eq $masterBranch) -or ($_.base.ref -eq $masterBranch))
+}
#!/bin/bash
# Verify fallback source and current filter field usage.
rg -n -C3 '\$prs = \(Invoke-GithubRequest .*pulls\?state=open' src/Action/Issue.psm1
rg -n -C2 '\$prs = \$prs \| Where-Object' src/Action/Issue.psm1
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Action/Issue.psm1` at line 119, Existing PR filtering uses $prs = $prs |
Where-Object { $_.title -eq $titleToBePosted -and $_.baseRefName -eq
$masterBranch }, which only matches GraphQL payloads; after the REST fallback
$prs items have base.ref instead of baseRefName so matches are missed—update the
filter in Issue.psm1 to check both fields (e.g. compare $_.baseRefName -eq
$masterBranch -or $_.base.ref -eq $masterBranch) or normalize each PR object
before filtering (set a common property like $pr.baseRefName = $_.base.ref when
present) while keeping the title check ($_.title -eq $titleToBePosted) intact so
both GraphQL and REST payloads are handled.
src/Github.psm1 (1)

19-23: ⚠️ Potential issue | 🟡 Minor

Process pipeline input correctly or remove pipeline binding.

Invoke-GithubGraphQL declares ValueFromPipeline on Line 19, but there is no process {} block, so pipeline items are not handled per-item.

#!/bin/bash
# Verify pipeline-enabled parameter and absence/presence of process block.
rg -n -C3 'function Invoke-GithubGraphQL|ValueFromPipeline|^\s*process\s*\{' src/Github.psm1
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Github.psm1` around lines 19 - 23, The function Invoke-GithubGraphQL
declares ValueFromPipeline on the [String] $Query parameter but lacks a process
block to handle pipelined input; either remove the ValueFromPipeline attribute
from the Query parameter or add a process { } block in Invoke-GithubGraphQL that
iterates over incoming pipeline values and executes the existing request logic
for each item (i.e., treat each piped $Query as a separate call). Update the
function body (Invoke-GithubGraphQL) to use the process block when preserving
pipeline behavior, or remove ValueFromPipeline from the [String] $Query
parameter to disable pipeline binding.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/Action/Issue.psm1`:
- Around line 71-89: The GraphQL query string assigned to $graphqlQuery
incorrectly nests rateLimit inside repository; update the query in Issue.psm1 so
rateLimit is a top-level field (a sibling of repository) rather than inside
repository, ensuring the query braces remain balanced and the fields (repository
{ defaultBranchRef { name } pullRequests { nodes { number title body baseRefName
} } } and rateLimit { remaining }) are at the top level of the query string.

In `@src/Github.psm1`:
- Around line 6-13: The comment-based help for the GitHub GraphQL function is
out of sync: it documents a .PARAMETER UseFallback that no longer exists in the
param(...) block; update the help to match the actual signature by either
removing the ".PARAMETER UseFallback" stanza from the comment-based help or
re-introducing a matching UseFallback parameter in the param(...) and
implementing its logic where needed (search for the function block containing
the param(...) and the comment header in Github.psm1 to locate the spot).
- Around line 113-124: Invoke-GithubGraphQLParallel currently creates a runspace
pool using [runspacefactory]::CreateRunspacePool(1, [Math]::Min(5,
$Queries.Count)) which will break when $Queries is empty; add a guard at the
start of the function to handle an empty $Queries (e.g., if ($null -eq $Queries
-or $Queries.Count -eq 0) { return @() } or otherwise set a safe max value)
and/or ensure the max runspaces passed to CreateRunspacePool is at least 1
before creating $runspacePool; update references to $Queries and $runspacePool
in Invoke-GithubGraphQLParallel accordingly.

---

Duplicate comments:
In `@src/Action/Issue.psm1`:
- Around line 143-146: The catch/fail-safe in the branch protection check
currently logs the error then sets $isProtected = $true and immediately
overrides it with $isProtected = $false; remove the contradictory assignment so
the fail-safe leaves $isProtected = $true. Locate the catch block containing
Write-Log and the two $isProtected assignments and delete the line that sets
$isProtected = $false, ensuring the safe default remains true.
- Line 119: Existing PR filtering uses $prs = $prs | Where-Object { $_.title -eq
$titleToBePosted -and $_.baseRefName -eq $masterBranch }, which only matches
GraphQL payloads; after the REST fallback $prs items have base.ref instead of
baseRefName so matches are missed—update the filter in Issue.psm1 to check both
fields (e.g. compare $_.baseRefName -eq $masterBranch -or $_.base.ref -eq
$masterBranch) or normalize each PR object before filtering (set a common
property like $pr.baseRefName = $_.base.ref when present) while keeping the
title check ($_.title -eq $titleToBePosted) intact so both GraphQL and REST
payloads are handled.

In `@src/Github.psm1`:
- Around line 19-23: The function Invoke-GithubGraphQL declares
ValueFromPipeline on the [String] $Query parameter but lacks a process block to
handle pipelined input; either remove the ValueFromPipeline attribute from the
Query parameter or add a process { } block in Invoke-GithubGraphQL that iterates
over incoming pipeline values and executes the existing request logic for each
item (i.e., treat each piped $Query as a separate call). Update the function
body (Invoke-GithubGraphQL) to use the process block when preserving pipeline
behavior, or remove ValueFromPipeline from the [String] $Query parameter to
disable pipeline binding.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 1328263 and 5fd664c.

📒 Files selected for processing (2)
  • src/Action/Issue.psm1
  • src/Github.psm1

@MiyakoMeow
Copy link
Copy Markdown
Author

@coderabbitai review

@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Mar 3, 2026

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

♻️ Duplicate comments (2)
src/Action/Issue.psm1 (2)

144-147: ⚠️ Potential issue | 🟠 Major

Fix contradictory fallback assignment in branch-protection error handling.

Line 145 sets safe default ($true), but Line 146 immediately overrides it to $false, which re-enables direct-push behavior when protection status is unknown.

🔧 Proposed fix
             } catch {
                 Write-Log "Failed to check branch protection status: $($_.Exception.Message). Assuming branch is protected for safety."
                 $isProtected = $true
-                $isProtected = $false
             }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Action/Issue.psm1` around lines 144 - 147, The fallback in the
branch-protection error handler sets $isProtected to $true then immediately to
$false, undoing the safe default; locate the try/catch or error-handling block
around Write-Log "Failed to check branch protection status..." that manipulates
$isProtected and remove or correct the contradictory assignment so $isProtected
remains the safe default (true) when protection status cannot be determined,
ensuring Write-Log and the catch block still record the error.

120-120: ⚠️ Potential issue | 🟠 Major

Handle both GraphQL and REST PR shapes in the base-branch filter.

Line 120 only checks baseRefName, so the REST fallback path can fail to match existing PRs and create duplicates.

🔧 Proposed fix
-        $prs = $prs | Where-Object { $_.title -eq $titleToBePosted -and $_.baseRefName -eq $masterBranch }
+        $prs = $prs | Where-Object {
+            $_.title -eq $titleToBePosted -and (
+                $_.baseRefName -eq $masterBranch -or $_.base.ref -eq $masterBranch
+            )
+        }
GitHub REST API "List pull requests" response: which field contains the base branch name (`base.ref` vs `baseRefName`)?
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Action/Issue.psm1` at line 120, The current filter in the $prs pipeline
(Where-Object) only checks GraphQL's baseRefName and misses REST PR shapes,
causing duplicate PRs; update the filter that selects PRs by title
($titleToBePosted) and base branch ($masterBranch) to accept either GraphQL or
REST fields—i.e., match when $_.title -eq $titleToBePosted and (either
$_.baseRefName -eq $masterBranch or the REST shape $_.base.ref -eq
$masterBranch) so both PR response shapes are handled.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/Github.psm1`:
- Around line 114-138: Remove the duplicate state resets and redundant runspace
pool creation: delete the repeated initializations of $results and $errors and
remove the first [runspacefactory]::CreateRunspacePool(1, [Math]::Min(5,
$Queries.Count)) so there is only a single runspace pool created and opened
(keep the later $runspacePool.Open() sequence); ensure the early-return checks
for $Queries ($null check and Count check) remain singular and consistent so
$runspacePool is not overwritten and no dead duplicate control flow remains.

---

Duplicate comments:
In `@src/Action/Issue.psm1`:
- Around line 144-147: The fallback in the branch-protection error handler sets
$isProtected to $true then immediately to $false, undoing the safe default;
locate the try/catch or error-handling block around Write-Log "Failed to check
branch protection status..." that manipulates $isProtected and remove or correct
the contradictory assignment so $isProtected remains the safe default (true)
when protection status cannot be determined, ensuring Write-Log and the catch
block still record the error.
- Line 120: The current filter in the $prs pipeline (Where-Object) only checks
GraphQL's baseRefName and misses REST PR shapes, causing duplicate PRs; update
the filter that selects PRs by title ($titleToBePosted) and base branch
($masterBranch) to accept either GraphQL or REST fields—i.e., match when
$_.title -eq $titleToBePosted and (either $_.baseRefName -eq $masterBranch or
the REST shape $_.base.ref -eq $masterBranch) so both PR response shapes are
handled.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 5fd664c and 5d863a5.

📒 Files selected for processing (2)
  • src/Action/Issue.psm1
  • src/Github.psm1

Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

♻️ Duplicate comments (1)
src/Action/Issue.psm1 (1)

120-120: ⚠️ Potential issue | 🟠 Major

Fix PR base-branch filtering for REST fallback objects.

At Line 120, filtering only on $.baseRefName works for GraphQL nodes but fails for REST PR objects ($.base.ref). In fallback mode, existing PRs can be missed, causing duplicate PR creation.

Proposed fix
-        $prs = $prs | Where-Object { $_.title -eq $titleToBePosted -and $_.baseRefName -eq $masterBranch }
+        $prs = $prs | Where-Object {
+            $_.title -eq $titleToBePosted -and
+            (($_.baseRefName -eq $masterBranch) -or ($_.base.ref -eq $masterBranch))
+        }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/Action/Issue.psm1` at line 120, The PR filtering currently only checks
$_.baseRefName which works for GraphQL nodes but misses REST fallback PR objects
that use $_.base.ref; update the $prs filtering (the pipeline that assigns $prs,
using variables $prs, $titleToBePosted, $masterBranch) to match PRs whose title
equals $titleToBePosted and whose base branch equals $masterBranch by checking
either $_.baseRefName -eq $masterBranch OR $_.base.ref -eq $masterBranch so both
GraphQL and REST PR objects are detected.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Duplicate comments:
In `@src/Action/Issue.psm1`:
- Line 120: The PR filtering currently only checks $_.baseRefName which works
for GraphQL nodes but misses REST fallback PR objects that use $_.base.ref;
update the $prs filtering (the pipeline that assigns $prs, using variables $prs,
$titleToBePosted, $masterBranch) to match PRs whose title equals
$titleToBePosted and whose base branch equals $masterBranch by checking either
$_.baseRefName -eq $masterBranch OR $_.base.ref -eq $masterBranch so both
GraphQL and REST PR objects are detected.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 5d863a5 and 9afb768.

📒 Files selected for processing (2)
  • src/Action/Issue.psm1
  • src/Github.psm1
🚧 Files skipped from review as they are similar to previous changes (1)
  • src/Github.psm1

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.

1 participant