# Copyright (c) 2013, Web Notes Technologies Pvt. Ltd. and Contributors
# License: GNU General Public License v3. See license.txt

#!/usr/bin/env python
from __future__ import unicode_literals
import os, sys
import argparse

is_redhat = is_debian = None
root_password = None

requirements = [
	"chardet", 
	"cssmin", 
	"dropbox", 
	"google-api-python-client", 
	"gunicorn", 
	"httplib2", 
	"jinja2", 
	"markdown2", 
	"markupsafe", 
	"mysql-python==1.2.4", 
	"pygeoip", 
	"python-dateutil", 
	"python-memcached", 
	"pytz==2013d", 
	"requests", 
	"six", 
	"slugify", 
	"termcolor", 
	"werkzeug",
	"semantic_version",
	"gitpython==0.3.2.RC1"
]

def install(install_path):
	setup_folders(install_path)
	install_erpnext(install_path)
	
	post_install(install_path)
	
def install_pre_requisites():
	global is_redhat, is_debian
	is_redhat, is_debian = validate_install()
	if is_redhat:
		install_using_yum()
	elif is_debian:
		install_using_apt()
		
	install_python_modules()
	
	print "-"*80
	print "Pre-requisites Installed"
	print "-"*80

def validate_install():
	import platform

	# check os
	operating_system = platform.system()
	print "Operating System =", operating_system
	if operating_system != "Linux":
		raise Exception, "Sorry! This installer works only for Linux based Operating Systems"
	
	# check python version
	python_version = sys.version.split(" ")[0]
	print "Python Version =", python_version
	if not (python_version and int(python_version.split(".")[0])==2 and int(python_version.split(".")[1]) >= 7):
		raise Exception, "Hey! ERPNext needs Python version to be 2.7+"
	
	# check distribution
	distribution = platform.linux_distribution()[0].lower().replace('"', '')
	print "Distribution = ", distribution
	is_redhat = distribution in ("redhat", "red hat enterprise linux server", "centos", "centos linux", "fedora")
	is_debian = distribution in ("debian", "ubuntu", "elementary os", "linuxmint")
	
	if not (is_redhat or is_debian):
		raise Exception, "Sorry! This installer works only with yum or apt-get package management"
	
	return is_redhat, is_debian
		
def install_using_yum():
	packages = "python python-setuptools gcc python-devel MySQL-python git memcached ntp vim-enhanced screen"
	
	print "-"*80
	print "Installing Packages: (This may take some time)"
	print packages
	print "-"*80
	exec_in_shell("yum install -y %s" % packages)
	
	if not exec_in_shell("which mysql"):
		packages = "mysql mysql-server mysql-devel"
		print "Installing Packages:", packages
		exec_in_shell("yum install -y %s" % packages)
		exec_in_shell("service mysqld restart")
		
		# set a root password post install
		global root_password
		print "Please create a password for root user of MySQL"
		root_password = (get_root_password() or "erpnext").strip()
		exec_in_shell('mysqladmin -u root password "%s"' % (root_password,))
		print "Root password set as", root_password
	
	# install htop
	if not exec_in_shell("which htop"):
		try:
			exec_in_shell("cd /tmp && rpm -i --force http://packages.sw.be/rpmforge-release/rpmforge-release-0.5.2-2.el6.rf.x86_64.rpm && yum install -y htop")
		except:
			pass
	
	update_config_for_redhat()
	
def update_config_for_redhat():
	import re
	
	# set to autostart on startup
	for service in ("mysqld", "memcached", "ntpd"):
		exec_in_shell("chkconfig --level 2345 %s on" % service)
		exec_in_shell("service %s restart" % service)
	
def install_using_apt():
	exec_in_shell("apt-get update")
	packages = "python python-setuptools python-dev build-essential python-pip python-mysqldb git memcached ntp vim screen htop"
	print "-"*80
	print "Installing Packages: (This may take some time)"
	print packages
	print "-"*80
	exec_in_shell("apt-get install -y %s" % packages)
	global root_password
	if not root_password:
		root_password = get_root_password()
	exec_in_shell("echo mysql-server mysql-server/root_password password %s | sudo debconf-set-selections" % root_password)
	exec_in_shell("echo mysql-server mysql-server/root_password_again password %s | sudo debconf-set-selections" % root_password)
	
	if not exec_in_shell("which mysql"):
		packages = "mysql-server libmysqlclient-dev"
		print "Installing Packages:", packages
		exec_in_shell("apt-get install -y %s" % packages)
	
	update_config_for_debian()
	
def update_config_for_debian():
	for service in ("mysql", "ntpd"):
		exec_in_shell("service %s restart" % service)
	
def install_python_modules():
	print "-"*80
	print "Installing Python Modules: (This may take some time)"
	print "-"*80
	
	if not exec_in_shell("which pip-2.7"):
		exec_in_shell("easy_install-2.7 pip")
	
	exec_in_shell("pip-2.7 install --upgrade pip")
	exec_in_shell("pip-2.7 install --upgrade setuptools")
	exec_in_shell("pip-2.7 install --upgrade virtualenv")
	exec_in_shell("pip-2.7 install {}".format(' '.join(requirements)))
	
def install_erpnext(install_path):
	print
	print "-"*80
	print "Installing ERPNext"
	print "-"*80
	
	# ask for details
	global root_password
	if not root_password:
		root_password = get_root_password()
		test_root_connection(root_password)
	
	db_name = raw_input("ERPNext Database Name: ")
	if not db_name:
		raise Exception, "Sorry! You must specify ERPNext Database Name"
	
	# setup paths
	sys.path = [".", "lib", "app"] + sys.path
	import wnf
	
	# install database, run patches, update schema
	# setup_db(install_path, root_password, db_name)
	wnf.install(db_name, root_password=root_password)

	setup_cron(install_path)
	
