This is an automated email from the ASF dual-hosted git repository.
zhangjintao pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/apisix-ingress-controller.git
The following commit(s) were added to refs/heads/master by this push:
new 2a73216 fix: verify generation in record status (#706)
2a73216 is described below
commit 2a732167c9e1b47a80f4b1fc89b4623bf669332e
Author: kv <[email protected]>
AuthorDate: Wed Oct 27 00:49:37 2021 +0800
fix: verify generation in record status (#706)
---
pkg/ingress/apisix_cluster_config.go | 8 +--
pkg/ingress/apisix_consumer.go | 4 +-
pkg/ingress/apisix_route.go | 12 ++--
pkg/ingress/apisix_tls.go | 6 +-
pkg/ingress/apisix_upstream.go | 10 +--
pkg/ingress/secret.go | 8 +--
pkg/ingress/status.go | 128 +++++++++++++++++++--------------
samples/deploy/crd/v1/ApisixRoute.yaml | 72 +++++++++++++++++++
test/e2e/ingress/status.go | 71 ++++++++++++++++++
test/e2e/scaffold/k8s.go | 8 +++
10 files changed, 250 insertions(+), 77 deletions(-)
diff --git a/pkg/ingress/apisix_cluster_config.go
b/pkg/ingress/apisix_cluster_config.go
index 835203b..ea2146c 100644
--- a/pkg/ingress/apisix_cluster_config.go
+++ b/pkg/ingress/apisix_cluster_config.go
@@ -143,7 +143,7 @@ func (c *apisixClusterConfigController) sync(ctx
context.Context, ev *types.Even
zap.Any("opts", clusterOpts),
)
c.controller.recorderEvent(acc,
corev1.EventTypeWarning, _resourceSyncAborted, err)
- c.controller.recordStatus(acc, _resourceSyncAborted,
err, metav1.ConditionFalse)
+ c.controller.recordStatus(acc, _resourceSyncAborted,
err, metav1.ConditionFalse, acc.GetGeneration())
return err
}
}
@@ -157,7 +157,7 @@ func (c *apisixClusterConfigController) sync(ctx
context.Context, ev *types.Even
zap.Any("object", acc),
)
c.controller.recorderEvent(acc, corev1.EventTypeWarning,
_resourceSyncAborted, err)
- c.controller.recordStatus(acc, _resourceSyncAborted, err,
metav1.ConditionFalse)
+ c.controller.recordStatus(acc, _resourceSyncAborted, err,
metav1.ConditionFalse, acc.GetGeneration())
return err
}
log.Debugw("translated global_rule",
@@ -176,11 +176,11 @@ func (c *apisixClusterConfigController) sync(ctx
context.Context, ev *types.Even
zap.Any("cluster", acc.Name),
)
c.controller.recorderEvent(acc, corev1.EventTypeWarning,
_resourceSyncAborted, err)
- c.controller.recordStatus(acc, _resourceSyncAborted, err,
metav1.ConditionFalse)
+ c.controller.recordStatus(acc, _resourceSyncAborted, err,
metav1.ConditionFalse, acc.GetGeneration())
return err
}
c.controller.recorderEvent(acc, corev1.EventTypeNormal,
_resourceSynced, nil)
- c.controller.recordStatus(acc, _resourceSynced, nil,
metav1.ConditionTrue)
+ c.controller.recordStatus(acc, _resourceSynced, nil,
metav1.ConditionTrue, acc.GetGeneration())
return nil
}
diff --git a/pkg/ingress/apisix_consumer.go b/pkg/ingress/apisix_consumer.go
index 0cf28ba..28ce7e3 100644
--- a/pkg/ingress/apisix_consumer.go
+++ b/pkg/ingress/apisix_consumer.go
@@ -116,7 +116,7 @@ func (c *apisixConsumerController) sync(ctx
context.Context, ev *types.Event) er
zap.Any("ApisixConsumer", ac),
)
c.controller.recorderEvent(ac, corev1.EventTypeWarning,
_resourceSyncAborted, err)
- c.controller.recordStatus(ac, _resourceSyncAborted, err,
metav1.ConditionFalse)
+ c.controller.recordStatus(ac, _resourceSyncAborted, err,
metav1.ConditionFalse, ac.GetGeneration())
return err
}
log.Debug("got consumer object from ApisixConsumer",
@@ -130,7 +130,7 @@ func (c *apisixConsumerController) sync(ctx
context.Context, ev *types.Event) er
zap.Any("consumer", consumer),
)
c.controller.recorderEvent(ac, corev1.EventTypeWarning,
_resourceSyncAborted, err)
- c.controller.recordStatus(ac, _resourceSyncAborted, err,
metav1.ConditionFalse)
+ c.controller.recordStatus(ac, _resourceSyncAborted, err,
metav1.ConditionFalse, ac.GetGeneration())
c.controller.metricsCollector.IncrSyncOperation("consumer",
"failure")
return err
}
diff --git a/pkg/ingress/apisix_route.go b/pkg/ingress/apisix_route.go
index e7de855..d1af33a 100644
--- a/pkg/ingress/apisix_route.go
+++ b/pkg/ingress/apisix_route.go
@@ -270,13 +270,13 @@ func (c *apisixRouteController) handleSyncErr(obj
interface{}, errOrigin error)
c.controller.recorderEvent(ar.V1(),
v1.EventTypeNormal, _resourceSynced, nil)
case kube.ApisixRouteV2alpha1:
c.controller.recorderEvent(ar.V2alpha1(), v1.EventTypeNormal, _resourceSynced,
nil)
-
c.controller.recordStatus(ar.V2alpha1(), _resourceSynced, nil,
metav1.ConditionTrue)
+
c.controller.recordStatus(ar.V2alpha1(), _resourceSynced, nil,
metav1.ConditionTrue, ar.V2alpha1().GetGeneration())
case kube.ApisixRouteV2beta1:
c.controller.recorderEvent(ar.V2beta1(), v1.EventTypeNormal, _resourceSynced,
nil)
- c.controller.recordStatus(ar.V2beta1(),
_resourceSynced, nil, metav1.ConditionTrue)
+ c.controller.recordStatus(ar.V2beta1(),
_resourceSynced, nil, metav1.ConditionTrue, ar.V2beta1().GetGeneration())
case kube.ApisixRouteV2beta2:
c.controller.recorderEvent(ar.V2beta2(), v1.EventTypeNormal, _resourceSynced,
nil)
- c.controller.recordStatus(ar.V2beta2(),
_resourceSynced, nil, metav1.ConditionTrue)
+ c.controller.recordStatus(ar.V2beta2(),
_resourceSynced, nil, metav1.ConditionTrue, ar.V2beta2().GetGeneration())
}
} else {
log.Errorw("failed list ApisixRoute",
@@ -299,13 +299,13 @@ func (c *apisixRouteController) handleSyncErr(obj
interface{}, errOrigin error)
c.controller.recorderEvent(ar.V1(),
v1.EventTypeWarning, _resourceSyncAborted, errOrigin)
case kube.ApisixRouteV2alpha1:
c.controller.recorderEvent(ar.V2alpha1(),
v1.EventTypeWarning, _resourceSyncAborted, errOrigin)
- c.controller.recordStatus(ar.V2alpha1(),
_resourceSyncAborted, errOrigin, metav1.ConditionFalse)
+ c.controller.recordStatus(ar.V2alpha1(),
_resourceSyncAborted, errOrigin, metav1.ConditionFalse,
ar.V2alpha1().GetGeneration())
case kube.ApisixRouteV2beta1:
c.controller.recorderEvent(ar.V2beta1(),
v1.EventTypeWarning, _resourceSyncAborted, errOrigin)
- c.controller.recordStatus(ar.V2beta1(),
_resourceSyncAborted, errOrigin, metav1.ConditionFalse)
+ c.controller.recordStatus(ar.V2beta1(),
_resourceSyncAborted, errOrigin, metav1.ConditionFalse,
ar.V2beta1().GetGeneration())
case kube.ApisixRouteV2beta2:
c.controller.recorderEvent(ar.V2beta2(),
v1.EventTypeWarning, _resourceSyncAborted, errOrigin)
- c.controller.recordStatus(ar.V2beta2(),
_resourceSyncAborted, errOrigin, metav1.ConditionFalse)
+ c.controller.recordStatus(ar.V2beta2(),
_resourceSyncAborted, errOrigin, metav1.ConditionFalse,
ar.V2beta2().GetGeneration())
}
} else {
log.Errorw("failed list ApisixRoute",
diff --git a/pkg/ingress/apisix_tls.go b/pkg/ingress/apisix_tls.go
index 79c9478..a289b31 100644
--- a/pkg/ingress/apisix_tls.go
+++ b/pkg/ingress/apisix_tls.go
@@ -120,7 +120,7 @@ func (c *apisixTlsController) sync(ctx context.Context, ev
*types.Event) error {
zap.Any("ApisixTls", tls),
)
c.controller.recorderEvent(tls, corev1.EventTypeWarning,
_resourceSyncAborted, err)
- c.controller.recordStatus(tls, _resourceSyncAborted, err,
metav1.ConditionFalse)
+ c.controller.recordStatus(tls, _resourceSyncAborted, err,
metav1.ConditionFalse, tls.GetGeneration())
return err
}
log.Debugw("got SSL object from ApisixTls",
@@ -143,11 +143,11 @@ func (c *apisixTlsController) sync(ctx context.Context,
ev *types.Event) error {
zap.Any("ssl", ssl),
)
c.controller.recorderEvent(tls, corev1.EventTypeWarning,
_resourceSyncAborted, err)
- c.controller.recordStatus(tls, _resourceSyncAborted, err,
metav1.ConditionFalse)
+ c.controller.recordStatus(tls, _resourceSyncAborted, err,
metav1.ConditionFalse, tls.GetGeneration())
return err
}
c.controller.recorderEvent(tls, corev1.EventTypeNormal,
_resourceSynced, nil)
- c.controller.recordStatus(tls, _resourceSynced, nil,
metav1.ConditionTrue)
+ c.controller.recordStatus(tls, _resourceSynced, nil,
metav1.ConditionTrue, tls.GetGeneration())
return err
}
diff --git a/pkg/ingress/apisix_upstream.go b/pkg/ingress/apisix_upstream.go
index 481eb1c..f2e6261 100644
--- a/pkg/ingress/apisix_upstream.go
+++ b/pkg/ingress/apisix_upstream.go
@@ -129,7 +129,7 @@ func (c *apisixUpstreamController) sync(ctx
context.Context, ev *types.Event) er
if err != nil {
log.Errorf("failed to get service %s: %s", key, err)
c.controller.recorderEvent(au, corev1.EventTypeWarning,
_resourceSyncAborted, err)
- c.controller.recordStatus(au, _resourceSyncAborted, err,
metav1.ConditionFalse)
+ c.controller.recordStatus(au, _resourceSyncAborted, err,
metav1.ConditionFalse, au.GetGeneration())
return err
}
@@ -150,7 +150,7 @@ func (c *apisixUpstreamController) sync(ctx
context.Context, ev *types.Event) er
}
log.Errorf("failed to get upstream %s: %s",
upsName, err)
c.controller.recorderEvent(au,
corev1.EventTypeWarning, _resourceSyncAborted, err)
- c.controller.recordStatus(au,
_resourceSyncAborted, err, metav1.ConditionFalse)
+ c.controller.recordStatus(au,
_resourceSyncAborted, err, metav1.ConditionFalse, au.GetGeneration())
return err
}
var newUps *apisixv1.Upstream
@@ -167,7 +167,7 @@ func (c *apisixUpstreamController) sync(ctx
context.Context, ev *types.Event) er
zap.Error(err),
)
c.controller.recorderEvent(au,
corev1.EventTypeWarning, _resourceSyncAborted, err)
- c.controller.recordStatus(au,
_resourceSyncAborted, err, metav1.ConditionFalse)
+ c.controller.recordStatus(au,
_resourceSyncAborted, err, metav1.ConditionFalse, au.GetGeneration())
return err
}
} else {
@@ -189,14 +189,14 @@ func (c *apisixUpstreamController) sync(ctx
context.Context, ev *types.Event) er
zap.String("cluster", clusterName),
)
c.controller.recorderEvent(au,
corev1.EventTypeWarning, _resourceSyncAborted, err)
- c.controller.recordStatus(au,
_resourceSyncAborted, err, metav1.ConditionFalse)
+ c.controller.recordStatus(au,
_resourceSyncAborted, err, metav1.ConditionFalse, au.GetGeneration())
return err
}
}
}
if ev.Type != types.EventDelete {
c.controller.recorderEvent(au, corev1.EventTypeNormal,
_resourceSynced, nil)
- c.controller.recordStatus(au, _resourceSynced, nil,
metav1.ConditionTrue)
+ c.controller.recordStatus(au, _resourceSynced, nil,
metav1.ConditionTrue, au.GetGeneration())
}
return err
}
diff --git a/pkg/ingress/secret.go b/pkg/ingress/secret.go
index 6104728..839fba3 100644
--- a/pkg/ingress/secret.go
+++ b/pkg/ingress/secret.go
@@ -159,7 +159,7 @@ func (c *secretController) sync(ctx context.Context, ev
*types.Event) error {
go func(tls *configv1.ApisixTls) {
c.controller.recorderEventS(tls,
corev1.EventTypeWarning, _resourceSyncAborted,
fmt.Sprintf("sync from secret
%s changes failed, error: %s", key, err.Error()))
- c.controller.recordStatus(tls,
_resourceSyncAborted, err, metav1.ConditionFalse)
+ c.controller.recordStatus(tls,
_resourceSyncAborted, err, metav1.ConditionFalse, tls.GetGeneration())
}(tls)
return true
}
@@ -177,7 +177,7 @@ func (c *secretController) sync(ctx context.Context, ev
*types.Event) error {
go func(tls *configv1.ApisixTls) {
c.controller.recorderEventS(tls,
corev1.EventTypeWarning, _resourceSyncAborted,
fmt.Sprintf("sync from ca
secret %s changes failed, error: %s", key, err.Error()))
- c.controller.recordStatus(tls,
_resourceSyncAborted, err, metav1.ConditionFalse)
+ c.controller.recordStatus(tls,
_resourceSyncAborted, err, metav1.ConditionFalse, tls.GetGeneration())
}(tls)
return true
}
@@ -203,11 +203,11 @@ func (c *secretController) sync(ctx context.Context, ev
*types.Event) error {
)
c.controller.recorderEventS(tls,
corev1.EventTypeWarning, _resourceSyncAborted,
fmt.Sprintf("sync from secret %s
changes failed, error: %s", key, err.Error()))
- c.controller.recordStatus(tls,
_resourceSyncAborted, err, metav1.ConditionFalse)
+ c.controller.recordStatus(tls,
_resourceSyncAborted, err, metav1.ConditionFalse, tls.GetGeneration())
} else {
c.controller.recorderEventS(tls,
corev1.EventTypeNormal, _resourceSynced,
fmt.Sprintf("sync from secret %s
changes", key))
- c.controller.recordStatus(tls, _resourceSynced,
nil, metav1.ConditionTrue)
+ c.controller.recordStatus(tls, _resourceSynced,
nil, metav1.ConditionTrue, tls.GetGeneration())
}
}(ssl, tls)
return true
diff --git a/pkg/ingress/status.go b/pkg/ingress/status.go
index bf0d075..f19873e 100644
--- a/pkg/ingress/status.go
+++ b/pkg/ingress/status.go
@@ -35,18 +35,28 @@ const (
_commonSuccessMessage = "Sync Successfully"
)
+// verifyGeneration verify generation to decide whether to update status
+func (c *Controller) verifyGeneration(conditions *[]metav1.Condition,
newCondition metav1.Condition) bool {
+ existingCondition := meta.FindStatusCondition(*conditions,
newCondition.Type)
+ if existingCondition != nil && existingCondition.ObservedGeneration >=
newCondition.ObservedGeneration {
+ return false
+ }
+ return true
+}
+
// recordStatus record resources status
-func (c *Controller) recordStatus(at interface{}, reason string, err error,
status v1.ConditionStatus) {
+func (c *Controller) recordStatus(at interface{}, reason string, err error,
status v1.ConditionStatus, generation int64) {
// build condition
message := _commonSuccessMessage
if err != nil {
message = err.Error()
}
condition := metav1.Condition{
- Type: _conditionType,
- Reason: reason,
- Status: status,
- Message: message,
+ Type: _conditionType,
+ Reason: reason,
+ Status: status,
+ Message: message,
+ ObservedGeneration: generation,
}
client := c.kubeClient.APISIXClient
@@ -57,14 +67,16 @@ func (c *Controller) recordStatus(at interface{}, reason
string, err error, stat
conditions := make([]metav1.Condition, 0)
v.Status.Conditions = &conditions
}
- meta.SetStatusCondition(v.Status.Conditions, condition)
- if _, errRecord := client.ApisixV1().ApisixTlses(v.Namespace).
- UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
- log.Errorw("failed to record status change for
ApisixTls",
- zap.Error(errRecord),
- zap.String("name", v.Name),
- zap.String("namespace", v.Namespace),
- )
+ if c.verifyGeneration(v.Status.Conditions, condition) {
+ meta.SetStatusCondition(v.Status.Conditions, condition)
+ if _, errRecord :=
client.ApisixV1().ApisixTlses(v.Namespace).
+ UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
+ log.Errorw("failed to record status change for
ApisixTls",
+ zap.Error(errRecord),
+ zap.String("name", v.Name),
+ zap.String("namespace", v.Namespace),
+ )
+ }
}
case *configv1.ApisixUpstream:
// set to status
@@ -72,14 +84,16 @@ func (c *Controller) recordStatus(at interface{}, reason
string, err error, stat
conditions := make([]metav1.Condition, 0)
v.Status.Conditions = &conditions
}
- meta.SetStatusCondition(v.Status.Conditions, condition)
- if _, errRecord :=
client.ApisixV1().ApisixUpstreams(v.Namespace).
- UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
- log.Errorw("failed to record status change for
ApisixUpstream",
- zap.Error(errRecord),
- zap.String("name", v.Name),
- zap.String("namespace", v.Namespace),
- )
+ if c.verifyGeneration(v.Status.Conditions, condition) {
+ meta.SetStatusCondition(v.Status.Conditions, condition)
+ if _, errRecord :=
client.ApisixV1().ApisixUpstreams(v.Namespace).
+ UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
+ log.Errorw("failed to record status change for
ApisixUpstream",
+ zap.Error(errRecord),
+ zap.String("name", v.Name),
+ zap.String("namespace", v.Namespace),
+ )
+ }
}
case *configv2alpha1.ApisixRoute:
// set to status
@@ -87,14 +101,16 @@ func (c *Controller) recordStatus(at interface{}, reason
string, err error, stat
conditions := make([]metav1.Condition, 0)
v.Status.Conditions = &conditions
}
- meta.SetStatusCondition(v.Status.Conditions, condition)
- if _, errRecord :=
client.ApisixV2alpha1().ApisixRoutes(v.Namespace).
- UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
- log.Errorw("failed to record status change for
ApisixRoute",
- zap.Error(errRecord),
- zap.String("name", v.Name),
- zap.String("namespace", v.Namespace),
- )
+ if c.verifyGeneration(v.Status.Conditions, condition) {
+ meta.SetStatusCondition(v.Status.Conditions, condition)
+ if _, errRecord :=
client.ApisixV2alpha1().ApisixRoutes(v.Namespace).
+ UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
+ log.Errorw("failed to record status change for
ApisixRoute",
+ zap.Error(errRecord),
+ zap.String("name", v.Name),
+ zap.String("namespace", v.Namespace),
+ )
+ }
}
case *configv2beta1.ApisixRoute:
// set to status
@@ -102,14 +118,16 @@ func (c *Controller) recordStatus(at interface{}, reason
string, err error, stat
conditions := make([]metav1.Condition, 0)
v.Status.Conditions = conditions
}
- meta.SetStatusCondition(&v.Status.Conditions, condition)
- if _, errRecord :=
client.ApisixV2beta1().ApisixRoutes(v.Namespace).
- UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
- log.Errorw("failed to record status change for
ApisixRoute",
- zap.Error(errRecord),
- zap.String("name", v.Name),
- zap.String("namespace", v.Namespace),
- )
+ if c.verifyGeneration(&v.Status.Conditions, condition) {
+ meta.SetStatusCondition(&v.Status.Conditions, condition)
+ if _, errRecord :=
client.ApisixV2beta1().ApisixRoutes(v.Namespace).
+ UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
+ log.Errorw("failed to record status change for
ApisixRoute",
+ zap.Error(errRecord),
+ zap.String("name", v.Name),
+ zap.String("namespace", v.Namespace),
+ )
+ }
}
case *configv2beta2.ApisixRoute:
// set to status
@@ -117,14 +135,16 @@ func (c *Controller) recordStatus(at interface{}, reason
string, err error, stat
conditions := make([]metav1.Condition, 0)
v.Status.Conditions = conditions
}
- meta.SetStatusCondition(&v.Status.Conditions, condition)
- if _, errRecord :=
client.ApisixV2beta2().ApisixRoutes(v.Namespace).
- UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
- log.Errorw("failed to record status change for
ApisixRoute",
- zap.Error(errRecord),
- zap.String("name", v.Name),
- zap.String("namespace", v.Namespace),
- )
+ if c.verifyGeneration(&v.Status.Conditions, condition) {
+ meta.SetStatusCondition(&v.Status.Conditions, condition)
+ if _, errRecord :=
client.ApisixV2beta2().ApisixRoutes(v.Namespace).
+ UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
+ log.Errorw("failed to record status change for
ApisixRoute",
+ zap.Error(errRecord),
+ zap.String("name", v.Name),
+ zap.String("namespace", v.Namespace),
+ )
+ }
}
case *configv2alpha1.ApisixConsumer:
// set to status
@@ -132,14 +152,16 @@ func (c *Controller) recordStatus(at interface{}, reason
string, err error, stat
conditions := make([]metav1.Condition, 0)
v.Status.Conditions = &conditions
}
- meta.SetStatusCondition(v.Status.Conditions, condition)
- if _, errRecord :=
client.ApisixV2alpha1().ApisixConsumers(v.Namespace).
- UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
- log.Errorw("failed to record status change for
ApisixConsumer",
- zap.Error(errRecord),
- zap.String("name", v.Name),
- zap.String("namespace", v.Namespace),
- )
+ if c.verifyGeneration(v.Status.Conditions, condition) {
+ meta.SetStatusCondition(v.Status.Conditions, condition)
+ if _, errRecord :=
client.ApisixV2alpha1().ApisixConsumers(v.Namespace).
+ UpdateStatus(context.TODO(), v,
metav1.UpdateOptions{}); errRecord != nil {
+ log.Errorw("failed to record status change for
ApisixConsumer",
+ zap.Error(errRecord),
+ zap.String("name", v.Name),
+ zap.String("namespace", v.Namespace),
+ )
+ }
}
default:
// This should not be executed
diff --git a/samples/deploy/crd/v1/ApisixRoute.yaml
b/samples/deploy/crd/v1/ApisixRoute.yaml
index 63ad7a3..2be7791 100644
--- a/samples/deploy/crd/v1/ApisixRoute.yaml
+++ b/samples/deploy/crd/v1/ApisixRoute.yaml
@@ -316,6 +316,24 @@ spec:
required:
- serviceName
- servicePort
+ status:
+ type: object
+ properties:
+ conditions:
+ type: array
+ items:
+ type: object
+ properties:
+ "type":
+ type: string
+ reason:
+ type: string
+ status:
+ type: string
+ message:
+ type: string
+ observedGeneration:
+ type: integer
- name: v2alpha1
served: true
storage: false
@@ -603,6 +621,24 @@ spec:
required:
- serviceName
- servicePort
+ status:
+ type: object
+ properties:
+ conditions:
+ type: array
+ items:
+ type: object
+ properties:
+ "type":
+ type: string
+ reason:
+ type: string
+ status:
+ type: string
+ message:
+ type: string
+ observedGeneration:
+ type: integer
- name: v2beta1
served: true
storage: false
@@ -890,6 +926,24 @@ spec:
required:
- serviceName
- servicePort
+ status:
+ type: object
+ properties:
+ conditions:
+ type: array
+ items:
+ type: object
+ properties:
+ "type":
+ type: string
+ reason:
+ type: string
+ status:
+ type: string
+ message:
+ type: string
+ observedGeneration:
+ type: integer
- name: v2beta2
served: true
storage: true
@@ -1115,3 +1169,21 @@ spec:
required:
- serviceName
- servicePort
+ status:
+ type: object
+ properties:
+ conditions:
+ type: array
+ items:
+ type: object
+ properties:
+ "type":
+ type: string
+ reason:
+ type: string
+ status:
+ type: string
+ message:
+ type: string
+ observedGeneration:
+ type: integer
diff --git a/test/e2e/ingress/status.go b/test/e2e/ingress/status.go
new file mode 100644
index 0000000..fcf9060
--- /dev/null
+++ b/test/e2e/ingress/status.go
@@ -0,0 +1,71 @@
+// Licensed to the Apache Software Foundation (ASF) under one or more
+// contributor license agreements. See the NOTICE file distributed with
+// this work for additional information regarding copyright ownership.
+// The ASF licenses this file to You under the Apache License, Version 2.0
+// (the "License"); you may not use this file except in compliance with
+// the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package ingress
+
+import (
+ "fmt"
+ "strings"
+
+ "github.com/onsi/ginkgo"
+ "github.com/stretchr/testify/assert"
+
+ "github.com/apache/apisix-ingress-controller/test/e2e/scaffold"
+)
+
+var _ = ginkgo.Describe("Status subresource Testing", func() {
+ opts := &scaffold.Options{
+ Name: "default",
+ Kubeconfig: scaffold.GetKubeconfig(),
+ APISIXConfigPath: "testdata/apisix-gw-config.yaml",
+ IngressAPISIXReplicas: 1,
+ HTTPBinServicePort: 80,
+ APISIXRouteVersion: "apisix.apache.org/v2beta2",
+ }
+ s := scaffold.NewScaffold(opts)
+ ginkgo.It("check the status is recorded", func() {
+ backendSvc, backendSvcPort := s.DefaultHTTPBackend()
+ apisixRoute := fmt.Sprintf(`
+apiVersion: apisix.apache.org/v2beta2
+kind: ApisixRoute
+metadata:
+ name: httpbin-route
+spec:
+ http:
+ - name: rule1
+ match:
+ hosts:
+ - httpbin.com
+ paths:
+ - /ip
+ backends:
+ - serviceName: %s
+ servicePort: %d
+`, backendSvc, backendSvcPort[0])
+ assert.Nil(ginkgo.GinkgoT(),
s.CreateResourceFromString(apisixRoute))
+
+ err := s.EnsureNumApisixRoutesCreated(1)
+ assert.Nil(ginkgo.GinkgoT(), err, "Checking number of routes")
+ err = s.EnsureNumApisixUpstreamsCreated(1)
+ assert.Nil(ginkgo.GinkgoT(), err, "Checking number of
upstreams")
+ // status should be recorded as successful
+ output, err := s.GetOutputFromString("ar", "httpbin-route",
"-o", "yaml")
+ assert.Nil(ginkgo.GinkgoT(), err, "Get output of ApisixRoute
resource")
+ hasType := strings.Contains(output, "type: ResourcesAvailable")
+ assert.True(ginkgo.GinkgoT(), hasType, "Status is recorded")
+ hasMsg := strings.Contains(output, "message: Sync Successfully")
+ assert.True(ginkgo.GinkgoT(), hasMsg, "Status is recorded")
+ })
+})
diff --git a/test/e2e/scaffold/k8s.go b/test/e2e/scaffold/k8s.go
index 2c6b3fd..8761980 100644
--- a/test/e2e/scaffold/k8s.go
+++ b/test/e2e/scaffold/k8s.go
@@ -120,6 +120,14 @@ func (s *Scaffold) CreateResourceFromString(yaml string)
error {
return err
}
+func (s *Scaffold) GetOutputFromString(shell ...string) (string, error) {
+ cmdArgs := []string{}
+ cmdArgs = append(cmdArgs, "get")
+ cmdArgs = append(cmdArgs, shell...)
+ output, err := k8s.RunKubectlAndGetOutputE(ginkgo.GinkgoT(),
s.kubectlOptions, cmdArgs...)
+ return output, err
+}
+
// RemoveResourceByString remove resource from a loaded yaml string.
func (s *Scaffold) RemoveResourceByString(yaml string) error {
err := k8s.KubectlDeleteFromStringE(s.t, s.kubectlOptions, yaml)