Skip to content

Commit 9c1dbe7

Browse files
authored
Merge pull request #6889 from tstromberg/symlink-inversion
Fix inverted certificate symlink creation logic
2 parents d403da4 + 42670e6 commit 9c1dbe7

File tree

5 files changed

+89
-8
lines changed

5 files changed

+89
-8
lines changed

pkg/minikube/bootstrapper/certs.go

+6-6
Original file line numberDiff line numberDiff line change
@@ -130,9 +130,8 @@ func SetupCerts(cmd command.Runner, k8s config.KubernetesConfig, n config.Node)
130130
}
131131
}
132132

133-
// configure CA certificates
134-
if err := configureCACerts(cmd, caCerts); err != nil {
135-
return errors.Wrapf(err, "Configuring CA certs")
133+
if err := installCertSymlinks(cmd, caCerts); err != nil {
134+
return errors.Wrapf(err, "certificate symlinks")
136135
}
137136
return nil
138137
}
@@ -318,9 +317,9 @@ func getSubjectHash(cr command.Runner, filePath string) (string, error) {
318317
return stringHash, nil
319318
}
320319

321-
// configureCACerts looks up and installs all uploaded PEM certificates in /usr/share/ca-certificates to system-wide certificate store (/etc/ssl/certs).
320+
// installCertSymlinks installs certs in /usr/share/ca-certificates into system-wide certificate store (/etc/ssl/certs).
322321
// OpenSSL binary required in minikube ISO
323-
func configureCACerts(cr command.Runner, caCerts map[string]string) error {
322+
func installCertSymlinks(cr command.Runner, caCerts map[string]string) error {
324323
hasSSLBinary := true
325324
_, err := cr.RunCmd(exec.Command("openssl", "version"))
326325
if err != nil {
@@ -334,7 +333,8 @@ func configureCACerts(cr command.Runner, caCerts map[string]string) error {
334333
for _, caCertFile := range caCerts {
335334
dstFilename := path.Base(caCertFile)
336335
certStorePath := path.Join(vmpath.GuestCertStoreDir, dstFilename)
337-
cmd := fmt.Sprintf("test -f %s || ln -fs %s %s", caCertFile, certStorePath, caCertFile)
336+
// If the cert really exists, add a named symlink
337+
cmd := fmt.Sprintf("test -f %s && ln -fs %s %s", caCertFile, caCertFile, certStorePath)
338338
if _, err := cr.RunCmd(exec.Command("sudo", "/bin/bash", "-c", cmd)); err != nil {
339339
return errors.Wrapf(err, "create symlink for %s", caCertFile)
340340
}

pkg/minikube/bootstrapper/certs_test.go

+2-2
Original file line numberDiff line numberDiff line change
@@ -52,8 +52,8 @@ func TestSetupCerts(t *testing.T) {
5252
}
5353

5454
expected := map[string]string{
55-
`sudo /bin/bash -c "test -f /usr/share/ca-certificates/mycert.pem || ln -fs /etc/ssl/certs/mycert.pem /usr/share/ca-certificates/mycert.pem"`: "-",
56-
`sudo /bin/bash -c "test -f /usr/share/ca-certificates/minikubeCA.pem || ln -fs /etc/ssl/certs/minikubeCA.pem /usr/share/ca-certificates/minikubeCA.pem"`: "-",
55+
`sudo /bin/bash -c "test -f /usr/share/ca-certificates/mycert.pem && ln -fs /usr/share/ca-certificates/mycert.pem /etc/ssl/certs/mycert.pem"`: "-",
56+
`sudo /bin/bash -c "test -f /usr/share/ca-certificates/minikubeCA.pem && ln -fs /usr/share/ca-certificates/minikubeCA.pem /etc/ssl/certs/minikubeCA.pem"`: "-",
5757
}
5858
f := command.NewFakeCommandRunner()
5959
f.SetCommandToOutput(expected)

pkg/minikube/command/ssh_runner.go

+2
Original file line numberDiff line numberDiff line change
@@ -241,11 +241,13 @@ func (s *SSHRunner) sameFileExists(f assets.CopyableFile, dst string) (bool, err
241241
if err != nil {
242242
return false, err
243243
}
244+
glog.Infof("found %s: %d bytes, modified at %s", dst, dstSize, dstModTime)
244245

245246
// compare sizes and modtimes
246247
if srcSize != dstSize {
247248
return false, errors.New("source file and destination file are different sizes")
248249
}
250+
249251
return srcModTime.Equal(dstModTime), nil
250252
}
251253

test/integration/functional_test.go

+57
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ import (
2828
"net/url"
2929
"os"
3030
"os/exec"
31+
"path"
3132
"path/filepath"
3233
"regexp"
3334
"runtime"
@@ -57,10 +58,17 @@ func TestFunctional(t *testing.T) {
5758
profile := UniqueProfileName("functional")
5859
ctx, cancel := context.WithTimeout(context.Background(), Minutes(40))
5960
defer func() {
61+
if !*cleanup {
62+
return
63+
}
6064
p := localSyncTestPath()
6165
if err := os.Remove(p); err != nil {
6266
t.Logf("unable to remove %s: %v", p, err)
6367
}
68+
p = localTestCertPath()
69+
if err := os.Remove(p); err != nil {
70+
t.Logf("unable to remove %s: %v", p, err)
71+
}
6472
CleanupWithLogs(t, profile, cancel)
6573
}()
6674

@@ -110,6 +118,7 @@ func TestFunctional(t *testing.T) {
110118
{"SSHCmd", validateSSHCmd},
111119
{"MySQL", validateMySQL},
112120
{"FileSync", validateFileSync},
121+
{"CertSync", validateCertSync},
113122
{"UpdateContextCmd", validateUpdateContextCmd},
114123
{"DockerEnv", validateDockerEnv},
115124
{"NodeLabels", validateNodeLabels},
@@ -731,6 +740,16 @@ func localSyncTestPath() string {
731740
return filepath.Join(localpath.MiniPath(), "/files", vmSyncTestPath())
732741
}
733742

743+
// testCert is name of the test certificate installed
744+
func testCert() string {
745+
return fmt.Sprintf("%d.pem", os.Getpid())
746+
}
747+
748+
// localTestCertPath is where the test file will be synced into the VM
749+
func localTestCertPath() string {
750+
return filepath.Join(localpath.MiniPath(), "/certs", testCert())
751+
}
752+
734753
// Copy extra file into minikube home folder for file sync test
735754
func setupFileSync(ctx context.Context, t *testing.T, profile string) {
736755
p := localSyncTestPath()
@@ -739,6 +758,11 @@ func setupFileSync(ctx context.Context, t *testing.T, profile string) {
739758
if err != nil {
740759
t.Fatalf("copy: %v", err)
741760
}
761+
762+
err = copy.Copy("./testdata/minikube_test.pem", localTestCertPath())
763+
if err != nil {
764+
t.Fatalf("copy: %v", err)
765+
}
742766
}
743767

744768
// validateFileSync to check existence of the test file
@@ -766,6 +790,39 @@ func validateFileSync(ctx context.Context, t *testing.T, profile string) {
766790
}
767791
}
768792

793+
// validateCertSync to check existence of the test certificate
794+
func validateCertSync(ctx context.Context, t *testing.T, profile string) {
795+
if NoneDriver() {
796+
t.Skipf("skipping: ssh unsupported by none")
797+
}
798+
799+
want, err := ioutil.ReadFile("./testdata/minikube_test.pem")
800+
if err != nil {
801+
t.Errorf("test file not found: %v", err)
802+
}
803+
804+
// Check both the installed & reference certs (they should be symlinked)
805+
paths := []string{
806+
path.Join("/etc/ssl/certs", testCert()),
807+
path.Join("/usr/share/ca-certificates", testCert()),
808+
// hashed path generated by: 'openssl x509 -hash -noout -in testCert()'
809+
"/etc/ssl/certs/51391683.0",
810+
}
811+
for _, vp := range paths {
812+
t.Logf("Checking for existence of %s within VM", vp)
813+
rr, err := Run(t, exec.CommandContext(ctx, Target(), "-p", profile, "ssh", fmt.Sprintf("cat %s", vp)))
814+
if err != nil {
815+
t.Errorf("%s failed: %v", rr.Args, err)
816+
}
817+
818+
// Strip carriage returned by ssh
819+
got := strings.Replace(rr.Stdout.String(), "\r", "", -1)
820+
if diff := cmp.Diff(string(want), got); diff != "" {
821+
t.Errorf("minikube_test.pem -> %s mismatch (-want +got):\n%s", vp, diff)
822+
}
823+
}
824+
}
825+
769826
// validateUpdateContextCmd asserts basic "update-context" command functionality
770827
func validateUpdateContextCmd(ctx context.Context, t *testing.T, profile string) {
771828
rr, err := Run(t, exec.CommandContext(ctx, Target(), "-p", profile, "update-context", "--alsologtostderr", "-v=2"))
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
-----BEGIN CERTIFICATE-----
2+
MIIDsDCCApgCCQD5n0OIsOYIjDANBgkqhkiG9w0BAQsFADCBmTELMAkGA1UEBhMC
3+
VVMxEzARBgNVBAgMCkNhbGlmb3JuaWExFjAUBgNVBAcMDVNhbiBGcmFuY2lzY28x
4+
ETAPBgNVBAoMCG1pbmlrdWJlMRYwFAYDVQQLDA1QYXJ0eSBQYXJyb3RzMREwDwYD
5+
VQQDDAhtaW5pa3ViZTEfMB0GCSqGSIb3DQEJARYQbWluaWt1YmVAY25jZi5pbzAe
6+
Fw0yMDAzMDQyMTU2MjZaFw0yMTAzMDQyMTU2MjZaMIGZMQswCQYDVQQGEwJVUzET
7+
MBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQGA1UEBwwNU2FuIEZyYW5jaXNjbzERMA8G
8+
A1UECgwIbWluaWt1YmUxFjAUBgNVBAsMDVBhcnR5IFBhcnJvdHMxETAPBgNVBAMM
9+
CG1pbmlrdWJlMR8wHQYJKoZIhvcNAQkBFhBtaW5pa3ViZUBjbmNmLmlvMIIBIjAN
10+
BgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA/qVMQ/234ul5yWI1yaHvV4pZ5Ffy
11+
M0bSMjzZUwlsvzerXzF3WrdpeZs5GzBNBWL/Db9KziGHCtfX9j5okJqPvB2lxdL5
12+
d5hFIYSORSemYLX2kdlnlykY5fzmFLKIUO9xXs0YNF4JUMEBgGK6n/BdLvXDUULZ
13+
26QOKs6+iH7TAL4RtozxQ8YXKQArdmpeAvxy2PSZGvVk1htKtyuKQsiFqH3oRleK
14+
3mljXfC5LsoIJHqd/8lAsckH87+IfwYnJ1CNJM2gueaCf+HmudVrvXfHaszh1Wh1
15+
9HKPE95Azi6CKoBGlRGFxt8UR72YIcTjC/lYxzbHeCpU7RCiXfsC0iMTlQIDAQAB
16+
MA0GCSqGSIb3DQEBCwUAA4IBAQBhsKnghyBki4NOnK5gHm7ow+7S+xvkjJhXBQ6i
17+
/xQD4/GCZ1tH5iFHXmo+bt4jB9hvKLyN5M5a8TlDwwqTLIoPDQJh37UpSCwbY/6z
18+
nE2aP3N2ue1/DeY60tgAh1c1uJDMeTiFbalJqSkneaHpNfvEQhUORFoN4yQSVEYg
19+
+T9mzTAWQ55TeBgbRevmA25nXHdPAae1MvJWDeG+aJfhq1I2hCwaitJ3iSwgn2ew
20+
637It/aBkMLhsCKTHxlXDGUX401ddbc0ZiC308cyMbis3iBeh4RBjkFxP8eIWFmK
21+
sos/dyqdua742L1cOKYFbLJfjA1VyxJQUxQvWKkbaq0xi7ao
22+
-----END CERTIFICATE-----

0 commit comments

Comments
 (0)