[v5.6] Bump Buildah to v1.41.1

Bump Buildah to v1.41.1 in preparation for Podman
v5.6 RC2.  The c/* projects were bumped in #25752

Signed-off-by: tomsweeneyredhat <tsweeney@redhat.com>
This commit is contained in:
tomsweeneyredhat
2025-08-07 09:43:07 -04:00
parent 8865152a3b
commit 57493f61d0
14 changed files with 212 additions and 59 deletions

2
go.mod
View File

@ -11,7 +11,7 @@ require (
github.com/checkpoint-restore/checkpointctl v1.3.0
github.com/checkpoint-restore/go-criu/v7 v7.2.0
github.com/containernetworking/plugins v1.7.1
github.com/containers/buildah v1.41.0
github.com/containers/buildah v1.41.1
github.com/containers/common v0.64.1
github.com/containers/conmon v2.0.20+incompatible
github.com/containers/gvisor-tap-vsock v0.8.6

4
go.sum
View File

@ -62,8 +62,8 @@ github.com/containernetworking/cni v1.3.0 h1:v6EpN8RznAZj9765HhXQrtXgX+ECGebEYEm
github.com/containernetworking/cni v1.3.0/go.mod h1:Bs8glZjjFfGPHMw6hQu82RUgEPNGEaBb9KS5KtNMnJ4=
github.com/containernetworking/plugins v1.7.1 h1:CNAR0jviDj6FS5Vg85NTgKWLDzZPfi/lj+VJfhMDTIs=
github.com/containernetworking/plugins v1.7.1/go.mod h1:xuMdjuio+a1oVQsHKjr/mgzuZ24leAsqUYRnzGoXHy0=
github.com/containers/buildah v1.41.0 h1:GU350UeX6BkZrgCE3SB/d1Hu4xBaHUX07ayiJTvJD54=
github.com/containers/buildah v1.41.0/go.mod h1:1Ds26B4E4Z3NeLdi3xjjk8S72KVv2/xiFYYpwfFDgXI=
github.com/containers/buildah v1.41.1 h1:WiFZsxLbnPgo00gAX4pVwFa+e3Kypx0IoC9ubFMlQDs=
github.com/containers/buildah v1.41.1/go.mod h1:vVIYC6f5gbPNfhprdMZh9lkOJzzM7lta0romUtBFSw0=
github.com/containers/common v0.64.1 h1:E8vSiL+B84/UCsyVSb70GoxY9cu+0bseLujm4EKF6GE=
github.com/containers/common v0.64.1/go.mod h1:CtfQNHoCAZqWeXMwdShcsxmMJSeGRgKKMqAwRKmWrHE=
github.com/containers/conmon v2.0.20+incompatible h1:YbCVSFSCqFjjVwHTPINGdMX1F6JXHGTUje2ZYobNrkg=

View File

@ -2,6 +2,20 @@
# Changelog
## v1.41.1 (2025-08-06)
[release-1.41] Bump Buildah to v1.41.1
[release-1.41] Bump c/* projects and Buildah to v1.41.1
[release-1.41] generatePathChecksum: ignore ModTime, AccessTime
History should note unset-label, timestamp, and rewrite-timestamp
pkg/cli.GenBuildOptions(): don't hardwire optional bools
Only suppress "noted" items when not squashing
Test that pulled up parent directories are excluded at commit
Exclude pulled up parent directories at commit-time
copier.Ensure(): also return parent directories
copier.MkdirOptions: add ModTimeNew
Restore the default meaning of `--pull` (should be `always`).
## v1.41.0 (2025-07-16)
Bump to c/storage v1.59.0, c/image v5.36.0, ... c/common v0.64.0

View File

@ -1,3 +1,16 @@
- Changelog for v1.41.1 (2025-08-06)
* [release-1.41] Bump Buildah to v1.41.1
* [release-1.41] Bump c/* projects and Buildah to v1.41.1
* [release-1.41] generatePathChecksum: ignore ModTime, AccessTime
* History should note unset-label, timestamp, and rewrite-timestamp
* pkg/cli.GenBuildOptions(): don't hardwire optional bools
* Only suppress "noted" items when not squashing
* Test that pulled up parent directories are excluded at commit
* Exclude pulled up parent directories at commit-time
* copier.Ensure(): also return parent directories
* copier.MkdirOptions: add ModTimeNew
* Restore the default meaning of `--pull` (should be `always`).
- Changelog for v1.41.0 (2025-07-16)
* Bump to c/storage v1.59.0, c/image v5.36.0, ... c/common v0.64.0
* stage_executor: check platform of cache candidates

View File

@ -305,7 +305,8 @@ type removeResponse struct{}
// ensureResponse encodes a response to an Ensure request.
type ensureResponse struct {
Created []string // paths that were created because they weren't already present
Created []string // paths that were created because they weren't already present
Noted []EnsureParentPath // preexisting paths that are parents of created items
}
// conditionalRemoveResponse encodes a response to a conditionalRemove request.
@ -479,6 +480,7 @@ func Put(root string, directory string, options PutOptions, bulkReader io.Reader
// MkdirOptions controls parts of Mkdir()'s behavior.
type MkdirOptions struct {
UIDMap, GIDMap []idtools.IDMap // map from containerIDs to hostIDs when creating directories
ModTimeNew *time.Time // set mtime and atime of newly-created directories
ChownNew *idtools.IDPair // set ownership of newly-created directories
ChmodNew *os.FileMode // set permissions on newly-created directories
}
@ -2199,6 +2201,7 @@ func copierHandlerMkdir(req request, idMappings *idtools.IDMappings) (*response,
}
subdir := ""
var created []string
for _, component := range strings.Split(rel, string(os.PathSeparator)) {
subdir = filepath.Join(subdir, component)
path := filepath.Join(req.Root, subdir)
@ -2209,6 +2212,7 @@ func copierHandlerMkdir(req request, idMappings *idtools.IDMappings) (*response,
if err = chmod(path, dirMode); err != nil {
return errorResponse("copier: mkdir: error setting permissions on %q to 0%o: %v", path, dirMode)
}
created = append(created, path)
} else {
// FreeBSD can return EISDIR for "mkdir /":
// https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=59739.
@ -2217,6 +2221,17 @@ func copierHandlerMkdir(req request, idMappings *idtools.IDMappings) (*response,
}
}
}
// set timestamps last, in case we needed to create some nested directories, which would
// update the timestamps on directories that we'd just set timestamps on, if we had done
// that immediately
if req.MkdirOptions.ModTimeNew != nil {
when := *req.MkdirOptions.ModTimeNew
for _, newDirectory := range created {
if err = lutimes(false, newDirectory, when, when); err != nil {
return errorResponse("copier: mkdir: error setting datestamp on %q: %v", newDirectory, err)
}
}
}
return &response{Error: "", Mkdir: mkdirResponse{}}, nil, nil
}
@ -2255,12 +2270,22 @@ type EnsureOptions struct {
Paths []EnsurePath
}
// EnsureParentPath is a parent (or grandparent, or...) directory of an item
// created by Ensure(), along with information about it, from before the item
// in question was created. If the information about this directory hasn't
// changed when commit-time rolls around, it's most likely that this directory
// is only being considered for inclusion in the layer because it was pulled
// up, and it was not actually changed.
type EnsureParentPath = ConditionalRemovePath
// Ensure ensures that the specified mount point targets exist under the root.
// If the root directory is not specified, the current root directory is used.
// If root is specified and the current OS supports it, and the calling process
// has the necessary privileges, the operation is performed in a chrooted
// context.
func Ensure(root, directory string, options EnsureOptions) ([]string, error) {
// Returns a slice with the pathnames of items that needed to be created and a
// slice of affected parent directories and information about them.
func Ensure(root, directory string, options EnsureOptions) ([]string, []EnsureParentPath, error) {
req := request{
Request: requestEnsure,
Root: root,
@ -2269,12 +2294,12 @@ func Ensure(root, directory string, options EnsureOptions) ([]string, error) {
}
resp, err := copier(nil, nil, req)
if err != nil {
return nil, err
return nil, nil, err
}
if resp.Error != "" {
return nil, errors.New(resp.Error)
return nil, nil, errors.New(resp.Error)
}
return resp.Ensure.Created, nil
return resp.Ensure.Created, resp.Ensure.Noted, nil
}
func copierHandlerEnsure(req request, idMappings *idtools.IDMappings) *response {
@ -2283,6 +2308,7 @@ func copierHandlerEnsure(req request, idMappings *idtools.IDMappings) *response
}
slices.SortFunc(req.EnsureOptions.Paths, func(a, b EnsurePath) int { return strings.Compare(a.Path, b.Path) })
var created []string
notedByName := map[string]EnsureParentPath{}
for _, item := range req.EnsureOptions.Paths {
uid, gid := 0, 0
if item.Chown != nil {
@ -2326,11 +2352,25 @@ func copierHandlerEnsure(req request, idMappings *idtools.IDMappings) *response
if parentPath == "" {
parentPath = "."
}
leaf := filepath.Join(subdir, component)
leaf := filepath.Join(parentPath, component)
parentInfo, err := os.Stat(filepath.Join(req.Root, parentPath))
if err != nil {
return errorResponse("copier: ensure: checking datestamps on %q (%d: %v): %v", parentPath, i, components, err)
}
if parentPath != "." {
parentModTime := parentInfo.ModTime().UTC()
parentMode := parentInfo.Mode()
uid, gid, err := owner(parentInfo)
if err != nil {
return errorResponse("copier: ensure: error reading owner of %q: %v", parentPath, err)
}
notedByName[parentPath] = EnsureParentPath{
Path: parentPath,
ModTime: &parentModTime,
Mode: &parentMode,
Owner: &idtools.IDPair{UID: uid, GID: gid},
}
}
if i < len(components)-1 || item.Typeflag == tar.TypeDir {
err = os.Mkdir(filepath.Join(req.Root, leaf), mode)
subdir = leaf
@ -2372,7 +2412,15 @@ func copierHandlerEnsure(req request, idMappings *idtools.IDMappings) *response
}
}
slices.Sort(created)
return &response{Error: "", Ensure: ensureResponse{Created: created}}
noted := make([]EnsureParentPath, 0, len(notedByName))
for _, n := range notedByName {
if slices.Contains(created, n.Path) {
continue
}
noted = append(noted, n)
}
slices.SortFunc(noted, func(a, b EnsureParentPath) int { return strings.Compare(a.Path, b.Path) })
return &response{Error: "", Ensure: ensureResponse{Created: created, Noted: noted}}
}
// ConditionalRemovePath is a single item being passed to an ConditionalRemove() call.

View File

@ -29,7 +29,7 @@ const (
// identify working containers.
Package = "buildah"
// Version for the Package. Also used by .packit.sh for Packit builds.
Version = "1.41.0"
Version = "1.41.1"
// DefaultRuntime if containers.conf fails.
DefaultRuntime = "runc"

View File

@ -50,11 +50,14 @@ const (
// containerExcludesDir is the subdirectory of the container data
// directory where we drop exclusions
containerExcludesDir = "commit-excludes"
// containerPulledUpDir is the subdirectory of the container
// data directory where we drop exclusions when we're not squashing
containerPulledUpDir = "commit-pulled-up"
// containerExcludesSubstring is the suffix of files under
// $cdir/containerExcludesDir which should be ignored, as they only
// exist because we use CreateTemp() to create uniquely-named files,
// but we don't want to try to use their contents until after they've
// been written to
// $cdir/containerExcludesDir and $cdir/containerPulledUpDir which
// should be ignored, as they only exist because we use CreateTemp() to
// create uniquely-named files, but we don't want to try to use their
// contents until after they've been written to
containerExcludesSubstring = ".tmp"
)
@ -1440,10 +1443,18 @@ func (b *Builder) makeContainerImageRef(options CommitOptions) (*containerImageR
return nil, fmt.Errorf("getting the per-container data directory for %q: %w", b.ContainerID, err)
}
excludesFiles, err := filepath.Glob(filepath.Join(cdir, containerExcludesDir, "*"))
mountTargetFiles, err := filepath.Glob(filepath.Join(cdir, containerExcludesDir, "*"))
if err != nil {
return nil, fmt.Errorf("checking for commit exclusions for %q: %w", b.ContainerID, err)
}
pulledUpFiles, err := filepath.Glob(filepath.Join(cdir, containerPulledUpDir, "*"))
if err != nil {
return nil, fmt.Errorf("checking for commit pulled-up items for %q: %w", b.ContainerID, err)
}
excludesFiles := slices.Clone(mountTargetFiles)
if !options.ConfidentialWorkloadOptions.Convert && !options.Squash {
excludesFiles = append(excludesFiles, pulledUpFiles...)
}
var layerExclusions []copier.ConditionalRemovePath
for _, excludesFile := range excludesFiles {
if strings.Contains(excludesFile, containerExcludesSubstring) {
@ -1462,6 +1473,7 @@ func (b *Builder) makeContainerImageRef(options CommitOptions) (*containerImageR
if options.CompatLayerOmissions == types.OptionalBoolTrue {
layerExclusions = append(layerExclusions, compatLayerExclusions...)
}
logrus.Debugf("excluding these items from committed layer: %#v", layerExclusions)
manifestType := options.PreferredManifestType
if manifestType == "" {

View File

@ -1155,8 +1155,9 @@ func (s *StageExecutor) getImageRootfs(ctx context.Context, image string) (mount
return builder.MountPoint, nil
}
// getContentSummary generates content summary for cases where we added content and need
// to get summary with updated digests.
// getContentSummary generates a description of what was most recently added to the container,
// typically in the form "file", "dir", or "multi" followed by a colon and the hex part of the
// digest of the content, for inclusion in the corresponding history entry's "createdBy" field
func (s *StageExecutor) getContentSummaryAfterAddingContent() string {
contentType, digest := s.builder.ContentDigester.Digest()
summary := contentType
@ -1889,13 +1890,17 @@ func (s *StageExecutor) historyAndDiffIDsMatch(baseHistory []v1.History, baseDif
return history[len(baseHistory)].CreatedBy == createdBy, nil
}
// getCreatedBy returns the command the image at node will be created by. If
// the passed-in CompositeDigester is not nil, it is assumed to have the digest
// information for the content if the node is ADD or COPY.
// getCreatedBy returns the value to store in the history entry for the node.
// If the the passed-in addedContentSummary is not an empty string, it is
// assumed to have the digest information for the content if the node is ADD or
// COPY.
//
// This function acts differently if getCreatedBy is invoked by LastStep. For instances
// certain instructions like `removing annotations` does not makes sense for every step
// but only makes sense if the step is last step of a build.
// The metadata string which is appended to the instruction may need to
// indicate that certain last-minute changes (generally things which couldn't
// be done by appending to the parsed Dockerfile, such as modifying timestamps
// in the layer, unsetting labels, or anything having to do with annotations)
// were made so that a future build won't mistake this result for a cache hit
// unless the same flags are being used at that time.
func (s *StageExecutor) getCreatedBy(node *parser.Node, addedContentSummary string, isLastStep bool) (string, error) {
if node == nil {
return "/bin/sh", nil
@ -2602,33 +2607,65 @@ func (s *StageExecutor) EnsureContainerPathAs(path, user string, mode *os.FileMo
return s.builder.EnsureContainerPathAs(path, user, mode)
}
func (s *StageExecutor) buildMetadata(isLastStep bool, addcopy bool) string {
// buildMetadata constructs the text at the end of the createdBy value for the
// history entry that we'll generate for the instruction that we're currently
// processing. Any flags that affect the output image in a way that affects
// whether or not it should be used as a cache hit for another build with that
// flag set differently should be reflected in its result. Some build settings
// only take affect at the final step, so only note those when they're applied.
func (s *StageExecutor) buildMetadata(isLastStep bool, isAddOrCopy bool) string {
unsetLabels := ""
inheritLabels := ""
unsetAnnotations := ""
inheritAnnotations := ""
newAnnotations := ""
layerMutations := ""
// If --inherit-label was manually set to false then update history.
if s.executor.inheritLabels == types.OptionalBoolFalse {
inheritLabels = "|inheritLabels=false"
}
// If --unsetlabel was used to clear a label, make a note of it.
for _, label := range s.executor.unsetLabels {
unsetLabels += "|unsetLabel=" + label
}
if isLastStep {
// If --unsetannotation was used to clear an annotation, make a note of it.
for _, annotation := range s.executor.unsetAnnotations {
unsetAnnotations += "|unsetAnnotation=" + annotation
}
// If --inherit-annotation was manually set to false then update history.
// If --inherit-annotation was manually set to false then we cleared the inherited annotations.
if s.executor.inheritAnnotations == types.OptionalBoolFalse {
inheritAnnotations = "|inheritAnnotations=false"
}
// If new annotations are added, they must be added as part of the last step of the build,
// so mention in history that new annotations were added inorder to make sure the builds
// can either reuse layers or burst the cache depending upon new annotations.
// so mention in history that new annotations were added in order to make sure that subsequent builds
// only use this image as a cache hit if it was built with the same set of annotations.
if len(s.executor.annotations) > 0 {
newAnnotations += strings.Join(s.executor.annotations, ",")
}
}
if addcopy {
return inheritLabels + " " + unsetAnnotations + " " + inheritAnnotations + " " + newAnnotations
// If we're messing with timestamps in layer contents, make a note of how we're doing it.
if s.executor.timestamp != nil || (s.executor.sourceDateEpoch != nil && s.executor.rewriteTimestamp) {
var t time.Time
modtype := ""
if s.executor.timestamp != nil {
t = s.executor.timestamp.UTC()
modtype = "force-mtime"
}
if s.executor.sourceDateEpoch != nil && s.executor.rewriteTimestamp {
t = s.executor.sourceDateEpoch.UTC()
modtype = "clamp-mtime"
if s.executor.timestamp != nil && s.executor.timestamp.Before(*s.executor.sourceDateEpoch) {
t = s.executor.timestamp.UTC()
modtype = "force-mtime"
}
}
layerMutations = "|" + modtype + "=" + strconv.FormatInt(t.Unix(), 10)
}
return inheritLabels + unsetAnnotations + inheritAnnotations + newAnnotations
if isAddOrCopy {
return unsetLabels + " " + inheritLabels + " " + unsetAnnotations + " " + inheritAnnotations + " " + layerMutations + " " + newAnnotations
}
return unsetLabels + inheritLabels + unsetAnnotations + inheritAnnotations + layerMutations + newAnnotations
}

View File

@ -6,6 +6,7 @@ import (
"os"
"path/filepath"
"strings"
"time"
"github.com/containers/buildah"
digest "github.com/opencontainers/go-digest"
@ -69,6 +70,11 @@ func generatePathChecksum(sourcePath string) (string, error) {
}
header.Name = filepath.ToSlash(relPath)
// Zero out timestamp fields to ignore modification time in checksum calculation
header.ModTime = time.Time{}
header.AccessTime = time.Time{}
header.ChangeTime = time.Time{}
if err := tarWriter.WriteHeader(header); err != nil {
return err
}

View File

@ -355,6 +355,23 @@ func GenBuildOptions(c *cobra.Command, inputArgs []string, iopts BuildOptions) (
sbomScanOptions = append(sbomScanOptions, *sbomScanOption)
}
var compatVolumes, createdAnnotation, inheritAnnotations, inheritLabels, skipUnusedStages types.OptionalBool
if c.Flag("compat-volumes").Changed {
compatVolumes = types.NewOptionalBool(iopts.CompatVolumes)
}
if c.Flag("created-annotation").Changed {
createdAnnotation = types.NewOptionalBool(iopts.CreatedAnnotation)
}
if c.Flag("inherit-annotations").Changed {
inheritAnnotations = types.NewOptionalBool(iopts.InheritAnnotations)
}
if c.Flag("inherit-labels").Changed {
inheritLabels = types.NewOptionalBool(iopts.InheritLabels)
}
if c.Flag("skip-unused-stages").Changed {
skipUnusedStages = types.NewOptionalBool(iopts.SkipUnusedStages)
}
options = define.BuildOptions{
AddCapabilities: iopts.CapAdd,
AdditionalBuildContexts: additionalBuildContext,
@ -371,14 +388,14 @@ func GenBuildOptions(c *cobra.Command, inputArgs []string, iopts BuildOptions) (
CDIConfigDir: iopts.CDIConfigDir,
CNIConfigDir: iopts.CNIConfigDir,
CNIPluginPath: iopts.CNIPlugInPath,
CompatVolumes: types.NewOptionalBool(iopts.CompatVolumes),
CompatVolumes: compatVolumes,
ConfidentialWorkload: confidentialWorkloadOptions,
CPPFlags: iopts.CPPFlags,
CommonBuildOpts: commonOpts,
Compression: compression,
ConfigureNetwork: networkPolicy,
ContextDirectory: contextDir,
CreatedAnnotation: types.NewOptionalBool(iopts.CreatedAnnotation),
CreatedAnnotation: createdAnnotation,
Devices: iopts.Devices,
DropCapabilities: iopts.CapDrop,
Err: stderr,
@ -390,8 +407,8 @@ func GenBuildOptions(c *cobra.Command, inputArgs []string, iopts BuildOptions) (
IIDFile: iopts.Iidfile,
IgnoreFile: iopts.IgnoreFile,
In: stdin,
InheritLabels: types.NewOptionalBool(iopts.InheritLabels),
InheritAnnotations: types.NewOptionalBool(iopts.InheritAnnotations),
InheritLabels: inheritLabels,
InheritAnnotations: inheritAnnotations,
Isolation: isolation,
Jobs: &iopts.Jobs,
Labels: iopts.Label,
@ -423,7 +440,7 @@ func GenBuildOptions(c *cobra.Command, inputArgs []string, iopts BuildOptions) (
SBOMScanOptions: sbomScanOptions,
SignBy: iopts.SignBy,
SignaturePolicyPath: iopts.SignaturePolicy,
SkipUnusedStages: types.NewOptionalBool(iopts.SkipUnusedStages),
SkipUnusedStages: skipUnusedStages,
SourceDateEpoch: sourceDateEpoch,
Squash: iopts.Squash,
SystemContext: systemContext,

View File

@ -281,7 +281,7 @@ always: pull base and SBOM scanner images even if the named images are present
missing: pull base and SBOM scanner images if the named images are not present in store.
never: only use images present in store if available.
newer: only pull base and SBOM scanner images when newer images exist on the registry than those in the store.`)
fs.Lookup("pull").NoOptDefVal = "missing" // treat a --pull with no argument like --pull=missing
fs.Lookup("pull").NoOptDefVal = "always" // treat a --pull with no argument like --pull=always
fs.BoolVar(&flags.PullAlways, "pull-always", false, "pull the image even if the named image is present in store")
if err := fs.MarkHidden("pull-always"); err != nil {
panic(fmt.Sprintf("error marking the pull-always flag as hidden: %v", err))

View File

@ -527,9 +527,9 @@ func pullPolicyWithFlags(policySpec string, always, never bool) (define.PullPoli
}
policy := strings.ToLower(policySpec)
switch policy {
case "true", "missing", "ifmissing", "notpresent":
case "missing", "ifmissing", "notpresent":
return define.PullIfMissing, nil
case "always":
case "true", "always":
return define.PullAlways, nil
case "false", "never":
return define.PullNever, nil

View File

@ -2119,11 +2119,12 @@ func (b *Builder) createMountTargets(spec *specs.Spec) ([]copier.ConditionalRemo
if len(targets.Paths) == 0 {
return nil, nil
}
created, err := copier.Ensure(rootfsPath, rootfsPath, targets)
created, noted, err := copier.Ensure(rootfsPath, rootfsPath, targets)
if err != nil {
return nil, err
}
logrus.Debugf("created mount targets at %v", created)
logrus.Debugf("parents of mount targets at %+v", noted)
var remove []copier.ConditionalRemovePath
for _, target := range created {
cleanedTarget := strings.Trim(path.Clean(filepath.ToSlash(target)), "/")
@ -2151,23 +2152,28 @@ func (b *Builder) createMountTargets(spec *specs.Spec) ([]copier.ConditionalRemo
if err != nil {
return nil, fmt.Errorf("finding working container bookkeeping directory: %w", err)
}
if err := os.Mkdir(filepath.Join(cdir, containerExcludesDir), 0o700); err != nil && !errors.Is(err, os.ErrExist) {
return nil, fmt.Errorf("creating exclusions directory: %w", err)
for excludesDir, exclusions := range map[string][]copier.ConditionalRemovePath{
containerExcludesDir: remove,
containerPulledUpDir: noted,
} {
if err := os.Mkdir(filepath.Join(cdir, excludesDir), 0o700); err != nil && !errors.Is(err, os.ErrExist) {
return nil, fmt.Errorf("creating exclusions directory: %w", err)
}
encoded, err := json.Marshal(exclusions)
if err != nil {
return nil, fmt.Errorf("encoding list of items to exclude at commit-time: %w", err)
}
f, err := os.CreateTemp(filepath.Join(cdir, excludesDir), "filter*"+containerExcludesSubstring)
if err != nil {
return nil, fmt.Errorf("creating exclusions file: %w", err)
}
defer os.Remove(f.Name())
defer f.Close()
if err := ioutils.AtomicWriteFile(strings.TrimSuffix(f.Name(), containerExcludesSubstring), encoded, 0o600); err != nil {
return nil, fmt.Errorf("writing exclusions file: %w", err)
}
}
encoded, err := json.Marshal(remove)
if err != nil {
return nil, fmt.Errorf("encoding list of items to exclude at commit-time: %w", err)
}
f, err := os.CreateTemp(filepath.Join(cdir, containerExcludesDir), "filter*"+containerExcludesSubstring)
if err != nil {
return nil, fmt.Errorf("creating exclusions file: %w", err)
}
defer os.Remove(f.Name())
defer f.Close()
if err := ioutils.AtomicWriteFile(strings.TrimSuffix(f.Name(), containerExcludesSubstring), encoded, 0o600); err != nil {
return nil, fmt.Errorf("writing exclusions file: %w", err)
}
// return that set of paths directly, in case the caller would prefer
// to clear them out before commit-time
// return the set of to-remove-now paths directly, in case the caller would prefer
// to clear them out itself now instead of waiting until commit-time
return remove, nil
}

2
vendor/modules.txt vendored
View File

@ -108,7 +108,7 @@ github.com/containernetworking/cni/pkg/version
# github.com/containernetworking/plugins v1.7.1
## explicit; go 1.23.0
github.com/containernetworking/plugins/pkg/ns
# github.com/containers/buildah v1.41.0
# github.com/containers/buildah v1.41.1
## explicit; go 1.23.3
github.com/containers/buildah
github.com/containers/buildah/bind