fix(plugin): write slash-separated paths in plugin tarballs

CreatePluginTarball used filepath.Join for tar member names. On Windows
that emits backslashes, which Unix extractors treat as a literal
character, so plugin.yaml is not found after helm plugin package.

Match chart save and convert names with filepath.ToSlash.

Signed-off-by: Zhaoqi Xu <lzy00419@outlook.com>
pull/32620/head
Zhaoqi Xu 1 week ago
parent fa11636b01
commit 57c3ea747a

@ -130,8 +130,8 @@ func CreatePluginTarball(sourceDir, pluginName string, w io.Writer) error {
return err return err
} }
// Include the base directory name in the tarball // Tar member names must use / even when packaging on Windows.
header.Name = filepath.Join(baseDir, relPath) header.Name = filepath.ToSlash(filepath.Join(baseDir, relPath))
// Write header // Write header
if err := tw.WriteHeader(header); err != nil { if err := tw.WriteHeader(header); err != nil {

@ -16,6 +16,11 @@ limitations under the License.
package plugin package plugin
import ( import (
"archive/tar"
"bytes"
"compress/gzip"
"errors"
"io"
"os" "os"
"path/filepath" "path/filepath"
"testing" "testing"
@ -78,3 +83,42 @@ runtimeConfig:
// The signature should contain the tarball hash // The signature should contain the tarball hash
assert.Contains(t, sig, "sha256:"+expectedHash, "signature does not contain expected tarball hash: sha256:%s", expectedHash) assert.Contains(t, sig, "sha256:"+expectedHash, "signature does not contain expected tarball hash: sha256:%s", expectedHash)
} }
func TestCreatePluginTarballUsesSlashSeparatedNames(t *testing.T) {
tempDir := t.TempDir()
pluginDir := filepath.Join(tempDir, "test-plugin")
require.NoError(t, os.MkdirAll(filepath.Join(pluginDir, "bin"), 0o755))
pluginYAML := `apiVersion: v1
name: test-plugin
type: cli/v1
runtime: subprocess
version: 1.0.0
runtimeConfig:
platformCommand:
- command: echo`
require.NoError(t, os.WriteFile(filepath.Join(pluginDir, "plugin.yaml"), []byte(pluginYAML), 0o644))
require.NoError(t, os.WriteFile(filepath.Join(pluginDir, "bin", "helper"), []byte("echo\n"), 0o755))
var buf bytes.Buffer
require.NoError(t, CreatePluginTarball(pluginDir, "test-plugin", &buf))
gzr, err := gzip.NewReader(&buf)
require.NoError(t, err)
t.Cleanup(func() { gzr.Close() })
tr := tar.NewReader(gzr)
var names []string
for {
header, err := tr.Next()
if errors.Is(err, io.EOF) {
break
}
require.NoError(t, err)
assert.Equalf(t, filepath.ToSlash(header.Name), header.Name, "tar member %q must use slash separators", header.Name)
names = append(names, header.Name)
}
assert.Contains(t, names, "test-plugin/plugin.yaml")
assert.Contains(t, names, "test-plugin/bin/helper")
}

Loading…
Cancel
Save