Merge branch fix/provider-upload-chunks
Pipelines as Code CI / hwlab-web-probe-sentinel-nc01- Success
Pipelines as Code CI / platform-infra-gitea-nc01- Failed
Pipelines as Code CI / unidesk-host- Success

This commit is contained in:
pikastech
2026-07-19 11:36:53 +02:00
2 changed files with 34 additions and 8 deletions
+26
View File
@@ -87,6 +87,32 @@ describe("ssh text transfer preflight", () => {
}
});
test("uploads files above one chunk without concatenating padded base64 blocks", async () => {
const dir = mkdtempSync(join(tmpdir(), "unidesk-chunked-transfer-"));
const source = join(dir, "payload.bin");
const content = Buffer.alloc((3 * 1024 * 1024) + 17, 0xa5);
writeFileSync(source, content);
const fake = fakeTransfer(content);
const invocation = parseSshInvocation("D601:/tmp", ["upload", source, "/tmp/payload.bin"]);
try {
expect(await runSshFileTransferOperation(
invocation,
["upload", source, "/tmp/payload.bin"],
fake.executor,
fake.builders,
)).toBe(0);
expect(fake.calls).toEqual([
"write-b64-begin",
"write-b64-append-stdin",
"write-b64-append-stdin",
"write-b64-commit",
"stat",
]);
} finally {
rmSync(dir, { recursive: true, force: true });
}
});
test("allows an explicit generated-text override without bypassing verification", async () => {
const dir = mkdtempSync(join(tmpdir(), "unidesk-generated-transfer-"));
const source = join(dir, "result.json");
+8 -8
View File
@@ -96,7 +96,7 @@ class SshFileTransferError extends Error {
}
const fileTransferWriteB64ArgvLimit = 48_000;
const fileTransferWriteRawChunkBytes = 131_072;
const fileTransferWriteRawChunkBytes = 3 * 1024 * 1024;
const fileTransferWriteB64ChunkChars = 1_398_104;
const fileTransferProgressEveryChunks = 16;
@@ -763,15 +763,15 @@ function posixFileTransferScript(): string {
" actual_sha256=$(sha256_file \"$target\"); if [ \"$actual_sha256\" != \"$expected_sha256\" ]; then printf 'transfer final sha256 mismatch for %s\\n' \"$target\" >&2; exit 25; fi",
" ;;",
" write-b64-begin)",
" target=$1; token=$2; ensure_parent \"$target\"; set_tmp_paths \"$target\" \"$token\"; : > \"$tmp_b64\"",
" target=$1; token=$2; ensure_parent \"$target\"; set_tmp_paths \"$target\" \"$token\"; : > \"$tmp\"",
" ;;",
" write-b64-append-stdin)",
" target=$1; token=$2; set_tmp_paths \"$target\" \"$token\"; cat >> \"$tmp_b64\"",
" target=$1; token=$2; set_tmp_paths \"$target\" \"$token\"",
" if ! base64 -d >> \"$tmp\"; then rm -f -- \"$tmp\"; printf 'transfer base64 chunk decode failed for %s\\n' \"$target\" >&2; exit 22; fi",
" ;;",
" write-b64-commit)",
" target=$1; token=$2; expected_bytes=$3; expected_sha256=$4; set_tmp_paths \"$target\" \"$token\"",
" if ! base64 -d < \"$tmp_b64\" > \"$tmp\"; then rm -f -- \"$tmp\" \"$tmp_b64\"; printf 'transfer base64 decode failed for %s\\n' \"$target\" >&2; exit 22; fi",
" rm -f -- \"$tmp_b64\"; verify_tmp \"$target\" \"$tmp\" \"$expected_bytes\" \"$expected_sha256\"; mv -f -- \"$tmp\" \"$target\"",
" verify_tmp \"$target\" \"$tmp\" \"$expected_bytes\" \"$expected_sha256\"; mv -f -- \"$tmp\" \"$target\"",
" actual_sha256=$(sha256_file \"$target\"); if [ \"$actual_sha256\" != \"$expected_sha256\" ]; then printf 'transfer final sha256 mismatch for %s\\n' \"$target\" >&2; exit 25; fi",
" ;;",
" *) printf 'unsupported transfer op: %s\\n' \"$op\" >&2; exit 2;;",
@@ -819,9 +819,9 @@ function windowsFileTransferScript(basePath: string | null, operation: SshFileTr
" 'stat' { if (-not (Test-Path -LiteralPath $target -PathType Leaf)) { Fail ('file not found: ' + $target) 1 }; $bytes = ([System.IO.FileInfo]$target).Length; $digest = Get-Sha256 $target; [Console]::Out.WriteLine(([string]$bytes) + ' ' + $digest); break }",
" 'write-b64-argv' { Decode-ToTarget $target ([string]::Concat($argvChunks)) ([Int64]$arg1) $arg2; break }",
" 'write-b64-stdin' { Decode-ToTarget $target ([Console]::In.ReadToEnd()) ([Int64]$arg1) $arg2; break }",
" 'write-b64-begin' { Ensure-Parent $target; Set-TmpPaths $target $arg1; [System.IO.File]::WriteAllText($script:tmpB64, '', [System.Text.Encoding]::ASCII); break }",
" 'write-b64-append-stdin' { Set-TmpPaths $target $arg1; $chunk = ([Console]::In.ReadToEnd()) -replace '\\s',''; [System.IO.File]::AppendAllText($script:tmpB64, $chunk, [System.Text.Encoding]::ASCII); break }",
" 'write-b64-commit' { Set-TmpPaths $target $arg1; $encoded = [System.IO.File]::ReadAllText($script:tmpB64, [System.Text.Encoding]::ASCII); Remove-Item -LiteralPath $script:tmpB64 -Force -ErrorAction SilentlyContinue; Decode-ToTarget $target $encoded ([Int64]$arg2) $arg3; break }",
" 'write-b64-begin' { Ensure-Parent $target; Set-TmpPaths $target $arg1; [System.IO.File]::WriteAllBytes($script:tmp, [byte[]]::new(0)); break }",
" 'write-b64-append-stdin' { Set-TmpPaths $target $arg1; try { $bytes = [Convert]::FromBase64String((([Console]::In.ReadToEnd()) -replace '\\s','')) } catch { Remove-Item -LiteralPath $script:tmp -Force -ErrorAction SilentlyContinue; Fail ('transfer base64 chunk decode failed for ' + $target + ': ' + $_.Exception.Message) 22 }; $stream = [System.IO.File]::Open($script:tmp, [System.IO.FileMode]::Append, [System.IO.FileAccess]::Write, [System.IO.FileShare]::None); try { $stream.Write($bytes, 0, $bytes.Length) } finally { $stream.Dispose() }; break }",
" 'write-b64-commit' { Set-TmpPaths $target $arg1; Verify-Temp $target $script:tmp ([Int64]$arg2) $arg3; Move-Item -LiteralPath $script:tmp -Destination $target -Force; $actualSha256 = Get-Sha256 $target; if ($actualSha256 -ne $arg3) { Fail ('transfer final sha256 mismatch for ' + $target) 25 }; break }",
" default { Fail ('unsupported transfer op: ' + $operation) 2 }",
"}",
].join(" ");