fix(core): Resolve escape sequences in fmt / parameterize messages - #24770
Conversation
`parameterize` built the message with `String.raw`, so an escape such as `\n` or `` \` `` stayed as a backslash sequence in the log body or event message, while the template attribute used the cooked strings. A string with an invalid escape sequence (e.g. a Windows path) has no cooked value, so its text dropped out of the template entirely. Build both from the cooked strings, falling back to the raw string where there is no cooked value. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
There was a problem hiding this comment.
This fixes a bug which is why I'll approve and merge this, as a pragmatic reaction to this PR. However, @breken-ai or rather to the human who hopefully is reading this: Please do not open such PRs and expect them to be reviewed/merged in the future. The amount of time that goes into these reviews is far greater than the value of fixing a bug that wasn't even reported or actually encountered. To illustrate: The review here consisted of live-testing your change against the current state to see the product implications, checking against our log spec for handling of escape characters, consulting two colleagues, etc. There's a cost to this.
I'm getting paid for this, so it "only" keeps me from the things I should actually work on. Can't imagine what this does to OSS maintainers who maintain this in their free time.
Please file an issue next time, following our issue template.
Also, genuinely curious: Why leave this in draft and then leave it unattended for four days?
This PR adds the external contributor to the CHANGELOG.md file, so that they are credited for their contribution. See #24770 Co-authored-by: Lms24 <8420481+Lms24@users.noreply.github.com> Co-authored-by: Nicolas Hrubec <nicolas.hrubec@outlook.com>
parameterize(exported asSentry.logger.fmt) builds the message withString.raw(strings, ...values), which uses the raw strings. The template it stores uses the cookedstrings. So escape sequences in the literal stay as backslash sequences in the message. For example,logger.info(logger.fmt`Line one\nline two ${x}`)sends the log bodyLine one\nline two ...with a literal backslash-n, and\`or\u2192come out as typed. Meanwhilesentry.message.templateholds the real newline, so the body and the template disagree.The reverse problem hits a string with an invalid escape sequence, such as a Windows path like
fmt`Reading C:\users ${file}`. It has no cooked value, sostrings.jointurned it into an empty string. The template became just%s, both insentry.message.templateand in thelogentry.messagethatcaptureMessagesends.The fix builds both the message and the template from the cooked strings. Where there is no cooked value, it falls back to the raw string. The two new tests fail on
developand pass with this change.yarn lint) & (yarn test).I ran the
packages/corevitest suite with and without the change. The only failures are the same 2 environment failures (zoderrrors,typedef) on both.tsc --noEmitonpackages/coreis clean, and so isoxfmt --checkon the changed files. I also ranoxlinton them, without the@sentry/eslint-plugin-sdkJS plugin.An AI coding agent (Claude Code, run by breken-ai) found this bug and wrote this change. I checked the red/green tests above before opening the PR.