diff --git a/cmd/kubeadm/app/cmd/options/constant.go b/cmd/kubeadm/app/cmd/options/constant.go index 7a657bb1640..3f7b7dbcf53 100644 --- a/cmd/kubeadm/app/cmd/options/constant.go +++ b/cmd/kubeadm/app/cmd/options/constant.go @@ -148,4 +148,7 @@ const ( // Print the addon manifests to STDOUT instead of installing them. PrintManifest = "print-manifest" + + // CleanupTmpDir flag indicates whether reset will cleanup the tmp dir + CleanupTmpDir = "cleanup-tmp-dir" ) diff --git a/cmd/kubeadm/app/cmd/phases/reset/cleanupnode.go b/cmd/kubeadm/app/cmd/phases/reset/cleanupnode.go index 8b918c71edc..74ef15e958e 100644 --- a/cmd/kubeadm/app/cmd/phases/reset/cleanupnode.go +++ b/cmd/kubeadm/app/cmd/phases/reset/cleanupnode.go @@ -20,6 +20,7 @@ import ( "fmt" "io" "os" + "path" "path/filepath" "github.com/pkg/errors" @@ -47,6 +48,7 @@ func NewCleanupNodePhase() workflow.Phase { InheritFlags: []string{ options.CertificatesDir, options.NodeCRISocket, + options.CleanupTmpDir, }, } } @@ -103,7 +105,12 @@ func runCleanupNode(c workflow.RunData) error { if certsDir != kubeadmapiv1.DefaultCertificatesDir { klog.Warningf("[reset] WARNING: Cleaning a non-default certificates directory: %q\n", certsDir) } + dirsToClean = append(dirsToClean, certsDir) + if r.CleanupTmpDir() { + tempDir := path.Join(kubeadmconstants.KubernetesDir, kubeadmconstants.TempDirForKubeadm) + dirsToClean = append(dirsToClean, tempDir) + } resetConfigDir(kubeadmconstants.KubernetesDir, dirsToClean, r.DryRun()) if r.Cfg() != nil && features.Enabled(r.Cfg().FeatureGates, features.RootlessControlPlane) { diff --git a/cmd/kubeadm/app/cmd/phases/reset/cleanupnode_test.go b/cmd/kubeadm/app/cmd/phases/reset/cleanupnode_test.go index ed7d374893d..61a1049c6a0 100644 --- a/cmd/kubeadm/app/cmd/phases/reset/cleanupnode_test.go +++ b/cmd/kubeadm/app/cmd/phases/reset/cleanupnode_test.go @@ -142,6 +142,17 @@ func TestConfigDirCleaner(t *testing.T) { "test-path", }, }, + "cleanup temp directory": { + setupDirs: []string{ + "tmp", + }, + setupFiles: []string{ + "tmp/kubeadm-init-dryrun2845575027", + }, + verifyExists: []string{ + "tmp", + }, + }, } for name, test := range tests { @@ -176,6 +187,7 @@ func TestConfigDirCleaner(t *testing.T) { dirsToClean := []string{ filepath.Join(tmpDir, test.resetDir), filepath.Join(tmpDir, kubeadmconstants.ManifestsSubDirName), + filepath.Join(tmpDir, kubeadmconstants.TempDirForKubeadm), } resetConfigDir(tmpDir, dirsToClean, false) @@ -185,6 +197,7 @@ func TestConfigDirCleaner(t *testing.T) { assertNotExists(t, filepath.Join(tmpDir, kubeadmconstants.KubeletKubeConfigFileName)) assertDirEmpty(t, filepath.Join(tmpDir, "manifests")) assertDirEmpty(t, filepath.Join(tmpDir, "pki")) + assertDirEmpty(t, filepath.Join(tmpDir, "tmp")) // Verify the files as requested by the test: for _, path := range test.verifyExists { diff --git a/cmd/kubeadm/app/cmd/phases/reset/data.go b/cmd/kubeadm/app/cmd/phases/reset/data.go index f85848900ec..27a961de991 100644 --- a/cmd/kubeadm/app/cmd/phases/reset/data.go +++ b/cmd/kubeadm/app/cmd/phases/reset/data.go @@ -36,4 +36,5 @@ type resetData interface { Client() clientset.Interface CertificatesDir() string CRISocketPath() string + CleanupTmpDir() bool } diff --git a/cmd/kubeadm/app/cmd/phases/reset/data_test.go b/cmd/kubeadm/app/cmd/phases/reset/data_test.go index 252e77854ff..bdf95a9daa2 100644 --- a/cmd/kubeadm/app/cmd/phases/reset/data_test.go +++ b/cmd/kubeadm/app/cmd/phases/reset/data_test.go @@ -39,3 +39,4 @@ func (t *testData) DryRun() bool { return false } func (t *testData) Client() clientset.Interface { return nil } func (t *testData) CertificatesDir() string { return "" } func (t *testData) CRISocketPath() string { return "" } +func (t *testData) CleanupTmpDir() bool { return false } diff --git a/cmd/kubeadm/app/cmd/reset.go b/cmd/kubeadm/app/cmd/reset.go index 5033907bc5a..a3a46b202f2 100644 --- a/cmd/kubeadm/app/cmd/reset.go +++ b/cmd/kubeadm/app/cmd/reset.go @@ -19,6 +19,7 @@ package cmd import ( "fmt" "io" + "path" "github.com/lithammer/dedent" "github.com/spf13/cobra" @@ -65,6 +66,7 @@ type resetOptions struct { ignorePreflightErrors []string kubeconfigPath string dryRun bool + cleanupTmpDir bool } // resetData defines all the runtime information used when running the kubeadm reset workflow; @@ -79,6 +81,7 @@ type resetData struct { outputWriter io.Writer cfg *kubeadmapi.InitConfiguration dryRun bool + cleanupTmpDir bool } // newResetOptions returns a struct ready for being used for creating cmd join flags. @@ -87,6 +90,7 @@ func newResetOptions() *resetOptions { certificatesDir: kubeadmapiv1.DefaultCertificatesDir, forceReset: false, kubeconfigPath: kubeadmconstants.GetAdminKubeConfigPath(), + cleanupTmpDir: false, } } @@ -136,6 +140,7 @@ func newResetData(cmd *cobra.Command, options *resetOptions, in io.Reader, out i outputWriter: out, cfg: cfg, dryRun: options.dryRun, + cleanupTmpDir: options.cleanupTmpDir, }, nil } @@ -160,6 +165,10 @@ func AddResetFlags(flagSet *flag.FlagSet, resetOptions *resetOptions) { &resetOptions.dryRun, options.DryRun, resetOptions.dryRun, "Don't apply any changes; just output what would be done.", ) + flagSet.BoolVar( + &resetOptions.cleanupTmpDir, options.CleanupTmpDir, resetOptions.cleanupTmpDir, + fmt.Sprintf("Cleanup the %q directory", path.Join(kubeadmconstants.KubernetesDir, kubeadmconstants.TempDirForKubeadm)), + ) options.AddKubeConfigFlag(flagSet, &resetOptions.kubeconfigPath) options.AddIgnorePreflightErrorsFlag(flagSet, &resetOptions.ignorePreflightErrors) @@ -215,11 +224,16 @@ func (r *resetData) Cfg() *kubeadmapi.InitConfiguration { return r.cfg } -// DryRun returns the DryRun flag. +// DryRun returns the dryRun flag. func (r *resetData) DryRun() bool { return r.dryRun } +// CleanupTmpDir returns the cleanupTmpDir flag. +func (r *resetData) CleanupTmpDir() bool { + return r.cleanupTmpDir +} + // CertificatesDir returns the CertificatesDir. func (r *resetData) CertificatesDir() string { return r.certificatesDir