GitHub issue workflow
This project uses the UBC-FRESH phase/task issue workflow. GitHub issues are part of the project specification, not an informal chat log. The issue body must let a new student, an external collaborator, or a coding agent understand the task, do it, verify it, and close it without the conversation that created it.
The portal assistant may draft and file an issue on the user’s behalf, but it must use this page, the tracked issue templates, and the repository state. It must not invent repository names, parent issue numbers, task identifiers, labels, or verification evidence.
Choose the type and level first
Ask the user enough questions to classify the request before drafting. A short set of questions is usually enough:
Is this a bug, a feature request, a documentation change, a maintenance task, or a question?
What user-visible behaviour or file is affected?
Which workbook version, portal page, command, notebook, or package area is involved?
What is the impact and urgency: blocker, wrong result, confusing output, or a nice-to-have?
Is this one task under the active phase, or a coherent multi-task deliverable that needs a new phase?
What is in scope, and what is explicitly out of scope?
How will we know it is done? What command, test, screenshot, or read-back proves it?
For a bug: what are the exact steps, expected result, actual result, version, and relevant output?
For a feature: what problem does it solve, who benefits, and what alternatives were considered?
For documentation: which page is wrong or missing, and what should it say instead?
Does the report contain secrets, private workbook data, personal paths, or other material that must not be published?
The issue level is one of:
Phase(parent issue)A coherent deliverable made of multiple tasks. Use the
phasetemplate only after the maintainer agrees to a new roadmap phase. Title:P<n>: <phase name>.Task(child issue)The default for a bug, feature request, documentation change, or maintenance item. Use the
tasktemplate and link the issue as a sub-issue of the active phase. Title:P<n>.<m>: <task name>.Subtask(checklist item)A step inside an existing task issue. Do not create a fourth issue level.
Issue type is metadata, not a fourth level. Prefer labels that already exist in the repository:
bugfor incorrect behaviour or an incorrect result;enhancementfor a feature request;documentationfor a docs-only change;questionfor a request for information that may not become code;help wantedorgood first issuewhen the maintainer has decided that they apply.
The canonical workflow also uses phase and task labels to express the level. Check
gh label list before posting. If a required label is missing, say so and ask the maintainer to
create it rather than silently inventing a different convention.
Before drafting
Audit the repository read-only first:
gh issue list --state open
gh issue view <n> --json number,title,state,body,labels
gh pr list --state open
sed -n '1,180p' ROADMAP.md
Find the active phase parent issue and the next task identifier in ROADMAP.md. Do not guess them.
If the issue belongs to a different phase, confirm that with the maintainer. If no open parent issue
exists for the active phase, ask whether to create it from phase.md or attach the task to an
existing phase before creating the child issue.
Draft the body from the template
Use the tracked template:
.github/ISSUE_TEMPLATE/task.mdfor a task;.github/ISSUE_TEMPLATE/phase.mdfor a new phase.
The task body has these labelled sections, in this order:
Task identifier:
Parent phase issue:
Status:
Branch:
Related planning:
Goal:
Scope:
Out of scope:
Subtasks:
Acceptance criteria:
Verification:
Artifacts:
Risks:
Completion metadata:
The phase body uses Phase identifier:, Status:, Branch:, Roadmap:, and
Pull request: instead of the task header, and adds Architecture notes: and
Child task checklist:.
Formatting rules:
Put each section label on its own line.
Use real task-list syntax, one item per line:
- [ ] First subtask..Wrap branch names, paths, commands, issue numbers, and commit hashes in backticks.
Replace every placeholder such as
<n>,<m>,<parent>, or<task name>.Do not build the body with escaped strings or inline pseudo-checklists.
Do not include tokens, private workbook contents, personal home paths, or raw transcripts.
Validate and confirm before posting
Write the body to an ignored file, for example tmp/issue-<slug>.md. Validate it with the local
checker before posting:
python scripts/check_issue_body.py \
--kind task \
--title "P28.10: Add an example task" \
--file tmp/issue-add-example-task.md
Then show the user the proposed title, labels, parent issue, and body. Ask for explicit confirmation before creating the issue, unless the user already gave a complete, unambiguous request and asked you to file it immediately. If required information is missing, ask only for the missing details and say what is already known.
Post and verify
Create the issue from the body file:
gh issue create \
--repo UBC-FRESH/fable-pyculator \
--title "P28.10: Add an example task" \
--body-file tmp/issue-add-example-task.md \
--label task \
--label enhancement
Link a task to its parent when the web interface does not do it automatically:
child_id=$(gh api repos/UBC-FRESH/fable-pyculator/issues/<child> --jq .id)
gh api -X POST repos/UBC-FRESH/fable-pyculator/issues/<parent>/sub_issues \
-F sub_issue_id="$child_id"
Read the result back before reporting success:
gh issue view <child> --json number,title,state,body,labels,url
Report the issue number and URL. If GitHub is unavailable or unauthenticated, record the exact
command, exit status, and error text, keep a draft manifest under tmp/ or notes/, and say that
the issue was not filed. Never describe the GitHub side as complete when it is not.
Assistant behaviour
When the user asks to “file an issue”, “report a bug”, or “request a feature”, the portal assistant must:
Read this page and the selected template before drafting.
Ask for the missing type, scope, scale, impact, reproduction or desired outcome, acceptance criteria, and verification details.
Inspect
ROADMAP.mdand the current GitHub issues to choose the parent phase and task ID.Draft the canonical body, write it to a file, and run
scripts/check_issue_body.py.Show the draft and get confirmation.
Post with
gh issue create --body-file, link the parent, read it back, and report the URL.Stop and explain the exact blocker if filing cannot be completed.