diff --git a/tests/e2e/sample-applications/virt-todo/README.MD b/tests/e2e/sample-applications/virt-todo/README.MD new file mode 100644 index 00000000000..f3e1d65586c --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/README.MD @@ -0,0 +1,49 @@ +# notes: +Obviously there are improvements to this workflow, however this is meant to +serve as a template or example to fit into other working test frameworks. + +# To install +setup the openshift-virtualization operator + +# Start vm +`oc create -f namemspace-virttodo.yaml -f virtualmachine-fedora-close-carp.yaml -f service.yaml -f vmroute.yaml` + +# Check volumeMode +`oc get pvc fedora-close-carp -o yaml -n virttodo | grep volumeMode` + +# Wait for the cloud-init scripts to: +* install mariadb +* install and start the todolist app + +* login w/ test/dog8code +`tail -f /var/log/cloud-init-output.log` + +# Add data to the todolist +* get the route +* `oc get route -n virttodo` +* open browser to $route + * add data + +* alternatively, use the python test.py script to populate data. +`python test.py --base_url=$route` + +* alternatively you can use curl commands, for example: +``` +export date=`date "+%F-%T"` +curl -d "description=curl_todo_1_$date&completed=false" -X POST http://localhost:8000/todo +curl -d "description=curl_todo_2_$date&completed=false" -X POST http://localhost:8000/todo +curl -d "description=curl_todo_3_$date&completed=false" -X POST http://localhost:8000/todo +curl -d "id=1&completed=true" -X POST http://localhost:8000/todo/1 +``` + +# Backup vm +`oc create -f backup_virttodo.yaml` + +# Delete everything +`oc delete -f namemspace-virttodo.yaml -f virtualmachine-fedora-close-carp.yaml -f service.yaml -f vmroute.yaml` + +# Restore vm +`oc create -f restore_virttodo.yaml` + +# Check the data +* compare the data you entered prior to the backup with the current data diff --git a/tests/e2e/sample-applications/virt-todo/backup_virttodo.yaml b/tests/e2e/sample-applications/virt-todo/backup_virttodo.yaml new file mode 100644 index 00000000000..1e33f13c15d --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/backup_virttodo.yaml @@ -0,0 +1,12 @@ +apiVersion: velero.io/v1 +kind: Backup +metadata: + name: virttodo-backup-dm-1 + namespace: openshift-adp +spec: + includedNamespaces: + - virttodo + storageLocation: default + ttl: 720h0m0s + snapshotMoveData: True + defaultVolumesToFsBackup: False diff --git a/tests/e2e/sample-applications/virt-todo/namemspace-virttodo.yaml b/tests/e2e/sample-applications/virt-todo/namemspace-virttodo.yaml new file mode 100644 index 00000000000..7a24a7a178b --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/namemspace-virttodo.yaml @@ -0,0 +1,4 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: virttodo diff --git a/tests/e2e/sample-applications/virt-todo/restore_virttodo.yaml b/tests/e2e/sample-applications/virt-todo/restore_virttodo.yaml new file mode 100644 index 00000000000..836743d0fa8 --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/restore_virttodo.yaml @@ -0,0 +1,8 @@ +apiVersion: velero.io/v1 +kind: Restore +metadata: + name: virttodo-restore-1 + namespace: openshift-adp +spec: + backupName: virttodo-backup-dm-1 + restorePVs: true diff --git a/tests/e2e/sample-applications/virt-todo/service.yaml b/tests/e2e/sample-applications/virt-todo/service.yaml new file mode 100644 index 00000000000..0c4696ce352 --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/service.yaml @@ -0,0 +1,13 @@ +apiVersion: v1 +kind: Service +metadata: + name: vm-service + namespace: virttodo +spec: + selector: + special: key + ports: + - name: todoport + port: 8000 + targetPort: 8000 + type: NodePort diff --git a/tests/e2e/sample-applications/virt-todo/test.py b/tests/e2e/sample-applications/virt-todo/test.py new file mode 100755 index 00000000000..9b381e2ed9e --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/test.py @@ -0,0 +1,183 @@ +#!/usr/bin/env python + +import argparse +import json +import requests + +from datetime import datetime + + +def updateToDo(base_url, id, completed): + """Update data to the todo application + + Args: + item_dict: dict of todo item + completed: bool + + Returns: + bool + """ + data = { + "id": id, + "completed": completed + } + + # Set the endpoint URL + endpoint = base_url + "/todo/" + str(id) + # Send a POST request with the data and the endpoint URL + response = requests.post(endpoint, data=data) + # Check the status code of the response + if response.status_code == 201 or response.status_code == 200: + print("Task updated successfully!") + return True + else: + print("Error updating task.") + return False + + +def createToDo(base_url, description, completed): + """Post data to the todo application + + Args: + description: todo list description + completed: bool + + Returns: + id of todo item in db + """ + data = { + "description": description, + "completed": completed + } + + # Set the endpoint URL + endpoint = base_url + "/todo" + # Send a POST request with the data and the endpoint URL + response = requests.post(endpoint, data=data) + # Check the status code of the response + if response.status_code == 201 or response.status_code == 200: + print("Task created successfully!") + else: + print("Error creating task.") + response_dict = json.loads(response.text)[0] + return response_dict + +def checkToDoLists(base_url, completed): + """Get data from the todo application + + Args: + completed: bool + + Returns: + json dict + """ + # Set the endpoint URL + if completed: + endpoint = base_url + "/todo-completed" + else: + endpoint = base_url + "/todo-incomplete" + # Send a POST request with the data and the endpoint URL + response = requests.get(endpoint) + # Check the status code of the response + if response.status_code == 201 or response.status_code == 200: + print("Got list of items") + else: + print("Failed to get list of items") + response_dict = json.loads(response.text) + return response_dict + +def deleteToDoItems(base_url, item): + """Delete data from the todo application + + Args: + item: dict + + Returns: + bool + """ + + endpoint = base_url + "/todo/" + str(item["Id"]) + # Send a POST request with the data and the endpoint URL + response = requests.delete(endpoint) + # Check the status code of the response + if response.status_code == 201 or response.status_code == 200: + print("Deleted item " + str(item["Id"])) + return True + else: + print("Failed to delete item " + str(item["Id"])) + return False + +def main(): + parser = argparse.ArgumentParser(description='Process some integers.') + parser.add_argument('--base_url', dest='base_url', required=True, + help='The openshift route to the VM') + args = parser.parse_args() + print(args.base_url) + base_url = args.base_url + + + date = datetime.today().strftime('%Y-%m-%d-%H:%M:%S') + # create todo items + test1 = createToDo(base_url, "pytest-1-" + date, False) + test2 = createToDo(base_url, "pytest-2-" + date, False) + test3 = createToDo(base_url, "pytest-1-" + date, False) + + # update todo items + success = updateToDo(base_url, test1["Id"], True) + success = updateToDo(base_url, test2["Id"], True) + + # check todo's + completed = checkToDoLists(base_url, True) + incomplete = checkToDoLists(base_url, False) + print("COMPLETED ITEMS:") + print(completed) + print("INCOMPLETE ITEMS:") + print(incomplete) + + # test complete or incomplete + found_completed = False + for i in completed: + if test1["Description"] == i["Description"]: + found_completed = True + + found_incomplete = False + for i in incomplete: + if test3["Description"] == i["Description"]: + found_incomplete = True + + if found_completed == False or found_incomplete == False: + print("FAILED complete / incomplete TEST") + else: + print("SUCCESS!") + + # Delete items + deleteToDoItems(base_url, test1) + deleteToDoItems(base_url, test3) + completed = checkToDoLists(base_url, True) + incomplete = checkToDoLists(base_url, False) + print("COMPLETED ITEMS:") + print(completed) + print("INCOMPLETE ITEMS:") + print(incomplete) + + # Test deleted items + found_completed = False + for i in completed: + if test1["Description"] == i["Description"]: + found_completed = True + + found_incomplete = False + for i in incomplete: + if test3["Description"] == i["Description"]: + found_incomplete = True + + if found_completed == True or found_incomplete == True: + print("FAILED Delete TEST") + else: + print("SUCCESS!") + + + +if __name__ == "__main__": + main() + diff --git a/tests/e2e/sample-applications/virt-todo/virtualmachine-fedora-close-carp.yaml b/tests/e2e/sample-applications/virt-todo/virtualmachine-fedora-close-carp.yaml new file mode 100644 index 00000000000..3634a56ee0a --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/virtualmachine-fedora-close-carp.yaml @@ -0,0 +1,126 @@ +apiVersion: kubevirt.io/v1 +kind: VirtualMachine +metadata: + annotations: + vm.kubevirt.io/validations: | + [ + { + "name": "minimal-required-memory", + "path": "jsonpath::.spec.domain.memory.guest", + "rule": "integer", + "message": "This VM requires more memory.", + "min": 1073741824 + } + ] + labels: + app: fedora-close-carp + vm.kubevirt.io/template: fedora-server-small + vm.kubevirt.io/template.namespace: openshift + vm.kubevirt.io/template.revision: '1' + vm.kubevirt.io/template.version: v0.26.0 + name: fedora-close-carp + namespace: virttodo +spec: + dataVolumeTemplates: + - apiVersion: cdi.kubevirt.io/v1beta1 + kind: DataVolume + metadata: + creationTimestamp: null + name: fedora-close-carp + spec: + sourceRef: + kind: DataSource + name: fedora + namespace: openshift-virtualization-os-images + storage: + resources: + requests: + storage: 30Gi + running: true + template: + metadata: + annotations: + vm.kubevirt.io/flavor: small + vm.kubevirt.io/os: fedora + vm.kubevirt.io/workload: server + creationTimestamp: null + labels: + kubevirt.io/domain: fedora-close-carp + kubevirt.io/size: small + special: key + spec: + architecture: amd64 + domain: + cpu: + cores: 1 + sockets: 1 + threads: 1 + devices: + disks: + - disk: + bus: virtio + name: rootdisk + - disk: + bus: virtio + name: cloudinitdisk + interfaces: + - macAddress: '02:73:43:00:00:07' + masquerade: {} + model: virtio + name: default + networkInterfaceMultiqueue: true + rng: {} + features: + acpi: {} + smm: + enabled: true + firmware: + bootloader: + efi: {} + machine: + type: pc-q35-rhel9.2.0 + memory: + guest: 2Gi + resources: {} + networks: + - name: default + pod: {} + terminationGracePeriodSeconds: 180 + volumes: + - dataVolume: + name: fedora-close-carp + name: rootdisk + - cloudInitConfigDrive: + userData: |- + #cloud-config + user: fedora + password: dog8code + chpasswd: { expire: False } + user: test + password: dog8code + chpasswd: { expire: False } + packages: + - mariadb-server + - unzip + - wget + runcmd: + - systemctl stop firewalld + - systemctl disable firewalld + - systemctl start mariadb + - systemctl enable mariadb + - mysql -uroot -e "CREATE DATABASE todolist; USE todolist; CREATE USER 'test'@'localhost' IDENTIFIED BY 'test';" + - mysql -uroot -e "grant all privileges on todolist.* to test@'localhost' identified by 'test'; FLUSH PRIVILEGES;" + - pushd /home/test/ + - wget https://github.com/weshayutin/todolist-mariadb-go/releases/download/testing3/todolist-linux-amd64.zip + - unzip todolist-linux-amd64.zip + - chown -R test:test /home/test + - semanage fcontext --add --type bin_t '/home/test/todolist-linux-amd64' + - restorecon -Fv /home/test/todolist-linux-amd64 + - cp systemd/todolist-mariadb.service /etc/systemd/system/ + - popd + - systemctl daemon-reload + - systemctl start todolist-mariadb.service + - systemctl enable todolist-mariadb.service + - systemctl status todolist-mariadb.service + - systemctl disable cloud-init + name: cloudinitdisk diff --git a/tests/e2e/sample-applications/virt-todo/vmroute.yaml b/tests/e2e/sample-applications/virt-todo/vmroute.yaml new file mode 100644 index 00000000000..3989f062a78 --- /dev/null +++ b/tests/e2e/sample-applications/virt-todo/vmroute.yaml @@ -0,0 +1,14 @@ +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: vmroute + namespace: virttodo +spec: + #host: vmroute-openshift-virtualization-os-images.apps.cluster-wdh03122024metala.wdh03122024metala.mg.dog8code.com + port: + targetPort: todoport + to: + kind: Service + name: vm-service + weight: 100 + wildcardPolicy: None