Compare commits

...

4 Commits

Author SHA1 Message Date
Nikita Tomchik aa3ff604e1
Merge e1369aadf7 into 236ba5690e 2025-08-09 00:18:15 +02:00
Christophe 236ba5690e
Add archive notice to README (#3502) 2025-06-03 10:36:10 -04:00
Quan Zhang fa67e45814
chore: remove @zhangquan and @jeromeju from maintainer list (#3345) 2025-06-03 10:21:02 -04:00
Nikita e1369aadf7 Allow to exclude build-args and env vars from cache key 2024-04-26 12:03:26 +03:00
6 changed files with 90 additions and 20 deletions

View File

@ -1,2 +0,0 @@
Jerome Ju <jeromeju@google.com>
Quan Zhang <zhangquan@google.com>

View File

@ -1,3 +1,11 @@
# 🧊 This project is archived and no longer developed or maintained. 🧊
The code remains available for historic purposes.
The README as of the archival date remains unchanged below for historic purposes.
-----
# kaniko - Build Images In Kubernetes
## 🚨NOTE: kaniko is not an officially supported Google product🚨

View File

@ -257,6 +257,8 @@ func addKanikoOptionsFlags() {
RootCmd.PersistentFlags().VarP(&opts.Compression, "compression", "", "Compression algorithm (gzip, zstd)")
RootCmd.PersistentFlags().IntVarP(&opts.CompressionLevel, "compression-level", "", -1, "Compression level")
RootCmd.PersistentFlags().BoolVarP(&opts.Cache, "cache", "", false, "Use cache when building image")
RootCmd.PersistentFlags().VarP(&opts.ExcludeBuildArgsFromCacheKey, "exclude-build-arg-from-cache-key", "", "This flag allows you to exclude ARG values from the cache key. Set it repeatedly for multiple values.")
RootCmd.PersistentFlags().VarP(&opts.ExcludeEnvsFromCacheKey, "exclude-env-from-cache-key", "", "This flag allows you to exclude ENV values from the cache key. Set it repeatedly for multiple values.")
RootCmd.PersistentFlags().BoolVarP(&opts.CompressedCaching, "compressed-caching", "", true, "Compress the cached layers. Decreases build time, but increases memory usage.")
RootCmd.PersistentFlags().BoolVarP(&opts.Cleanup, "cleanup", "", false, "Clean the filesystem at the end")
RootCmd.PersistentFlags().DurationVarP(&opts.CacheTTL, "cache-ttl", "", time.Hour*336, "Cache timeout, requires value and unit of duration -> ex: 6h. Defaults to two weeks.")

View File

@ -28,6 +28,9 @@ import (
type CacheOptions struct {
CacheDir string
CacheTTL time.Duration
ExcludeBuildArgsFromCacheKey multiArg
ExcludeEnvsFromCacheKey multiArg
}
// RegistryOptions are all the options related to the registries, set by command line arguments.

View File

@ -199,20 +199,39 @@ func isOCILayout(path string) bool {
}
func (s *stageBuilder) populateCompositeKey(command commands.DockerCommand, files []string, compositeKey CompositeCache, args *dockerfile.BuildArgs, env []string) (CompositeCache, error) {
// First replace all the environment variables or args in the command
replacementEnvs := args.ReplacementEnvs(env)
// The sort order of `replacementEnvs` is basically undefined, sort it
// so we can ensure a stable cache key.
sort.Strings(replacementEnvs)
// Use the special argument "|#" at the start of the args array. This will
// avoid conflicts with any RUN command since commands can not
// start with | (vertical bar). The "#" (number of build envs) is there to
// help ensure proper cache matches.
if command.IsArgsEnvsRequiredInCache() {
if len(replacementEnvs) > 0 {
compositeKey.AddKey(fmt.Sprintf("|%d", len(replacementEnvs)))
compositeKey.AddKey(replacementEnvs...)
filteredEnvs := []string{}
for _, e := range env {
envName := strings.SplitN(e, "=", 2)[0]
if s.opts.ExcludeEnvsFromCacheKey.Contains(envName) {
continue
}
filteredEnvs = append(filteredEnvs, e)
}
// First replace all the environment variables or args in the command
envsAndBuildArgs := args.ReplacementEnvs(filteredEnvs)
filteredEnvsAndBuildArgs := []string{}
for i, env := range envsAndBuildArgs {
envArgName := strings.SplitN(env, "=", 2)[0]
if s.opts.ExcludeBuildArgsFromCacheKey.Contains(envArgName) {
continue
}
filteredEnvsAndBuildArgs = append(filteredEnvs, envsAndBuildArgs[i])
}
// The sort order of `filteredEnvs` is basically undefined, sort it
// so we can ensure a stable cache key.
sort.Strings(filteredEnvsAndBuildArgs)
if len(filteredEnvsAndBuildArgs) > 0 {
// Use the special argument "|#" at the start of the args array. This will
// avoid conflicts with any RUN command since commands can not
// start with | (vertical bar). The "#" (number of build envs) is there to
// help ensure proper cache matches.
compositeKey.AddKey(fmt.Sprintf("|%d", len(filteredEnvsAndBuildArgs)))
compositeKey.AddKey(filteredEnvsAndBuildArgs...)
}
}

View File

@ -655,10 +655,12 @@ func newStageContext(command string, args map[string]string, env []string) stage
func Test_stageBuilder_populateCompositeKey(t *testing.T) {
type testcase struct {
description string
cmd1 stageContext
cmd2 stageContext
shdEqual bool
description string
cmd1 stageContext
cmd2 stageContext
shdEqual bool
excludeBuildArgsFromCacheKey []string
excludeEnvsFromCacheKey []string
}
testCases := []testcase{
{
@ -744,6 +746,21 @@ func Test_stageBuilder_populateCompositeKey(t *testing.T) {
[]string{},
),
},
{
description: "cache key for same command [RUN] with a build arg values, with excludeBuildArgsFromCacheKey set",
cmd1: newStageContext(
"RUN echo $ARG > test",
map[string]string{"ARG": "foo"},
[]string{},
),
cmd2: newStageContext(
"RUN echo $ARG > test",
map[string]string{"ARG": "bar"},
[]string{},
),
shdEqual: true,
excludeBuildArgsFromCacheKey: []string{"ARG"},
},
{
description: "cache key for same command [RUN] with different env values",
cmd1: newStageContext(
@ -798,6 +815,21 @@ func Test_stageBuilder_populateCompositeKey(t *testing.T) {
),
shdEqual: false,
},
{
description: "cache key for command [RUN] with different env values, when excludeEnvsFromCacheKey is set",
cmd1: newStageContext(
"RUN echo ${APP_VERSION%.*} ${APP_VERSION%-*} > test",
map[string]string{"ARG": "foo"},
[]string{"ENV=1"},
),
cmd2: newStageContext(
"RUN echo ${APP_VERSION%.*} ${APP_VERSION%-*} > test",
map[string]string{"ARG": "foo"},
[]string{"ENV=2"},
),
shdEqual: true,
excludeEnvsFromCacheKey: []string{"ENV"},
},
func() testcase {
dir, files := tempDirAndFile(t)
file := files[0]
@ -867,7 +899,15 @@ func Test_stageBuilder_populateCompositeKey(t *testing.T) {
}
for _, tc := range testCases {
t.Run(tc.description, func(t *testing.T) {
sb := &stageBuilder{fileContext: util.FileContext{Root: "workspace"}}
sb := &stageBuilder{
fileContext: util.FileContext{Root: "workspace"},
opts: &config.KanikoOptions{
CacheOptions: config.CacheOptions{
ExcludeBuildArgsFromCacheKey: tc.excludeBuildArgsFromCacheKey,
ExcludeEnvsFromCacheKey: tc.excludeEnvsFromCacheKey,
},
},
}
ck := CompositeCache{}
instructions1, err := dockerfile.ParseCommands([]string{tc.cmd1.command.String()})