feat(house): Actions permissions in the house preset - #12
Conversation
PR Summary by QodoConfigure GitHub Actions permissions in the house preset
AI Description
Diagram
High-Level Assessment
Files changed (4)
|
Code Review by Qodo
1.
|
There was a problem hiding this comment.
Stale comment
Risk: high. Left a non-blocking comment; no reviewers assigned. Cursor Bugbot and Cursor Security Agent completed with no findings, but this house-wide Actions permission change is above the medium approval threshold and needs human review.
Sent by Cursor Approval Agent: Pull Request Router and Approver
Matches Resnovas/.github#12, where the refresh job gets the write access it needs when it falls back to the workflow token. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com>
There was a problem hiding this comment.
Stale comment
Risk: high. Left a non-blocking comment; no reviewers assigned. Cursor Security Agent completed with no findings and Bugbot was not present, but this house-wide Actions permission change is above the medium approval threshold and needs human review.
Sent by Cursor Approval Agent: Pull Request Router and Approver
The preset now sets GitHub Actions through smartcloud: a read-only workflow token by default (every house workflow declares its permissions), which may still open pull requests for the Graphify refresh's fallback, and on private repositories an organisation access level, the setting whose loss broke house-graphify. GOVERNANCE.md and the README describe it. Refs SMC-63 Signed-off-by: Jonathan Stevens <jonathan@resnovas.com>
…flow token The house preset allows the workflow token to create pull requests so the Graphify refresh can fall back to it, but the caller granted only contents: read and the refresh job declared nothing. The caller now sets contents and pull-requests write as the ceiling, and the refresh job asks for both; the check job stays read-only. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com>
e31de7b to
209902f
Compare
|
Rebased onto main after #11 and #20 landed (209902f). Two conflicts, both kept:
|
There was a problem hiding this comment.
Graphify reviewed this change.
Worth a look — the grounded gate found no coupling regressions or blocking issues, but 1 advisory finding(s) below merit a look before merge.
Graphify review — findings
Makes the Graphify refresh fall back to the workflow token when ACCESS_TOKEN is unset — it now pushes house/graphify and opens the refresh pull request instead of skipping with a notice — which requires the called workflow and its caller to grant contents: write and pull-requests: write. Adds an actions settings block to house.yml that keeps the workflow token read-only by default (workflowPermissions: read), allows it to create pull requests (createPullRequests: true), and sets accessLevel: organization so private repositories stay callable across the org. Documents that this access level must be set by hand once when a repo goes private, since the reusable workflows that apply the preset can't run until it is.
Worth a look
- Write-capable GitHub token is passed to a mutable third-party action tag —
.github/workflows/graphify.yml· Escalate · medium- agreed by 2 of 2 members but NOT verified (no proof, no reproducing execution) — consensus is not a verdict; needs human review
Analysis details — impact, health, verification
Impact & health
Graphify review
Impact — 72 functions depend on the 72 functions this change touches.
Health — grade A; no new coupling hotspots.
Verification — 72 functions in the blast radius were not formally verified this run (proofs are advisory here).
Gate & verification
graphify gate
PASS — objectively clean (no health regressions, tests not run — proofs not run this pass (advisory)). Grounded, not self-assessed.
Advisory (not blocking):
- verification_scope: 72 function(s) in the blast radius were not formally verified this run
There was a problem hiding this comment.
Risk: high. Left a non-blocking comment; no reviewers assigned. Cursor Bugbot completed with no findings, but Cursor Security Agent did not finish within 8 minutes, and this house-wide Actions permission change is above the medium approval threshold and needs human review.
Sent by Cursor Approval Agent: Pull Request Router and Approver
Matches Resnovas/.github#12, where the refresh job gets the write access it needs when it falls back to the workflow token. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com>
#644) * feat(settings): Actions, access, webhooks, Pages and variables as code The settings section now also covers GitHub Actions permissions (allowed actions, SHA pinning, the workflow token's default permissions and whether it may open pull requests, and the access level that decides which private repositories may call this one's reusable workflows), collaborators and teams, webhooks, the Pages site, and a check that required Actions variables exist, by name only. Teams go through GraphQL's updateTeamsRepository so every call stays bound to the repository. Webhooks are matched by URL, their config is patched on its own endpoint so a secret set by hand survives, and reports name only the host. The access level exists only for private repositories, so on a public one it is skipped with a notice. Refs SMC-63 Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> * fix(dry-run): keep only the origin of URLs in recorded request bodies A webhook URL can carry a token in its path or query, and dry-run output printed the recorded POST /hooks body in full. The recorder now keeps only the URL's origin, matching the host-only webhook descriptions in the plan. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> * fix(config): reject webhook URLs that do not parse The pattern accepted values such as http://[ that only fail once GitHub is called. A URL.canParse filter now rejects them when the config loads; the JSON schema is unchanged. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> * ci(house): sync the Graphify caller's write permissions Matches Resnovas/.github#12, where the refresh job gets the write access it needs when it falls back to the workflow token. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> * fix(settings): enforce Pages HTTPS in its own call after the domain GitHub refuses https_enforced until the custom domain has a certificate, which is issued only once the domain is stored. Sending both in one PUT meant a first-time config never stored the domain; now the domain is set first and HTTPS is enforced on a later run if not yet possible. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> * fix(settings): redact dry-run webhook URLs with a password or fragment Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> * fix(settings): ignore a Pages branch and path on a workflow site A workflow-built site has no source, but a config setting buildType: workflow with a branch or path sent both build_type workflow and a source. The branch and path are now ignored for a workflow site. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> * fix(config): keep a rejected webhook URL out of the decode error A webhook URL that failed the pattern or did not parse was repeated in the config error, so a token in it reached logs. Both checks now report a fixed message. Signed-off-by: Jonathan Stevens <jonathan@resnovas.com> --------- Signed-off-by: Jonathan Stevens <jonathan@resnovas.com>


