-
Notifications
You must be signed in to change notification settings - Fork 604
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: support push with soci #2467
Conversation
|
||
// CreateSoci creates a SOCI index(`rawRef`) | ||
func CreateSoci(rawRef string) error { | ||
sociExecutable, err := exec.LookPath("soci") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is shelling out to the SOCI CLI a design goal or is it just because the CLI has non-trivial logic?
I would think using SOCI as a library here would be better long term.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If I understand correctly, the pros of using SOCI library include:
- Does not require SOCI CLI to be installed in Nerdctl env
- Cleaner code to call library instead of calling commands
However, there is already a common practice of calling commands of dependencies in Nerdctl, such as Buildkit, Cosign, Notation, and soci-snapshotter-grpc
is anyways needed to be pre-configured as part of SOCI provisioning. So the two pros don't seem significant.
Here are the reasons of leaning to using SOCI CLI instead of library for now.
- SOCI CLI has well-defined documentation and the backward compatibility is respected by default. The library code doesn't have documentation and it is not clear about how much backward compatibility it will have. It may also be difficult for SOCI maintainers to promise and define that.
- SOCI CLI layer has some business logic which can call multiple methods of library code, which is tedious to duplicate in Nerdctl.
For both above, some refactoring in SOCI similar to what Nerdctl is doing could help (with that, the library code can include all the business logic and can be clearly defined and promised backward compatibility) but may not deserve.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The SOCI CLI does not guarantee backwards compatibility at this point https://github.com/awslabs/soci-snapshotter/blob/main/RELEASES.md#api-stability, but you're probably right that the CLI is more likely to be backwards compatible than the library.
I agree that the CLI is the right thing to do for this PR. I was curious what the longer term vision was, but it seems that there's precedence for relying on the CLI indefinitely.
pkg/snapshotterutil/sociutil.go
Outdated
return err | ||
} | ||
ref := rawRef | ||
if !strings.Contains(ref, "@") { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is there a use-case where this is true? The current call site always contains a specific digest reference, right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You are right. Fixed.
@AkihiroSuda @djdongjin May I get basic concensus of the high level approach (See PR description) before polishing the implementation and adding tests? |
👍 on exec-ing the |
b1aa161
to
da8220d
Compare
cd84ab1
to
ea46b02
Compare
pkg/snapshotterutil/sociutil.go
Outdated
return err | ||
} | ||
|
||
sociCmd := exec.Command(sociExecutable, []string{"create"}...) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You should also pass --namespace
, --address
(containerd address), and maybe --timeout
.
d4fd880
to
fc75f2a
Compare
sociCmd.Args = append(sociCmd.Args, "--namespace", gOpts.Namespace) | ||
} | ||
if sOpts.SpanSize != -1 { | ||
sociCmd.Args = append(sociCmd.Args, "--span-size", strconv.FormatInt(sOpts.SpanSize, 10)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks like values are in bytes in soci cli. See https://github.com/awslabs/soci-snapshotter/blob/f556b45e8e241ff243776e15352a6b7bd38f2161/soci/soci_index.go#L57-L58
defaultSpanSize = int64(1 << 22) // 4MiB
defaultMinLayerSize = 10 << 20 // 10MiB
Maybe room for improved UX to specify value with mib
, m
, kib
, k
suffix and do the conversion?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah. Maybe this can contribute to soci CLI later.
@@ -174,3 +176,69 @@ func TestPushNonDistributableArtifacts(t *testing.T) { | |||
} | |||
assert.Equal(t, resp.StatusCode, http.StatusOK, "non-distributable blob should be available") | |||
} | |||
|
|||
func TestPushSoci(t *testing.T) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
test LGTM. maybe could deduplicate some of https://github.com/containerd/nerdctl/blob/main/cmd/nerdctl/container_run_soci_linux_test.go
pkg/snapshotterutil/sociutil.go
Outdated
logrus.Warn("soci: " + err.Error()) | ||
} | ||
if err := sociCmd.Start(); err != nil { | ||
// only return err if it's critical (soci start failed.) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit:
// only return err if it's critical (soci start failed.) | |
// only return err if it's critical (soci command failed to start.) |
012f353
to
374a376
Compare
da21d43
to
6420080
Compare
pkg/testutil/testutil_linux.go
Outdated
@@ -60,6 +60,7 @@ var ( | |||
const ( | |||
FedoraESGZImage = "ghcr.io/stargz-containers/fedora:30-esgz" // eStargz | |||
FfmpegSociImage = "public.ecr.aws/soci-workshop-examples/ffmpeg:latest" // SOCI | |||
UbuntuImage = "public.ecr.aws/docker/library/ubuntu:latest" // Large enough for testing soci index creation |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please pin the version
bf32896
to
6dd044b
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, LGTM if CI is green
Failing
|
928e0b6
to
412a0b7
Compare
Signed-off-by: Ziwen Ning <ningziwe@amazon.com>
Issue
#1329
High level approach
The current approach integrates both
soci create
andsoci push
tonerdctl push
when soci is specified innerdctl push
. The change is based on the assumption that we want to integrate whole soci workflow to nerdctl seamlessly without letting users run any soci commands by themselves.One alternative is to integrate
soci create
tonerdctl build
andsoci push
tonerdctl push
.nerdctl build
makes sense to be independent withnerdctl push
because the image can ran or exported locally without pushing later, but soci index is for lazy pull, which doesn't make sense without pushing to a registry later. The soci getting-started guide also putssoci create
after pushing image to registry. So didn't choose this approach.SOCI flags
When calling
soci
commands innerdctl push
. There are many flags insoci create
andsoci push
to be set properly. There are several possible ways of setting them:soci
. (Similar to the style in Cosign)quiet
is true in soci, Nerdctl quiet should already suppress anything