Skip to content

Commit

Permalink
adding automatic cr file read functionality (#526)
Browse files Browse the repository at this point in the history
  • Loading branch information
vrushch authored Nov 25, 2021
1 parent ddb78f3 commit d773de2
Show file tree
Hide file tree
Showing 9 changed files with 83 additions and 43 deletions.
25 changes: 21 additions & 4 deletions tests/functional-tests/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,17 +6,34 @@ This Functional Test Automation Suite exercises and tests the IBM Spectrum Scale

- IBM Spectrum Scale Cluster - 5.1.0.1+ Version (**IBM Spectrum Scale supported kernel version**)
- Kubernetes Cluster Version 1.19 - 1.22
- Openshift Version 4.6.x, 4.7.x, 4.8.x
- IBM Spectrum Scale Cluster CSI Version - 2.1.0+
- Openshift Version 4.8.x, 4.9.x
- IBM Spectrum Scale Cluster CSI Version - 2.4.0+


### How to run IBM Spectrum Scale CSI test automation using container

- Configure parameters in [csiscaleoperators.csi.ibm.com_cr.yaml](../../operator/config/samples/csiscaleoperators.csi.ibm.com_cr.yaml) file.
Note: Use `oc` command instead of `kubectl` in case of Openshift Container Platform

#### In case IBM Spectrum Scale CSI operator and driver is already deployed

- Configuring parameters such as uid/gid, secret username/password, cacert path & remote/local filesystem name, you must modify relevant fields in [test.config](./config/test.config) file.

Note: Use `oc` command instead of `kubectl` in case of Openshift Container Platform
- Create config map using [test.config](./config/test.config) & kubeconfig file (default location `~/.kube/config`)

```
kubectl create configmap test-config --from-file=test.config=<test.config file path> --from-file=kubeconfig=<kubeconfig file path>
```

```
eg. kubectl create configmap test-config --from-file=test.config=/root/ibm-spectrum-scale-csi/tests/functional-tests/config/test.config --from-file=kubeconfig=/root/.kube/config
```

#### In case IBM Spectrum Scale CSI operator and driver is not deployed
- Configure parameters in [csiscaleoperators.csi.ibm.com_cr.yaml](../../operator/config/samples/csiscaleoperators.csi.ibm.com_cr.yaml) file.

- Configuring parameters such as uid/gid, secret username/password, cacert path & remote/local filesystem name, you must modify relevant fields in [test.config](./config/test.config) file.

- Create config map using [test.config](./config/test.config),[csiscaleoperators.csi.ibm.com_cr.yaml](../..//operator/config/samples/csiscaleoperators.csi.ibm.com_cr.yaml) & kubeconfig file (default location `~/.kube/config`)

Expand Down
6 changes: 3 additions & 3 deletions tests/functional-tests/Readme.kubernetes.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@ This Functional Test Automation Suite exercises and tests the IBM Spectrum Scale
### Tested Testbed environment

- IBM Spectrum Scale Cluster - 5.1.0.1+ Version (**IBM Spectrum Scale supported kernel version**)
- Kubernetes Cluster Version 1.19 - 1.21
- Openshift Version 4.6.x, 4.7.x, 4.8.x
- IBM Spectrum Scale Cluster CSI Version - 2.1.0+
- Kubernetes Cluster Version 1.20 - 1.22
- Openshift Version 4.8.x, 4.9.x
- IBM Spectrum Scale Cluster CSI Version - 2.4.0+

### Pre-requesite for automation framework

Expand Down
2 changes: 2 additions & 0 deletions tests/functional-tests/config/test.config
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ keepobjects: "False"
# image name that is to be used in pod
image_name: "nginx:1.19.0"

# csiscaleoperator custom resource object name
csiscaleoperator_name: "ibm-spectrum-scale-csi"

volDirBasePath: "LW"
parentFileset: "root"
Expand Down
6 changes: 3 additions & 3 deletions tests/functional-tests/driver_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@ def values(request):
global data, driver_object, kubeconfig_value # are required in every testcase
kubeconfig_value, clusterconfig_value, operator_namespace, test_namespace, runslow_val = scaleop.get_cmd_values(request)

data = scaleop.read_driver_data(clusterconfig_value, test_namespace)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace)
data = scaleop.read_driver_data(clusterconfig_value, test_namespace, operator_namespace, kubeconfig_value)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace, kubeconfig_value)
keep_objects = data["keepobjects"]
if not(data["volBackendFs"] == ""):
data["primaryFs"] = data["volBackendFs"]
Expand All @@ -22,7 +22,7 @@ def values(request):
operator_object = scaleop.Scaleoperatorobject(operator_data, kubeconfig_value)
condition = scaleop.check_ns_exists(kubeconfig_value, operator_namespace)
if condition is True:
if not(operator_object.check()):
if not(operator_object.check(data["csiscaleoperator_name"])):
LOGGER.error("Operator custom object is not deployed succesfully")
assert False
else:
Expand Down
6 changes: 3 additions & 3 deletions tests/functional-tests/remote_snapshot_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@ def values(request):
global data, remote_data, snapshot_object, kubeconfig_value # are required in every testcase
kubeconfig_value, clusterconfig_value, operator_namespace, test_namespace, runslow_val = scaleop.get_cmd_values(request)

