dissertation-3-evaluation/evaluation.ipynb

333 lines
180 KiB
Plaintext
Raw Normal View History

{
"cells": [
{
"cell_type": "code",
"execution_count": 1,
"metadata": {
"collapsed": true
},
"outputs": [],
"source": [
"import os\n",
"import ipaddress\n",
"\n",
"import runners\n",
"from structure import Bridge\n",
"from structure import SpeedTestServer, RemoteServer, LocalServer\n",
"from structure import Interface, IpMethod\n",
"\n",
"%load_ext dotenv\n",
"%dotenv"
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
2020-11-01 18:35:10 +00:00
"outputs": [
{
"ename": "NameError",
"evalue": "name 'runners' is not defined",
"output_type": "error",
"traceback": [
"\u001B[0;31m---------------------------------------------------------------------------\u001B[0m",
"\u001B[0;31mNameError\u001B[0m Traceback (most recent call last)",
"\u001B[0;32m<ipython-input-2-5781debf60ce>\u001B[0m in \u001B[0;36m<module>\u001B[0;34m\u001B[0m\n\u001B[0;32m----> 1\u001B[0;31m runner = runners.ProxmoxRunner(\n\u001B[0m\u001B[1;32m 2\u001B[0m \u001B[0mhost\u001B[0m\u001B[0;34m=\u001B[0m\u001B[0mos\u001B[0m\u001B[0;34m.\u001B[0m\u001B[0mgetenv\u001B[0m\u001B[0;34m(\u001B[0m\u001B[0;34m'PROXMOX_HOST'\u001B[0m\u001B[0;34m)\u001B[0m\u001B[0;34m,\u001B[0m\u001B[0;34m\u001B[0m\u001B[0;34m\u001B[0m\u001B[0m\n\u001B[1;32m 3\u001B[0m \u001B[0mnode\u001B[0m\u001B[0;34m=\u001B[0m\u001B[0mos\u001B[0m\u001B[0;34m.\u001B[0m\u001B[0mgetenv\u001B[0m\u001B[0;34m(\u001B[0m\u001B[0;34m'PROXMOX_NODE'\u001B[0m\u001B[0;34m)\u001B[0m\u001B[0;34m,\u001B[0m\u001B[0;34m\u001B[0m\u001B[0;34m\u001B[0m\u001B[0m\n\u001B[1;32m 4\u001B[0m \u001B[0muser\u001B[0m\u001B[0;34m=\u001B[0m\u001B[0mos\u001B[0m\u001B[0;34m.\u001B[0m\u001B[0mgetenv\u001B[0m\u001B[0;34m(\u001B[0m\u001B[0;34m'PROXMOX_USER'\u001B[0m\u001B[0;34m)\u001B[0m\u001B[0;34m,\u001B[0m\u001B[0;34m\u001B[0m\u001B[0;34m\u001B[0m\u001B[0m\n\u001B[1;32m 5\u001B[0m \u001B[0mtoken_name\u001B[0m\u001B[0;34m=\u001B[0m\u001B[0mos\u001B[0m\u001B[0;34m.\u001B[0m\u001B[0mgetenv\u001B[0m\u001B[0;34m(\u001B[0m\u001B[0;34m'PROXMOX_TOKEN_NAME'\u001B[0m\u001B[0;34m)\u001B[0m\u001B[0;34m,\u001B[0m\u001B[0;34m\u001B[0m\u001B[0;34m\u001B[0m\u001B[0m\n",
"\u001B[0;31mNameError\u001B[0m: name 'runners' is not defined"
]
}
],
"source": [
"runner = runners.ProxmoxRunner(\n",
" host=os.getenv('PROXMOX_HOST'),\n",
" node=os.getenv('PROXMOX_NODE'),\n",
" user=os.getenv('PROXMOX_USER'),\n",
" token_name=os.getenv('PROXMOX_TOKEN_NAME'),\n",
" token_value=os.getenv('PROXMOX_TOKEN_VALUE'),\n",
"\n",
" template_id=9000,\n",
" initial_vm_id=21002,\n",
"\n",
" internet_bridge='vmbr2',\n",
"\n",
" management_bridge='vmbr4',\n",
" management_initial_ip=ipaddress.ip_address('10.21.12.2'),\n",
")"
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
"outputs": [],
"source": [
"g_st = SpeedTestServer([Interface(IpMethod.Auto4)])\n",
"l_st = SpeedTestServer([Interface(IpMethod.Dhcp4)])\n",
"\n",
"rs = RemoteServer([Interface(IpMethod.Auto4)])\n",
"ls = LocalServer([\n",
" Interface(IpMethod.Auto4, limit=1),\n",
" Interface(IpMethod.Auto4, limit=1),\n",
"], l_st)\n",
"\n",
"top_level_bridge = Bridge(*[\n",
" g_st.get_interfaces()[0],\n",
" rs.get_interfaces()[0],\n",
" *ls.get_interfaces()[0:2],\n",
"])\n",
"runner.build(top_level_bridge)\n",
"\n",
"# Test from the client to the global network via the proxy\n",
"g_st.server()\n",
"l_st.client(rs.get_interfaces()[0])\n",
"\n",
"# Test from the global network to the client via the proxy\n",
"g_st.server()\n",
"l_st.client(rs.get_interfaces()[0])\n",
"\n",
"# Clean up\n",
"runner.teardown()"
]
},
{
"cell_type": "code",
2020-11-03 20:55:44 +00:00
"execution_count": 13,
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
2020-11-01 18:35:10 +00:00
"outputs": [],
"source": [
"from itertools import cycle\n",
"import matplotlib.pyplot as plt\n",
"\n",
"def plot_iperf_results(data, title, events=None, filename=None, start_at_zero=True):\n",
" cycol = cycle('brgy')\n",
2020-11-01 18:35:10 +00:00
"\n",
" fig = plt.figure()\n",
" axes = fig.add_axes([0,0,1,1])\n",
"\n",
" axes.set_title(title, pad=20.0)\n",
2020-11-01 18:35:10 +00:00
" axes.set_xlabel('Time (s)')\n",
" axes.set_ylabel('Throughput (Mbps)')\n",
"\n",
" for k, v in data.items():\n",
" intervals = [x['sum'] for x in v['intervals'] if not x['sum']['omitted']]\n",
"\n",
" x_axis = [((x['start'] + x['end'])/2) for x in intervals]\n",
" y_axis = [x['bits_per_second']/1e6 for x in intervals]\n",
2020-11-01 18:35:10 +00:00
" axes.plot(x_axis, y_axis, next(cycol), label=k)\n",
"\n",
" legend = axes.legend()\n",
"\n",
" if start_at_zero:\n",
" axes.set_ylim(bottom=0)\n",
" axes.set_xlim(left=0)\n",
"\n",
2020-11-01 18:35:10 +00:00
" if events is not None:\n",
" for k, v in events.items():\n",
2020-11-03 20:55:44 +00:00
" axes.axvline(k, linestyle='--', color='grey')\n",
" axes.annotate(v, (k, 1.02), xycoords=axes.get_xaxis_transform(), ha='center')\n",
2020-11-01 18:35:10 +00:00
"\n",
" if filename is not None:\n",
" fig.savefig(filename, bbox_extra_artists=(legend,), bbox_inches='tight', pad_inches=0.3)"
]
},
{
"cell_type": "code",
2020-11-03 20:55:44 +00:00
"execution_count": 4,
2020-11-01 18:35:10 +00:00
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
"outputs": [],
"source": [
"# Manual results\n",
"# sudo iperf3 -c X.X.X.X -t 30 -O 5 -J\n",
"\n",
"import json\n",
"\n",
"def load_json_from_file(path):\n",
" with open(path, 'r') as f:\n",
" return json.loads(f.read())\n",
"\n",
"One1MBStraight = load_json_from_file('manual/One1MBStraight.json')\n",
"One2MBStraight = load_json_from_file('manual/One2MBStraight.json')\n",
"\n",
"Two1MBAggregate = load_json_from_file('manual/Two1MBAggregate.json')\n",
"Two2MBAggregate = load_json_from_file('manual/Two2MBAggregate.json')\n",
"\n",
"One1MBOne2MBAggregate = load_json_from_file('manual/One1MBOne2MBAggregate.json')\n",
"\n",
2020-11-03 20:55:44 +00:00
"# A 60 second long test\n",
"Two2MBAggregateKillOneRecoverOne = load_json_from_file('manual/Two2MBAggregateKillOneRecoverOne.json')\n"
]
2020-11-01 18:35:10 +00:00
},
{
"cell_type": "code",
2020-11-03 20:55:44 +00:00
"execution_count": 9,
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
2020-11-01 18:35:10 +00:00
"outputs": [
{
"data": {
"text/plain": "<Figure size 432x288 with 1 Axes>",
2020-11-03 20:55:44 +00:00
"image/png": "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
2020-11-01 18:35:10 +00:00
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plot_iperf_results(\n",
" {\n",
" '1x1MBps connection (not proxied)': One1MBStraight,\n",
" '2x1MBps connections (proxied)': Two1MBAggregate,\n",
" },\n",
" 'Proxying adds additional bandwidth',\n",
2020-11-01 18:35:10 +00:00
")"
]
},
{
"cell_type": "code",
2020-11-03 20:55:44 +00:00
"execution_count": 10,
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
"outputs": [
{
"data": {
"text/plain": "<Figure size 432x288 with 1 Axes>",
2020-11-03 20:55:44 +00:00
"image/png": "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
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plot_iperf_results(\n",
" {\n",
" '1x1MBps connection (not proxied)': One1MBStraight,\n",
" '2x1MBps connections (proxied)': Two1MBAggregate,\n",
" '1x2MBps connection (not proxied)': One2MBStraight,\n",
" '2x2MBps connections (proxied)': Two2MBAggregate,\n",
" },\n",
2020-11-03 20:55:44 +00:00
" 'Proxing bandwidth scaling/overhead',\n",
")"
]
},
{
"cell_type": "code",
2020-11-03 20:55:44 +00:00
"execution_count": 11,
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
"outputs": [
{
"data": {
"text/plain": "<Figure size 432x288 with 1 Axes>",
2020-11-03 20:55:44 +00:00
"image/png": "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
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
2020-11-01 18:35:10 +00:00
],
"source": [
"plot_iperf_results(\n",
" {\n",
" '2x1MBps connections (proxied)': Two1MBAggregate,\n",
" '1x1MBps+1x2MBps connections (proxied)': One1MBOne2MBAggregate,\n",
" '2x2MBps connections (proxied)': Two2MBAggregate,\n",
" },\n",
" 'Imbalanced connections add',\n",
")"
]
},
{
"cell_type": "code",
2020-11-03 20:55:44 +00:00
"execution_count": 14,
2020-11-01 18:35:10 +00:00
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
"outputs": [
{
"data": {
"text/plain": "<Figure size 432x288 with 1 Axes>",
2020-11-03 20:55:44 +00:00
"image/png": "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
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plot_iperf_results(\n",
" {\n",
" '1x2MBps+1xYMBps connections (proxied)': Two2MBAggregateKillOneRecoverOne,\n",
" },\n",
" 'Killed connection',\n",
" events={15: 'Y = 0', 40: 'Y = 2'},\n",
2020-11-03 20:55:44 +00:00
" filename='graph4.png',\n",
")"
]
2020-11-01 18:35:10 +00:00
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {
"pycharm": {
"name": "#%%\n"
}
},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.8.6"
}
},
"nbformat": 4,
"nbformat_minor": 1
}