def get_root_password():
	# ask for root mysql password
	import getpass
	root_pwd = None
	root_pwd = getpass.getpass("MySQL Root user's Password: ")
	return root_pwd
	
def test_root_connection(root_pwd):
	out = exec_in_shell("mysql -u root %s -e 'exit'" % \
		(("-p"+root_pwd) if root_pwd else "").replace('$', '\$').replace(' ', '\ '))
	if "access denied" in out.lower():
		raise Exception("Incorrect MySQL Root user's password")
		
def setup_folders(install_path):
	os.chdir(install_path)
	app = os.path.join(install_path, "app")
	if not os.path.exists(app):
		print "Cloning erpnext"
		exec_in_shell("cd %s && git clone --branch master https://github.com/webnotes/erpnext.git app" % install_path)
		exec_in_shell("cd app && git config core.filemode false")
		if not os.path.exists(app):
			raise Exception, "Couldn't clone erpnext repository"
	
	lib = os.path.join(install_path, "lib")
	if not os.path.exists(lib):
		print "Cloning wnframework"
		exec_in_shell("cd %s && git clone --branch master https://github.com/webnotes/wnframework.git lib" % install_path)
		exec_in_shell("cd lib && git config core.filemode false")
		if not os.path.exists(lib):
			raise Exception, "Couldn't clone wnframework repository"
	
	public = os.path.join(install_path, "public")
	for p in [public, os.path.join(public, "files"), os.path.join(public, "backups"),
		os.path.join(install_path, "logs")]:
			if not os.path.exists(p):
				os.mkdir(p)
				
def setup_conf(install_path, db_name):
	import os, string, random, re

	# generate db password
	char_range = string.ascii_letters + string.digits
	db_password = "".join((random.choice(char_range) for n in xrange(16)))
	
	# make conf file
	with open(os.path.join(install_path, "lib", "conf", "conf.py"), "r") as template:
		conf = template.read()
	
	conf = re.sub("db_name.*", 'db_name = "%s"' % (db_name,), conf)
	conf = re.sub("db_password.*", 'db_password = "%s"' % (db_password,), conf)
	
	with open(os.path.join(install_path, "conf.py"), "w") as conf_file:
		conf_file.write(conf)
	
	return db_password
	
def post_install(install_path):
	pass

def exec_in_shell(cmd):
	# using Popen instead of os.system - as recommended by python docs
	from subprocess import Popen
	import tempfile

	with tempfile.TemporaryFile() as stdout:
		with tempfile.TemporaryFile() as stderr:
			p = Popen(cmd, shell=True, stdout=stdout, stderr=stderr)
			p.wait()

			stdout.seek(0)
			out = stdout.read()
			if out: out = out.decode('utf-8')

			stderr.seek(0)
			err = stderr.read()
			if err: err = err.decode('utf-8')

	if err and any((kw in err.lower() for kw in ["traceback", "error", "exception"])):
		print out
		raise Exception, err
	else:
		print "."

	return out

def parse_args():
	parser = argparse.ArgumentParser()
	parser.add_argument('--create_user', default=False, action='store_true')
	parser.add_argument('--username', default='erpnext')
	parser.add_argument('--password', default='erpnext')
	parser.add_argument('--no_install_prerequisites', default=False, action='store_true')
	return parser.parse_args()

def create_user(username, password):
	import subprocess, pwd
	p = subprocess.Popen("useradd -m -d /home/{username} -s {shell} {username}".format(username=username, shell=os.environ.get('SHELL')).split())
	p.wait()
	p = subprocess.Popen("passwd {username}".format(username=username).split(), stdin=subprocess.PIPE)
	p.communicate('{password}\n{password}\n'.format(password=password))
	p.wait()
	return pwd.getpwnam(username).pw_uid

def setup_cron(install_path):
	erpnext_cron_entries = [
		"*/3 * * * * cd %s && python2.7 lib/wnf.py --run_scheduler >> erpnext-sch.log 2>&1" % install_path,
		"0 */6 * * * cd %s && python2.7 lib/wnf.py --backup >> erpnext-backup.log 2>&1" % install_path
		]
	for row in erpnext_cron_entries:
		try:
			existing_cron = exec_in_shell("crontab -l")
			if row not in existing_cron:
				exec_in_shell('{ crontab -l; echo "%s"; } | crontab' % row)
		except:
			exec_in_shell('echo "%s" | crontab' % row)

if __name__ == "__main__":
	args = parse_args()
	install_path = os.getcwd()
	if os.getuid() != 0 and args.create_user and not args.no_install_prequisites:
		raise Exception, "Please run this script as root"

	if args.create_user:
		uid = create_user(args.username, args.password)
		install_path = '/home/{username}/erpnext'.format(username=args.username)

	if not args.no_install_prerequisites:
		install_pre_requisites()

	if os.environ.get('SUDO_UID') and not args.create_user:
		os.setuid(int(os.environ.get('SUDO_UID')))
	
	if os.getuid() == 0 and args.create_user:
		os.setuid(uid)
		if install_path:
			os.mkdir(install_path)
	
	install(install_path=install_path)
	print
	print "-"*80
	print "Installation complete"
	print "To start the development server,"
	print "Login as {username} with password {password}".format(username=args.username, password=args.password)
	print "cd {}".format(install_path)
	print "./lib/wnf.py --serve"
	print "-"*80
	print "Open your browser and go to http://localhost:8000"
	print "Login using username = Administrator and password = admin"