The house preset now sets GitHub Actions through smartcloud's new
settings.actionssection (Resnovas/smartcloud#644):workflowPermissions: read: the workflow token is read-only by default. Every workflow in the org already declares itspermissions; I checked each repository before choosing this.createPullRequests: true: the Graphify refresh falls back to the workflow token whereACCESS_TOKENis unavailable, and it has to be able to open its pull request.accessLevel: organization: a private repository's reusable workflows stay callable from the rest of the organisation. This is the setting whose loss broke house-graphify. Public repositories have no access level, and smartcloud skips it there with a notice.GOVERNANCE.md (root and template) lists the new baseline. The README says the access level must be set by hand once when this repository becomes private, because the workflows that would apply it cannot run until it is set.
Checks: the
node --testsuite, the render check and the surfaces check all pass locally, and the preset validates with the smartcloud CLI from #644.Stacks on #11 (SMC-62).
Closes SMC-63
Note
Medium Risk
Changes org-wide GitHub Actions token defaults and elevates Graphify refresh job permissions when falling back to the workflow token; behaviour is intentional but affects CI on every house-managed repository.
Overview
Adds GitHub Actions baseline to the house smartcloud preset: read-only workflow tokens by default, PR creation still allowed, and organisation-wide access to reusable workflows on private repos (
settings.actionsinsmartcloud/house.yml). GOVERNANCE and the README describe the new baseline and the one-time manual Actions access step when this repo is private.Graphify no longer skips the default-branch refresh when
ACCESS_TOKENis missing. The reusable workflow’s refresh job requestscontentsandpull-requestswrite, usessecrets.token || github.tokenforcreate-pull-request, and drops the “skipped without token” notice. house-graphify caller permissions are raised so the refresh path can push and open PRs under the workflow token fallback.Reviewed by Cursor Bugbot for commit 209902f. Bugbot is set up for automated code reviews on this repo. Configure here.