kubecertagent: use initial event for when key can't be found

This should fix integration tests running on clusters that don't have
visible controller manager pods (e.g., GKE). Pinniped should boot, not
find any controller manager pods, but still post a status in the CIC.

I also updated a test helper so that we could tell the difference
between when an event was not added and when an event was added with
an empty key.

Signed-off-by: Andrew Keesler <akeesler@vmware.com>
This commit is contained in:
Andrew Keesler 2020-09-24 16:54:20 -04:00
parent d853cbc7ff
commit 9e0195e024
No known key found for this signature in database
GPG Key ID: 27CE0444346F9413
5 changed files with 36 additions and 4 deletions

View File

@ -103,7 +103,7 @@ func TestManagerControllerOptions(t *testing.T) {
when("starting up", func() { when("starting up", func() {
it("asks for an initial event because the Secret may not exist yet and it needs to run anyway", func() { it("asks for an initial event because the Secret may not exist yet and it needs to run anyway", func() {
r.Equal(controllerlib.Key{ r.Equal(&controllerlib.Key{
Namespace: installedInNamespace, Namespace: installedInNamespace,
Name: certsSecretResourceName, Name: certsSecretResourceName,
}, observableWithInitialEventOption.GetInitialEventKey()) }, observableWithInitialEventOption.GetInitialEventKey())

View File

@ -44,6 +44,7 @@ func NewCreaterController(
kubeSystemPodInformer corev1informers.PodInformer, kubeSystemPodInformer corev1informers.PodInformer,
agentPodInformer corev1informers.PodInformer, agentPodInformer corev1informers.PodInformer,
withInformer pinnipedcontroller.WithInformerOptionFunc, withInformer pinnipedcontroller.WithInformerOptionFunc,
withInitialEvent pinnipedcontroller.WithInitialEventOptionFunc,
) controllerlib.Controller { ) controllerlib.Controller {
return controllerlib.New( return controllerlib.New(
controllerlib.Config{ controllerlib.Config{
@ -69,6 +70,10 @@ func NewCreaterController(
pinnipedcontroller.SimpleFilter(isAgentPod), pinnipedcontroller.SimpleFilter(isAgentPod),
controllerlib.InformerOption{}, controllerlib.InformerOption{},
), ),
// Be sure to run once even to make sure the CIC is updated if there are no controller manager
// pods. We should be able to pass an empty key since we don't use the key in the sync (we sync
// the world).
withInitialEvent(controllerlib.Key{}),
) )
} }

View File

@ -48,11 +48,35 @@ func TestCreaterControllerFilter(t *testing.T) {
kubeSystemPodInformer, kubeSystemPodInformer,
agentPodInformer, agentPodInformer,
observableWithInformerOption.WithInformer, observableWithInformerOption.WithInformer,
controllerlib.WithInitialEvent,
) )
}, },
) )
} }
func TestCreaterControllerInitialEvent(t *testing.T) {
kubeSystemInformerClient := kubernetesfake.NewSimpleClientset()
kubeSystemInformers := kubeinformers.NewSharedInformerFactory(kubeSystemInformerClient, 0)
agentInformerClient := kubernetesfake.NewSimpleClientset()
agentInformers := kubeinformers.NewSharedInformerFactory(agentInformerClient, 0)
observableWithInitialEventOption := testutil.NewObservableWithInitialEventOption()
_ = NewCreaterController(
nil, // agentPodConfig, shouldn't matter
nil, // credentialIssuerConfigLocationConfig, shouldn't matter
nil, // clock, shound't matter
nil, // k8sClient, shouldn't matter
nil, // pinnipedAPIClient, shouldn't matter
kubeSystemInformers.Core().V1().Pods(),
agentInformers.Core().V1().Pods(),
controllerlib.WithInformer,
observableWithInitialEventOption.WithInitialEvent,
)
require.Equal(t, &controllerlib.Key{}, observableWithInitialEventOption.GetInitialEventKey())
}
func TestCreaterControllerSync(t *testing.T) { func TestCreaterControllerSync(t *testing.T) {
spec.Run(t, "CreaterControllerSync", func(t *testing.T, when spec.G, it spec.S) { spec.Run(t, "CreaterControllerSync", func(t *testing.T, when spec.G, it spec.S) {
const kubeSystemNamespace = "kube-system" const kubeSystemNamespace = "kube-system"
@ -98,6 +122,7 @@ func TestCreaterControllerSync(t *testing.T) {
kubeSystemInformers.Core().V1().Pods(), kubeSystemInformers.Core().V1().Pods(),
agentInformers.Core().V1().Pods(), agentInformers.Core().V1().Pods(),
controllerlib.WithInformer, controllerlib.WithInformer,
controllerlib.WithInitialEvent,
) )
// Set this at the last second to support calling subject.Name(). // Set this at the last second to support calling subject.Name().

View File

@ -180,6 +180,7 @@ func PrepareControllers(c *Config) (func(ctx context.Context), error) {
informers.kubeSystemNamespaceK8s.Core().V1().Pods(), informers.kubeSystemNamespaceK8s.Core().V1().Pods(),
informers.installationNamespaceK8s.Core().V1().Pods(), informers.installationNamespaceK8s.Core().V1().Pods(),
controllerlib.WithInformer, controllerlib.WithInformer,
controllerlib.WithInitialEvent,
), ),
singletonWorker, singletonWorker,
). ).

View File

@ -6,7 +6,7 @@ package testutil
import "go.pinniped.dev/internal/controllerlib" import "go.pinniped.dev/internal/controllerlib"
type ObservableWithInitialEventOption struct { type ObservableWithInitialEventOption struct {
key controllerlib.Key key *controllerlib.Key
} }
func NewObservableWithInitialEventOption() *ObservableWithInitialEventOption { func NewObservableWithInitialEventOption() *ObservableWithInitialEventOption {
@ -14,10 +14,11 @@ func NewObservableWithInitialEventOption() *ObservableWithInitialEventOption {
} }
func (i *ObservableWithInitialEventOption) WithInitialEvent(key controllerlib.Key) controllerlib.Option { func (i *ObservableWithInitialEventOption) WithInitialEvent(key controllerlib.Key) controllerlib.Option {
i.key = key i.key = new(controllerlib.Key)
*i.key = key
return controllerlib.WithInitialEvent(key) return controllerlib.WithInitialEvent(key)
} }
func (i *ObservableWithInitialEventOption) GetInitialEventKey() controllerlib.Key { func (i *ObservableWithInitialEventOption) GetInitialEventKey() *controllerlib.Key {
return i.key return i.key
} }