data = scaleop.read_driver_data(clusterconfig_value, test_namespace)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace)
data = scaleop.read_driver_data(clusterconfig_value, test_namespace, operator_namespace, kubeconfig_value)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace, kubeconfig_value)
keep_objects = data["keepobjects"]
if not("remote" in data):
LOGGER.error("remote data is not provided in cr file")
Expand All @@ -27,7 +27,7 @@ def values(request):
operator_object = scaleop.Scaleoperatorobject(operator_data, kubeconfig_value)
condition = scaleop.check_ns_exists(kubeconfig_value, operator_namespace)
if condition is True:
if not(operator_object.check()):
if not(operator_object.check(data["csiscaleoperator_name"])):
LOGGER.error("Operator custom object is not deployed succesfully")
assert False
else:
Expand Down
6 changes: 3 additions & 3 deletions tests/functional-tests/remote_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@ def values(request):
global data, remote_data, driver_object, kubeconfig_value # are required in every testcase
kubeconfig_value, clusterconfig_value, operator_namespace, test_namespace, runslow_val = scaleop.get_cmd_values(request)

data = scaleop.read_driver_data(clusterconfig_value, test_namespace)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace)
data = scaleop.read_driver_data(clusterconfig_value, test_namespace, operator_namespace, kubeconfig_value)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace, kubeconfig_value)
keep_objects = data["keepobjects"]
if not("remote" in data):
LOGGER.error("remote data is not provided in cr file")
Expand All @@ -27,7 +27,7 @@ def values(request):
operator_object = scaleop.Scaleoperatorobject(operator_data, kubeconfig_value)
condition = scaleop.check_ns_exists(kubeconfig_value, operator_namespace)
if condition is True:
if not(operator_object.check()):
if not(operator_object.check(data["csiscaleoperator_name"])):
LOGGER.error("Operator custom object is not deployed succesfully")
assert False
else:
Expand Down
49 changes: 30 additions & 19 deletions tests/functional-tests/scale_operator.py
Original file line number Diff line number Diff line change
Expand Up @@ -202,20 +202,20 @@ def delete(self):
ob.delete_configmap(remote_cacert_name)
ob.check_configmap_is_deleted(remote_cacert_name)

def check(self):
def check(self, csiscaleoperator_name="ibm-spectrum-scale-csi"):
config.load_kube_config(config_file=self.kubeconfig)

is_deployed = ob.check_scaleoperatorobject_is_deployed()
is_deployed = ob.check_scaleoperatorobject_is_deployed(csiscaleoperator_name)
if(is_deployed is False):
return False

ob.check_scaleoperatorobject_statefulsets_state(
"ibm-spectrum-scale-csi-attacher")
csiscaleoperator_name+"-attacher")

ob.check_scaleoperatorobject_statefulsets_state(
"ibm-spectrum-scale-csi-provisioner")
csiscaleoperator_name+"-provisioner")

val, self.desired_number_scheduled = ob.check_scaleoperatorobject_daemonsets_state()
val, self.desired_number_scheduled = ob.check_scaleoperatorobject_daemonsets_state(csiscaleoperator_name)

# ob.check_pod_running("ibm-spectrum-scale-csi-snapshotter-0")

Expand Down Expand Up @@ -678,18 +678,22 @@ def get_test_data():
return data


def read_driver_data(clusterconfig, namespace):
def read_driver_data(clusterconfig, namespace, operator_namespace, kubeconfig):

data = get_test_data()

data["namespace"] = namespace

try:
with open(clusterconfig, "r") as f:
loadcr_yaml = yaml.full_load(f.read())
except yaml.YAMLError as exc:
LOGGER.error(f"Error in parsing the cr file {clusterconfig} : {exc}")
assert False
config.load_kube_config(config_file=kubeconfig)
loadcr_yaml = ob.get_scaleoperatorobject_values(operator_namespace, data["csiscaleoperator_name"])

if loadcr_yaml is False:
try:
with open(clusterconfig, "r") as f:
loadcr_yaml = yaml.full_load(f.read())
except yaml.YAMLError as exc:
LOGGER.error(f"Error in parsing the cr file {clusterconfig} : {exc}")
assert False

for cluster in loadcr_yaml["spec"]["clusters"]:
if "primary" in cluster.keys():
Expand Down Expand Up @@ -767,18 +771,25 @@ def check_nodes_available(label, label_name):
assert False


