From a4b5f8e7c91eb004f6e55ecbb807bdd55d641360 Mon Sep 17 00:00:00 2001 From: Ryan Moran Date: Mon, 29 Mar 2021 17:19:19 -0700 Subject: [PATCH] Add bill of materials entry facility for postal.Service --- postal/buildpack.go | 12 ++++----- postal/service.go | 27 ++++++++++++++++++++ postal/service_test.go | 57 +++++++++++++++++++++++++++++++++++++++++- 3 files changed, 89 insertions(+), 7 deletions(-) diff --git a/postal/buildpack.go b/postal/buildpack.go index 9e46ba26..7161404a 100644 --- a/postal/buildpack.go +++ b/postal/buildpack.go @@ -16,15 +16,9 @@ type Dependency struct { // ID is the identifier used to specify the dependency. ID string `toml:"id"` - // Version is the specific version of the dependency. - Version string `toml:"version"` - // Name is the human-readable name of the dependency. Name string `toml:"name"` - // URI is the uri location of the built dependency. - URI string `toml:"uri"` - // SHA256 is the hex-encoded SHA256 checksum of the built dependency. SHA256 string `toml:"sha256"` @@ -36,6 +30,12 @@ type Dependency struct { // Stacks is a list of stacks for which the dependency is built. Stacks []string `toml:"stacks"` + + // URI is the uri location of the built dependency. + URI string `toml:"uri"` + + // Version is the specific version of the dependency. + Version string `toml:"version"` } func parseBuildpack(path, name string) ([]Dependency, string, error) { diff --git a/postal/service.go b/postal/service.go index 233c0391..eb9bdd66 100644 --- a/postal/service.go +++ b/postal/service.go @@ -7,8 +7,10 @@ import ( "regexp" "sort" "strings" + "time" "github.com/Masterminds/semver/v3" + "github.com/paketo-buildpacks/packit" "github.com/paketo-buildpacks/packit/cargo" "github.com/paketo-buildpacks/packit/postal/internal" "github.com/paketo-buildpacks/packit/vacation" @@ -177,3 +179,28 @@ func (s Service) Deliver(dependency Dependency, cnbPath, layerPath, platformPath func (s Service) Install(dependency Dependency, cnbPath, layerPath string) error { return s.Deliver(dependency, cnbPath, layerPath, "/platform") } + +// GenerateBillOfMaterials will generate a list of BOMEntry values given a +// collection of Dependency values. +func (s Service) GenerateBillOfMaterials(dependencies ...Dependency) []packit.BOMEntry { + var entries []packit.BOMEntry + for _, dependency := range dependencies { + entry := packit.BOMEntry{ + Name: dependency.Name, + Metadata: map[string]interface{}{ + "sha256": dependency.SHA256, + "stacks": dependency.Stacks, + "uri": dependency.URI, + "version": dependency.Version, + }, + } + + if (dependency.DeprecationDate != time.Time{}) { + entry.Metadata["deprecation-date"] = dependency.DeprecationDate + } + + entries = append(entries, entry) + } + + return entries +} diff --git a/postal/service_test.go b/postal/service_test.go index 84827b0f..72fcd99d 100644 --- a/postal/service_test.go +++ b/postal/service_test.go @@ -14,6 +14,7 @@ import ( "testing" "time" + "github.com/paketo-buildpacks/packit" "github.com/paketo-buildpacks/packit/postal" "github.com/paketo-buildpacks/packit/postal/fakes" "github.com/sclevine/spec" @@ -38,7 +39,6 @@ func testService(t *testing.T, context spec.G, it spec.S) { Expect(err).NotTo(HaveOccurred()) path = file.Name() - _, err = file.WriteString(` [[metadata.dependencies]] deprecation_date = 2022-04-01T00:00:00Z @@ -823,4 +823,59 @@ version = "this is super not semver" }) }) }) + + context("GenerateBillOfMaterials", func() { + var deprecationDate time.Time + + it.Before(func() { + var err error + deprecationDate, err = time.Parse(time.RFC3339, "2022-04-01T00:00:00Z") + Expect(err).NotTo(HaveOccurred()) + }) + + it("returns a list of BOMEntry values", func() { + entries := service.GenerateBillOfMaterials( + postal.Dependency{ + DeprecationDate: deprecationDate, + ID: "some-entry", + Name: "Some Entry", + SHA256: "some-sha", + Source: "some-source", + Stacks: []string{"some-stack"}, + URI: "some-uri", + Version: "1.2.3", + }, + postal.Dependency{ + ID: "other-entry", + Name: "Other Entry", + SHA256: "other-sha", + Source: "other-source", + Stacks: []string{"other-stack"}, + URI: "other-uri", + Version: "4.5.6", + }, + ) + Expect(entries).To(Equal([]packit.BOMEntry{ + { + Name: "Some Entry", + Metadata: map[string]interface{}{ + "deprecation-date": deprecationDate, + "sha256": "some-sha", + "stacks": []string{"some-stack"}, + "uri": "some-uri", + "version": "1.2.3", + }, + }, + { + Name: "Other Entry", + Metadata: map[string]interface{}{ + "sha256": "other-sha", + "stacks": []string{"other-stack"}, + "uri": "other-uri", + "version": "4.5.6", + }, + }, + })) + }) + }) }