Codex 또는 Claude로 설치 이 Prompt를 복사해 Codex, Claude 또는 다른 어시스턴트에 붙여 넣으면 Skill 페이지를 검토하고 설치를 진행할 수 있습니다.
직접 명령은 검토 Prompt를 거치지 않습니다. 실행하기 전에 소스를 확인하세요.
npx skills add https://github.com/Morrison-Lab/ai-config --skill discussions명령은 한 줄로 유지됩니다. 복사하기 전에 가로로 스크롤해 전체 내용을 확인하세요.
로컬 사본을 원하시나요? SkillsMP에서 현재 제공할 수 있는 파일을 다운로드하세요.
SKILL.md 표시 중
| name | discussions |
| description | Manage forge discussions. |
| user-invocable | true |
| allowed-tools | ["Bash","Read"] |
Read a repo's GitHub Discussions and respond to a topic: list open topics, read one with its comment thread, draft a reply, post it, and (on Q&A topics) mark a comment as the accepted answer.
If the topic really belongs in the issue tracker (a concrete, actionable bug or task), hand off to migrate-discussion instead of just replying.
Writing goes through GraphQL.
There is no gh discussion subcommand and no mcp__github__*
Discussions tool, so posting a comment, creating a topic, or marking an
answer all require gh api graphql.
Reading does not.
GitHub serves repository discussions over REST, so these work from any
session that can reach api.github.com with a token:
gh api repos/<owner>/<repo>/discussions # list topics
gh api repos/<owner>/<repo>/discussions/<N> # one topic
gh api repos/<owner>/<repo>/discussions/<N>/comments # its comments
Without gh, the same three are a plain curl against
https://api.github.com/... with an Authorization: bearer header.
Which path a session has:
gh: everything works.
Use gh api graphql for writes (shown below) and either form for reads.gh): the GitHub MCP server exposes
no Discussions tools, but the REST reads above still work, so the topic and
its comments are readable.
Writes need an authenticated GraphQL passthrough -- and some sandboxes
refuse GraphQL outright while serving REST normally.
When the write path is missing, say so and hand the drafted text to the user
rather than faking a reply that never posted.Don't report a discussion as unreachable without trying the REST read: half of what this skill does is available even where GraphQL is blocked.
<owner>/<repo> below are the repository; <N> is a discussion number. Use
-F for typed (Int) variables and -f for strings.
The REST repo object carries this, so the check itself does not need GraphQL:
gh api repos/<owner>/<repo> --jq .has_discussions
If it is false, stop and tell the user -- there's nothing to read or post to.
The GraphQL equivalent is repository { hasDiscussionsEnabled }, if you are
already making a GraphQL call for another reason.
Don't substitute "the list endpoint returned 200" for either: a repo with
Discussions enabled and no topics yet returns an empty 200, so a 200 does
not distinguish enabled-but-empty from anything else.
LIST_DISCUSSIONS (abstract operation token; resolve to your model's tool via
tool-mappings.md -- there is no GitHub MCP tool for
Discussions, so every model runs one of the two gh api forms below).
Prefer REST, since it works in sessions where GraphQL is blocked:
gh api repos/<owner>/<repo>/discussions --jq \
'.[] | {number, title, html_url, updated_at, comments,
category: .category.name, answer: .answer_html_url}'
A non-null answer_html_url means a Q&A topic already has an accepted answer.
The category object carries is_answerable, which marks a Q&A category.
The GraphQL form returns the same fields under different names, and is what to use when you also want node IDs in the same call:
gh api graphql -f owner='<owner>' -f repo='<repo>' -f query='
query($owner: String!, $repo: String!) {
repository(owner: $owner, name: $repo) {
discussions(first: 20, orderBy: {field: UPDATED_AT, direction: DESC}) {
nodes {
number title url updatedAt
category { name isAnswerable }
answerChosenAt
comments { totalCount }
}
}
}
}'
answerChosenAt is the GraphQL spelling of the same accepted-answer signal.
Report the list to the user with clickable URLs.
To read the topic and its thread, REST is enough, and works where GraphQL
is blocked (VIEW_DISCUSSION):
gh api repos/<owner>/<repo>/discussions/<N> # the topic
gh api repos/<owner>/<repo>/discussions/<N>/comments # its thread
The topic object carries node_id (e.g. D_kwDOS6B1yM4AoI39), which is the
discussionId step 5's top-level-reply mutation wants -- so a REST read is
sufficient to post a top-level comment.
Use the GraphQL form when you need a comment's node id, for a threaded
reply (replyToId) or to mark an answer.
Whether REST's comment objects also expose node_id is unverified: every
discussion in this org currently has zero comments, so there was nothing to
check it against.
Verify it on a thread that has comments before relying on REST for those two
mutations.
gh api graphql -f owner='<owner>' -f repo='<repo>' -F number=<N> -f query='
query($owner: String!, $repo: String!, $number: Int!) {
repository(owner: $owner, name: $repo) {
discussion(number: $number) {
id title body url
author { login }
category { name isAnswerable }
answerChosenAt
comments(first: 50) {
nodes {
id body isAnswer
author { login }
replies(first: 20) { nodes { id body author { login } } }
}
}
}
}
}'
Note the discussion's id (for a top-level reply) and any comment id (to
reply in-thread or mark as the answer).
Posting to a public forum is outward-facing and hard to unsay. Draft the reply
first, show it to the user, and wait for explicit approval before posting. Apply
the plain-prose style (use-preferred-style): answer the actual question, be
direct, no filler. If the answer isn't clear from context, ask the user rather
than guessing on a public thread.
Top-level comment on the discussion (uses the discussion id from step 3,
COMMENT_DISCUSSION):
gh api graphql -f discussionId='<discussion-id>' -f body='<reply text>
_Posted by Claude Code (AI agent) --- not written by a human._' -f query='
mutation($discussionId: ID!, $body: String!) {
addDiscussionComment(input: {discussionId: $discussionId, body: $body}) {
comment { id url }
}
}'
Threaded reply to a specific comment — add replyToId (the comment id,
also COMMENT_DISCUSSION):
gh api graphql -f discussionId='<discussion-id>' -f replyToId='<comment-id>' -f body='<reply text>
_Posted by Claude Code (AI agent) --- not written by a human._' -f query='
mutation($discussionId: ID!, $replyToId: ID!, $body: String!) {
addDiscussionComment(input: {discussionId: $discussionId, replyToId: $replyToId, body: $body}) {
comment { id url }
}
}'
Only categories where isAnswerable is true accept an answer. Mark a comment
(usually one you just posted, or an existing one the user points to,
ANSWER_DISCUSSION):
gh api graphql -f commentId='<comment-id>' -f query='
mutation($commentId: ID!) {
markDiscussionCommentAsAnswer(input: {id: $commentId}) {
discussion { url answerChosenAt }
}
}'
Use unmarkDiscussionCommentAsAnswer with the same input shape to undo it.
Give the user the posted comment's URL as a clickable link, and note whether an answer was marked.
gh discussion ... exists — it doesn't; use gh api graphql.isAnswerable categories
accept one; the mutation errors otherwise.