mirror of
https://github.com/usmannasir/cyberpanel.git
synced 2025-11-07 22:06:05 +01:00
Replace Rainloop with SnappyMail
This change is a draft. I do not have the unzip method for tar.gz running where it was unzipping regular .zip
This commit is contained in:
@@ -9,7 +9,7 @@ Webhosting control panel that uses OpenLiteSpeed as web server.
|
||||
* FTP Server.
|
||||
* Light weight DNS Server (PowerDNS).
|
||||
* PHPMYAdmin.
|
||||
* Email Support (Rainloop).
|
||||
* Email Support (SnappyMail).
|
||||
* FileManager.
|
||||
* PHP Managment.
|
||||
* Firewall (FirewallD & ConfigServer Firewall Intregration).
|
||||
|
||||
52
README.md.bak
Normal file
52
README.md.bak
Normal file
@@ -0,0 +1,52 @@
|
||||
# CyberPanel
|
||||
|
||||
Webhosting control panel that uses OpenLiteSpeed as web server.
|
||||
|
||||
## Features
|
||||
|
||||
* Different Level Of users.
|
||||
* Auto SSL.
|
||||
* FTP Server.
|
||||
* Light weight DNS Server (PowerDNS).
|
||||
* PHPMYAdmin.
|
||||
* Email Support (Rainloop).
|
||||
* FileManager.
|
||||
* PHP Managment.
|
||||
* Firewall (FirewallD & ConfigServer Firewall Intregration).
|
||||
* One click Backup and Restore.
|
||||
|
||||
# Supported PHPs
|
||||
|
||||
* PHP 5.3
|
||||
* PHP 5.4
|
||||
* PHP 5.5
|
||||
* PHP 5.6
|
||||
* PHP 7.0
|
||||
* PHP 7.1
|
||||
* PHP 7.2
|
||||
* PHP 7.3
|
||||
* PHP 7.4
|
||||
* PHP 8.0
|
||||
|
||||
# Installation Instructions
|
||||
|
||||
|
||||
```
|
||||
sh <(curl https://cyberpanel.net/install.sh || wget -O - https://cyberpanel.net/install.sh)
|
||||
```
|
||||
|
||||
# Upgrading
|
||||
|
||||
|
||||
```
|
||||
sh <(curl https://raw.githubusercontent.com/usmannasir/cyberpanel/stable/preUpgrade.sh || wget -O - https://raw.githubusercontent.com/usmannasir/cyberpanel/stable/preUpgrade.sh)
|
||||
```
|
||||
|
||||
# Resources
|
||||
|
||||
* [Official Site.](https://cyberpanel.net)
|
||||
* [Documentation.](https://docs.cyberpanel.net)
|
||||
* [Forums.](https://forums.cyberpanel.net)
|
||||
* [Discord.](https://discord.gg/g8k8Db3)
|
||||
* [Facebook Group.](https://www.facebook.com/groups/cyberpanel)
|
||||
|
||||
@@ -584,7 +584,7 @@
|
||||
</li>
|
||||
{% endif %}
|
||||
{% if admin or createEmail %}
|
||||
<li><a href="/rainloop/index.php" title="{% trans 'Access Webmail' %}"
|
||||
<li><a href="/snappymail/index.php" title="{% trans 'Access Webmail' %}"
|
||||
target="_blank"><span>{% trans "Access Webmail" %}</span></a>
|
||||
</li>
|
||||
{% endif %}
|
||||
|
||||
1102
baseTemplate/templates/baseTemplate/index.html.bak
Normal file
1102
baseTemplate/templates/baseTemplate/index.html.bak
Normal file
File diff suppressed because it is too large
Load Diff
@@ -1282,7 +1282,7 @@ sed -i "s|https://www.litespeedtech.com/|https://cyberpanel.sh/www.litespeedtech
|
||||
sed -i 's|composer.sh|composer_cn.sh|g' install.py
|
||||
sed -i 's|./composer_cn.sh|COMPOSER_ALLOW_SUPERUSER=1 ./composer_cn.sh|g' install.py
|
||||
sed -i 's|http://www.litespeedtech.com|https://cyberpanel.sh/www.litespeedtech.com|g' install.py
|
||||
sed -i 's|https://www.rainloop.net/repository/webmail/rainloop-community-latest.zip|https://cyberpanel.sh/www.rainloop.net/repository/webmail/rainloop-community-latest.zip|g' install.py
|
||||
sed -i 's|https://snappymail.eu/repository/latest.tar.gz|https://cyberpanel.sh/www.snappymail.eu/repository/latest.tar.gz|g' install.py
|
||||
|
||||
sed -i "s|rep.cyberpanel.net|cyberpanel.sh/rep.cyberpanel.net|g" installCyberPanel.py
|
||||
sed -i "s|rep.cyberpanel.net|cyberpanel.sh/rep.cyberpanel.net|g" install.py
|
||||
@@ -1617,7 +1617,7 @@ fi
|
||||
}
|
||||
|
||||
Post_Install_Display_Final_Info() {
|
||||
RainloopAdminPass=$(grep SetPassword /usr/local/CyberCP/public/rainloop.php| sed -e 's|$oConfig->SetPassword(||g' -e "s|');||g" -e "s|'||g")
|
||||
snappymailAdminPass=$(grep SetPassword /usr/local/CyberCP/public/snappymail.php| sed -e 's|$oConfig->SetPassword(||g' -e "s|');||g" -e "s|'||g")
|
||||
Elapsed_Time="$((Time_Count / 3600)) hrs $(((SECONDS / 60) % 60)) min $((Time_Count % 60)) sec"
|
||||
echo "###################################################################"
|
||||
echo " CyberPanel Successfully Installed "
|
||||
@@ -1639,9 +1639,9 @@ fi
|
||||
#echo " WebAdmin console username: admin "
|
||||
#echo " WebAdmin console password: $Webadmin_Pass "
|
||||
#echo " "
|
||||
#echo " Visit: https://$Server_IP:8090/rainloop/?admin "
|
||||
#echo " Rainloop Admin username: admin "
|
||||
#echo " Rainloop Admin password: $RainloopAdminPass "
|
||||
#echo " Visit: https://$Server_IP:8090/snappymail/?admin "
|
||||
#echo " snappymail Admin username: admin "
|
||||
#echo " snappymail Admin password: $snappymailAdminPass "
|
||||
echo " "
|
||||
echo -e " Run \e[31mcyberpanel help\e[39m to get FAQ info"
|
||||
echo -e " Run \e[31mcyberpanel upgrade\e[39m to upgrade it to latest version."
|
||||
|
||||
1963
cyberpanel.sh.bak
Normal file
1963
cyberpanel.sh.bak
Normal file
File diff suppressed because it is too large
Load Diff
@@ -119,7 +119,7 @@ def recursive_permissions(path, dir_mode=755, file_mode=644, topdir=True):
|
||||
# Set recursive chown for a path
|
||||
# recursive_chown(my_path, 'root', 'root')
|
||||
# for changing group recursively without affecting user
|
||||
# recursive_chown('/usr/local/lscp/cyberpanel/rainloop/data', -1, 'lscpd')
|
||||
# recursive_chown('/usr/local/lscp/cyberpanel/snappymail/data', -1, 'lscpd')
|
||||
|
||||
# explicitly set permissions for directories/folders to 0755 and files to 0644
|
||||
# recursive_permissions(my_path, 755, 644)
|
||||
|
||||
190
install/filesPermsUtilities.py.bak
Normal file
190
install/filesPermsUtilities.py.bak
Normal file
@@ -0,0 +1,190 @@
|
||||
import os
|
||||
import shutil
|
||||
import pathlib
|
||||
import stat
|
||||
|
||||
|
||||
def mkdir_p(path, exist_ok=True):
|
||||
"""
|
||||
Creates the directory and paths leading up to it like unix mkdir -p .
|
||||
Defaults to exist_ok so if it exists were not throwing fatal errors
|
||||
https://docs.python.org/3.7/library/os.html#os.makedirs
|
||||
"""
|
||||
if not os.path.exists(path):
|
||||
print('creating directory: ' + path)
|
||||
os.makedirs(path, exist_ok)
|
||||
|
||||
|
||||
def chmod_digit(file_path, perms):
|
||||
"""
|
||||
Helper function to chmod like you would in unix without having to preface 0o or converting to octal yourself.
|
||||
Credits: https://stackoverflow.com/a/60052847/1621381
|
||||
"""
|
||||
try:
|
||||
os.chmod(file_path, int(str(perms), base=8))
|
||||
except:
|
||||
print(f'Could not chmod : {file_path} to {perms}')
|
||||
pass
|
||||
|
||||
|
||||
def touch(filepath: str, exist_ok=True):
|
||||
"""
|
||||
Touches a file like unix `touch somefile` would.
|
||||
"""
|
||||
try:
|
||||
pathlib.Path(filepath).touch(exist_ok)
|
||||
except FileExistsError:
|
||||
print('Could touch : ' + filepath)
|
||||
pass
|
||||
|
||||
|
||||
def symlink(src, dst):
|
||||
"""
|
||||
Symlink a path to another if the src exists.
|
||||
"""
|
||||
try:
|
||||
if os.access(src, os.R_OK):
|
||||
os.symlink(src, dst)
|
||||
except:
|
||||
print(f'Could not symlink Source: {src} > Destination: {dst}')
|
||||
pass
|
||||
|
||||
|
||||
def chown(path, user, group=-1):
|
||||
"""
|
||||
Chown file/path to user/group provided. Passing -1 to user or group will leave it unchanged.
|
||||
Useful if just changing user or group vs both.
|
||||
"""
|
||||
try:
|
||||
shutil.chown(path, user, group)
|
||||
except PermissionError:
|
||||
print(f'Could not change permissions for: {path} to {user}:{group}')
|
||||
pass
|
||||
|
||||
|
||||
def recursive_chown(path, owner, group=-1):
|
||||
"""
|
||||
Recursively chown a path and contents to owner.
|
||||
https://docs.python.org/3/library/shutil.html
|
||||
"""
|
||||
for dirpath, dirnames, filenames in os.walk(path):
|
||||
try:
|
||||
shutil.chown(dirpath, owner, group)
|
||||
except PermissionError:
|
||||
print('Could not change permissions for: ' + dirpath + ' to: ' + owner)
|
||||
pass
|
||||
for filename in filenames:
|
||||
try:
|
||||
shutil.chown(os.path.join(dirpath, filename), owner, group)
|
||||
except PermissionError:
|
||||
print('Could not change permissions for: ' + os.path.join(dirpath, filename) + ' to: ' + owner)
|
||||
pass
|
||||
|
||||
|
||||
def recursive_permissions(path, dir_mode=755, file_mode=644, topdir=True):
|
||||
"""
|
||||
Recursively chmod a path and contents to mode.
|
||||
Defaults to chmod top level directory but can be optionally
|
||||
toggled off when you want to chmod only contents of like a user's homedir vs homedir itself
|
||||
https://docs.python.org/3.6/library/os.html#os.walk
|
||||
"""
|
||||
|
||||
# Here we are converting the integers to string and then to octal.
|
||||
# so this function doesn't need to be called with 0o prefixed for the file and dir mode
|
||||
dir_mode = int(str(dir_mode), base=8)
|
||||
file_mode = int(str(file_mode), base=8)
|
||||
|
||||
if topdir:
|
||||
# Set chmod on top level path
|
||||
try:
|
||||
os.chmod(path, dir_mode)
|
||||
except:
|
||||
print('Could not chmod :' + path + ' to ' + str(dir_mode))
|
||||
for root, dirs, files in os.walk(path):
|
||||
for d in dirs:
|
||||
try:
|
||||
os.chmod(os.path.join(root, d), dir_mode)
|
||||
except:
|
||||
print('Could not chmod :' + os.path.join(root, d) + ' to ' + str(dir_mode))
|
||||
pass
|
||||
for f in files:
|
||||
try:
|
||||
os.chmod(os.path.join(root, f), file_mode)
|
||||
except:
|
||||
print('Could not chmod :' + path + ' to ' + str(file_mode))
|
||||
pass
|
||||
|
||||
|
||||
# Left intentionally here for reference.
|
||||
# Set recursive chown for a path
|
||||
# recursive_chown(my_path, 'root', 'root')
|
||||
# for changing group recursively without affecting user
|
||||
# recursive_chown('/usr/local/lscp/cyberpanel/rainloop/data', -1, 'lscpd')
|
||||
|
||||
# explicitly set permissions for directories/folders to 0755 and files to 0644
|
||||
# recursive_permissions(my_path, 755, 644)
|
||||
|
||||
# Fix permissions and use default values
|
||||
# recursive_permissions(my_path)
|
||||
# =========================================================
|
||||
# Below is a helper class for getting and working with permissions
|
||||
# Original credits to : https://github.com/keysemble/perfm
|
||||
|
||||
def perm_octal_digit(rwx):
|
||||
digit = 0
|
||||
if rwx[0] == 'r':
|
||||
digit += 4
|
||||
if rwx[1] == 'w':
|
||||
digit += 2
|
||||
if rwx[2] == 'x':
|
||||
digit += 1
|
||||
return digit
|
||||
|
||||
|
||||
class FilePerm:
|
||||
def __init__(self, filepath):
|
||||
filemode = stat.filemode(os.stat(filepath).st_mode)
|
||||
permissions = [filemode[-9:][i:i + 3] for i in range(0, len(filemode[-9:]), 3)]
|
||||
self.filepath = filepath
|
||||
self.access_dict = dict(zip(['user', 'group', 'other'], [list(perm) for perm in permissions]))
|
||||
|
||||
def mode(self):
|
||||
mode = 0
|
||||
for shift, digit in enumerate(self.octal()[::-1]):
|
||||
mode += digit << (shift * 3)
|
||||
return mode
|
||||
|
||||
def digits(self):
|
||||
"""Get the octal chmod equivalent value 755 in single string"""
|
||||
return "".join(map(str, self.octal()))
|
||||
|
||||
def octal(self):
|
||||
"""Get the octal value in a list [7, 5, 5]"""
|
||||
return [perm_octal_digit(p) for p in self.access_dict.values()]
|
||||
|
||||
def access_bits(self, access):
|
||||
if access in self.access_dict.keys():
|
||||
r, w, x = self.access_dict[access]
|
||||
return [r == 'r', w == 'w', x == 'x']
|
||||
|
||||
def update_bitwise(self, settings):
|
||||
def perm_list(read=False, write=False, execute=False):
|
||||
pl = ['-', '-', '-']
|
||||
if read:
|
||||
pl[0] = 'r'
|
||||
if write:
|
||||
pl[1] = 'w'
|
||||
if execute:
|
||||
pl[2] = 'x'
|
||||
return pl
|
||||
|
||||
self.access_dict = dict(
|
||||
[(access, perm_list(read=r, write=w, execute=x)) for access, [r, w, x] in settings.items()])
|
||||
os.chmod(self.filepath, self.mode())
|
||||
|
||||
# project_directory = os.path.abspath(os.path.dirname(sys.argv[0]))
|
||||
# home_directory = os.path.expanduser('~')
|
||||
# print(f'Path: {home_directory} Mode: {FilePerm(home_directory).mode()} Octal: {FilePerm(home_directory).octal()} '
|
||||
# f'Digits: {FilePerm(home_directory).digits()}')
|
||||
# Example: Output
|
||||
# Path: /home/cooluser Mode: 493 Octal: [7, 5, 5] Digits: 755
|
||||
@@ -546,7 +546,7 @@ password="%s"
|
||||
command = "chown -R root:root /usr/local/lscp"
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 0, os.EX_OSERR)
|
||||
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 0, os.EX_OSERR)
|
||||
|
||||
command = "chmod 700 /usr/local/CyberCP/cli/cyberPanel.py"
|
||||
@@ -648,11 +648,11 @@ password="%s"
|
||||
command = 'chmod 640 /usr/local/lscp/cyberpanel/logs/access.log'
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 0, os.EX_OSERR)
|
||||
|
||||
command = 'mkdir -p/usr/local/lscp/cyberpanel/rainloop/data/_data_/_default_/configs/'
|
||||
command = 'mkdir -p/usr/local/lscp/cyberpanel/snappymail/data/_data_/_default_/configs/'
|
||||
|
||||
rainloopinipath = '/usr/local/lscp/cyberpanel/rainloop/data/_data_/_default_/configs/application.ini'
|
||||
snappymailinipath = '/usr/local/lscp/cyberpanel/snappymail/data/_data_/_default_/configs/application.ini'
|
||||
|
||||
command = 'chmod 600 /usr/local/CyberCP/public/rainloop.php'
|
||||
command = 'chmod 600 /usr/local/CyberCP/public/snappymail.php'
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 0, os.EX_OSERR)
|
||||
|
||||
###
|
||||
@@ -1236,24 +1236,24 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
if not os.path.exists("/usr/local/CyberCP/public"):
|
||||
os.mkdir("/usr/local/CyberCP/public")
|
||||
|
||||
if os.path.exists("/usr/local/CyberCP/public/rainloop"):
|
||||
if os.path.exists("/usr/local/CyberCP/public/snappymail"):
|
||||
return 0
|
||||
|
||||
os.chdir("/usr/local/CyberCP/public")
|
||||
|
||||
command = 'wget https://www.rainloop.net/repository/webmail/rainloop-community-latest.zip'
|
||||
command = 'wget https://snappymail.eu/repository/latest.tar.gz'
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 1, os.EX_OSERR)
|
||||
|
||||
#############
|
||||
|
||||
command = 'unzip rainloop-community-latest.zip -d /usr/local/CyberCP/public/rainloop'
|
||||
command = 'unzip latest.tar.gz -d /usr/local/CyberCP/public/snappymail'
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 1, os.EX_OSERR)
|
||||
|
||||
os.remove("rainloop-community-latest.zip")
|
||||
os.remove("latest.tar.gz")
|
||||
|
||||
#######
|
||||
|
||||
os.chdir("/usr/local/CyberCP/public/rainloop")
|
||||
os.chdir("/usr/local/CyberCP/public/snappymail")
|
||||
|
||||
command = 'find . -type d -exec chmod 755 {} \;'
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 0, os.EX_OSERR)
|
||||
@@ -1265,15 +1265,15 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
|
||||
######
|
||||
|
||||
command = "mkdir -p /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "mkdir -p /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 0, os.EX_OSERR)
|
||||
|
||||
### Enable sub-folders
|
||||
|
||||
command = "mkdir -p /usr/local/lscp/cyberpanel/rainloop/data/_data_/_default_/configs/"
|
||||
command = "mkdir -p /usr/local/lscp/cyberpanel/snappymail/data/_data_/_default_/configs/"
|
||||
preFlightsChecks.call(command, self.distro, command, command, 1, 0, os.EX_OSERR)
|
||||
|
||||
labsPath = '/usr/local/lscp/cyberpanel/rainloop/data/_data_/_default_/configs/application.ini'
|
||||
labsPath = '/usr/local/lscp/cyberpanel/snappymail/data/_data_/_default_/configs/application.ini'
|
||||
|
||||
labsData = """[labs]
|
||||
imap_folder_list_limit = 0
|
||||
@@ -1283,9 +1283,9 @@ imap_folder_list_limit = 0
|
||||
writeToFile.write(labsData)
|
||||
writeToFile.close()
|
||||
|
||||
iPath = os.listdir('/usr/local/CyberCP/public/rainloop/rainloop/v/')
|
||||
iPath = os.listdir('/usr/local/CyberCP/public/snappymail/snappymail/v/')
|
||||
|
||||
path = "/usr/local/CyberCP/public/rainloop/rainloop/v/%s/include.php" % (iPath[0])
|
||||
path = "/usr/local/CyberCP/public/snappymail/snappymail/v/%s/include.php" % (iPath[0])
|
||||
|
||||
data = open(path, 'r').readlines()
|
||||
writeToFile = open(path, 'w')
|
||||
@@ -1293,14 +1293,14 @@ imap_folder_list_limit = 0
|
||||
for items in data:
|
||||
if items.find("$sCustomDataPath = '';") > -1:
|
||||
writeToFile.writelines(
|
||||
" $sCustomDataPath = '/usr/local/lscp/cyberpanel/rainloop/data';\n")
|
||||
" $sCustomDataPath = '/usr/local/lscp/cyberpanel/snappymail/data';\n")
|
||||
else:
|
||||
writeToFile.writelines(items)
|
||||
|
||||
writeToFile.close()
|
||||
|
||||
except BaseException as msg:
|
||||
logging.InstallLog.writeToFile('[ERROR] ' + str(msg) + " [downoad_and_install_rainloop]")
|
||||
logging.InstallLog.writeToFile('[ERROR] ' + str(msg) + " [downoad_and_install_snappymail]")
|
||||
return 0
|
||||
|
||||
return 1
|
||||
@@ -2337,10 +2337,10 @@ def main():
|
||||
# checks.disablePackegeUpdates()
|
||||
|
||||
try:
|
||||
# command = 'mkdir -p /usr/local/lscp/cyberpanel/rainloop/data/data/default/configs/'
|
||||
# command = 'mkdir -p /usr/local/lscp/cyberpanel/snappymail/data/data/default/configs/'
|
||||
# subprocess.call(shlex.split(command))
|
||||
|
||||
writeToFile = open('/usr/local/lscp/cyberpanel/rainloop/data/_data_/_default_/configs/application.ini', 'a')
|
||||
writeToFile = open('/usr/local/lscp/cyberpanel/snappymail/data/_data_/_default_/configs/application.ini', 'a')
|
||||
|
||||
writeToFile.write("""
|
||||
[security]
|
||||
@@ -2353,23 +2353,23 @@ admin_password = "12345"
|
||||
|
||||
content = """<?php
|
||||
|
||||
$_ENV['RAINLOOP_INCLUDE_AS_API'] = true;
|
||||
include '/usr/local/CyberCP/public/rainloop/index.php';
|
||||
$_ENV['snappymail_INCLUDE_AS_API'] = true;
|
||||
include '/usr/local/CyberCP/public/snappymail/index.php';
|
||||
|
||||
$oConfig = \RainLoop\Api::Config();
|
||||
$oConfig = \snappymail\Api::Config();
|
||||
$oConfig->SetPassword('%s');
|
||||
echo $oConfig->Save() ? 'Done' : 'Error';
|
||||
|
||||
?>""" % (randomPassword.generate_pass())
|
||||
|
||||
writeToFile = open('/usr/local/CyberCP/public/rainloop.php', 'w')
|
||||
writeToFile = open('/usr/local/CyberCP/public/snappymail.php', 'w')
|
||||
writeToFile.write(content)
|
||||
writeToFile.close()
|
||||
|
||||
command = '/usr/local/lsws/lsphp72/bin/php /usr/local/CyberCP/public/rainloop.php'
|
||||
command = '/usr/local/lsws/lsphp72/bin/php /usr/local/CyberCP/public/snappymail.php'
|
||||
subprocess.call(shlex.split(command))
|
||||
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
subprocess.call(shlex.split(command))
|
||||
except:
|
||||
pass
|
||||
|
||||
2383
install/install.py.bak
Normal file
2383
install/install.py.bak
Normal file
File diff suppressed because it is too large
Load Diff
@@ -86,7 +86,7 @@ if [[ $SERVER_COUNTRY == "CN" ]] ; then
|
||||
#sed -i "${line2}i\ \ \ \ \ \ \ \ command = 'wget cyberpanel.sh/cyberpanel-git.tar.gz'" install.py
|
||||
sed -i 's|wget https://rpms.litespeedtech.com/debian/|wget --no-check-certificate https://rpms.litespeedtech.com/debian/|g' install.py
|
||||
sed -i 's|https://repo.powerdns.com/repo-files/centos-auth-42.repo|https://'$DOWNLOAD_SERVER'/powerdns/powerdns.repo|g' installCyberPanel.py
|
||||
sed -i 's|https://www.rainloop.net/repository/webmail/rainloop-community-latest.zip|https://'$DOWNLOAD_SERVER'/misc/rainloop-community-latest.zip|g' install.py
|
||||
sed -i 's|https://snappymail.eu/repository/latest.tar.gz|https://'$DOWNLOAD_SERVER'/repository/latest.tar.gz|g' install.py
|
||||
|
||||
sed -i 's|rpm -ivh https://rpms.litespeedtech.com/centos/litespeed-repo-1.1-1.el7.noarch.rpm|curl -o /etc/yum.repos.d/litespeed.repo https://'$DOWNLOAD_SERVER'/litespeed/litespeed.repo|g' install.py
|
||||
|
||||
|
||||
1290
install/venvsetup.sh.bak
Normal file
1290
install/venvsetup.sh.bak
Normal file
File diff suppressed because it is too large
Load Diff
@@ -1475,7 +1475,7 @@ milter_default_action = accept
|
||||
command = "chown -R root:root /usr/local/lscp"
|
||||
ProcessUtilities.executioner(command)
|
||||
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
ProcessUtilities.executioner(command)
|
||||
|
||||
command = "chmod 700 /usr/local/CyberCP/cli/cyberPanel.py"
|
||||
|
||||
1713
mailServer/mailserverManager.py.bak
Normal file
1713
mailServer/mailserverManager.py.bak
Normal file
File diff suppressed because it is too large
Load Diff
@@ -96,7 +96,7 @@
|
||||
</div>
|
||||
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="/rainloop/index.php" title="{% trans 'Access Webmail' %}"
|
||||
<a href="/snappymail/index.php" title="{% trans 'Access Webmail' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "Access Webmail" %}
|
||||
|
||||
121
mailServer/templates/mailServer/index.html.bak
Normal file
121
mailServer/templates/mailServer/index.html.bak
Normal file
@@ -0,0 +1,121 @@
|
||||
{% extends "baseTemplate/index.html" %}
|
||||
{% load i18n %}
|
||||
{% block title %}{% trans "Mail Functions - CyberPanel" %}{% endblock %}
|
||||
{% block content %}
|
||||
|
||||
{% load static %}
|
||||
{% get_current_language as LANGUAGE_CODE %}
|
||||
<!-- Current language: {{ LANGUAGE_CODE }} -->
|
||||
|
||||
<div class="container">
|
||||
<div id="page-title">
|
||||
<h2>{% trans "Mail Functions" %}</h2>
|
||||
<p>{% trans "Manage email accounts on this page." %}</p>
|
||||
</div>
|
||||
|
||||
<div class="panel col-md-12">
|
||||
<div class="panel-body">
|
||||
<h3 class="content-box-header">
|
||||
{% trans "Available Functions" %}
|
||||
</h3>
|
||||
|
||||
<div class="example-box-wrapper">
|
||||
<div class="row">
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="{% url 'createEmailAccount' %}" title="{% trans 'Create Email' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "Create Email" %}
|
||||
</div>
|
||||
<div class="tile-content-wrapper">
|
||||
<i class="fa fa-plus-square"></i>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="{% url 'listEmails' %}" title="{% trans 'List Emails' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "List Emails" %}
|
||||
</div>
|
||||
<div class="tile-content-wrapper">
|
||||
<i class="fa fa-plus-square"></i>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="{% url 'deleteEmailAccount' %}" title="{% trans 'Delete Email' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "Delete Email" %}
|
||||
</div>
|
||||
<div class="tile-content-wrapper">
|
||||
<i class="fa fa-trash"></i>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="{% url 'emailForwarding' %}" title="{% trans 'Email Forwarding' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "Email Forwarding" %}
|
||||
</div>
|
||||
<div class="tile-content-wrapper">
|
||||
<i class="fa fa-plus-square"></i>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="{% url 'changeEmailAccountPassword' %}" title="{% trans 'Change Password' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "Change Password" %}
|
||||
</div>
|
||||
<div class="tile-content-wrapper">
|
||||
<i class="fa fa-key"></i>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="{% url 'dkimManager' %}" title="{% trans 'DKIM Manager' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "DKIM Manager" %}
|
||||
</div>
|
||||
<div class="tile-content-wrapper">
|
||||
<i class="fa fa-key"></i>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div class="col-md-3 btn-min-width">
|
||||
<a href="/snappymail/index.php" title="{% trans 'Access Webmail' %}"
|
||||
class="tile-box tile-box-shortcut btn-primary">
|
||||
<div class="tile-header">
|
||||
{% trans "Access Webmail" %}
|
||||
</div>
|
||||
<div class="tile-content-wrapper">
|
||||
<i class="fa fa-key"></i>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
{% endblock %}
|
||||
BIN
phpmyadmin.zip
BIN
phpmyadmin.zip
Binary file not shown.
@@ -119,7 +119,7 @@ def recursive_permissions(path, dir_mode=755, file_mode=644, topdir=True):
|
||||
# Set recursive chown for a path
|
||||
# recursive_chown(my_path, 'root', 'root')
|
||||
# for changing group recursively without affecting user
|
||||
# recursive_chown('/usr/local/lscp/cyberpanel/rainloop/data', -1, 'lscpd')
|
||||
# recursive_chown('/usr/local/lscp/cyberpanel/snappymail/data', -1, 'lscpd')
|
||||
|
||||
# explicitly set permissions for directories/folders to 0755 and files to 0644
|
||||
# recursive_permissions(my_path, 755, 644)
|
||||
|
||||
190
plogical/filesPermsUtilities.py.bak
Normal file
190
plogical/filesPermsUtilities.py.bak
Normal file
@@ -0,0 +1,190 @@
|
||||
import os
|
||||
import shutil
|
||||
import pathlib
|
||||
import stat
|
||||
|
||||
|
||||
def mkdir_p(path, exist_ok=True):
|
||||
"""
|
||||
Creates the directory and paths leading up to it like unix mkdir -p .
|
||||
Defaults to exist_ok so if it exists were not throwing fatal errors
|
||||
https://docs.python.org/3.7/library/os.html#os.makedirs
|
||||
"""
|
||||
if not os.path.exists(path):
|
||||
print('creating directory: ' + path)
|
||||
os.makedirs(path, exist_ok)
|
||||
|
||||
|
||||
def chmod_digit(file_path, perms):
|
||||
"""
|
||||
Helper function to chmod like you would in unix without having to preface 0o or converting to octal yourself.
|
||||
Credits: https://stackoverflow.com/a/60052847/1621381
|
||||
"""
|
||||
try:
|
||||
os.chmod(file_path, int(str(perms), base=8))
|
||||
except:
|
||||
print(f'Could not chmod : {file_path} to {perms}')
|
||||
pass
|
||||
|
||||
|
||||
def touch(filepath: str, exist_ok=True):
|
||||
"""
|
||||
Touches a file like unix `touch somefile` would.
|
||||
"""
|
||||
try:
|
||||
pathlib.Path(filepath).touch(exist_ok)
|
||||
except FileExistsError:
|
||||
print('Could touch : ' + filepath)
|
||||
pass
|
||||
|
||||
|
||||
def symlink(src, dst):
|
||||
"""
|
||||
Symlink a path to another if the src exists.
|
||||
"""
|
||||
try:
|
||||
if os.access(src, os.R_OK):
|
||||
os.symlink(src, dst)
|
||||
except:
|
||||
print(f'Could not symlink Source: {src} > Destination: {dst}')
|
||||
pass
|
||||
|
||||
|
||||
def chown(path, user, group=-1):
|
||||
"""
|
||||
Chown file/path to user/group provided. Passing -1 to user or group will leave it unchanged.
|
||||
Useful if just changing user or group vs both.
|
||||
"""
|
||||
try:
|
||||
shutil.chown(path, user, group)
|
||||
except PermissionError:
|
||||
print(f'Could not change permissions for: {path} to {user}:{group}')
|
||||
pass
|
||||
|
||||
|
||||
def recursive_chown(path, owner, group=-1):
|
||||
"""
|
||||
Recursively chown a path and contents to owner.
|
||||
https://docs.python.org/3/library/shutil.html
|
||||
"""
|
||||
for dirpath, dirnames, filenames in os.walk(path):
|
||||
try:
|
||||
shutil.chown(dirpath, owner, group)
|
||||
except PermissionError:
|
||||
print('Could not change permissions for: ' + dirpath + ' to: ' + owner)
|
||||
pass
|
||||
for filename in filenames:
|
||||
try:
|
||||
shutil.chown(os.path.join(dirpath, filename), owner, group)
|
||||
except PermissionError:
|
||||
print('Could not change permissions for: ' + os.path.join(dirpath, filename) + ' to: ' + owner)
|
||||
pass
|
||||
|
||||
|
||||
def recursive_permissions(path, dir_mode=755, file_mode=644, topdir=True):
|
||||
"""
|
||||
Recursively chmod a path and contents to mode.
|
||||
Defaults to chmod top level directory but can be optionally
|
||||
toggled off when you want to chmod only contents of like a user's homedir vs homedir itself
|
||||
https://docs.python.org/3.6/library/os.html#os.walk
|
||||
"""
|
||||
|
||||
# Here we are converting the integers to string and then to octal.
|
||||
# so this function doesn't need to be called with 0o prefixed for the file and dir mode
|
||||
dir_mode = int(str(dir_mode), base=8)
|
||||
file_mode = int(str(file_mode), base=8)
|
||||
|
||||
if topdir:
|
||||
# Set chmod on top level path
|
||||
try:
|
||||
os.chmod(path, dir_mode)
|
||||
except:
|
||||
print('Could not chmod :' + path + ' to ' + str(dir_mode))
|
||||
for root, dirs, files in os.walk(path):
|
||||
for d in dirs:
|
||||
try:
|
||||
os.chmod(os.path.join(root, d), dir_mode)
|
||||
except:
|
||||
print('Could not chmod :' + os.path.join(root, d) + ' to ' + str(dir_mode))
|
||||
pass
|
||||
for f in files:
|
||||
try:
|
||||
os.chmod(os.path.join(root, f), file_mode)
|
||||
except:
|
||||
print('Could not chmod :' + path + ' to ' + str(file_mode))
|
||||
pass
|
||||
|
||||
|
||||
# Left intentionally here for reference.
|
||||
# Set recursive chown for a path
|
||||
# recursive_chown(my_path, 'root', 'root')
|
||||
# for changing group recursively without affecting user
|
||||
# recursive_chown('/usr/local/lscp/cyberpanel/rainloop/data', -1, 'lscpd')
|
||||
|
||||
# explicitly set permissions for directories/folders to 0755 and files to 0644
|
||||
# recursive_permissions(my_path, 755, 644)
|
||||
|
||||
# Fix permissions and use default values
|
||||
# recursive_permissions(my_path)
|
||||
# =========================================================
|
||||
# Below is a helper class for getting and working with permissions
|
||||
# Original credits to : https://github.com/keysemble/perfm
|
||||
|
||||
def perm_octal_digit(rwx):
|
||||
digit = 0
|
||||
if rwx[0] == 'r':
|
||||
digit += 4
|
||||
if rwx[1] == 'w':
|
||||
digit += 2
|
||||
if rwx[2] == 'x':
|
||||
digit += 1
|
||||
return digit
|
||||
|
||||
|
||||
class FilePerm:
|
||||
def __init__(self, filepath):
|
||||
filemode = stat.filemode(os.stat(filepath).st_mode)
|
||||
permissions = [filemode[-9:][i:i + 3] for i in range(0, len(filemode[-9:]), 3)]
|
||||
self.filepath = filepath
|
||||
self.access_dict = dict(zip(['user', 'group', 'other'], [list(perm) for perm in permissions]))
|
||||
|
||||
def mode(self):
|
||||
mode = 0
|
||||
for shift, digit in enumerate(self.octal()[::-1]):
|
||||
mode += digit << (shift * 3)
|
||||
return mode
|
||||
|
||||
def digits(self):
|
||||
"""Get the octal chmod equivalent value 755 in single string"""
|
||||
return "".join(map(str, self.octal()))
|
||||
|
||||
def octal(self):
|
||||
"""Get the octal value in a list [7, 5, 5]"""
|
||||
return [perm_octal_digit(p) for p in self.access_dict.values()]
|
||||
|
||||
def access_bits(self, access):
|
||||
if access in self.access_dict.keys():
|
||||
r, w, x = self.access_dict[access]
|
||||
return [r == 'r', w == 'w', x == 'x']
|
||||
|
||||
def update_bitwise(self, settings):
|
||||
def perm_list(read=False, write=False, execute=False):
|
||||
pl = ['-', '-', '-']
|
||||
if read:
|
||||
pl[0] = 'r'
|
||||
if write:
|
||||
pl[1] = 'w'
|
||||
if execute:
|
||||
pl[2] = 'x'
|
||||
return pl
|
||||
|
||||
self.access_dict = dict(
|
||||
[(access, perm_list(read=r, write=w, execute=x)) for access, [r, w, x] in settings.items()])
|
||||
os.chmod(self.filepath, self.mode())
|
||||
|
||||
# project_directory = os.path.abspath(os.path.dirname(sys.argv[0]))
|
||||
# home_directory = os.path.expanduser('~')
|
||||
# print(f'Path: {home_directory} Mode: {FilePerm(home_directory).mode()} Octal: {FilePerm(home_directory).octal()} '
|
||||
# f'Digits: {FilePerm(home_directory).digits()}')
|
||||
# Example: Output
|
||||
# Path: /home/cooluser Mode: 493 Octal: [7, 5, 5] Digits: 755
|
||||
@@ -366,20 +366,20 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
try:
|
||||
#######
|
||||
|
||||
if os.path.exists("/usr/local/CyberCP/public/rainloop"):
|
||||
if os.path.exists("/usr/local/CyberCP/public/snappymail"):
|
||||
|
||||
if os.path.exists("/usr/local/lscp/cyberpanel/rainloop/data"):
|
||||
if os.path.exists("/usr/local/lscp/cyberpanel/snappymail/data"):
|
||||
pass
|
||||
else:
|
||||
command = "mv /usr/local/CyberCP/public/rainloop/data /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "mv /usr/local/CyberCP/public/snappymail/data /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
Upgrade.executioner(command, 0)
|
||||
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
Upgrade.executioner(command, 0)
|
||||
|
||||
iPath = os.listdir('/usr/local/CyberCP/public/rainloop/rainloop/v/')
|
||||
iPath = os.listdir('/usr/local/CyberCP/public/snappymail/snappymail/v/')
|
||||
|
||||
path = "/usr/local/CyberCP/public/rainloop/rainloop/v/%s/include.php" % (iPath[0])
|
||||
path = "/usr/local/CyberCP/public/snappymail/snappymail/v/%s/include.php" % (iPath[0])
|
||||
|
||||
data = open(path, 'r').readlines()
|
||||
writeToFile = open(path, 'w')
|
||||
@@ -387,7 +387,7 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
for items in data:
|
||||
if items.find("$sCustomDataPath = '';") > -1:
|
||||
writeToFile.writelines(
|
||||
" $sCustomDataPath = '/usr/local/lscp/cyberpanel/rainloop/data';\n")
|
||||
" $sCustomDataPath = '/usr/local/lscp/cyberpanel/snappymail/data';\n")
|
||||
else:
|
||||
writeToFile.writelines(items)
|
||||
|
||||
@@ -404,7 +404,7 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
count = 1
|
||||
|
||||
while (1):
|
||||
command = 'wget https://www.rainloop.net/repository/webmail/rainloop-community-latest.zip'
|
||||
command = 'wget https://www.snappymail.net/repository/webmail/snappymail-community-latest.zip'
|
||||
cmd = shlex.split(command)
|
||||
res = subprocess.call(cmd)
|
||||
if res != 0:
|
||||
@@ -419,7 +419,7 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
count = 0
|
||||
|
||||
while (1):
|
||||
command = 'unzip rainloop-community-latest.zip -d /usr/local/CyberCP/public/rainloop'
|
||||
command = 'unzip snappymail-community-latest.zip -d /usr/local/CyberCP/public/snappymail'
|
||||
|
||||
cmd = shlex.split(command)
|
||||
res = subprocess.call(cmd)
|
||||
@@ -430,11 +430,11 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
else:
|
||||
break
|
||||
|
||||
os.remove("rainloop-community-latest.zip")
|
||||
os.remove("snappymail-community-latest.zip")
|
||||
|
||||
#######
|
||||
|
||||
os.chdir("/usr/local/CyberCP/public/rainloop")
|
||||
os.chdir("/usr/local/CyberCP/public/snappymail")
|
||||
|
||||
count = 0
|
||||
|
||||
@@ -465,9 +465,9 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
break
|
||||
######
|
||||
|
||||
iPath = os.listdir('/usr/local/CyberCP/public/rainloop/rainloop/v/')
|
||||
iPath = os.listdir('/usr/local/CyberCP/public/snappymail/snappymail/v/')
|
||||
|
||||
path = "/usr/local/CyberCP/public/rainloop/rainloop/v/%s/include.php" % (iPath[0])
|
||||
path = "/usr/local/CyberCP/public/snappymail/snappymail/v/%s/include.php" % (iPath[0])
|
||||
|
||||
data = open(path, 'r').readlines()
|
||||
writeToFile = open(path, 'w')
|
||||
@@ -475,16 +475,16 @@ $cfg['Servers'][$i]['LogoutURL'] = 'phpmyadminsignin.php?logout';
|
||||
for items in data:
|
||||
if items.find("$sCustomDataPath = '';") > -1:
|
||||
writeToFile.writelines(
|
||||
" $sCustomDataPath = '/usr/local/lscp/cyberpanel/rainloop/data';\n")
|
||||
" $sCustomDataPath = '/usr/local/lscp/cyberpanel/snappymail/data';\n")
|
||||
else:
|
||||
writeToFile.writelines(items)
|
||||
|
||||
writeToFile.close()
|
||||
|
||||
command = "mkdir -p /usr/local/lscp/cyberpanel/rainloop/data/_data_/_default_/configs/"
|
||||
Upgrade.executioner(command, 'mkdir rainloop configs', 0)
|
||||
command = "mkdir -p /usr/local/lscp/cyberpanel/snappymail/data/_data_/_default_/configs/"
|
||||
Upgrade.executioner(command, 'mkdir snappymail configs', 0)
|
||||
|
||||
labsPath = '/usr/local/lscp/cyberpanel/rainloop/data/_data_/_default_/configs/application.ini'
|
||||
labsPath = '/usr/local/lscp/cyberpanel/snappymail/data/_data_/_default_/configs/application.ini'
|
||||
|
||||
labsData = """[labs]
|
||||
imap_folder_list_limit = 0
|
||||
@@ -1906,20 +1906,20 @@ imap_folder_list_limit = 0
|
||||
return ''.join(random.choice(chars) for x in range(size))
|
||||
|
||||
content = """<?php
|
||||
$_ENV['RAINLOOP_INCLUDE_AS_API'] = true;
|
||||
include '/usr/local/CyberCP/public/rainloop/index.php';
|
||||
$_ENV['snappymail_INCLUDE_AS_API'] = true;
|
||||
include '/usr/local/CyberCP/public/snappymail/index.php';
|
||||
|
||||
$oConfig = \RainLoop\Api::Config();
|
||||
$oConfig = \snappymail\Api::Config();
|
||||
$oConfig->SetPassword('%s');
|
||||
echo $oConfig->Save() ? 'Done' : 'Error';
|
||||
|
||||
?>""" % (generate_pass())
|
||||
|
||||
writeToFile = open('/usr/local/CyberCP/public/rainloop.php', 'w')
|
||||
writeToFile = open('/usr/local/CyberCP/public/snappymail.php', 'w')
|
||||
writeToFile.write(content)
|
||||
writeToFile.close()
|
||||
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
subprocess.call(shlex.split(command))
|
||||
|
||||
except:
|
||||
@@ -1971,7 +1971,7 @@ echo $oConfig->Save() ? 'Done' : 'Error';
|
||||
command = "chown -R root:root /usr/local/lscp"
|
||||
Upgrade.executioner(command, 'chown core code', 0)
|
||||
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/rainloop/data"
|
||||
command = "chown -R lscpd:lscpd /usr/local/lscp/cyberpanel/snappymail/data"
|
||||
Upgrade.executioner(command, 'chown core code', 0)
|
||||
|
||||
command = "chmod 700 /usr/local/CyberCP/cli/cyberPanel.py"
|
||||
@@ -2079,10 +2079,10 @@ echo $oConfig->Save() ? 'Done' : 'Error';
|
||||
command = 'chmod 640 /usr/local/lscp/cyberpanel/logs/access.log'
|
||||
Upgrade.executioner(command, 0)
|
||||
|
||||
command = '/usr/local/lsws/lsphp72/bin/php /usr/local/CyberCP/public/rainloop.php'
|
||||
command = '/usr/local/lsws/lsphp72/bin/php /usr/local/CyberCP/public/snappymail.php'
|
||||
Upgrade.executioner(command, 0)
|
||||
|
||||
command = 'chmod 600 /usr/local/CyberCP/public/rainloop.php'
|
||||
command = 'chmod 600 /usr/local/CyberCP/public/snappymail.php'
|
||||
Upgrade.executioner(command, 0)
|
||||
|
||||
###
|
||||
|
||||
2696
plogical/upgrade.py.bak
Normal file
2696
plogical/upgrade.py.bak
Normal file
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user