Soft Patch Panel
 help / color / Atom feed
From: yasufum.o@gmail.com
To: spp@dpdk.org, ferruh.yigit@intel.com, yasufum.o@gmail.com
Subject: [spp] [PATCH 1/3] test: add test for spp_nfv
Date: Tue, 17 Dec 2019 11:37:28 +0900
Message-ID: <20191217023730.30477-2-yasufum.o@gmail.com> (raw)
In-Reply-To: <20191217023730.30477-1-yasufum.o@gmail.com>

From: Yasufumi Ogawa <yasufum.o@gmail.com>

This patch is to add a unit test code for spp_nfv. Test cases are
defined by following SPP REST API, such as checking status, adding port
or so.

Configurations for the tests are defined as `test/config.ini`. Host IP
or assignment of resouces can be changed in the config.

Unit tests are expected to be run in the `test` dir.

  $ cd /path/to/spp/test
  $ python3 -m unittest  # or add `-v` for showing details

Signed-off-by: Yasufumi Ogawa <yasufum.o@gmail.com>
---
 test/config.ini      |  12 +++
 test/test_spp_nfv.py | 179 +++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 191 insertions(+)
 create mode 100644 test/config.ini
 create mode 100644 test/test_spp_nfv.py

diff --git a/test/config.ini b/test/config.ini
new file mode 100644
index 0000000..8890413
--- /dev/null
+++ b/test/config.ini
@@ -0,0 +1,12 @@
+# SPDX-License-Identifier: BSD-3-Clause
+# Copyright(c) 2019 Nippon Telegraph and Telephone Corporation
+
+[spp-ctl]
+host = 127.0.0.1
+ctl_api_port = 7777
+api_version = v1
+
+# spp_nfv mainly tested
+[spp_nfv]
+lcores = 1,2
+mem = 512
diff --git a/test/test_spp_nfv.py b/test/test_spp_nfv.py
new file mode 100644
index 0000000..1ebb3d3
--- /dev/null
+++ b/test/test_spp_nfv.py
@@ -0,0 +1,179 @@
+# SPDX-License-Identifier: BSD-3-Clause
+# Copyright(c) 2019 Nippon Telegraph and Telephone Corporation
+
+import configparser
+import json
+import requests
+import time
+import unittest
+
+
+class TestSppNfv(unittest.TestCase):
+    """Test spp_nfv.
+
+    Test as following the REST API reference. It does not include terminating
+    spp_nfv process because it is done as tearDown() task.
+    """
+
+    def setUp(self):
+        """Launch default spp_nfv used for the tests."""
+
+        self.sec_type = 'nfvs'
+        self.default_sec_id = 1
+
+        self.config = configparser.ConfigParser()
+        self.config.read('config.ini')
+
+        host = self.config['spp-ctl']['host']
+        ctl_api_port = self.config['spp-ctl']['ctl_api_port']
+        api_version = self.config['spp-ctl']['api_version']
+
+        self.base_url = 'http://{host}:{port}/{api_ver}'.format(
+                host=host, port=ctl_api_port, api_ver=api_version)
+
+        # Launch default spp_nfv
+        sec_port = '6666'
+        nfv = {'mem': self.config['spp_nfv']['mem'],
+               'lcores': self.config['spp_nfv']['lcores']}
+        params = {
+                'proc_name': 'spp_nfv',
+                'client_id': str(self.default_sec_id),
+                'eal': {
+                    '-m': nfv['mem'], '-l': nfv['lcores'],
+                    '--proc-type': 'secondary'},
+                'app': {
+                    '-s': '{}:{}'.format(host, sec_port),
+                    '-n': str(self.default_sec_id)}
+                }
+        url = '{baseurl}/primary/launch'.format(baseurl=self.base_url)
+        requests.put(url, data=json.dumps(params))
+        time.sleep(0.2)  # wait until be launched
+
+    def tearDown(self):
+        """Shutdown default spp_nfv."""
+
+        url = '{baseurl}/{sec_type}/{sec_id}'.format(
+                baseurl=self.base_url,
+                sec_type=self.sec_type,
+                sec_id=self.default_sec_id)
+        response = requests.delete(url)
+
+    def _get_status(self):
+        """Get status of default spp_nfv process."""
+
+        url = "{baseurl}/{sec_type}/{sec_id}".format(
+                baseurl=self.base_url,
+                sec_type=self.sec_type,
+                sec_id=self.default_sec_id)
+        response = requests.get(url)
+        return response.json()
+
+    def _set_forwarding_status(self, action):
+        """Set forwarding status as start or stop."""
+
+        if action in ['start', 'stop']:
+            url = "{baseurl}/{sec_type}/{sec_id}/forward".format(
+                    baseurl=self.base_url,
+                    sec_type=self.sec_type,
+                    sec_id=self.default_sec_id)
+            params = {'action': action}
+            response = requests.put(url, data=json.dumps(params))
+            return True
+        else:
+            return False
+
+    def _add_or_del_port(self, action, res_uid):
+        if action in ['add', 'del']:
+            url = "{baseurl}/{sec_type}/{sec_id}/ports".format(
+                    baseurl=self.base_url,
+                    sec_type=self.sec_type,
+                    sec_id=self.default_sec_id)
+            params = {'action': action, 'port': res_uid}
+            requests.put(url, data=json.dumps(params))
+            return True
+        else:
+            return False
+
+    def _add_port(self, res_uid):
+        self._add_or_del_port('add', res_uid)
+
+    def _del_port(self, res_uid):
+        self._add_or_del_port('del', res_uid)
+
+    def _assert_add_del_port(self, port):
+        self._add_port(port)
+        nfv = self._get_status()
+        self.assertTrue(port in nfv['ports'])
+
+        self._del_port(port)
+        nfv = self._get_status()
+        self.assertFalse(port in nfv['ports'])
+
+    def _patch(self, src, dst):
+        """Set patch between given ports."""
+
+        url = "{baseurl}/{sec_type}/{sec_id}/patches".format(
+                baseurl=self.base_url,
+                sec_type=self.sec_type,
+                sec_id=self.default_sec_id)
+        params = {'src': src, 'dst': dst}
+        requests.put(url, data=json.dumps(params))
+
+    def _reset_patches(self):
+        url = "{baseurl}/{sec_type}/{sec_id}/patches".format(
+                baseurl=self.base_url,
+                sec_type=self.sec_type,
+                sec_id=self.default_sec_id)
+        requests.delete(url)
+
+    # Test methods for testing spp_nfv from here.
+    def test_sec_id(self):
+        """Confirm sec ID is expected value."""
+
+        nfv = self._get_status()
+        self.assertEqual(nfv['client-id'], 1)
+
+    def test_forward_stop(self):
+        """Confirm forwarding is started and stopped."""
+
+        self._set_forwarding_status('start')
+        nfv = self._get_status()
+        self.assertEqual(nfv['status'], 'running')
+
+        self._set_forwarding_status('stop')
+        nfv = self._get_status()
+        self.assertEqual(nfv['status'], 'idling')
+
+    def test_add_del_ring(self):
+        """Check if ring PMD is added."""
+
+        port = 'ring:0'
+        self._assert_add_del_port(port)
+
+    def test_add_del_vhost(self):
+        """Check if vhost PMD is added."""
+
+        port = 'vhost:1'
+        self._assert_add_del_port(port)
+
+    def test_add_del_pcap(self):
+        """Check if pcap PMD is added."""
+
+        # TODO(yasufum): pcap cannot be adde because I do not know why...
+        port = 'pcap:1'
+        pass
+
+    def test_make_patch(self):
+        """Check if patch between ports is created and reseted."""
+
+        ports = ['ring:1', 'ring:2']
+
+        for port in ports:
+            self._add_port(port)
+        self._patch(ports[0], ports[1])
+        nfv = self._get_status()
+        self.assertTrue({'src': ports[0], 'dst': ports[1]} in nfv['patches'])
+
+        self._reset_patches()
+        nfv = self._get_status()
+        self.assertEqual(nfv['patches'], [])
-- 
2.17.1


  reply index

Thread overview: 4+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2019-12-17  2:37 [spp] [PATCH 0/3] Introduce unit test for SPP processes yasufum.o
2019-12-17  2:37 ` yasufum.o [this message]
2019-12-17  2:37 ` [spp] [PATCH 2/3] test: add spp_nfv test for forwarding yasufum.o
2019-12-17  2:37 ` [spp] [PATCH 3/3] test: add test for spp_primary yasufum.o

Reply instructions:

You may reply publically to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20191217023730.30477-2-yasufum.o@gmail.com \
    --to=yasufum.o@gmail.com \
    --cc=ferruh.yigit@intel.com \
    --cc=spp@dpdk.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

Soft Patch Panel

Archives are clonable:
	git clone --mirror http://inbox.dpdk.org/spp/0 spp/git/0.git

	# If you have public-inbox 1.1+ installed, you may
	# initialize and index your mirror using the following commands:
	public-inbox-init -V2 spp spp/ http://inbox.dpdk.org/spp \
		spp@dpdk.org
	public-inbox-index spp


Newsgroup available over NNTP:
	nntp://inbox.dpdk.org/inbox.dpdk.spp


AGPL code for this site: git clone https://public-inbox.org/ public-inbox