in lib/src/context.dart [370:433]
bool _needsNormalization(String path) {
var start = 0;
final codeUnits = path.codeUnits;
int? previousPrevious;
int? previous;
// Skip past the root before we start looking for snippets that need
// normalization. We want to normalize "//", but not when it's part of
// "http://".
final root = style.rootLength(path);
if (root != 0) {
start = root;
previous = chars.slash;
// On Windows, the root still needs to be normalized if it contains a
// forward slash.
if (style == Style.windows) {
for (var i = 0; i < root; i++) {
if (codeUnits[i] == chars.slash) return true;
}
}
}
for (var i = start; i < codeUnits.length; i++) {
final codeUnit = codeUnits[i];
if (style.isSeparator(codeUnit)) {
// Forward slashes in Windows paths are normalized to backslashes.
if (style == Style.windows && codeUnit == chars.slash) return true;
// Multiple separators are normalized to single separators.
if (previous != null && style.isSeparator(previous)) return true;
// Single dots and double dots are normalized to directory traversals.
//
// This can return false positives for ".../", but that's unlikely
// enough that it's probably not going to cause performance issues.
if (previous == chars.period &&
(previousPrevious == null ||
previousPrevious == chars.period ||
style.isSeparator(previousPrevious))) {
return true;
}
}
previousPrevious = previous;
previous = codeUnit;
}
// Empty paths are normalized to ".".
if (previous == null) return true;
// Trailing separators are removed.
if (style.isSeparator(previous)) return true;
// Single dots and double dots are normalized to directory traversals.
if (previous == chars.period &&
(previousPrevious == null ||
style.isSeparator(previousPrevious) ||
previousPrevious == chars.period)) {
return true;
}
return false;
}