Deduplicate discussion comment mutation flow across comment actions#43482
Conversation
|
🧠 Matt Pocock Skills Reviewer has completed the skills-based review. ✅ |
|
✅ PR Code Quality Reviewer completed the code quality review. No code to review: PR #43482 contains exactly one commit ('Initial plan') with zero file changes. All files on the branch (github_api_helpers.cjs, add_comment.cjs, add_reaction_and_edit_comment.cjs) have identical SHAs to main. The PR body describes planned work that has not yet been implemented. There is no diff to analyze. |
|
✅ Design Decision Gate 🏗️ completed the design decision gate check. No ADR enforcement needed: PR #43482 does not have the 'implementation' label and has 0 new lines of code in business logic directories (threshold: 100). |
|
✅ Test Quality Sentinel completed test quality analysis. No test files were added or modified in this PR (#43482: 'Deduplicate discussion comment mutation flow across comment actions'). The PR metadata shows 0 additions/deletions with no test files in the diff. Test Quality Sentinel skipped. |
There was a problem hiding this comment.
Skills-Based Review 🧠
Applied /codebase-design and /tdd — this PR is in the planning stage (0 changed files; only an "Initial plan" commit). This review covers the design described in the PR body and the existing code the plan targets.
📋 Key Design Observations
Design Decision: Shared Primitive Signature
The plan proposes createDiscussionComment(github, discussionId, body, replyToId?) where the caller pre-resolves the discussion node ID. The two existing callers have different starting points today:
add_comment.cjsusescommentOnDiscussion(owner, repo, discussionNumber, ...)— resolves the node ID internally and returns{ id, html_url, discussion_url }. Thediscussion_urlis needed for caller output.add_reaction_and_edit_comment.cjsalready holdsdiscussionId(fromgetDiscussionNodeIdinadd_reaction.cjs) and only needs{ id, url }downstream.
Having callers pre-resolve the ID is a good choice for testability (the shared primitive can be tested without mocking the lookup query), but the plan should explicitly state this contract.
Return Value Shape Divergence
add_comment.cjs needs discussion_url in the result; the other caller does not. The shared helper should document which shape it returns and whether callers are expected to ignore unneeded fields, or whether discussion_url needs to be obtained separately (e.g., by the ID-resolution step that already runs in commentOnDiscussion).
getDiscussionNodeId Is a Third Duplication Site
add_reaction.cjs exports getDiscussionNodeId using the same discussion(number: $num) { id } query that commentOnDiscussion in add_comment.cjs runs inline. The plan addresses mutation duplication but not lookup duplication. Moving getDiscussionNodeId to github_api_helpers.cjs and having add_reaction.cjs re-export or import from there would complete the deduplication.
Error Contract Not Specified
commentOnDiscussion throws ERR_NOT_FOUND when the discussion is missing. The inline path in add_reaction_and_edit_comment.cjs wraps the whole comment-creation block in a catch that logs a warning rather than rethrowing. The shared helper plan should specify whether the primitive throws (callers decide on recovery) or swallows errors — the two callers currently diverge.
Positive Aspects
- ✅ Correct scope: isolating the
addDiscussionCommentmutation assembly is the right deduplication unit. - ✅ Keeping
resolveTopLevelDiscussionCommentIdand body assembly at call sites is correct — those are workflow-specific. - ✅ Placing the new helper in
github_api_helpers.cjsis consistent with module structure.
🧪 TDD — Write These Tests Before Implementing
In github_api_helpers.test.cjs:
createDiscussionComment— noreplyToId→ calls 2-variable mutation form, returns{ id, url }createDiscussionComment— withreplyToId→ calls 3-variable mutation formcreateDiscussionComment—replyToId: nulltreated same as omitted (no extra variable)- Error propagation: when
github.graphqlrejects, the error propagates to the caller
Regression checks in callers:
add_comment.cjsdiscussion path still producesdiscussion_urlin its resultadd_reaction_and_edit_comment.cjsdiscussion path still callssetCommentOutputswith the correctidandurl
Recommendations Before Implementing
- Document the ID contract — state that callers must pass a pre-resolved GraphQL node ID, not a numeric discussion number.
- Agree on the return shape —
{ id, url }or{ id, html_url, discussion_url }. Ifdiscussion_urlis needed, either the helper returns it or it comes from the ID-resolution step. - Migrate
getDiscussionNodeIdtogithub_api_helpers.cjs— completes the deduplication and removes a second duplicated GraphQL query. - Specify the error contract — throw on API failure (recommended; callers handle recovery) or swallow and log?
- Write the TDD tests above before coding — this ensures no behavioral regression across both callers.
🧠 Reviewed using Matt Pocock's skills by Matt Pocock Skills Reviewer · 80.2 AIC · ⌖ 5.54 AIC · ⊞ 6.6K
Comment /matt to run again
There was a problem hiding this comment.
Review: Deduplicate Discussion Comment Mutation Flow
Status: This PR contains only an "Initial plan" commit with 0 changed files — no implementation yet.
The proposed refactoring is well-reasoned. Below are design issues to address during implementation.
Key issues to address
-
Interface mismatch between the two callers
add_reaction_and_edit_comment.cjsalready has a pre-resolveddiscussionId(node ID fromgetDiscussionNodeId). The proposedcreateDiscussionComment(github, discussionId, body, replyToId?)fits naturally here.add_comment.cjs→commentOnDiscussion()takes(github, owner, repo, discussionNumber, message, replyToId)and resolves the node ID internally — querying bothidandurl. Refactoring it to use the shared helper will require an extra step to preserve thediscussionUrlneeded for the return value{ id, html_url, discussion_url }.
-
Return type difference
The proposed helper returns
{ id, url }(raw GraphQL shape).commentOnDiscussion()returns{ id, html_url, discussion_url }. Callers inadd_comment.cjsdepend onhtml_urlfor logging anddiscussion_urlin the return data. The wrapper must mapurl→html_urland carrydiscussion_urlseparately. -
githubis ambient inadd_reaction_and_edit_comment.cjsThat file currently uses the
githubglobal injected bygithub-script. The shared helper signaturecreateDiscussionComment(github, ...)is correct, but theadd_reactioncaller must pass the globalgithubexplicitly — wire this consistently. -
getDiscussionNodeIdonly fetchesid, noturladd_reaction_and_edit_comment.cjscallsgetDiscussionNodeId()which only queries theid. The shared helper returning{ id, url }is fine here since only those fields go tosetCommentOutputs. Confirmadd_comment.cjsreconstructsdiscussion_urlfrom a separate query or field. -
No test changes noted
add_comment.test.cjsandadd_reaction_and_edit_comment.test.cjsshould verify the shared helper is called correctly. The PR description does not mention tests.
Suggested shared helper:
// github_api_helpers.cjs
async function createDiscussionComment(github, discussionId, body, replyToId) { ... }
// returns { id: string, url: string }Then commentOnDiscussion() in add_comment.cjs delegates:
const comment = await createDiscussionComment(github, discussionId, message, replyToId);
return { id: comment.id, html_url: comment.url, discussion_url: discussionUrl };The refactoring goal is correct. Address the type-mapping and test coverage gaps, then this will be a clean improvement.
🧵 Reviewed using Impeccable skills by Impeccable Skills Reviewer · 125.6 AIC · ⌖ 6.18 AIC · ⊞ 4.8K
🤖 PR Triage — Run #7
Score breakdown: impact 0 + urgency 10 + quality 2 This PR has 0 files changed (empty diff). The refactor intent (deduplicating discussion comment mutation flow into
|
|
@copilot please run the
|
Co-authored-by: gh-aw-bot <259018956+gh-aw-bot@users.noreply.github.com>
Co-authored-by: gh-aw-bot <259018956+gh-aw-bot@users.noreply.github.com>
Implemented the requested PR-finisher pass. The deduplication changes are now on the branch in commit |
Two comment workflows implemented the same discussion-comment creation path independently (discussion lookup, optional
replyToId,addDiscussionCommentmutation, metadata extraction), creating drift risk in threaded reply behavior and output shaping.Extract shared discussion comment creation primitive
createDiscussionComment(github, discussionId, body, replyToId?)inactions/setup/js/github_api_helpers.cjs.Refactor existing callers to reuse shared flow
actions/setup/js/add_comment.cjsnow delegates discussion comment creation to the shared helper after discussion resolution.actions/setup/js/add_reaction_and_edit_comment.cjsnow uses the same helper for discussion/discussion_comment follow-up comment creation.Keep workflow-specific behavior at call sites
resolveTopLevelDiscussionCommentId) and body assembly remain in each workflow module.