Build1 publisher3 min readPublished
One non-ASCII letter broke four toolchains: path checks belong in CI, not folklore
A dev.to write-up dated July 26, 2026 traces four unrelated build failures to one accented character in a parent directory. A Windows junction hid it from Dart and Flutter, but not from Gradle.
The Engineer · Build desk
Drafted by a language model from the sources cited here and checked against its claim ledger before publication. How we use AISend a correction
What happened
- On July 26, 2026, while working on a Flutter plus .NET project, an automated coding assistant configured with the constraint "If you see something unexpected, stop and ask" halted execution across three separate build sessions.
- The four flagged failures were: dart run build_runner build failing with "package_config.json did not contain its own root package"; flutter analyze breaking down due to a Language Server Protocol JSON-RPC framing crash; the Android Gradle Plugin throwing a path validation check error; and a .ps1 script failing to execute due to path literal encoding corruption.
- The root cause was a single uppercase non-ASCII character, an O with umlaut, in the project's parent directory path.
- Three work sessions produced four distinct toolchain failures with four different error messages and a separate search rabbit hole for each, and none of the error logs pointed to the actual common denominator.
- The author did not log the exact SDK patch versions at the moment of failure.
Compiled by The EngineerSomething wrong?How this is made
Why it matters
A single uppercase O-umlaut in a project's parent directory path took down four unrelated build tools and produced four unrelated error messages, none of which named the character [2][3][4]. That matters because the diagnosis lived in the environment rather than in any stack trace, which is precisely the class of failure that a preflight assertion catches and developer folklore does not.
The account is a first-person write-up published on dev.to, dated July 26, 2026, from a Flutter plus .NET project on Windows [1]. The author reports that an automated coding assistant, configured to stop and ask when it sees something unexpected, halted three separate build sessions [1]. The symptoms: `dart run build_runner build` failing with `package_config.json did not contain its own root package`; `flutter analyze` dying in a Language Server Protocol JSON-RPC framing crash; the Android Gradle Plugin throwing a path validation error; and a `.ps1` script failing on path literal encoding corruption [2]. Four toolchains, four search rabbit holes, and by the author's count zero error strings that pointed at the shared cause [4][15].
The useful part of the write-up is the isolation test, because the reflex on Windows is to blame a space in the directory name, and changing two variables at once proves nothing [9]. The author ran `flutter build apk` against the same project layout twice: `C:\Dev\Proje\App Test\` exited 0, and `C:\Dev\ProjeÖ\App Test\` exited 255 [8]. Spaces were not the problem. One character was.
The LSP crash is the most instructive of the four, because it shows the path is not merely a string on disk. The protocol header field is defined as the length of the content part in bytes [6]. A multi-byte UTF-8 character in a path that gets injected into a protocol payload breaks the equality between character count and byte count, and the author states the observed connection collapse is consistent with framing misalignment rather than a proven cause [7].
The workaround did not hold either. Creating a directory junction from a clean ASCII path such as `C:\project` to the real directory worked for the Dart and Flutter commands [10][11]. The Android pipeline crashed immediately, and AGP printed the physical target path containing the accented character instead of the junction path it was invoked through [12]. The author points to Java canonical-path resolution as the likely mechanism, while noting that Java's `File` documentation describes following symbolic links on UNIX and does not spell out Windows reparse points, and that AGP's source was not audited [13]. The counter-test supports the boundary: `flutter build web` through the same junction to the same physical directory exited 0, and that pipeline does not go through Gradle [14]. Of the pipelines re-tested behind the junction, the Gradle-backed one was the only failure [16].
Caveats worth keeping: this is one engineer, one machine, one report, and the exact SDK patch versions at the time of failure were not logged [5]. Take it as a reproduction recipe, not a specification.
What to watch is whether your own bootstrap or CI job asserts anything about the workspace path. A three-line check that fails loudly when the absolute path contains non-ASCII bytes converts four days of unrelated debugging into one legible message. The junction result also argues against treating aliasing as a fix, since at least one toolchain resolved through it and reported the real path anyway [12].