Skip to content
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

Add flag to export image to OCI layout format - (Experimental) #1314

Closed
wants to merge 10 commits into from

Conversation

jjbustamante
Copy link
Member

@jjbustamante jjbustamante commented Oct 26, 2021

Summary

Eric Hripko worked a few months ago on integrating Buildkit with Lifecycle (watch demo here), after that work some ideas on improving lifecycle were designed, one idea was to add a new flag to export the container image into OCI format.

This PR adds the experimental feature in Pack to invoke the lifecycle supporting this new flag for exporting the image.

Output

A new flag -oci-dir was added, this new flag is a string and the argument specifies the path in the local filesystem where the OCI image must be exported

Screen Shot 2021-10-26 at 2 09 57 PM

The following image shows the arguments during the exporting phase

Screen Shot 2021-10-26 at 2 11 02 PM

We can notice three things here:

  1. layout flag is sent to the lifecycle
  2. CNB_LAYOUT_DIR environment variable is also sent to lifecycle
  3. We can notice a new volume mounted in the local filesystem and pointing to the directory specified in the environment variable CNB_LAYOUT_DIR is also created

Finally, the following image shows the final output. A new folder /oci is created and inside this folder, the image in OCI format is saved

Screen Shot 2021-10-26 at 2 12 22 PM

Before

The exporting flag didn't exist

After

A new flag --oci-dir was added

Documentation

  • Should this change be documented?
    • Yes, see #___
    • [x ] No

Related

This feature requires a new version of the lifecycle, but is still on experimental mode
Resolves #___

@jjbustamante jjbustamante requested a review from a team as a code owner October 26, 2021 19:28
@github-actions github-actions bot added the type/enhancement Issue that requests a new feature or improvement. label Oct 26, 2021
@github-actions github-actions bot added this to the 0.22.0 milestone Oct 26, 2021
Copy link
Contributor

@aemengo aemengo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's quite a lot of commits here. Perhaps we can "squash" some of these 😅

Also: to help us see the end result, can we get a build of the experimental lifecycle?

build.go Outdated
@@ -573,6 +584,32 @@ func allBuildpacks(builderImage imgutil.Image, additionalBuildpacks []dist.Build
return all, nil
}

func (c *Client) processOCIPath(ociPath string) (string, error) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A couple things:

  1. Perhaps you're not already familiar with the os.MkdirAll stdlib function, which makes a directory if it doesn't it exists. It could simplify some of the code written here.
  2. Perhaps we can always make an oci/ directory, even if the user provided a path. e.g. filepath.Join(ociPath, "oci"). Up to you but I think it's a pretty low stakes move and, again, it could simplify some of the code written here.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks the hint @aemengo I just did some changes in the following commit to simplify the code based on the feedback

Comment on lines 391 to 446
if l.opts.OCIPath != "" {
flagsOpt = WithFlags("-layout")
}
_, layoutOpt, layoutEnv := l.configureLayout([]string{})

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What does the -layout flag do in the analyze phase? If it doesn't yet have a purpose, I'd rather that it would be kept out.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well, during analyzing it is used to mount the previous image reading from the OCI layout format, for example, you ran the command and export your image to /oci folder in your local, if you run again the build, then the /oci previously generated is mounted and analyze do its job

@@ -553,3 +565,15 @@ func addTags(flags, additionalTags []string) []string {
}
return flags
}

func (l *LifecycleExecution) configureLayout(flags []string) ([]string, PhaseConfigProviderOperation, PhaseConfigProviderOperation) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just my opinion here, but I'd rather not have this function. All the flags and PhaseConfigProviderOperation construction that we have is definitely ugly and overdue for a refactor. But having this function here, that I have to jump into to see what it's doing and what's being returned, doesn't help much.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agreed that the code it's a little ugly :) , but I removed the function, just because it is making it hard to read the code.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I liked the idea though.

Please take a look at my commit and see if you like my interpretation of your idea.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sweet!!! That's a more elegant approach!!! hahahah Thanks!


if l.opts.OCIPath != "" {
flags = append(flags, "-layout")
layoutOpt = WithBinds(fmt.Sprintf("%s:%s:%s", l.opts.OCIPath, l.mountPaths.ociDir(), "rw"))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The downside of this WithBinds is that it wouldn't work for a remote docker daemon. If that matters, another option can be to copy out the directory before the container is stopped

See some sample code.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh! but you have that function in your interactive branch any chance to get that function merged into main to be available to use it?. I tried to find something similar but then I decided for WithBinds but thanks for feedback.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would probably take longer get the function merged independently. 😅 You could copy-n-paste it into this PR. I'd be happy to pair with you on it, if needed.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@aemengo I did some changes, I took the function you created in the interactive branch and removed the WithBinds. As I mentioned, I was having some issues with the unit tests, but following your suggestions, I added a new method in the export, could you just take a look? it's this line

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like it much better. 👍🏾 from me.

I was inspired though and took it a little further. Please take a look at my commit and see if how you feel about it.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, I can see you went into the zone ... 😄

@jromero jromero modified the milestones: 0.22.0, 0.23.0 Nov 2, 2021
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
…xporting path then we assumed the feature must be enable, also the flag is hidden under experimentals flags

Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
…xporting path then we assumed the feature must be enable, also the flag is hidden under experimentals flags

Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
@jjbustamante jjbustamante force-pushed the feature/oci-layout branch 2 times, most recently from f6ef239 to c61754f Compare November 4, 2021 01:10
Signed-off-by: Juan Bustamante <jbustamante@vmware.com>
@jromero
Copy link
Member

jromero commented Mar 22, 2022

Whatever happened to this? Should this be draft or do we still want to push it out?

@jjbustamante
Copy link
Member Author

Whatever happened to this? Should this be draft or do we still want to push it out?

I think the best is to convert the PR to Draft

@jromero jromero marked this pull request as draft March 29, 2022 18:36
@dfreilich dfreilich modified the milestones: 0.25.0, 0.26.0 Apr 15, 2022
@jromero jromero removed this from the 0.26.0 milestone Apr 20, 2022
@jromero jromero added the experimental Issue or PR refers to an experimental feature. label Aug 24, 2022
@jjbustamante
Copy link
Member Author

Closing this PR on behalf of 1596

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
experimental Issue or PR refers to an experimental feature. type/enhancement Issue that requests a new feature or improvement.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants