Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion src/dotenv/env_loader.rs
Original file line number Diff line number Diff line change
Expand Up @@ -994,7 +994,9 @@ struct Parser<'a> {
value_buffer: &'a mut Vec<u8>,
}

const WHITESPACE_CHARS: &[u8] = b"\t\x0B\x0C \xA0\n\r";
// Input is UTF-8, so this set must be ASCII-only: 0xA0 is a continuation byte
// there (NBSP is C2 A0), and trimming it byte-wise corrupts multi-byte sequences.
const WHITESPACE_CHARS: &[u8] = b"\t\x0B\x0C \n\r";

impl<'a> Parser<'a> {
fn skip_line(&mut self) {
Expand Down
19 changes: 19 additions & 0 deletions test/cli/run/env.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import {
isWindows,
tempDirWithFiles,
} from "harness";
import { parseEnv } from "node:util";
import path from "path";

function bunRunWithoutTrim(file: string, env?: Record<string, string>) {
Expand Down Expand Up @@ -372,6 +373,24 @@ test(".env space edgecase (issue #411)", () => {
expect(stdout).toBe("[A B]");
});

test(".env does not byte-trim 0xA0 out of UTF-8 values", () => {
// U+0920 DEVANAGARI LETTER TTHA encodes as E0 A4 A0 (trailing 0xA0)
// U+00A0 NO-BREAK SPACE encodes as C2 A0; Node.js preserves it verbatim.
expect(parseEnv("A=x\u0920\nB=\u00A0x\u00A0\nC=\u00A0\nD= x \n")).toEqual({
A: "x\u0920",
B: "\u00A0x\u00A0",
C: "\u00A0",
D: "x",
});

const dir = tempDirWithFiles("dotenv-utf8-nbsp", {
".env": "A=x\u0920\nB=\u00A0x\u00A0\n",
"index.ts": "console.log(JSON.stringify({ A: process.env.A, B: process.env.B }));",
});
const { stdout } = bunRun(`${dir}/index.ts`);
expect(JSON.parse(stdout)).toEqual({ A: "x\u0920", B: "\u00A0x\u00A0" });
});

test(".env special characters 1 (issue #2823)", () => {
const dir = tempDirWithFiles("dotenv-issue-2823", {
".env": 'A="a$t"\nC=`c\\$v`',
Expand Down
Loading