#!/usr/bin/python # Description : Virtual Host Manage Script # Below is the json format description: # 1. Add new user # {"website":"www.baidu.com", "ftp":["user","passwd"], "mysql":["db_name","m_user","m_passwd"]} # 2. Enable/Disable 1 (0=disable, 1=enable) # {"manage":{"website":["www.baidu.com",0], "ftp":["user",1], "mysql":["m_user", "db_name",1]}} # 3. Modify password for [ftp/mysql] (if you only modify ftp,then set mysql items "") # {"ftp":["789","789", "new_passwd"], "mysql":["","","", ""]} # 4. Restart Service for apache/ftp/mysql 1 (0=stop,1=start,2=restart) # {"service":{"apache":1, "ftp":0, "mysql":0}} # 5. Add/Delete/Modify/Query apache ServerAlias (Add=1,Delete=2,Modify=3,Query=4) # {"alias":["zhuzusong.com","1","www.baidu.com www.iciba.com"]} import os import time import subprocess import SocketServer import MySQLdb import simplejson as json class Add_User(SocketServer.StreamRequestHandler): def setup(self): self.connection = self.request self.rfile = self.connection.makefile('rb', self.rbufsize) self.wfile = self.connection.makefile('wb', self.wbufsize) self.Error = [] self.Error_log = '/tmp/Add_User_%s.log' %(time.strftime('%Y%m%d')) self.apache_document_root = '/data/www' self.vhost_conf = '/etc/httpd/conf.d' self.vuser_list = '/etc/vsftpd/vsftpd_login.txt' self.vuser_conf = '/etc/vsftpd/vuser_conf' def add_mysql_account(self, mysql_db, mysql_user, mysql_passwd): try: conn=MySQLdb.connect(host='localhost',port=3306,user='root',passwd='123ewq') cursor = conn.cursor() rownumber = cursor.execute('select User from mysql.user where User="%s"' %mysql_user) # make sure the mysql login username is unique ! assert cursor.rowcount == 0, 'mysql account %s is exist' %mysql_user cursor.execute('create database %s' %mysql_db) cursor.execute('grant all privileges on %s.* to "%s"@"%%" identified by "%s"' \ %(mysql_db, mysql_user, mysql_passwd)) cursor.close() conn.close() except Exception, error: self.Error.append("Function(add_mysql_account) Error : %s" %error) def del_mysql_account(self, mysql_db, mysql_user): try: conn=MySQLdb.connect(host='localhost',port=3306,user='root',passwd='123ewq') cursor = conn.cursor() cursor.execute('drop database %s' %mysql_db) cursor.execute('DELETE FROM mysql.user WHERE USER="%s" AND HOST="%%"' %mysql_user) cursor.execute('DELETE FROM mysql.db WHERE USER="%s" AND db="%s"' %(mysql_user, mysql_db)) cursor.execute('flush privileges') cursor.close() conn.close() except Exception, error: self.Error.append("Function(del_mysql_account) Error : %s" %error) def add_apache_vhost(self, website): apache_document_root = self.apache_document_root vhost_conf = self.vhost_conf vhost_conf_template = '''<VirtualHost *:80> ServerName %s DocumentRoot %s/%s ServerAlias %s DirectoryIndex default.htm default.html default.php index.htm index.html index.php php_admin_value open_basedir "%s/%s:/tmp" <IfModule bw_mod.c> BandWidthModule On BandWidth all 4194304 MaxConnection all 500 </IfModule> <Directory %s/%s> AllowOverride All Options +Includes </Directory> </VirtualHost>''' %(website, apache_document_root, website, website, apache_document_root, website, apache_document_root, website) if os.path.isfile('%s/%s' %(vhost_conf, website)): self.Error.append("vhost %s is exist" %website) else: try: fd_vhost = open('%s/%s' %(vhost_conf, website), 'w') fd_vhost.writelines(vhost_conf_template) fd_vhost.close() os.system('service httpd reload > /dev/null') except Exception, error: self.Error.append("Function(add_apache_vhost) Error : %s" %error) def del_apache_vhost(self, website): try: vhost_conf = self.vhost_conf os.remove('%s/%s' %(vhost_conf, website)) except OSError,error: self.Error.append("Function(del_apache_vhost) Error:" %error) def add_ftp_account(self, website, ftp_user, ftp_passwd): vuser_list = self.vuser_list vuser_conf = '%s/%s' %(self.vuser_conf, ftp_user) apache_document_root = self.apache_document_root vuser_conf_template = '''guest_enable=YES guest_username=vuser local_root=%s/%s write_enable=yes anon_world_readable_only=YES anon_upload_enable=YES anon_mkdir_write_enable=YES anon_other_write_enable=YES''' %(apache_document_root, website) if os.path.isfile(vuser_conf): self.Error.append("FTP account %s is exist" %ftp_user) else: try: fd1 = open(vuser_conf,'w') fd1.writelines(vuser_conf_template) os.system('mkdir -p %s/%s' %(apache_document_root, website)) os.system('chmod 570 %s/%s' %(apache_document_root, website)) os.system('chown apache:vuser %s/%s' %(apache_document_root, website)) fd1.flush() fd1.close() fd2 = open(vuser_list, 'a') fd2.write(ftp_user + '\n') fd2.write(ftp_passwd + '\n') fd2.flush() fd2.close() cmd = '/usr/bin/db_load -T -t hash -f %s "/etc/vsftpd/vsftpd_login.db"' %(vuser_list) status = subprocess.Popen(cmd, shell=True,stderr = subprocess.PIPE) except Exception,error: self.Error.append("Function(add_ftp_account) Error : %s" %error) def del_ftp_account(self, ftp_user, ftp_passwd): vuser_list = self.vuser_list vuser_conf = '%s/%s' %(self.vuser_conf, ftp_user) os.remove(vuser_conf) os.system("/bin/sed -i 'N;/%s\n%s/d' %s" %(ftp_user, ftp_passwd, vuser_list)) def enable_website(self, website): vhost_conf = self.vhost_conf cmd = 'mv %s/../disabled_website/%s %s/' %(vhost_conf, website, vhost_conf) os.system(cmd) os.system('service httpd reload > /dev/null') def disable_website(self, website): vhost_conf = self.vhost_conf cmd = 'mv %s/%s %s/../disabled_website/' %(vhost_conf, website, vhost_conf) os.system(cmd) os.system('service httpd reload > /dev/null') def enable_ftp(self,ftp_user): cmd = 'mv %s/../vuser_disable/%s %s' %(self.vuser_conf, ftp_user, self.vuser_conf) os.system(cmd) def disable_ftp(self,ftp_user): vuser_conf = '%s/%s' %(self.vuser_conf, ftp_user) cmd = 'mv %s %s/../vuser_disable/' %(vuser_conf, self.vuser_conf) os.system(cmd) def enable_mysql(self, mysql_db, mysql_user): conn=MySQLdb.connect(host='localhost',port=3306,user='root',passwd='123ewq') cursor = conn.cursor() sql1 = 'update mysql.user set host="%%" where user="%s"' %(mysql_user) sql2 = 'update mysql.db set host="%%" where user="%s" and db="%s"' %(mysql_user, mysql_db) sql3 = 'flush privileges' ret = cursor.execute(sql1) ret = cursor.execute(sql2) ret = cursor.execute(sql3) cursor.close() conn.close() def disable_mysql(self, mysql_db, mysql_user): conn=MySQLdb.connect(host='localhost',port=3306,user='root',passwd='123ewq') cursor = conn.cursor() sql1 = 'update mysql.user set host="localhost" where user="%s"' %(mysql_user) sql2 = 'update mysql.db set host="localhost" where user="%s" and db="%s"' %(mysql_user, mysql_db) sql3 = 'flush privileges' ret = cursor.execute(sql1) ret = cursor.execute(sql2) ret = cursor.execute(sql3) cursor.close() conn.close() def modify_ftp_passwd(self, ftp_user, old_passwd, new_passwd): check_passwd = 'no' vuser_list = self.vuser_list f = open(vuser_list) while True: f_ftp_user = f.readline().strip('\n') f_old_passwd = f.readline().strip('\n') if f_ftp_user != '' or f_old_passwd != '': if ftp_user == f_ftp_user: if old_passwd == f_old_passwd: check_passwd = 'yes' break else: self.Error.append("ftp password does not match: %s" %ftp_user) else: break f.close() if check_passwd == 'yes': cmd1 = "/bin/sed -i '/%s/{n;s/%s/%s/}' %s" %(f_ftp_user, f_old_passwd, new_passwd, vuser_list) cmd2 = '/usr/bin/db_load -T -t hash -f %s "/etc/vsftpd/vsftpd_login.db"' %(vuser_list) os.system(cmd1) os.system(cmd2) def modify_mysql_passwd(self, mysql_db, mysql_user, old_passwd, new_passwd): try: # verify mysql_user passwd conn=MySQLdb.connect(host='localhost',port=3306,user='root',passwd='123ewq') cursor = conn.cursor() sql1 = 'select password from mysql.user where user="%s"' %mysql_user sql2 = 'select password("%s")' %old_passwd cursor.execute(sql1) store_password = cursor.fetchall()[0][0] cursor.execute(sql2) old_passwd = cursor.fetchall()[0][0] if old_passwd == store_password: # verified ok then modify the passwd sql3 = 'update mysql.user set password=PASSWORD("%s") where user="%s"' %(new_passwd, mysql_user) sql4 = 'flush privileges' ret = cursor.execute(sql3) ret = cursor.execute(sql4) cursor.close() conn.close() else: self.Error.append("mysql password does not match: %s" %mysql_user) except Exception, error: self.Error.append("Function(modify_mysql_passwd) Error: %s" %error) def handle(self): self.data = self.rfile.readline().strip() if self.data: try: recv_data = json.loads(self.data) except Exception,error: self.Error.append("Json Error : %s" %error) if len(recv_data) == 3: # for add_function try: website = recv_data['website'] ftp_user = recv_data['ftp'][0] ftp_passwd = recv_data['ftp'][1] mysql_db = recv_data['mysql'][0] mysql_user = recv_data['mysql'][1] mysql_passwd = recv_data['mysql'][2] self.add_mysql_account(mysql_db, mysql_user, mysql_passwd) self.add_apache_vhost(website) self.add_ftp_account(website, ftp_user, ftp_passwd) except Exception,error: self.Error.append('handle(add) error: %s' %error) # when the three function add_* run error, then clean data if self.Error: n = 0 for e in self.Error: if e.find('add_mysql_account') > 0: n += 1 if n == 0: self.del_mysql_account(mysql_db, mysql_user) self.del_apache_vhost(website) self.del_ftp_account(ftp_user, ftp_passwd) else: self.del_apache_vhost(website) self.del_ftp_account(ftp_user, ftp_passwd) elif len(recv_data) == 2: # for modify ftp/mysql passwd try: ftp_user = recv_data['ftp'][0] ftp_old_passwd = recv_data['ftp'][1] ftp_new_passwd = recv_data['ftp'][2] mysql_db = recv_data['mysql'][0] mysql_user = recv_data['mysql'][1] mysql_old_passwd = recv_data['mysql'][2] mysql_new_passwd = recv_data['mysql'][3] if ftp_user != '': self.modify_ftp_passwd(ftp_user, ftp_old_passwd, ftp_new_passwd) if mysql_db != '': self.modify_mysql_passwd(mysql_db, mysql_user, mysql_old_passwd, mysql_new_passwd) except Exception,error: self.Error.append('handle(modify) error: %s' %error) elif len(recv_data) == 1: if recv_data.keys() == ['manage']: # for manage [website,ftp,mysql] [enable,disable] try: m_data = recv_data['manage'] website = m_data['website'][0] website_stats = m_data['website'][1] ftp_user = m_data['ftp'][0] ftp_stats = m_data['ftp'][1] mysql_user = m_data['mysql'][0] mysql_db = m_data['mysql'][1] mysql_stats = m_data['mysql'][2] if website_stats == 0: self.disable_website(website) elif website_stats == 1: self.enable_website(website) if ftp_stats == 0: self.disable_ftp(ftp_user) elif ftp_stats == 1: self.enable_ftp(ftp_user) if mysql_stats == 0: self.disable_mysql(mysql_db, mysql_user) elif mysql_stats == 1: self.enable_mysql(mysql_db, mysql_user) except Exception,error: self.Error.append('handle(manage) error: %s' %error) elif recv_data.keys() == ['service']: # for service [ftp/mysql/apache] [start/stop/restart] try: s_data = recv_data['service'] apache_status = s_data['apache'] ftp_status = s_data['ftp'] mysql_status = s_data['mysql'] if apache_status == 0: os.system('service httpd stop > /dev/null') elif apache_status == 1: os.system('service httpd start > /dev/null') elif apache_status == 2: os.system('service httpd restart > /dev/null') if ftp_status == 0: os.system('service vsftpd stop > /dev/null') elif ftp_status == 1: os.system('service vsftpd start > /dev/null') elif ftp_status == 2: os.system('service vsftpd restart > /dev/null') if mysql_status == 0: os.system('service mysqld stop > /dev/null') elif mysql_status == 1: os.system('service mysqld start > /dev/null') elif mysql_status == 2: os.system('service mysqld restart > /dev/null') except Exception,error: self.Error.append('handle(service) error: %s' %error) elif recv_data.keys() == ['alias']: # for add/delete/modify/query apache ServerAlias try: alias_data = recv_data['alias'] website = alias_data[0] signal = int(alias_data[1]) server_alias = alias_data[2] website_path = self.vhost_conf + '/' + website if os.path.isfile(website_path): if signal == 4: cmd = "/bin/egrep '#?ServerAlias' %s" %website_path p = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE) result = p.stdout.read() # return ServerAlias self.Error.append(' '.join(result.split()[1:])) else: cmd = "/bin/sed -i '/#\{0,1\}ServerAlias/c\ServerAlias %s' %s" %(server_alias, website_path) os.system(cmd) else: self.Error.append('handle(alias) error: no such website %s' %website) except Exception,error: self.Error.append('handle(alias) error: %s' %error) else: self.Error.append('Json data error') self.wfile.write(json.dumps(self.Error)) fd = open(self.Error_log,'a') fd.write('%s %s %s\n' %(time.strftime('%Y-%m-%d %H:%M:%S'), self.data, self.Error)) fd.close() if __name__ == '__main__': HOST, PORT = '', 4444 server = SocketServer.ThreadingTCPServer((HOST, PORT),Add_User) server.serve_forever()