fix(archive): sanitize non-UTF-8 entry names during extraction (#3225)

ZIP archives with GBK-encoded names inserted raw bytes into the
database, failing the whole task with 'pq: invalid byte sequence for
encoding UTF8'. Entry names now pass through ToValidUTF8 at both the
listing and extraction layers, so masked extraction stays consistent
and undecodable names degrade to replacement chars instead of a crash.
The existing encoding picker (gbk/gb18030/big5/shiftjis/...) remains
the way to recover proper names.

Generated with [Devin](https://devin.ai)

Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
pull/3582/head
Tomas Dvorak 2 weeks ago
parent 01e65f4e69
commit 4b5433179e

@ -283,7 +283,7 @@ func getZipFileList(ctx context.Context, file io.ReaderAt, size int64, textEncod
info := f.FileInfo() info := f.FileInfo()
modTime := info.ModTime() modTime := info.ModTime()
fileList = append(fileList, ArchivedFile{ fileList = append(fileList, ArchivedFile{
Name: util.FormSlash(hdr.Name), Name: util.FormSlash(strings.ToValidUTF8(hdr.Name, "<22>")),
Size: info.Size(), Size: info.Size(),
UpdatedAt: &modTime, UpdatedAt: &modTime,
IsDirectory: info.IsDir(), IsDirectory: info.IsDir(),
@ -303,7 +303,7 @@ func get7zFileList(ctx context.Context, file io.ReaderAt, size int64, extEncodin
info := f.FileInfo() info := f.FileInfo()
modTime := info.ModTime() modTime := info.ModTime()
fileList = append(fileList, ArchivedFile{ fileList = append(fileList, ArchivedFile{
Name: util.FormSlash(f.Name), Name: util.FormSlash(strings.ToValidUTF8(f.Name, "<22>")),
Size: info.Size(), Size: info.Size(),
UpdatedAt: &modTime, UpdatedAt: &modTime,
IsDirectory: info.IsDir(), IsDirectory: info.IsDir(),

@ -375,7 +375,7 @@ func (m *ExtractArchiveTask) masterExtractArchive(ctx context.Context, dep depen
return nil return nil
} }
rawPath := util.FormSlash(f.NameInArchive) rawPath := util.FormSlash(strings.ToValidUTF8(f.NameInArchive, "<22>"))
savePath := dst.JoinRaw(rawPath) savePath := dst.JoinRaw(rawPath)
// If file mask is not empty, check if the path is in the mask // If file mask is not empty, check if the path is in the mask
@ -751,7 +751,7 @@ func (m *SlaveExtractArchiveTask) Do(ctx context.Context) (task.Status, error) {
return nil return nil
} }
rawPath := util.FormSlash(f.NameInArchive) rawPath := util.FormSlash(strings.ToValidUTF8(f.NameInArchive, "<22>"))
savePath := dst.JoinRaw(rawPath) savePath := dst.JoinRaw(rawPath)
// If file mask is not empty, check if the path is in the mask // If file mask is not empty, check if the path is in the mask

Loading…
Cancel
Save