#!/usr/bin/python3
# coding=utf8

import os, argparse, subprocess, socket

class Parms():

	positiv = ('1', 'Y', 'YES', 'ON')
	negativ = ('0', 'N', 'NO', 'OFF')

	@classmethod
	def setup(cls):
		cls.applName = "dejsem"
		cls.version = 1.00

		cls.defaultsFile = os.path.join("/etc/default", cls.applName)
		cls.parsedflts()
		cls.parsecmdl()

		cls.clientMode = False		# řídí chování při ABENDu: client po ABENDu sys.exit(), server pokračuje

		cls.debugLevel = cls.cmdl("debugLevel", int(cls.env("DEB", cls.dflt("DEB", 0))))
		cls.random_seed= int(cls.env('RS', 0))

		cls.action = cls.cmdl("action", cls.env("ACT", "")).upper()
		cls.clientMode = cls.action != "SRV"

		cls.ssl = True

		cls.sslchannel = int(cls.cmdl("sslchannel", cls.env("CHAN", cls.dflt("CHAN", 2))))
		cls.sslPath = cls.cmdl("sslPath", cls.env("SSLP", cls.dflt("SSLP", os.path.join("/usr/share", cls.applName, "ssl"))))
		cls.sslCAPath = os.path.join(cls.sslPath, "dejCA.crt")
		cls.sslCert = os.path.join(cls.sslPath, "{:02d}.pem".format(cls.sslchannel))

		cls.srvhost = cls.cmdl("srvhost", cls.env("HOST", cls.dflt("HOST", "dejsem.org")))
		cls.filedir = "files"
		cls.exposed = ".exposed_to_http"
		cls.clipfile = "clipboard"
		cls.histdir = "history"		# cliboard history dir
		cls.srv_wwwhomedir = os.path.join("/var/www/html", cls.applName)
		cls.srv_homedir = os.path.join("/usr/local/", cls.applName)
		cls.client_homedir = cls.env("HOME", os.path.join("/home", "{}".format(os.getlogin)))
		cls.client_appldir = os.path.join(cls.client_homedir, ".local/share", cls.applName)
		cls.client_histdir = os.path.join(cls.client_appldir, cls.histdir)

		cls.bindhost = cls.env("BINDHOST", cls.dflt("BINDHOST", cls.getbindhost()))
		# cls.bindhost = cls.env("BINDHOST", "")
		# cls.broadcast = cls.env("BROADCAST", cls.getbroadcast(cls.bindhost))
		cls.broadcast = cls.env("BROADCAST", "255.255.255.255")
		cls.baseport = int(cls.env("BASEPORT", cls.dflt("BASEPORT", 42000)))
		cls.udpport = 4242 if cls.applName == "dejsem" else 4224 
		cls.pullPeerIface = None

		cls.bufSize = 256 * 1024
		cls.connThreshold = 77
		cls.connTimeout = 0.01
		cls.blockTimeout = 20
		cls.accept_timeout = 60  	# seconds
		cls.long_run_accept_timeout = 60  	# seconds
		cls.peer_accept_timeout = 60  		# seconds

		cls.datapaths = cls.args["datapaths"]	# data paths from cmdline
		cls.orig = cls.cmdl("datapaths", list(cls.env("ORIG", "")))		# origin data path
		cls.dest = cls.env("DEST", "")		# destination data path from ENV

	@classmethod
	def parsecmdl(cls):
		parser = argparse.ArgumentParser(description='sdílení clipboardu a filů přes server, přenos filů peer-to-peer')
		cmds = parser.add_mutually_exclusive_group()
		cmds.add_argument('--push', dest='action',
			action='store_const', const='PUSHCLIP',
			help='copy from local clipboard to shared clipboard')
		cmds.add_argument('--pull', dest='action',
			action='store_const', const='PULLCLIP',
			help='copy from shared clipboard to local clipboard')
		cmds.add_argument('--pullhist', dest='action',
			action='store_const', const='PULLHIST',
			help='synchronize local clipboard history from shared clipboard')
		cmds.add_argument('--pushsrv', '--pushfile', '--puf', dest='action',
			action='store_const', const='PUSHFILE',
			help='copy local file to server')
		cmds.add_argument('--pullsrv', '--pullfile', '--plf', dest='action',
			action='store_const', const='PULLFILE',
			help='copy server file to local')
		cmds.add_argument('--pulllist', dest='action',
			action='store_const', const='PULLLIST',
			help='list files on server')
		cmds.add_argument('--pushpeer', '--pup', dest='action',
			action='store_const', const='PUSHPEER',
			help='copy from local file to LAN peer')
		cmds.add_argument('--pullpeer', '--plp', dest='action',
			action='store_const', const='PULLPEER',
			help='copy from LAN peer to local dir')
		options = parser.add_argument_group(title='options')
		options.add_argument('-d', dest='debugLevel', type=int,
			metavar='<debug level>', help='debug level 0-5, ENV DEB')
		options.add_argument('-s', dest='srvhost',
			metavar='<srvhost>', help='server domain name or ip, ENV HOST')
		options.add_argument('-c', dest='sslchannel', type=int,
			metavar='<channel#>', help='ssl channel NN, ENV CHAN')
		options.add_argument('-x', dest='sslPath',
			metavar='<sslhome>', help='ssl keys store directory, ENV SSL')
		options.add_argument('-i', dest='pullPeerIface',
			metavar='<iface>', help='copy from LAN peer via <iface>')
		parser.add_argument('datapaths', nargs='*', metavar='datapath')
		cls.args = vars(parser.parse_args())

	@classmethod
	def parsedflts(cls):
		cls.defaults = dict()
		with open(cls.defaultsFile) as df:
			for line in df:
				key, value = line.split('=')
				cls.defaults[key] = value[:-1]

	@classmethod
	def dflt(cls, key, wired):
		return cls.defaults[key] if key in cls.defaults else wired

	@classmethod
	def env(cls, key, default):
		return os.environ[key] if key in os.environ else default

	@classmethod
	def cmdl(cls, arg, default):
		return cls.args[arg] if (arg in cls.args and cls.args[arg]) else default

	@classmethod
	def getbindhost(cls):
		return socket.getfqdn()

		"""
		p = subprocess.Popen(["host", "-t", "A", socket.gethostname()], stdout=subprocess.PIPE)
		p.wait()
		if p.returncode == 0:
			return p.stdout.readlines()[0].decode().split()[3]
		else:
			return ''
		"""

	@classmethod
	def getbroadcast(cls, bindhost):
		return '255.255.255.255'

		"""zatím mimo použití, je to hodně nejasné
		p = subprocess.Popen(("ip", "-o", "addr", "list"), stdout=subprocess.PIPE)
		p.wait()
		if p.returncode == 0:
			return subprocess.check_output(("grep", bindhost), stdin=p.stdout).decode().split()[5]
		else:
			return '255.255.255.255'
		"""


