Skip to content

Commit

Permalink
Merge pull request #10 from cloudfoundry/strip-components
Browse files Browse the repository at this point in the history
Adds strip-components option to tar archives
  • Loading branch information
ryanmoran authored Apr 17, 2020
2 parents 4ac03a0 + 71092dc commit fecca40
Show file tree
Hide file tree
Showing 2 changed files with 82 additions and 9 deletions.
37 changes: 31 additions & 6 deletions vacation/vacation.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,20 +7,24 @@ import (
"io"
"os"
"path/filepath"
"strings"

"github.com/ulikunitz/xz"
)

type TarArchive struct {
reader io.Reader
reader io.Reader
components int
}

type TarGzipArchive struct {
reader io.Reader
reader io.Reader
components int
}

type TarXZArchive struct {
reader io.Reader
reader io.Reader
components int
}

func NewTarArchive(inputReader io.Reader) TarArchive {
Expand All @@ -46,7 +50,13 @@ func (ta TarArchive) Decompress(destination string) error {
return fmt.Errorf("failed to read tar response: %s", err)
}

path := filepath.Join(destination, hdr.Name)
fileNames := strings.Split(hdr.Name, string(filepath.Separator))

if len(fileNames) <= ta.components {
continue
}

path := filepath.Join(append([]string{destination}, fileNames[ta.components:]...)...)
switch hdr.Typeflag {
case tar.TypeDir:
err = os.MkdirAll(path, os.ModePerm)
Expand Down Expand Up @@ -88,7 +98,7 @@ func (gz TarGzipArchive) Decompress(destination string) error {
return fmt.Errorf("failed to create gzip reader: %w", err)
}

return NewTarArchive(gzr).Decompress(destination)
return NewTarArchive(gzr).StripComponents(gz.components).Decompress(destination)
}

func (txz TarXZArchive) Decompress(destination string) error {
Expand All @@ -97,5 +107,20 @@ func (txz TarXZArchive) Decompress(destination string) error {
return fmt.Errorf("failed to create xz reader: %w", err)
}

return NewTarArchive(xzr).Decompress(destination)
return NewTarArchive(xzr).StripComponents(txz.components).Decompress(destination)
}

func (ta TarArchive) StripComponents(components int) TarArchive {
ta.components = components
return ta
}

func (gz TarGzipArchive) StripComponents(components int) TarGzipArchive {
gz.components = components
return gz
}

func (txz TarXZArchive) StripComponents(components int) TarXZArchive {
txz.components = components
return txz
}
54 changes: 51 additions & 3 deletions vacation/vacation_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ func testVacation(t *testing.T, context spec.G, it spec.S) {
Expect(os.RemoveAll(tempDir)).To(Succeed())
})

it("downloads the dependency and unpackages it into the path", func() {
it("unpackages the archive into the path", func() {
var err error
err = tarArchive.Decompress(tempDir)
Expect(err).ToNot(HaveOccurred())
Expand All @@ -96,6 +96,22 @@ func testVacation(t *testing.T, context spec.G, it spec.S) {
Expect(data).To(Equal([]byte(`first`)))
})

it("unpackages the archive into the path but also strips the first component", func() {
var err error
err = tarArchive.StripComponents(1).Decompress(tempDir)
Expect(err).ToNot(HaveOccurred())

files, err := filepath.Glob(fmt.Sprintf("%s/*", tempDir))
Expect(err).NotTo(HaveOccurred())
Expect(files).To(ConsistOf([]string{
filepath.Join(tempDir, "some-other-dir"),
}))

Expect(filepath.Join(tempDir, "some-other-dir")).To(BeADirectory())
Expect(filepath.Join(tempDir, "some-other-dir", "some-file")).To(BeARegularFile())

})

context("failure cases", func() {
context("when it fails to read the tar response", func() {
it("returns an error", func() {
Expand Down Expand Up @@ -213,7 +229,7 @@ func testVacation(t *testing.T, context spec.G, it spec.S) {
Expect(os.RemoveAll(tempDir)).To(Succeed())
})

it("downloads the dependency and unpackages it into the path", func() {
it("unpackages the archive into the path", func() {
var err error
err = tarGzipArchive.Decompress(tempDir)
Expect(err).ToNot(HaveOccurred())
Expand All @@ -240,6 +256,22 @@ func testVacation(t *testing.T, context spec.G, it spec.S) {
Expect(data).To(Equal([]byte(`first`)))
})

it("unpackages the archive into the path but also strips the first component", func() {
var err error
err = tarGzipArchive.StripComponents(1).Decompress(tempDir)
Expect(err).ToNot(HaveOccurred())

files, err := filepath.Glob(fmt.Sprintf("%s/*", tempDir))
Expect(err).NotTo(HaveOccurred())
Expect(files).To(ConsistOf([]string{
filepath.Join(tempDir, "some-other-dir"),
}))

Expect(filepath.Join(tempDir, "some-other-dir")).To(BeADirectory())
Expect(filepath.Join(tempDir, "some-other-dir", "some-file")).To(BeARegularFile())

})

context("failure cases", func() {
context("when it fails to create a grip reader", func() {
it("returns an error", func() {
Expand Down Expand Up @@ -303,7 +335,7 @@ func testVacation(t *testing.T, context spec.G, it spec.S) {
Expect(os.RemoveAll(tempDir)).To(Succeed())
})

it("downloads the dependency and unpackages it into the path", func() {
it("unpackages the archive into the path", func() {
var err error
err = tarXZArchive.Decompress(tempDir)
Expect(err).ToNot(HaveOccurred())
Expand All @@ -330,6 +362,22 @@ func testVacation(t *testing.T, context spec.G, it spec.S) {
Expect(data).To(Equal([]byte(`first`)))
})

it("unpackages the archive into the path but also strips the first component", func() {
var err error
err = tarXZArchive.StripComponents(1).Decompress(tempDir)
Expect(err).ToNot(HaveOccurred())

files, err := filepath.Glob(fmt.Sprintf("%s/*", tempDir))
Expect(err).NotTo(HaveOccurred())
Expect(files).To(ConsistOf([]string{
filepath.Join(tempDir, "some-other-dir"),
}))

Expect(filepath.Join(tempDir, "some-other-dir")).To(BeADirectory())
Expect(filepath.Join(tempDir, "some-other-dir", "some-file")).To(BeARegularFile())

})

context("failure cases", func() {
context("when it fails to create a xz reader", func() {
it("returns an error", func() {
Expand Down

0 comments on commit fecca40

Please sign in to comment.