Skip to content

Add the community WeChat QR code and a README Community section - #2574

Merged
Birfy merged 1 commit into
mainfrom
dev/775-community-qr
Nov 6, 2026
Merged

Birfy merged 1 commit into
mainfrom
dev/775-community-qr

Conversation

@Birfy

@Birfy Birfy commented Nov 6, 2026 •

Copy link
Copy Markdown
Collaborator

Written-by: Dev
Fixes #775
Owner: Chief
Reviewer: Reviewer
Tip SHA: 5c6dff0
Base: d5620ee
Docs-not-needed: README, one asset and a maintenance script; no architecture or subsystem change.

What changed

  • docs/assets/wechat-group.png — the group invite cut to the code plus a 20% white quiet zone, 674x674, RGBA, no text chunks (no EXIF, no personal data).
  • scripts/community-qr.mjs — reads the source JPEG, locates the code with jsQR, keeps only pixels inside the code quad and paints everything else white, downscales, and refuses to write unless the produced PNG decodes back to the same invite.
  • README.md / README.zh.md — a ## Community / ## 社区 section between ## Built on and ## License, with the image and alt text WeChat group QR code for FlyBot, one line on the group, and the expiry note (static image + ask for a fresh code).
  • changelog.d/775-community-qr.added.md, package.json — the fragment and the three devDependencies (jpeg-js, jsqr, pngjs); no runtime dependency changed.

Verification at the tip

Ran: node scripts/community-qr.mjs twice — same 674x674 PNG, both times sha256 3775e6a6692195a15c2dad9d813aa998f480bb10175959b183943b0ebfd9ae61, payload https://weixin.qq.com/g/AwYAADxvpVtVZlgHI9xPtdCVgn8QWvTLSEjzVtcR7rM665eSyKjcFl0rW--GSgi9; the script's own jsQR check decodes the written PNG back to that payload. node .github/scripts/changelog.mjs check -> 1 fragment well formed.

Not run (and why): TZ=UTC npm run verify locally — this tree has no core/node_modules, and the change touches no core or plugin code; CI runs it at this tip. Phone scan — this host has no camera and no vision model; that check stays the owner's.

Decoder evidence (the gap Chief flagged)

jsQR on the source JPEG 1080x1596 decodes. On the 1:1 crop (794 px code, 80/159/240/320 px margins) it fails, as does that crop thresholded to pure black/white at 80/110/140/170/200, and at 0.75x/1.5x/2x. Box-filter resampling decodes at 0.4x-0.6x (445-668 px); 0.65x fails again, so the failure is jsQR's above roughly 620 px on this code, not the crop. The committed file therefore uses a 480 px code edge (674x674 overall) and the script re-decodes it before writing, so a future regeneration cannot silently commit a dead code. This proves a decoder reads the file; it does not prove a phone camera does — that stays the owner's check.

Risks

The QR expires (WeChat rotates it about every 7 days); the README says so and points readers at Issues for a fresh one. Replacing it is one run of the script. package.json gains three devDependencies; the repo root had no lockfile and CI does not install root dependencies, so no CI impact.

Checkpoint

{
"pr": 2574,
"claim": "Chief",
"issue": 775,
"summary": "The community WeChat group QR code is now a committed 674x674 PNG cut from the owner photo: only the code and a white quiet zone, no metadata, no chat content. scripts/community-qr.mjs regenerates it and refuses to write unless jsQR decodes the result back to the same invite. README.md and README.zh.md gain a Community section with the image, alt text and an expiry note. A changelog fragment and three root devDependencies are added.",
"files": [
"docs/assets/wechat-group.png",
"scripts/community-qr.mjs",
"README.md",
"README.zh.md",
"package.json",
"changelog.d/775-community-qr.added.md"
],
"checks": {
"ran": "node scripts/community-qr.mjs; node .github/scripts/changelog.mjs check",
"result": "green",
"at": "5c6dff0a96eae2d784e92d8f6808e3fd62654b58"
},
"next": "none — ready for review; owner still has to scan the committed code with a phone"
}

The photo of the group invite lived only on the Bot machine. scripts/community-qr.mjs
cuts it to the code plus a white quiet zone, drops every pixel outside the code and all
metadata, and verifies the written PNG decodes back to the same invite. The committed
PNG is 674x674: the 794 px photo crop does not decode in jsQR at 1:1, the 480 px code
does, and a phone reads that size at least as well. README.md and README.zh.md get the
section between Built on and License, with the expiry note.

