From d6f9e1cf07503265fe076c34045c01c7682466e7 Mon Sep 17 00:00:00 2001 From: tbrehm <t.brehm@ispconfig.org> Date: Wed, 04 Jan 2012 06:07:14 -0500 Subject: [PATCH] Fixed: FS#1953 - SOAP method mail_user_update limits quota to about 2GB --- server/plugins-available/nginx_plugin.inc.php | 214 ++++++++++++++++++++++++++++++++--------------------- 1 files changed, 129 insertions(+), 85 deletions(-) diff --git a/server/plugins-available/nginx_plugin.inc.php b/server/plugins-available/nginx_plugin.inc.php index d45ee0c..f0c8925 100644 --- a/server/plugins-available/nginx_plugin.inc.php +++ b/server/plugins-available/nginx_plugin.inc.php @@ -168,7 +168,7 @@ $app->log("Creating CA-signed SSL Cert for: $domain",LOGLEVEL_DEBUG); if (filesize($crt_file)==0 || !file_exists($crt_file)) $app->log("CA-Certificate signing failed. openssl ca -out $crt_file -config ".$web_config['CA_path']."/openssl.cnf -passin pass:".$web_config['CA_pass']." -in $csr_file",LOGLEVEL_ERROR); }; - if (filesize($crt_file)==0 || !file_exists($crt_file)){ + if (@filesize($crt_file)==0 || !file_exists($crt_file)){ exec("openssl req -x509 -passin pass:$ssl_password -passout pass:$ssl_password -key $key_file -in $csr_file -out $crt_file -days $ssl_days -config $config_file "); $app->log("Creating self-signed SSL Cert for: $domain",LOGLEVEL_DEBUG); }; @@ -191,7 +191,7 @@ //* Save a SSL certificate to disk if($data["new"]["ssl_action"] == 'save') { $ssl_dir = $data["new"]["document_root"]."/ssl"; - $domain = $data["new"]["ssl_domain"]; + $domain = ($data["new"]["ssl_domain"] != '')?$data["new"]["ssl_domain"]:$data["new"]["domain"]; $csr_file = $ssl_dir.'/'.$domain.".csr"; $crt_file = $ssl_dir.'/'.$domain.".crt"; //$bundle_file = $ssl_dir.'/'.$domain.".bundle"; @@ -209,7 +209,7 @@ //* Delete a SSL certificate if($data['new']['ssl_action'] == 'del') { $ssl_dir = $data['new']['document_root'].'/ssl'; - $domain = $data['new']['ssl_domain']; + $domain = ($data["new"]["ssl_domain"] != '')?$data["new"]["ssl_domain"]:$data["new"]["domain"]; $csr_file = $ssl_dir.'/'.$domain.'.csr'; $crt_file = $ssl_dir.'/'.$domain.'.crt'; //$bundle_file = $ssl_dir.'/'.$domain.'.bundle'; @@ -229,7 +229,6 @@ $app->dbmaster->query("UPDATE web_domain SET ssl_action = '' WHERE domain = '".$data['new']['domain']."'"); $app->log('Deleting SSL Cert for: '.$domain,LOGLEVEL_DEBUG); } - } @@ -532,74 +531,89 @@ if($this->action == 'insert' || $data["new"]["system_user"] != $data["old"]["system_user"]) { // Chown and chmod the directories below the document root - $this->_exec('chown -R '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chown -R '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root']).'/web'); // The document root itself has to be owned by root in normal level and by the web owner in security level 20 if($web_config['security_level'] == 20) { - $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root']).'/web'); } else { - $this->_exec('chown root:root '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chown root:root '.escapeshellcmd($data['new']['document_root']).'/web'); } } - - - + //* If the security level is set to high - if($web_config['security_level'] == 20) { + if(($this->action == 'insert' && $data['new']['type'] == 'vhost') or ($web_config['set_folder_permissions_on_update'] == 'y' && $data['new']['type'] == 'vhost')) { + if($web_config['security_level'] == 20) { - $this->_exec('chmod 751 '.escapeshellcmd($data['new']['document_root'])); - $this->_exec('chmod 751 '.escapeshellcmd($data['new']['document_root']).'/*'); - $this->_exec('chmod 710 '.escapeshellcmd($data['new']['document_root'].'/web')); + $this->_exec('chmod 751 '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chmod 751 '.escapeshellcmd($data['new']['document_root']).'/*'); + $this->_exec('chmod 710 '.escapeshellcmd($data['new']['document_root'].'/web')); - // make tmp directory writable for nginx and the website users - $this->_exec('chmod 777 '.escapeshellcmd($data['new']['document_root'].'/tmp')); + // make tmp directory writable for nginx and the website users + $this->_exec('chmod 777 '.escapeshellcmd($data['new']['document_root'].'/tmp')); - // Set Log symlink to 755 to make the logs accessible by the FTP user - $this->_exec("chmod 755 ".escapeshellcmd($data["new"]["document_root"])."/log"); + // Set Log symlink to 755 to make the logs accessible by the FTP user + $this->_exec("chmod 755 ".escapeshellcmd($data["new"]["document_root"])."/log"); - $command = 'usermod'; - $command .= ' --groups sshusers'; - $command .= ' '.escapeshellcmd($data['new']['system_user']); - $this->_exec($command); + $command = 'usermod'; + $command .= ' --groups sshusers'; + $command .= ' '.escapeshellcmd($data['new']['system_user']); + $this->_exec($command); - //* if we have a chrooted nginx environment - if($nginx_chrooted) { - $this->_exec('chroot '.escapeshellcmd($web_config['website_basedir']).' '.$command); + //* if we have a chrooted nginx environment + if($nginx_chrooted) { + $this->_exec('chroot '.escapeshellcmd($web_config['website_basedir']).' '.$command); - //* add the nginx user to the client group in the chroot environment - $tmp_groupfile = $app->system->server_conf['group_datei']; - $app->system->server_conf['group_datei'] = $web_config['website_basedir'].'/etc/group'; - $app->system->add_user_to_group($groupname, escapeshellcmd($web_config['user'])); - $app->system->server_conf['group_datei'] = $tmp_groupfile; - unset($tmp_groupfile); - } + //* add the nginx user to the client group in the chroot environment + $tmp_groupfile = $app->system->server_conf['group_datei']; + $app->system->server_conf['group_datei'] = $web_config['website_basedir'].'/etc/group'; + $app->system->add_user_to_group($groupname, escapeshellcmd($web_config['user'])); + $app->system->server_conf['group_datei'] = $tmp_groupfile; + unset($tmp_groupfile); + } - //* add the nginx user to the client group - $app->system->add_user_to_group($groupname, escapeshellcmd($web_config['nginx_user'])); + //* add the nginx user to the client group + $app->system->add_user_to_group($groupname, escapeshellcmd($web_config['nginx_user'])); + + //* Chown all default directories + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/cgi-bin')); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/log')); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/ssl')); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/tmp')); + $this->_exec('chown -R '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/web')); - $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'])); + /* + * Workaround for jailkit: If jailkit is enabled for the site, the + * website root has to be owned by the root user and we have to chmod it to 755 then + */ - /* - * Workaround for jailkit: If jailkit is enabled for the site, the - * website root has to be owned by the root user and we have to chmod it to 755 then - */ + //* Check if there is a jailkit user for this site + $tmp = $app->db->queryOneRecord('SELECT count(shell_user_id) as number FROM shell_user WHERE parent_domain_id = '.$data['new']['domain_id']." AND chroot = 'jailkit'"); + if($tmp['number'] > 0) { + $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chown root:root '.escapeshellcmd($data['new']['document_root'])); + } + unset($tmp); - //* Check if there is a jailkit user for this site - $tmp = $app->db->queryOneRecord('SELECT count(shell_user_id) as number FROM shell_user WHERE parent_domain_id = '.$data['new']['domain_id']." AND chroot = 'jailkit'"); - if($tmp['number'] > 0) { + // If the security Level is set to medium + } else { + $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'].'/cgi-bin')); + $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'].'/log')); + $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'].'/ssl')); + $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'].'/web')); + + // make temp directory writable for nginx and the website users + $this->_exec('chmod 777 '.escapeshellcmd($data['new']['document_root'].'/tmp')); + $this->_exec('chown root:root '.escapeshellcmd($data['new']['document_root'])); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/cgi-bin')); + $this->_exec('chown root:root '.escapeshellcmd($data['new']['document_root'].'/log')); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/tmp')); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/ssl')); + $this->_exec('chown '.$username.':'.$groupname.' '.escapeshellcmd($data['new']['document_root'].'/web')); } - unset($tmp); - - // If the security Level is set to medium - } else { - - $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'])); - $this->_exec('chmod 755 '.escapeshellcmd($data['new']['document_root'].'/*')); - $this->_exec('chown root:root '.escapeshellcmd($data['new']['document_root'])); - - // make temp directory writable for nginx and the website users - $this->_exec('chmod 777 '.escapeshellcmd($data['new']['document_root'].'/tmp')); } // Change the ownership of the error log to the owner of the website @@ -828,7 +842,8 @@ $tpl->setVar('stats_auth_passwd_file', $data['new']['document_root']."/.htpasswd_stats"); // Create basic http auth for other directories - $tpl->setLoop('basic_auth_locations', $this->_create_web_folder_auth_configuration($data['new'])); + $basic_auth_locations = $this->_create_web_folder_auth_configuration($data['new']); + if(is_array($basic_auth_locations) && !empty($basic_auth_locations)) $tpl->setLoop('basic_auth_locations', $basic_auth_locations); $vhost_file = escapeshellcmd($web_config['nginx_vhost_conf_dir'].'/'.$data['new']['domain'].'.vhost'); //* Make a backup copy of vhost file @@ -881,6 +896,11 @@ unlink($vhost_symlink); $app->log('Removing symlink: '.$vhost_symlink.'->'.$vhost_file,LOGLEVEL_DEBUG); } + $vhost_symlink = escapeshellcmd($web_config['nginx_vhost_conf_enabled_dir'].'/'.$data['old']['domain'].'.vhost'); + if(is_link($vhost_symlink)) { + unlink($vhost_symlink); + $app->log('Removing symlink: '.$vhost_symlink.'->'.$vhost_file,LOGLEVEL_DEBUG); + } $vhost_file = escapeshellcmd($web_config['nginx_vhost_conf_dir'].'/'.$data['old']['domain'].'.vhost'); unlink($vhost_file); $app->log('Removing file: '.$vhost_file,LOGLEVEL_DEBUG); @@ -919,7 +939,13 @@ if($nginx_online_status_before_restart && !$nginx_online_status_after_restart) { $app->log('nginx did not restart after the configuration change for website '.$data['new']['domain'].' Reverting the configuration. Saved non-working config as '.$vhost_file.'.err',LOGLEVEL_WARN); copy($vhost_file,$vhost_file.'.err'); - copy($vhost_file.'~',$vhost_file); + if(is_file($vhost_file.'~')) { + //* Copy back the last backup file + copy($vhost_file.'~',$vhost_file); + } else { + //* There is no backup file, so we create a empty vhost file with a warning message inside + file_put_contents($vhost_file,"# nginx did not start after modifying this vhost file.\n# Please check file $vhost_file.err for syntax errors."); + } $app->services->restartService('httpd','restart'); } } else { @@ -950,9 +976,9 @@ //* Check if this is a chrooted setup if($web_config['website_basedir'] != '' && @is_file($web_config['website_basedir'].'/etc/passwd')) { - $apache_chrooted = true; + $nginx_chrooted = true; } else { - $apache_chrooted = false; + $nginx_chrooted = false; } if($data['old']['type'] != 'vhost' && $data['old']['parent_domain_id'] > 0) { @@ -967,26 +993,34 @@ } else { //* This is a website - // Deleting the vhost file, symlink and the data directory - $vhost_symlink = escapeshellcmd($web_config['nginx_vhost_conf_enabled_dir'].'/'.$data['old']['domain'].'.vhost'); - unlink($vhost_symlink); - $app->log('Removing symlink: '.$vhost_symlink.'->'.$vhost_file,LOGLEVEL_DEBUG); - + // Deleting the vhost file, symlink and the data directory $vhost_file = escapeshellcmd($web_config['nginx_vhost_conf_dir'].'/'.$data['old']['domain'].'.vhost'); + + $vhost_symlink = escapeshellcmd($web_config['nginx_vhost_conf_enabled_dir'].'/'.$data['old']['domain'].'.vhost'); + if(is_link($vhost_symlink)){ + unlink($vhost_symlink); + $app->log('Removing symlink: '.$vhost_symlink.'->'.$vhost_file,LOGLEVEL_DEBUG); + } + $vhost_symlink = escapeshellcmd($web_config['nginx_vhost_conf_enabled_dir'].'/900-'.$data['old']['domain'].'.vhost'); + if(is_link($vhost_symlink)){ + unlink($vhost_symlink); + $app->log('Removing symlink: '.$vhost_symlink.'->'.$vhost_file,LOGLEVEL_DEBUG); + } + $vhost_symlink = escapeshellcmd($web_config['nginx_vhost_conf_enabled_dir'].'/100-'.$data['old']['domain'].'.vhost'); + if(is_link($vhost_symlink)){ + unlink($vhost_symlink); + $app->log('Removing symlink: '.$vhost_symlink.'->'.$vhost_file,LOGLEVEL_DEBUG); + } + unlink($vhost_file); $app->log('Removing vhost file: '.$vhost_file,LOGLEVEL_DEBUG); - - // delete file for basic http authentication - $basic_auth_file = escapeshellcmd($web_config['nginx_vhost_conf_dir'].'/'.$data['old']['domain'].'.auth'); - unlink($basic_auth_file); - $app->log('Removing auth file: '.$basic_auth_file,LOGLEVEL_DEBUG); $docroot = escapeshellcmd($data['old']['document_root']); if($docroot != '' && !stristr($docroot,'..')) exec('rm -rf '.$docroot); - - //remove the php fastgi starter script if available + //remove the php fastgi starter script and PHP-FPM pool definition if available if ($data['old']['php'] == 'fast-cgi') { + $this->php_fpm_pool_delete($data,$web_config); $fastcgi_starter_path = str_replace('[system_user]',$data['old']['system_user'],$web_config['fastcgi_starter_path']); if (is_dir($fastcgi_starter_path)) { exec('rm -rf '.$fastcgi_starter_path); @@ -1035,16 +1069,14 @@ $command = 'userdel'; $command .= ' '.$data['old']['system_user']; exec($command); - if($apache_chrooted) $this->_exec('chroot '.escapeshellcmd($web_config['website_basedir']).' '.$command); + if($nginx_chrooted) $this->_exec('chroot '.escapeshellcmd($web_config['website_basedir']).' '.$command); //* Remove the awstats configuration file if($data['old']['stats_type'] == 'awstats') { $this->awstats_delete($data,$web_config); } - if($data['old']['php'] == 'fast-cgi') { - $this->php_fpm_pool_delete($data,$web_config); - } + $app->services->restartServiceDelayed('httpd','reload'); } } @@ -1098,7 +1130,7 @@ if(substr($folder['path'],0,1) == '/') $folder['path'] = substr($folder['path'],1); if(substr($folder['path'],-1) == '/') $folder['path'] = substr($folder['path'],0,-1); $folder_path = escapeshellcmd($website['document_root'].'/web/'.$folder['path']); - if(substr($folder_path,-1 != '/')) $folder_path .= '/'; + if(substr($folder_path,-1) != '/') $folder_path .= '/'; //* Check if the resulting path is inside the docroot if(stristr($folder_path,'..') || stristr($folder_path,'./') || stristr($folder_path,'\\')) { @@ -1107,15 +1139,22 @@ } //* Create the folder path, if it does not exist - if(!is_dir($folder_path)) exec('mkdir -p '.$folder_path); + if(!is_dir($folder_path)) { + exec('mkdir -p '.$folder_path); + chown($folder_path,$website['system_user']); + chgrp($folder_path,$website['system_group']); + } //* Create empty .htpasswd file, if it does not exist if(!is_file($folder_path.'.htpasswd')) { touch($folder_path.'.htpasswd'); chmod($folder_path.'.htpasswd',0755); + chown($folder_path.'.htpasswd',$website['system_user']); + chgrp($folder_path.'.htpasswd',$website['system_group']); $app->log('Created file'.$folder_path.'.htpasswd',LOGLEVEL_DEBUG); } + /* $auth_users = $app->db->queryAllRecords("SELECT * FROM web_folder_user WHERE active = 'y' AND web_folder_id = ".intval($folder_id)); $htpasswd_content = ''; if(is_array($auth_users) && !empty($auth_users)){ @@ -1126,9 +1165,9 @@ $htpasswd_content = trim($htpasswd_content); @file_put_contents($folder_path.'.htpasswd', $htpasswd_content); $app->log('Changed .htpasswd file: '.$folder_path.'.htpasswd',LOGLEVEL_DEBUG); + */ - /* - if($data['new']['username'] != $data['old']['username'] || $data['new']['active'] == 'n') { + if(($data['new']['username'] != $data['old']['username'] || $data['new']['active'] == 'n') && $data['old']['username'] != '') { $app->system->removeLine($folder_path.'.htpasswd',$data['old']['username'].':'); $app->log('Removed user: '.$data['old']['username'],LOGLEVEL_DEBUG); } @@ -1143,8 +1182,8 @@ $app->log('Added or updated user: '.$data['new']['username'],LOGLEVEL_DEBUG); } } - */ + // write basic auth configuration to vhost file because nginx does not support .htaccess $webdata['new'] = $webdata['old'] = $website; $this->update('web_domain_update', $webdata); } @@ -1155,7 +1194,7 @@ $folder_id = $data['old']['web_folder_id']; - $folder = $app->db->queryOneRecord("SELECT * FROM web_folder WHERE web_folder_id = ".intval($folder_id)); + $folder = $data['old']; $website = $app->db->queryOneRecord("SELECT * FROM web_domain WHERE domain_id = ".intval($folder['parent_domain_id'])); if(!is_array($folder) or !is_array($website)) { @@ -1167,7 +1206,7 @@ if(substr($folder['path'],0,1) == '/') $folder['path'] = substr($folder['path'],1); if(substr($folder['path'],-1) == '/') $folder['path'] = substr($folder['path'],0,-1); $folder_path = realpath($website['document_root'].'/web/'.$folder['path']); - if(substr($folder_path,-1 != '/')) $folder_path .= '/'; + if(substr($folder_path,-1) != '/') $folder_path .= '/'; //* Check if the resulting path is inside the docroot if(substr($folder_path,0,strlen($website['document_root'])) != $website['document_root']) { @@ -1181,6 +1220,7 @@ $app->log('Removed file '.$folder_path.'.htpasswd',LOGLEVEL_DEBUG); } + // write basic auth configuration to vhost file because nginx does not support .htaccess $webdata['new'] = $webdata['old'] = $website; $this->update('web_domain_update', $webdata); } @@ -1199,13 +1239,13 @@ //* Get the folder path. if(substr($data['old']['path'],0,1) == '/') $data['old']['path'] = substr($data['old']['path'],1); if(substr($data['old']['path'],-1) == '/') $data['old']['path'] = substr($data['old']['path'],0,-1); - $old_folder_path = escapeshellcmd($website['document_root'].'/web/'.$data['old']['path']); - if(substr($old_folder_path,-1 != '/')) $old_folder_path .= '/'; + $old_folder_path = realpath($website['document_root'].'/web/'.$data['old']['path']); + if(substr($old_folder_path,-1) != '/') $old_folder_path .= '/'; if(substr($data['new']['path'],0,1) == '/') $data['new']['path'] = substr($data['new']['path'],1); if(substr($data['new']['path'],-1) == '/') $data['new']['path'] = substr($data['new']['path'],0,-1); $new_folder_path = escapeshellcmd($website['document_root'].'/web/'.$data['new']['path']); - if(substr($new_folder_path,-1 != '/')) $new_folder_path .= '/'; + if(substr($new_folder_path,-1) != '/') $new_folder_path .= '/'; //* Check if the resulting path is inside the docroot if(stristr($new_folder_path,'..') || stristr($new_folder_path,'./') || stristr($new_folder_path,'\\')) { @@ -1236,11 +1276,12 @@ //* move .htpasswd file if(is_file($old_folder_path.'.htpasswd')) { rename($old_folder_path.'.htpasswd',$new_folder_path.'.htpasswd'); - $app->log('Moved file '.$new_folder_path.'.htpasswd',LOGLEVEL_DEBUG); + $app->log('Moved file '.$old_folder_path.'.htpasswd to '.$new_folder_path.'.htpasswd',LOGLEVEL_DEBUG); } } + // write basic auth configuration to vhost file because nginx does not support .htaccess $webdata['new'] = $webdata['old'] = $website; $this->update('web_domain_update', $webdata); } @@ -1295,6 +1336,9 @@ file_put_contents($awstats_conf_dir.'/awstats.'.$data['new']['domain'].'.conf',$content); $app->log('Created AWStats config file: '.$awstats_conf_dir.'/awstats.'.$data['new']['domain'].'.conf',LOGLEVEL_DEBUG); } + + if(is_file($data['new']['document_root']."/web/stats/index.html")) unlink($data['new']['document_root']."/web/stats/index.html"); + copy("/usr/local/ispconfig/server/conf/awstats_index.php.master",$data['new']['document_root']."/web/stats/index.php"); } //* Delete the awstats configuration file @@ -1413,7 +1457,7 @@ $pool_dir = escapeshellcmd($web_config['php_fpm_pool_dir']); if(substr($pool_dir,-1) != '/') $pool_dir .= '/'; - $pool_name = 'web'.$data['new']['domain_id']; + $pool_name = 'web'.$data['old']['domain_id']; if ( @is_file($pool_dir.$pool_name.'.conf') ) { unlink($pool_dir.$pool_name.'.conf'); -- Gitblit v1.9.1