def read_operator_data(clusterconfig, namespace):
def read_operator_data(clusterconfig, namespace, kubeconfig=None):

data = get_test_data()

data["namespace"] = namespace

try:
with open(clusterconfig, "r") as f:
loadcr_yaml = yaml.full_load(f.read())
except yaml.YAMLError as exc:
LOGGER.error(f"Error in parsing the cr file {clusterconfig} : {exc}")
assert False
if kubeconfig is not None:
config.load_kube_config(config_file=kubeconfig)
loadcr_yaml = ob.get_scaleoperatorobject_values(namespace, data["csiscaleoperator_name"])
else:
loadcr_yaml = False

if loadcr_yaml is False:
try:
with open(clusterconfig, "r") as f:
loadcr_yaml = yaml.full_load(f.read())
except yaml.YAMLError as exc:
LOGGER.error(f"Error in parsing the cr file {clusterconfig} : {exc}")
assert False

data["custom_object_body"] = copy.deepcopy(loadcr_yaml)
data["custom_object_body"]["metadata"]["namespace"] = namespace
Expand Down
6 changes: 3 additions & 3 deletions tests/functional-tests/snapshot_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@ def values(request):
global data, snapshot_object, kubeconfig_value # are required in every testcase
kubeconfig_value, clusterconfig_value, operator_namespace, test_namespace, runslow_val = scaleop.get_cmd_values(request)

data = scaleop.read_driver_data(clusterconfig_value, test_namespace)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace)
data = scaleop.read_driver_data(clusterconfig_value, test_namespace, operator_namespace, kubeconfig_value)
operator_data = scaleop.read_operator_data(clusterconfig_value, operator_namespace, kubeconfig_value)
keep_objects = data["keepobjects"]
ff.cred_check(data)
ff.set_data(data)
Expand All @@ -20,7 +20,7 @@ def values(request):
operator_object = scaleop.Scaleoperatorobject(operator_data, kubeconfig_value)
condition = scaleop.check_ns_exists(kubeconfig_value, operator_namespace)
if condition is True:
if not(operator_object.check()):
if not(operator_object.check(data["csiscaleoperator_name"])):
LOGGER.error("Operator custom object is not deployed succesfully")
assert False
else:
Expand Down
20 changes: 15 additions & 5 deletions tests/functional-tests/utils/scale_operator_object_function.py
Original file line number Diff line number Diff line change
Expand Up @@ -149,7 +149,7 @@ def check_scaleoperatorobject_is_deleted():
assert False


def check_scaleoperatorobject_is_deployed():
def check_scaleoperatorobject_is_deployed(csiscaleoperator_name="ibm-spectrum-scale-csi"):
"""
Checks csiscaleoperator exists or not
Expand All @@ -170,8 +170,7 @@ def check_scaleoperatorobject_is_deployed():
version="v1",
namespace=namespace_value,
plural="csiscaleoperators",

name="ibm-spectrum-scale-csi"
name=csiscaleoperator_name
)
LOGGER.debug(str(read_co_api_response))
LOGGER.info("SpectrumScale CSI custom object exists")
Expand Down Expand Up @@ -220,7 +219,7 @@ def check_scaleoperatorobject_statefulsets_state(stateful_name):
assert False


def check_scaleoperatorobject_daemonsets_state():
def check_scaleoperatorobject_daemonsets_state(csiscaleoperator_name="ibm-spectrum-scale-csi"):
"""
Checks daemonset exists or not
If not exists , It asserts
Expand All @@ -244,7 +243,7 @@ def check_scaleoperatorobject_daemonsets_state():
while (num < 30):
try:
read_daemonsets_api_response = read_daemonsets_api_instance.read_namespaced_daemon_set(
name="ibm-spectrum-scale-csi", namespace=namespace_value, pretty=True)
name=csiscaleoperator_name, namespace=namespace_value, pretty=True)
LOGGER.debug(read_daemonsets_api_response)
current_number_scheduled = read_daemonsets_api_response.status.current_number_scheduled
desired_number_scheduled = read_daemonsets_api_response.status.desired_number_scheduled
Expand Down Expand Up @@ -603,3 +602,14 @@ def get_driver_image():
LOGGER.info(f"CSI driver image id : {container.image_id}")
except ApiException:
LOGGER.info("Unable to get driver image")


def get_scaleoperatorobject_values(namespace_value, csiscaleoperator_name="ibm-spectrum-scale-csi"):
read_cr_api_instance = client.CustomObjectsApi()
try:
read_cr_api_response = read_cr_api_instance.get_namespaced_custom_object(group="csi.ibm.com",
version="v1", namespace=namespace_value, plural="csiscaleoperators", name=csiscaleoperator_name)
LOGGER.debug(str(read_cr_api_response))
return read_cr_api_response
except ApiException:
return False

0 comments on commit d773de2

Please sign in to comment.