Fixes #775
Docs-not-needed: README and a maintenance script only; no architecture or subsystem change.
@Birfy Birfy added the agent-pr Pull request opened by an agent label Nov 6, 2026
@Birfy Birfy self-assigned this Nov 6, 2026
@Birfy

Birfy commented Nov 6, 2026

Copy link
Copy Markdown
Collaborator Author

Verdict: PASS at 5c6dff0
Written-by: Reviewer
Attestation: 5c6dff0 role=Reviewer

Ran at this tip:

$ node scripts/community-qr.mjs
# payload https://weixin.qq.com/g/AwYAADxvpVtVZlgH…, 674x674, sha256 3775e6a6692195a15c2dad9d813aa998f480bb10175959b183943b0ebfd9ae61 — byte-identical to the committed PNG
$ node --test .github/scripts/changelog.test.mjs .github/scripts/docker-profile.test.mjs
# tests 16  # pass 16  # fail 0
$ node .github/scripts/changelog.mjs check
# changelog: 1 fragment(s) in changelog.d/ are well formed
$ node -e "PNG chunk / quiet-zone / jsQR check on docs/assets/wechat-group.png"
# 674x674 RGBA, IHDR/IDAT/IEND only (no text chunks), 0 non-white pixels in the outer 90 px, decodes to the same invite

Risk tier: T3 (risk-tier: T3; basis: package.json=T3, scripts/community-qr.mjs=T3, changelog.d/775-community-qr.added.md=T1, docs/assets/wechat-group.png=T0, README.md=T0, README.zh.md=T0).

What I checked

  • Scope. Compare d5620ee…5c6dff0a is ahead by 1 with exactly 6 files: README.md, README.zh.md, changelog.d/775-community-qr.added.md, docs/assets/wechat-group.png, package.json, scripts/community-qr.mjs. Nothing under core/, patches/ds-bot/ or plugins/.
  • Image. 674x674, bit 8, colour type 6 (RGBA), chunks IHDR/IDAT/IEND only — no tEXt/eXIf/tIME, so no source metadata travels. All pixels opaque, the outer 90 px is pure white (0 non-white pixels), and jsQR decodes the file back to the same WeChat invite. Quiet zone ≈ 97 px ≈ 8 modules.
  • Script. Re-running it on the source photo reproduced the committed bytes exactly (sha256 3775e6a6…), so the committed asset matches what the tool emits. The decode guard is live: with the code edge forced to 794 px the script throws "the cropped PNG does not decode to the same invite" (exit 1) and writes nothing, so a dead code cannot be committed silently.
  • README. English section lands between ## Built on and ## License, the Chinese one between ## 它建立在什么之上 and ## 许可; docs/assets/wechat-group.png resolves from the repo root; alt text is "WeChat group QR code for FlyBot" (issue requirement); both state the ~7-day expiry and point readers at Issues, which is the issue's expiry decision. README.zh.md is updated in step, as AGENTS.md asks.
  • Gates. checkpoint block is present and valid (969 chars, summary 436, 6 files, checks.ran/result/at, next 80); Owner: Chief and Reviewer: Reviewer are valid policy names and differ; agent-pr label present; Docs-not-needed is in both the branch commit message and the PR body.
  • CI at the tip. All check-runs terminal: tests-ok, package, plugins (tree/social/timeline/workflow), Node 24 · DSH 0.2.0-rc.2, merge-gate, judge, risk tier, policy-sign, reviewed tip, agent-audience all success. The only failure is enqueue-guard, which correctly says "no Verifier report names the tip 5c6dff0" — that is this comment.

Not run

  • TZ=UTC npm run verify locally: this clean copy has no core/node_modules, and the change touches no core or plugin code; CI ran the same suite at this tip and tests-ok is green there.
  • A phone scan of the committed code: this host has no camera and no vision model. The decoder check above is the strongest evidence available here; the phone scan remains the owner's check and the PR says so under "Not run".

Non-blocking notes

  • No repository test asserts the asset or the script; the executable guard is the script's own decode check, which I exercised in both directions above.
  • docs/assets/ is a new image directory (existing images live in docs/images/); it matches the README: add the community WeChat group QR code #775 specification and both READMEs resolve it.

@github-actions github-actions Bot added the pass label Nov 6, 2026
@Birfy
Birfy added this pull request to the merge queue Nov 6, 2026
Merged via the queue into main with commit 1849a9d Nov 6, 2026
14 of 16 checks passed
@Birfy
Birfy deleted the dev/775-community-qr branch November 6, 2026 22:28
@github-actions github-actions Bot removed the agent-pr Pull request opened by an agent label Nov 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

README: add the community WeChat group QR code

1 participant