mirror of
https://github.com/containers/skopeo.git
synced 2025-08-11 11:22:05 +00:00
Add (skopeo manifest-digest)
A plain sha256sum and the like is insufficient because we need to strip signatures from v2s1 manifests; so, add a subcommand. This can be used together with (skopeo inspect --raw) to download a manifest from a source untrusted to modify it under us; we download a manifest once using (skopeo inspect --raw), compute a digest using (skopeo manifest-digest), and then do all future operations using a digest reference.
This commit is contained in:
parent
e4315e82b0
commit
c236b29c75
11
cmd/skopeo/fixtures/v2s1-invalid-signatures.manifest.json
Normal file
11
cmd/skopeo/fixtures/v2s1-invalid-signatures.manifest.json
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
{
|
||||||
|
"schemaVersion": 1,
|
||||||
|
"name": "mitr/buxybox",
|
||||||
|
"tag": "latest",
|
||||||
|
"architecture": "amd64",
|
||||||
|
"fsLayers": [
|
||||||
|
],
|
||||||
|
"history": [
|
||||||
|
],
|
||||||
|
"signatures": 1
|
||||||
|
}
|
@ -61,6 +61,7 @@ func createApp() *cli.App {
|
|||||||
inspectCmd,
|
inspectCmd,
|
||||||
layersCmd,
|
layersCmd,
|
||||||
deleteCmd,
|
deleteCmd,
|
||||||
|
manifestDigestCmd,
|
||||||
standaloneSignCmd,
|
standaloneSignCmd,
|
||||||
standaloneVerifyCmd,
|
standaloneVerifyCmd,
|
||||||
}
|
}
|
||||||
|
35
cmd/skopeo/manifest.go
Normal file
35
cmd/skopeo/manifest.go
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"io/ioutil"
|
||||||
|
|
||||||
|
"github.com/containers/image/manifest"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
func manifestDigest(context *cli.Context) error {
|
||||||
|
if len(context.Args()) != 1 {
|
||||||
|
return errors.New("Usage: skopeo manifest-digest manifest")
|
||||||
|
}
|
||||||
|
manifestPath := context.Args()[0]
|
||||||
|
|
||||||
|
man, err := ioutil.ReadFile(manifestPath)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("Error reading manifest from %s: %v", manifestPath, err)
|
||||||
|
}
|
||||||
|
digest, err := manifest.Digest(man)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("Error computing digest: %v", err)
|
||||||
|
}
|
||||||
|
fmt.Fprintf(context.App.Writer, "%s\n", digest)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var manifestDigestCmd = cli.Command{
|
||||||
|
Name: "manifest-digest",
|
||||||
|
Usage: "Compute a manifest digest of a file",
|
||||||
|
ArgsUsage: "MANIFEST",
|
||||||
|
Action: manifestDigest,
|
||||||
|
}
|
31
cmd/skopeo/manifest_test.go
Normal file
31
cmd/skopeo/manifest_test.go
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestManifestDigest(t *testing.T) {
|
||||||
|
// Invalid command-line arguments
|
||||||
|
for _, args := range [][]string{
|
||||||
|
{},
|
||||||
|
{"a1", "a2"},
|
||||||
|
} {
|
||||||
|
out, err := runSkopeo(append([]string{"manifest-digest"}, args...)...)
|
||||||
|
assertTestFailed(t, out, err, "Usage")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Error reading manifest
|
||||||
|
out, err := runSkopeo("manifest-digest", "/this/doesnt/exist")
|
||||||
|
assertTestFailed(t, out, err, "/this/doesnt/exist")
|
||||||
|
|
||||||
|
// Error computing manifest
|
||||||
|
out, err = runSkopeo("manifest-digest", "fixtures/v2s1-invalid-signatures.manifest.json")
|
||||||
|
assertTestFailed(t, out, err, "computing digest")
|
||||||
|
|
||||||
|
// Success
|
||||||
|
out, err = runSkopeo("manifest-digest", "fixtures/image.manifest.json")
|
||||||
|
assert.NoError(t, err)
|
||||||
|
assert.Equal(t, fixturesTestImageManifestDigest+"\n", out)
|
||||||
|
}
|
@ -91,6 +91,11 @@ Get image layers of _image-name_
|
|||||||
|
|
||||||
_image-name_ name of the image to retrieve layers
|
_image-name_ name of the image to retrieve layers
|
||||||
|
|
||||||
|
## skopeo manifest-digest
|
||||||
|
**skopeo manifest-digest** _manifest-file_
|
||||||
|
|
||||||
|
Compute a manifest digest of _manifest-file_ and write it to standard output.
|
||||||
|
|
||||||
## skopeo standalone-sign
|
## skopeo standalone-sign
|
||||||
**skopeo standalone-sign** _manifest docker-reference key-fingerprint_ **--output**|**-o** _signature_
|
**skopeo standalone-sign** _manifest docker-reference key-fingerprint_ **--output**|**-o** _signature_
|
||||||
|
|
||||||
@ -184,6 +189,11 @@ $ ls layers-500650331/
|
|||||||
manifest.json
|
manifest.json
|
||||||
a3ed95caeb02ffe68cdd9fd84406680ae93d633cb16422d00e8a7c22955b46d4.tar
|
a3ed95caeb02ffe68cdd9fd84406680ae93d633cb16422d00e8a7c22955b46d4.tar
|
||||||
```
|
```
|
||||||
|
## skopeo manifest-digest
|
||||||
|
```sh
|
||||||
|
$ skopeo manifest-digest manifest.json
|
||||||
|
sha256:a59906e33509d14c036c8678d687bd4eec81ed7c4b8ce907b888c607f6a1e0e6
|
||||||
|
```
|
||||||
## skopeo standalone-sign
|
## skopeo standalone-sign
|
||||||
```sh
|
```sh
|
||||||
$ skopeo standalone-sign busybox-manifest.json registry.example.com/example/busybox 1D8230F6CDB6A06716E414C1DB72F2188BB46CC8 --output busybox.signature
|
$ skopeo standalone-sign busybox-manifest.json registry.example.com/example/busybox 1D8230F6CDB6A06716E414C1DB72F2188BB46CC8 --output busybox.signature
|
||||||
|
Loading…
Reference in New Issue
Block a user