Repository navigation
feat(cli): feedback says whether a person or an agent wrote it, with the email an app attaches - #4984
Conversation
…the email an app attaches
|
Preview deployment for your docs. Learn more about Mintlify Previews.
💡 Tip: Enable Automations to automatically generate PRs for you. |
jrusso1020
left a comment
There was a problem hiding this comment.
Approving. The email comes from one place and goes to one place, --source fails closed, and the current server does ignore both new fields.
Email (PII)
- The only reader is
feedbackEmail(), which readsHYPERFRAMES_FEEDBACK_EMAIL, trims it, and treats a blank value as absent. There's no flag and no fallback to git config,EMAILor any other variable. applyDotEnvskips the key, andcli.tsis the CLI's only.envloader. I grepped for otherreadFileSync(.env)and dotenv uses and found none.- The value goes only into the
submitFeedbackPOST body. It's not intrackRenderFeedback(the test pins this), not in the doctor or env summary (pinned too), not infileGithubIssue(that function never receives it), and not printed. - Two places iterate over
process.env.render/plan.tsresolveHfEnvOverridesreports names only.studioServerinjects onlyVITE_STUDIO_*. Neither exposes the value. - Docs cover it in both
cli.mdxand the feedback guide: never a flag, never from.env, not telemetry, unverified.
--source
- Allowed values are exactly
personandagent, trimmed and case-sensitive (Personis refused). When the flag is omitted the source isundefined, andJSON.stringifydrops it, so the body stays byte-identical to today's. A bad value printsSource must be "person" or "agent"and callsfailCommand()beforeshouldTrack(), so nothing is sent with telemetry on or off.
Server ignores the new fields (verified)
- EF master,
heygen/services/heygen_server/hyperframes/dto/feedback_dto.py:HyperframesFeedbackRequestis a plain pydanticBaseModelwith nomodel_config, soextradefaults toignore. The route (render_routes.py,submit_feedback) passes only rating, comment, cli_version, env and rating_scale toforward_feedback. So the new fields are dropped silently, with no 422.
Agent detection
--sourcedoesn't default fromdetectAgentRuntime(), and nothing checks the two against each other, so an agent can send--source person. That's acceptable because it's self-declared, like the comment. The forwardedenvstring also doesn't carryagent_runtime(onlyclient=), so the backend can't cross-check from the report alone.
Tests: 22/22 pass locally across the four files (after bun install and building parsers and core). Of 11 mutations, 10 were caught: accepting any source, defaulting to agent, case-folding, falling back to other variables, dropping the trim, dropping the .env skip, dropping the refusal, email in telemetry, dropping the cap, and dropping source from the body. The survivor was a console.log(feedbackEmail()) after submit, because no test asserts the email stays out of stdout. The code doesn't print it, so that's a test gap only.
CI is still running. Two non-required checks are red, both because the existing .env loader moved into a new file:
Comments:dotEnv.tsis at 24.2% comments andfeedbackSource.tsat 20.0%, against the package's 13.1%. The dotEnv comments are the original loader's, moved verbatim.Fallow audit:applyDotEnvhas cognitive complexity 22, over the threshold of 15. That's the old loop, unchanged.
Non-blocking
- The agent nudge in
telemetry/feedback.tsstill suggestshyperframes feedback --rating <0-10> --comment "..."without--source agent, so the most common agent-filed reports will stay unlabeled. Adding--source agentthere (or defaulting fromdetectAgentRuntime()when the flag is absent) would make the split useful sooner. --sourcewith--search-missis not validated: a bad value is accepted and ignored. The docs say a search-miss carries no source, so this is harmless, but it isn't refused the way it is on a rating.- The PR body says the env-only rule means an agent can't attach an email "through a command line". An agent with a shell can still run
HYPERFRAMES_FEEDBACK_EMAIL=x hyperframes feedback, and an agent the app launches inherits the variable if the app sets it in the agent's environment. The docs already say "not verified", which is the right contract. The app side should set the variable only on the feedback-button invocation, not in the agent's environment. - On every render,
resolveHfEnvOverrideswill listHYPERFRAMES_FEEDBACK_EMAIL(name only) as an operator override when an app sets it. That's not PII, just noise in that signal; consider adding it toCLI_INTERNAL_HF_ENV_KEYS. - The
submitFeedback.tscomment says the caps "match the backend DTO", but the backend has noemailfield yet. The 254 cap should land in the DTO with the server change.
— Rames
Edit accuracy: accurate 1556 (base branch 1556), smooth 1414 of thoseThe gate passes. Quarantined, measured but not gated (0) Unstable (1)
|
jrusso1020
left a comment
There was a problem hiding this comment.
Re-approving at 09b87c95. The delta since my approval at c484e971 is two commits on top of it (3 files, +28 −31), and it changes no behavior I can find.
.env loader split (dotEnv.ts)
entryOfandvalueOfare the old loop body, moved out unchanged: comment and blank lines skipped,exportstripped,eq < 1refused, a quoted value ends at its closing quote, an unterminated quote strips only the opener, and an unquoted#starts a comment only after whitespace. The feedback-email skip and the never-overwrite rule stay inapplyDotEnv.- To check this, I ran the
c484e971loader next to this one on 200,000 seeded random.envfiles. The files were built from fragments that hit each branch: quotes,export,=/==,pass#word,#c,\r, an empty key, andHYPERFRAMES_FEEDBACK_EMAILwith and without a preset key. The resulting env objects were identical every time.
cli.ts
- The
import("./utils/dotEnv.js")moved out of thetry, so a missing or broken loader module now throws instead of being swallowed. That part is right. The commit title also says "only a missing .env is ignored", but thecatch {}still swallows every error fromreadFileSync(EACCES, EISDIR) and fromapplyDotEnv, the same as before. That's not a regression, but the title promises more than the code does. If that was the intent,if (code !== "ENOENT") throwin the catch would make it true.
Docs and comments: the doc comments on the FeedbackSource type and FEEDBACK_EMAIL_ENV were folded into the feedbackEmail doc, which still says it is never a flag and never read from a project .env, and is unverified.
Tests and CI: dotEnv, feedbackSource, submitFeedback and the feedback command tests pass, 22/22. Comments and Fallow audit are now green with no ignores added. At the time I checked, other checks were still pending and none had failed.
My earlier non-blocking notes still stand unchanged (agent nudge without --source agent, --search-miss not validating --source, the email name in hfEnvOverrides, no backend email cap yet).
— Rames
What
hyperframes feedbackcan now say who wrote a report and, when an app launched the CLI for a signed-in person, carry that person's email.--source personor--source agentmarks the report. Any other value is refused before anything is sent.HYPERFRAMES_FEEDBACK_EMAILenvironment variable, which the launching app sets. It is never a flag, and the CLI's project.envloading now skips that key, so an agent cannot attach one through a command line or a file it writes. It is not verified: a way to reply, not proof of who sent the report.sourceandemail, the email capped at 254 characters. Without them the request body is exactly what it was before.Why
Apps that embed the CLI send two kinds of feedback through
hyperframes feedback: reports a person reviews and sends from a feedback button, and reports their agent files on its own. The team needs to tell the two apart when reading them, and to be able to reply to a signed-in person. Today both look the same and carry no way to reach the person.Related work
An embedding app can pass
--source personfrom its feedback button and--source agentfor its agent, and set the email only while the person is signed in, once this ships in a CLI release. The feedback service reads the two new fields separately; until it does, they are ignored.How
src/utils/feedbackSource.tsowns both values:parseFeedbackSource(absent, valid, or refused) andfeedbackEmail(the one environment variable, trimmed, blank as absent)..envloader moved fromsrc/cli.tsintosrc/utils/dotEnv.tsunchanged except that it skips the feedback email key;cli.tsstill imports it lazily.feedbackchecks--sourceright after--rating, so a bad value fails the same way whether or not telemetry is on.submitFeedbackadds the two fields to the existing POST;JSON.stringifydrops them when undefined.--file-issuedraft.feedbackis no longer described as anonymous: it is, unless the launching app attaches an email.feedbacksection of the CLI reference and "About feedback data" in the feedback guide say what the new flag and variable do.--sourceapplies to rating reports; a--search-missreport carries neither.Test plan
feedbackSource.test.ts: parsing and the variable.feedback.test.ts: a person report carries the email, which stays out of the telemetry event and the environment summary; an agent report without the variable carries none; an unknown source is refused with nothing sent.dotEnv.test.ts: the loader's existing behaviour, and that it never takes the email from a project file.submitFeedback.test.ts: both fields reach the body and the email is capped..envskip, and adding the email to telemetry.fetch), the embedding app's side, which lands separately, andcli.commands.test.tson my box, where the engine's built@hyperframes/coresubpaths were missing; CI runs it.