diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..1da8522
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+.idea
diff --git a/non-wheel/httpsrv/README.md b/non-wheel/httpsrv/README.md
new file mode 100644
index 0000000..53ba0f6
--- /dev/null
+++ b/non-wheel/httpsrv/README.md
@@ -0,0 +1,19 @@
+# httpsrv
+
+Python script to create, delete, and rename HTTP Server Instances on the IBM i.
+
+# Installing requisites
+
+I think this may require installing the toolkit. Is the toolkit already installed along
+with Python on the IBM i?
+
+# Usage examples:
+
+```commandline
+$ python3 httpsrv.py --help # Display help
+$ python3 httpsrv.py -c --conf=zendsvr6 --name=develop # Create an HTTP Server Instance. Configuration: PHP 5.6, Name: DEVELOP
+$ python3 httpsrv.py -c --conf=zendphp7 --name=develop # Create an HTTP Server Instance. Configuration: PHP 7, Name: DEVELOP
+$ python3 httpsrv.py -c --conf=apache --name=develop # Create an HTTP Server Instance. Configuration: Apache, Name: DEVELOP
+$ python3 httpsrv.py -d --name=develop # Delete HTTP Server Instance with name DEVELOP
+$ python3 httpsrv.py -r --name=develop --newname=test # Rename HTTP Server Instance DEVELOP to TEST
+```
diff --git a/non-wheel/httpsrv/httpsrv.py b/non-wheel/httpsrv/httpsrv.py
new file mode 100644
index 0000000..e3bb368
--- /dev/null
+++ b/non-wheel/httpsrv/httpsrv.py
@@ -0,0 +1,558 @@
+#!/usr/bin/env python3
+import argparse
+import os
+from itoolkit import *
+from itoolkit.lib.ilibcall import *
+import ibm_db_dbi as db2
+import shutil
+
+#########################################################################
+# #
+# Issues #
+# #
+# Using SQL to create an HTTP Server Instance does not work properly. #
+# The `mod_info_query` does not have any effect, so the new HTTP Server #
+# does not point at the correct httpd.conf #
+# #
+#########################################################################
+
+# TODO - The instance still isn't working when starting out of the box. it times out
+# TODO - zendsvr6 and apache configs have not been tested yet
+# TODO - Qzui APIs would be preferable for creating and deleting HTTP Apache Instances
+
+
+def get_index_html(name):
+ return '''
+
+
+
+
+ {0} Works
+
+
+
+ {0} works!!!
+
+
+'''.format(name)
+
+
+def get_fastcgi_conf(name):
+ return '''; Static PHP servers for default user
+Server type="application/x-httpd-php" CommandLine="/usr/local/zendphp7/bin/php-cgi.bin" StartProcesses="1" SetEnv="LIBPATH=/usr/local/zendphp7/lib" SetEnv="PHPRC=/usr/local/zendphp7/etc/" SetEnv="PHP_FCGI_CHILDREN=10" SetEnv="PHP_FCGI_MAX_REQUESTS=0" ConnectionTimeout="30" RequestTimeout="60" SetEnv="CCSID=1208" SetEnv="LANG=C" SetEnv="INSTALLATION_UID=100313092679" SetEnv="LDR_CNTRL=MAXDATA=0x40000000" SetEnv="ZEND_TMPDIR=/usr/local/zendphp7/tmp" SetEnv="TZ=5,M3.2.0,M11.1.0"
+
+; Where to place socket files
+IpcDir /www/{}/logs
+'''.format(name)
+
+
+def get_fastcgi_conf_twn(name):
+ return '''; Static PHP servers for default user
+Server type="application/x-httpd-php" CommandLine="/usr/local/zendphp7/bin/php-cgi.bin" StartProcesses="1" SetEnv="LIBPATH=/usr/local/zendphp7/lib" SetEnv="PHPRC=/usr/local/zendphp7/etc/" SetEnv="PHP_FCGI_CHILDREN=10" SetEnv="PHP_FCGI_MAX_REQUESTS=0" ConnectionTimeout="30" RequestTimeout="60" SetEnv="CCSID=1208" SetEnv="LANG=C" SetEnv="INSTALLATION_UID=100313092679" SetEnv="LDR_CNTRL=MAXDATA=0x40000000" SetEnv="ZEND_TMPDIR=/usr/local/zendphp7/tmp" SetEnv="TZ=-5"
+
+; Where to place socket files
+IpcDir /www/{}/logs
+'''.format(name)
+
+
+def get_fastcgi_dynamic_conf(name):
+ return '''; Static PHP servers for default user
+DynamicServer type="application/x-httpd-php" MinProcesses=5 MaxProcesses=100 CommandLine="/usr/local/zendphp7/bin/php-cgi.bin" SetEnv="LIBPATH=/usr/local/zendphp7/lib" SetEnv="PHPRC=/usr/local/zendphp7/etc/" SetEnv="PHP_FCGI_CHILDREN=1" SetEnv="PHP_FCGI_MAX_REQUESTS=0" ConnectionTimeout="60" RequestTimeout="60" SetEnv="CCSID=1208" SetEnv="LANG=en_US" SetEnv="INSTALLATION_UID=100313092679" SetEnv="LDR_CNTRL=MAXDATA=0x40000000" SetEnv="TZ=5,M3.2.0,M11.1.0"
+
+; Where to place socket files
+IpcDir /www/{}/logs
+
+;Minimum and Maximum of dynamic servers
+MinDynamicServers 5
+MaxDynamicServers 100
+
+
+;Usage of this configuration requires following PASE and DG1 PTFs
+;PASE PTFs
+;V5R4: SI43218
+;V6R1: SI43243
+;V7R1: SI43244
+
+;DG1 PTFs
+;V5R4: SI43221
+;V6R1: SI43224
+;V7R1: SI43222
+'''.format(name)
+
+
+def get_fastcgi_http_add_conf(name):
+ return '''Include /www/{}/conf/apache-sites
+'''.format(name)
+
+
+def get_req_all(s):
+ un = os.uname()
+ version = (int(un.version), int(un.release))
+ if version > (7, 1):
+ return 'Require all ' + s
+ else:
+ if s == 'granted':
+ return '''order allow,deny
+allow from all'''
+ else:
+ return '''order deny,allow
+deny from all'''
+
+
+def get_apache_conf(name, port):
+ return '''# Apache Default server configuration
+LoadModule proxy_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_http_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_connect_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_ftp_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule zend_enabler_module /QSYS.LIB/QHTTPSVR.LIB/QZFAST.SRVPGM
+
+# zend fastcgi
+AddType application/x-httpd-php .php
+AddHandler fastcgi-script .php
+
+# General setup directives
+Listen *:{0}
+HotBackup Off
+HostNameLookups Off
+UseCanonicalName On
+TimeOut 30000
+KeepAlive On
+KeepAliveTimeout 5
+DocumentRoot /www/{1}/htdocs
+AddLanguage en .en
+
+# protection (Basic)
+
+ {2}
+
+
+
+ Options FollowSymLinks
+ {3}
+ AllowOverride all
+
+
+IncludeOptional /www/{1}/conf/apache-sites/*.conf
+'''.format(port, name, get_req_all('denied'), get_req_all('granted'))
+
+
+def get_zendsvr6_conf(name, port):
+ return '''LoadModule proxy_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_http_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_connect_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_ftp_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule zend_enabler_module /QSYS.LIB/QHTTPSVR.LIB/QZFAST.SRVPGM
+DefaultFsCCSID 37
+CGIJobCCSID 37
+
+Listen *:{0}
+DocumentRoot /www/{1}/htdocs
+DirectoryIndex index.php index.html
+
+Options -ExecCGI -FollowSymLinks -SymLinksIfOwnerMatch -Includes -IncludesNoExec -Indexes -MultiViews
+LogFormat "%h %l %u %t \\"%r\\" %>s %b \\"%{{Referer}}i\\" \\"%{{User-Agent}}i\\"" combined
+LogFormat "%{{Cookie}}n \\"%r\\" %t" cookie
+LogFormat "%{{User-agent}}i" agent
+LogFormat "%{{Referer}}i -> %U" referer
+LogFormat "%h %l %u %t \\"%r\\" %>s %b" common
+CustomLog logs/access_log combined
+SetEnvIf "User-Agent" "Mozilla/2" nokeepalive
+SetEnvIf "User-Agent" "JDK/1\.0" force-response-1.0
+SetEnvIf "User-Agent" "Java/1\.0" force-response-1.0
+SetEnvIf "User-Agent" "RealPlayer 4\.0" force-response-1.0
+SetEnvIf "User-Agent" "MSIE 4\.0b2;" nokeepalive
+SetEnvIf "User-Agent" "MSIE 4\.0b2;" force-response-1.0
+
+TimeOut 30000
+KeepAlive On
+KeepAliveTimeout 5
+HotBackup Off
+
+#AddCharset UTF-8 .utf8
+#AddCharset utf-8 .utf8
+#AddCharset utf-7 .utf7
+AddCharset UTF-8 .htm .html .xml
+
+# zend fastcgi
+AddType application/x-httpd-php .php
+AddHandler fastcgi-script .php
+
+RewriteEngine on
+
+
+ {2}
+
+
+
+ Options FollowSymLinks
+ {3}
+ AllowOverride all
+
+
+#XML Toolkit http settings
+ScriptAlias /cgi-bin/ /QSYS.LIB/ZENDSVR6.LIB/
+
+ AllowOverride None
+ order allow,deny
+ allow from all
+ SetHandler cgi-script
+ Options +ExecCGI
+
+#End XML Toolkit http settings
+
+# keep access logs 10 days, error logs 10 days, FastCGI logs 10 days
+LogMaint /www/{1}/logs/access_log 10 0
+LogMaint /www/{1}/logs/error_log 10 0
+LogMaint /www/{1}/logs/error_zfcgi 10 0
+
+# Maintain Logs at 3 am (0 = midnight, 23 = 11 pm, etc)
+# Set for an hour when the server is active (i.e. not during an IPL or backup)
+LogMaintHour 3
+
+IncludeOptional /www/{1}/conf/apache-sites/*.conf
+'''.format(port, name, get_req_all('denied'), get_req_all('granted'))
+
+
+def get_zendphp7_conf(name, port):
+ return '''LoadModule proxy_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_http_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_connect_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule proxy_ftp_module /QSYS.LIB/QHTTPSVR.LIB/QZSRCORE.SRVPGM
+LoadModule zend_enabler_module /QSYS.LIB/QHTTPSVR.LIB/QZFAST.SRVPGM
+DefaultFsCCSID 37
+CGIJobCCSID 37
+
+Listen *:{0}
+DocumentRoot /www/{1}/htdocs
+DirectoryIndex index.php index.html
+
+Options -ExecCGI -FollowSymLinks -SymLinksIfOwnerMatch -Includes -IncludesNoExec -Indexes -MultiViews
+LogFormat "%h %l %u %t \\"%r\\" %>s %b \\"%{{Referer}}i\\" \\"%{{User-Agent}}i\\"" combined
+LogFormat "%{{Cookie}}n \\"%r\\" %t" cookie
+LogFormat "%{{User-agent}}i" agent
+LogFormat "%{{Referer}}i -> %U" referer
+LogFormat "%h %l %u %t \\"%r\\" %>s %b" common
+CustomLog logs/access_log combined
+SetEnvIf "User-Agent" "Mozilla/2" nokeepalive
+SetEnvIf "User-Agent" "JDK/1\.0" force-response-1.0
+SetEnvIf "User-Agent" "Java/1\.0" force-response-1.0
+SetEnvIf "User-Agent" "RealPlayer 4\.0" force-response-1.0
+SetEnvIf "User-Agent" "MSIE 4\.0b2;" nokeepalive
+SetEnvIf "User-Agent" "MSIE 4\.0b2;" force-response-1.0
+
+TimeOut 30000
+KeepAlive On
+KeepAliveTimeout 5
+HotBackup Off
+
+#AddCharset UTF-8 .utf8
+#AddCharset utf-8 .utf8
+#AddCharset utf-7 .utf7
+AddCharset UTF-8 .htm .html .xml
+
+# zend fastcgi
+AddType application/x-httpd-php .php
+AddHandler fastcgi-script .php
+
+RewriteEngine on
+
+
+ {2}
+
+
+
+ Options FollowSymLinks
+ {3}
+ AllowOverride all
+
+
+#XML Toolkit http settings
+ScriptAlias /cgi-bin/ /QSYS.LIB/zendphp7.LIB/
+
+ AllowOverride None
+ {3}
+ SetHandler cgi-script
+ Options +ExecCGI
+
+#End XML Toolkit http settings
+
+# keep access logs 10 days, error logs 10 days, FastCGI logs 10 days
+LogMaint /www/{1}/logs/access_log 10 0
+LogMaint /www/{1}/logs/error_log 10 0
+LogMaint /www/{1}/logs/error_zfcgi 10 0
+
+# Maintain Logs at 3 am (0 = midnight, 23 = 11 pm, etc)
+# Set for an hour when the server is active (i.e. not during an IPL or backup)
+LogMaintHour 3
+
+IncludeOptional /www/{1}/conf/apache-sites/*.conf
+'''.format(port, name, get_req_all('denied'), get_req_all('granted'))
+
+
+def get_example_vhost_conf(name, port):
+ return '''
+ ServerName {1}.domain.com
+ DocumentRoot /www/{1}/example-project/htdocs
+
+
+ Options Indexes FollowSymLinks
+ {2}
+ AllowOverride All
+ DirectoryIndex index.php index.html
+
+
+
+ ErrorLog "/www/{1}/example-project/logs/error_log"
+ CustomLog "/www/{1}/example-project/logs/access_log" common
+
+'''.format(port, name, get_req_all('granted'))
+
+
+def create(name, conf, port):
+ path = '/www/' + name
+ verification_text = '''/www/
+ {0}/
+ conf/
+ apache-sites/
+ example-vhost.conf
+ httpd.conf
+ example-project/
+ conf/
+ {0}.conf
+ htdocs/
+ index.html
+ logs/
+ htdocs/
+ index.html
+ logs/
+'''.format(name)
+
+ verification_text += "Does the above folder structure look correct? (Y/n) "
+
+ verified = input(verification_text) or 'Y'
+
+ if verified.lower() in ['y', 'yes']:
+ print('conf: ' + conf)
+ print('name: ' + name)
+ print('port: ' + port)
+ os.mkdir(path)
+ os.mkdir(path + '/conf')
+ os.mkdir(path + '/logs')
+ os.mkdir(path + '/htdocs')
+ index_file = open(path + '/htdocs/index.html', "w+")
+ index_file.write(get_index_html(name))
+
+ with open(path + '/conf/fastcgi.conf', "w+") as file:
+ file.write(get_fastcgi_conf(name))
+ with open(path + '/conf/fastcgi.conf.twn', "w+") as file:
+ file.write(get_fastcgi_conf_twn(name))
+ with open(path + '/conf/fastcgi_dynamic.conf', "w+") as file:
+ file.write(get_fastcgi_dynamic_conf(name))
+ with open(path + '/conf/fastcgi_http_add.conf', "w+") as file:
+ file.write(get_fastcgi_http_add_conf(name))
+
+ get_conf = globals()['get_{}_conf'.format(conf)]
+ with open(path + '/conf/httpd.conf', "w+") as conf_file:
+ conf_file.write(get_conf(name, port))
+
+ os.mkdir(path + '/conf/apache-sites')
+ os.mkdir(path + '/example-project')
+ os.mkdir(path + '/example-project/conf')
+ with open("{}/example-project/conf/{}.conf".format(path, name), "w+") as file:
+ file.write(get_example_vhost_conf(name, port))
+ os.mkdir(path + '/example-project/htdocs')
+ with open(path + '/example-project/htdocs/index.html', "w+") as file:
+ file.write(get_index_html('Example Project'))
+ os.mkdir(path + '/example-project/logs')
+ os.symlink(
+ "{}/example-project/conf/{}.conf".format(path, name),
+ path + '/conf/apache-sites/example-project.conf'
+ )
+
+ # create_with_qzui_api(name)
+ create_with_sql(name)
+
+
+# Hopefully to go away in favor of create_with_qzui_api
+def create_with_sql(name):
+ conn = db2.connect()
+ cur = conn.cursor()
+
+ sys_cmd = "CPYF FROMFILE(QUSRSYS/QATMHINSTC) TOFILE(QUSRSYS/QATMHINSTC) " +\
+ "FROMMBR(APACHEDFT) TOMBR({}) MBROPT(*REPLACE)".format(name)
+ crt_http_svr = "call qcmdexc('{}');".format(sys_cmd)
+ cur.execute(crt_http_svr)
+
+ query = 'create or replace alias QUSRSYS.QATMHINSTC_{0} for QUSRSYS.QATMHINSTC({0})'.format(name)
+ cur.execute(query)
+
+ query = '''update QUSRSYS.QATMHINSTC_{0}
+set CHARFIELD = '-apache -d /www/{0} -f conf/httpd.conf -AutoStartN' with NC'''.format(name)
+ cur.execute(query)
+
+ conn.commit()
+ cur.close()
+ conn.close()
+
+
+# This is the part that needs a lot of help.
+# I (Josh) do not know the Python Toolkit for IBM i. I'm willing to learn.
+def create_with_qzui_api(name):
+ itransport = iLibCall()
+ itool = iToolKit()
+
+ itool.add(iCmd('addlible', 'addlible QHTTPSVR'))
+ itool.add(
+ iSrvPgm('QzuiCreateInstance', 'QZHBCONF', 'QzuiCreateInstance',
+ iopt={'lib': 'QHTTPSVR'}) # This doesn't seem to work, thus the ADDLIBLE above
+ .addParm(iData('instance', '10a', name.upper()))
+ .addParm(
+ iDS('INSD0110', {'len': 'buflen'})
+ .addData(iData('autostart', '10a', '*NO'))
+ .addData(iData('threads', '10i0', '0'))
+ .addData(iData('ccsid', '10i0', '37'))
+ .addData(iData('out_table_name', '10a', '*GLOBAL'))
+ .addData(iData('out_table_lib', '10a', '*GLOBAL'))
+ .addData(iData('in_table_name', '10a', '*GLOBAL'))
+ .addData(iData('in_table_lib', '10a', '*GLOBAL'))
+ .addData(iData('config_file', '512a', '/www/' + name.lower() + '/httpd.conf'))
+ .addData(iData('server_root', '512a', '/www/' + name.lower()))
+ )
+ .addParm(iData('bufsize', '10i0', '', {'setlen': 'buflen'}))
+ .addParm(iData('format', '10a', 'INSD0110'))
+ .addParm(
+ iDS('qus_ec_t', {'len': 'errlen'})
+ .addData(iData('provided', '10i0', '', {'setlen': 'errlen'}))
+ .addData(iData('available', '10i0', ''))
+ .addData(iData('msgid', '7A', ''))
+ .addData(iData('reserved', '1A', ''))
+ # These are defined specifically for CPF3C1D
+ .addData(iData('parameter', '10i0', ''))
+ .addData(iData('parmlen', '10i0', ''))
+ .addData(iData('minlen', '10i0', ''))
+ .addData(iData('maxlen', '10i0', ''))
+ )
+ )
+
+ itool.call(itransport)
+
+ result = itool.dict_out('QzuiCreateInstance')
+ # print(result)
+ err = result['qus_ec_t']
+ if int(err['available']):
+ if err['msgid'] == 'CPF3C1D':
+ print("{4}: The length of {0} for parameter {1} is not valid. Values for this parameter must be greater than {2} and less than {3}.".format(
+ err['parmlen'], err['parameter'], err['minlen'], err['maxlen'], err['msgid']))
+ else:
+ print(err['msgid'])
+
+
+def delete_with_qzui_api(name):
+ print('delete')
+ # Use QzuiDeleteInstance to delete HTTP Server Instance
+
+
+def delete_with_sql(name):
+ conn = db2.connect()
+ cur = conn.cursor()
+
+ sys_cmd = 'RMVM FILE(QUSRSYS/QATMHINSTC) MBR({})'.format(name)
+ crt_http_svr = "call qcmdexc('{}');".format(sys_cmd)
+ cur.execute(crt_http_svr)
+
+ conn.commit()
+ cur.close()
+ conn.close()
+
+
+def rename(name, newname):
+ print('rename')
+ # Could not find a command for this one. Only idea is to use CHGPF or some command to change the member name
+ # rerun command to update update apache configuration path
+ # Then mv directory to rename directory
+
+
+def rename_with_sql(name, newname):
+ conn = db2.connect()
+ cur = conn.cursor()
+
+ sys_cmd = 'RNMM FILE(QUSRSYS/QATMHINSTC) MBR({}) NEWMBR({})'.format(name, newname)
+ crt_http_svr = "call qcmdexc('{}');".format(sys_cmd)
+ cur.execute(crt_http_svr)
+
+ query = 'create or replace alias QUSRSYS.QATMHINSTC_{0} for QUSRSYS.QATMHINSTC({0})'.format(newname)
+ cur.execute(query)
+
+ query = '''update QUSRSYS.QATMHINSTC_{0}
+set CHARFIELD = '-apache -d /www/{0} -f conf/httpd.conf -AutoStartN' with NC'''.format(newname)
+ cur.execute(query)
+
+ conn.commit()
+ cur.close()
+ conn.close()
+
+
+def start(name):
+ os.system("system 'STRTCPSVR SERVER(*HTTP) HTTPSVR(" + name.upper() + ")'")
+
+
+def restart(name):
+ os.system("system 'STRTCPSVR SERVER(*HTTP) RESTART(*HTTP) HTTPSVR(" + name.upper() + ")'")
+
+
+def stop(name):
+ os.system("system 'ENDTCPSVR SERVER(*HTTP) HTTPSVR(" + name.upper() + ")'")
+
+
+def main():
+ p = argparse.ArgumentParser()
+ sp = p.add_subparsers(title='commands', dest='command')
+
+ p_create = sp.add_parser('create', help='Create HTTP Server Instance')
+ p_create.add_argument('--conf', '-t', default="zendphp7", choices=['zendphp7', 'zendsvr6', 'apache'])
+ p_create.add_argument('--name', '-n', required=True)
+ p_create.add_argument('--port', '-p', required=True)
+
+ p_rename = sp.add_parser('rename', help='Rename HTTP Server Instance')
+ p_rename.add_argument('--name', '-n', required=True)
+ p_rename.add_argument('--newname', '-e', required=True)
+
+ p_delete = sp.add_parser('delete', help='Delete HTTP Server Instance')
+ p_delete.add_argument('--name', '-n', required=True)
+ p_delete.add_argument('--force', '-f', action='store_true', default=False)
+
+ p_start = sp.add_parser('start', help='Start HTTP Server Instance')
+ p_start.add_argument('--name', '-n', required=True)
+
+ p_restart = sp.add_parser('restart', help='Restart HTTP Server Instance')
+ p_restart.add_argument('--name', '-n', required=True)
+
+ p_stop = sp.add_parser('stop', help='Stop HTTP Server Instance')
+ p_stop.add_argument('--name', '-n', required=True)
+
+ args = p.parse_args()
+
+ if args.command == 'create':
+ create(args.name, args.conf, args.port)
+ elif args.command == 'rename':
+ rename_with_sql(args.name, args.newname)
+ elif args.command == 'delete':
+ if args.force:
+ delete_with_sql(args.name)
+ else:
+ verification_text = 'Are you sure you want to delete {}? This cannot be undone. (y/N) '.format(args.name)
+ verified = input(verification_text) or 'n'
+
+ if verified.lower() in ['y', 'yes']:
+ delete_with_sql(args.name)
+ elif args.command == 'start':
+ start(args.name)
+ elif args.command == 'restart':
+ restart(args.name)
+ elif args.command == 'stop':
+ stop(args.name)
+
+
+if __name__ == '__main__':
+ main()