From 1fa8f425b71db332a03ceef2d1e165083d0ba241 Mon Sep 17 00:00:00 2001 From: Falko Timme <ft@falkotimme.com> Date: Fri, 5 Dec 2014 23:50:34 +0100 Subject: [PATCH] - Directive snippets can now be made available to clients; clients can select an available directive snippet for a website - the appropriate snippet will then be written to the vhost configuration file. This is useful for example on nginx where clients have no access to the Options tab of a website. --- install/sql/incremental/upd_0079.sql | 2 + install/sql/ispconfig3.sql | 2 + .../classes/plugin_directive_snippets.inc.php | 72 +++++++++++++++++++ .../admin/form/directive_snippets.tform.php | 6 ++ .../admin/lib/lang/de_directive_snippets.lng | 1 + .../admin/lib/lang/en_directive_snippets.lng | 1 + .../templates/directive_snippets_edit.htm | 17 +++++ interface/web/sites/ajax_get_json.php | 11 +++ .../web/sites/form/web_vhost_domain.tform.php | 8 ++- .../lib/lang/de_web_directive_snippets.lng | 3 + .../lib/lang/en_web_directive_snippets.lng | 3 + .../templates/web_directive_snippets.htm | 14 ++++ .../sites/templates/web_vhost_domain_edit.htm | 23 +++++- interface/web/sites/web_vhost_domain_edit.php | 2 +- .../plugins-available/apache2_plugin.inc.php | 6 ++ server/plugins-available/nginx_plugin.inc.php | 11 ++- 16 files changed, 177 insertions(+), 5 deletions(-) create mode 100644 install/sql/incremental/upd_0079.sql create mode 100644 interface/lib/classes/plugin_directive_snippets.inc.php create mode 100644 interface/web/sites/lib/lang/de_web_directive_snippets.lng create mode 100644 interface/web/sites/lib/lang/en_web_directive_snippets.lng create mode 100644 interface/web/sites/templates/web_directive_snippets.htm diff --git a/install/sql/incremental/upd_0079.sql b/install/sql/incremental/upd_0079.sql new file mode 100644 index 0000000000..5dd0152753 --- /dev/null +++ b/install/sql/incremental/upd_0079.sql @@ -0,0 +1,2 @@ +ALTER TABLE `directive_snippets` ADD `customer_viewable` ENUM('n','y') NOT NULL DEFAULT 'n' AFTER `snippet`; +ALTER TABLE `web_domain` ADD `directive_snippets_id` int(11) unsigned NOT NULL default '0'; \ No newline at end of file diff --git a/install/sql/ispconfig3.sql b/install/sql/ispconfig3.sql index 3f65bfe32d..6af74fb984 100644 --- a/install/sql/ispconfig3.sql +++ b/install/sql/ispconfig3.sql @@ -429,6 +429,7 @@ CREATE TABLE IF NOT EXISTS `directive_snippets` ( `name` varchar(255) DEFAULT NULL, `type` varchar(255) DEFAULT NULL, `snippet` mediumtext, + `customer_viewable` ENUM('n','y') NOT NULL DEFAULT 'n', `active` enum('n','y') NOT NULL DEFAULT 'y', PRIMARY KEY (`directive_snippets_id`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ; @@ -1880,6 +1881,7 @@ CREATE TABLE `web_domain` ( `rewrite_rules` mediumtext, `added_date` date NOT NULL DEFAULT '0000-00-00', `added_by` varchar(255) DEFAULT NULL, + `directive_snippets_id` int(11) unsigned NOT NULL default '0', PRIMARY KEY (`domain_id`), UNIQUE KEY `serverdomain` ( `server_id` , `ip_address`, `domain` ) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ; diff --git a/interface/lib/classes/plugin_directive_snippets.inc.php b/interface/lib/classes/plugin_directive_snippets.inc.php new file mode 100644 index 0000000000..dbc7d4887d --- /dev/null +++ b/interface/lib/classes/plugin_directive_snippets.inc.php @@ -0,0 +1,72 @@ +<?php + + +class plugin_directive_snippets extends plugin_base +{ + var $module; + var $form; + var $tab; + var $record_id; + var $formdef; + var $options; + + public function onShow() + { + global $app; + + $listTpl = new tpl; + $listTpl->newTemplate('templates/web_directive_snippets.htm'); + + //* Loading language file + $lng_file = "lib/lang/".$_SESSION["s"]["language"]."_web_directive_snippets.lng"; + + include $lng_file; + $listTpl->setVar($wb); + + $message = ''; + $error = ''; + + $server_type = $app->getconf->get_server_config($this->form->dataRecord['server_id'], 'web'); + $server_type = $server_type['server_type']; + $records = $app->db->queryAllRecords("SELECT directive_snippets_id, name FROM directive_snippets WHERE customer_viewable = 'y' AND type = ? ORDER BY name ASC", $server_type); + + for ($i = 0, $c = count($records); $i < $c; $i++) + { + $records[$i]['is_selected'] = false; + + if ($this->form->dataRecord['directive_snippets_id'] === $records[$i]['directive_snippets_id']) + $records[$i]['is_selected'] = true; + } + + $listTpl->setLoop('records', $records); + + $list_name = 'directive_snippets_list'; + $_SESSION["s"]["list"][$list_name]["parent_id"] = $this->form->id; + $_SESSION["s"]["list"][$list_name]["parent_name"] = $app->tform->formDef["name"]; + $_SESSION["s"]["list"][$list_name]["parent_tab"] = $_SESSION["s"]["form"]["tab"]; + $_SESSION["s"]["list"][$list_name]["parent_script"] = $app->tform->formDef["action"]; + $_SESSION["s"]["form"]["return_to"] = $list_name; + + return $listTpl->grab(); + } + + public function onUpdate() + { + global $app, $conf; + + if (isset($this->form->dataRecord['directive_snippets_id']) && $this->form->oldDataRecord['directive_snippets_id'] !== $this->form->dataRecord['directive_snippets_id']) { + $app->db->query('UPDATE web_domain SET directive_snippets_id = ? WHERE domain_id = ?', $this->form->dataRecord['directive_snippets_id'], $this->form->id); + } + } + + public function onInsert() + { + global $app, $conf; + + if (isset($this->form->dataRecord['directive_snippets_id'])) { + $app->db->query('UPDATE web_domain SET directive_snippets_id = ? WHERE domain_id = ?', $this->form->dataRecord['directive_snippets_id'], $this->form->id); + } + } + +} +?> \ No newline at end of file diff --git a/interface/web/admin/form/directive_snippets.tform.php b/interface/web/admin/form/directive_snippets.tform.php index 2af05af6c3..8db725b95f 100644 --- a/interface/web/admin/form/directive_snippets.tform.php +++ b/interface/web/admin/form/directive_snippets.tform.php @@ -93,6 +93,12 @@ $form["tabs"]['directive_snippets'] = array ( 'maxlength' => '255', 'searchable' => 2 ), + 'customer_viewable' => array ( + 'datatype' => 'VARCHAR', + 'formtype' => 'CHECKBOX', + 'default' => 'n', + 'value' => array(0 => 'n', 1 => 'y') + ), 'active' => array ( 'datatype' => 'VARCHAR', 'formtype' => 'CHECKBOX', diff --git a/interface/web/admin/lib/lang/de_directive_snippets.lng b/interface/web/admin/lib/lang/de_directive_snippets.lng index 18ce2d51b2..83a6b3c5f7 100644 --- a/interface/web/admin/lib/lang/de_directive_snippets.lng +++ b/interface/web/admin/lib/lang/de_directive_snippets.lng @@ -7,4 +7,5 @@ $wb['active_txt'] = 'Aktiv'; $wb['directive_snippets_name_empty'] = 'Bitte geben Sie einen Namen für den Schnipsel an.'; $wb['directive_snippets_name_error_unique'] = 'Es existiert schon ein Direktiven-Schnipsel mit diesem Namen.'; $wb['variables_txt'] = 'Variablen'; +$wb['customer_viewable_txt'] = 'Sichtbar für Kunden'; ?> diff --git a/interface/web/admin/lib/lang/en_directive_snippets.lng b/interface/web/admin/lib/lang/en_directive_snippets.lng index 9d9b0ae8ee..e8733cd948 100644 --- a/interface/web/admin/lib/lang/en_directive_snippets.lng +++ b/interface/web/admin/lib/lang/en_directive_snippets.lng @@ -7,4 +7,5 @@ $wb["active_txt"] = 'Active'; $wb["directive_snippets_name_empty"] = 'Please specify a name for the snippet.'; $wb["directive_snippets_name_error_unique"] = 'There is already a directive snippet with this name.'; $wb['variables_txt'] = 'Variables'; +$wb['customer_viewable_txt'] = 'Customer viewable'; ?> \ No newline at end of file diff --git a/interface/web/admin/templates/directive_snippets_edit.htm b/interface/web/admin/templates/directive_snippets_edit.htm index 7a17cb679e..ca5cb9651c 100644 --- a/interface/web/admin/templates/directive_snippets_edit.htm +++ b/interface/web/admin/templates/directive_snippets_edit.htm @@ -18,6 +18,12 @@ <div class="ctrlHolder"> <label for="snippet">{tmpl_var name='snippet_txt'}</label> <textarea name="snippet" id="snippet" rows='10' cols='50' style="width:400px;">{tmpl_var name='snippet'}</textarea><span class="nginx"> {tmpl_var name='variables_txt'}: </span><a href="javascript:void(0);" class="addPlaceholder nginx">{DOCROOT}</a><span class="nginx">, </span><a href="javascript:void(0);" class="addPlaceholder nginx">{FASTCGIPASS}</a> + </div> + <div class="ctrlHolder"> + <p class="label">{tmpl_var name='customer_viewable_txt'}</p> + <div class="multiField"> + {tmpl_var name='customer_viewable'} + </div> </div> <div class="ctrlHolder"> <p class="label">{tmpl_var name='active_txt'}</p> @@ -43,8 +49,19 @@ } else { jQuery('.nginx:visible').hide(); } + + if (jQuery('#type').val() != 'nginx' && jQuery('#type').val() != 'apache') { + jQuery('#customer_viewable').closest('div.ctrlHolder:visible').hide(); + }else { + jQuery('#customer_viewable').closest('div.ctrlHolder:hidden').show(); + } jQuery('#type').change(function(){ + if (jQuery(this).val() != 'nginx' && jQuery(this).val() != 'apache') { + jQuery('#customer_viewable').closest('div.ctrlHolder:visible').hide(); + } else { + jQuery('#customer_viewable').closest('div.ctrlHolder:hidden').show(); + } if(jQuery(this).val() == 'nginx'){ jQuery('.nginx:hidden').show(); } else { diff --git a/interface/web/sites/ajax_get_json.php b/interface/web/sites/ajax_get_json.php index ddf7d8550b..fb2f1c093f 100644 --- a/interface/web/sites/ajax_get_json.php +++ b/interface/web/sites/ajax_get_json.php @@ -190,6 +190,17 @@ if($type == 'get_use_loadindicator'){ $json .= '"}'; } +if ($type == 'getdirectivesnippet') { + $server_type = 'apache'; + $web_config = $app->getconf->get_server_config($server_id, 'web'); + if (!empty($web_config['server_type'])) + $server_type = $web_config['server_type']; + + $snippets = $app->db->queryAllRecords("SELECT directive_snippets_id, name FROM directive_snippets WHERE customer_viewable = 'y' AND type = ? ORDER BY name ASC", $server_type); + + $json = json_encode($snippets); +} + //} header('Content-type: application/json'); diff --git a/interface/web/sites/form/web_vhost_domain.tform.php b/interface/web/sites/form/web_vhost_domain.tform.php index 7d50b97478..4d6b161db4 100644 --- a/interface/web/sites/form/web_vhost_domain.tform.php +++ b/interface/web/sites/form/web_vhost_domain.tform.php @@ -282,7 +282,13 @@ $form["tabs"]['domain'] = array ( //################################# // ENDE Datatable fields //################################# - ) + ), + 'plugins' => array ( + // needs serverId for web.server_type + 'directive_snippets_id' => array ( + 'class' => 'plugin_directive_snippets' + ), + ) ); // add type-specific field attributes diff --git a/interface/web/sites/lib/lang/de_web_directive_snippets.lng b/interface/web/sites/lib/lang/de_web_directive_snippets.lng new file mode 100644 index 0000000000..b6d898496e --- /dev/null +++ b/interface/web/sites/lib/lang/de_web_directive_snippets.lng @@ -0,0 +1,3 @@ +<?php +$wb['directive_snippets_id_txt'] = 'Gewünschte Konfiguration'; +?> \ No newline at end of file diff --git a/interface/web/sites/lib/lang/en_web_directive_snippets.lng b/interface/web/sites/lib/lang/en_web_directive_snippets.lng new file mode 100644 index 0000000000..05a004f654 --- /dev/null +++ b/interface/web/sites/lib/lang/en_web_directive_snippets.lng @@ -0,0 +1,3 @@ +<?php +$wb['directive_snippets_id_txt'] = 'Desired configuration'; +?> \ No newline at end of file diff --git a/interface/web/sites/templates/web_directive_snippets.htm b/interface/web/sites/templates/web_directive_snippets.htm new file mode 100644 index 0000000000..664a07fd58 --- /dev/null +++ b/interface/web/sites/templates/web_directive_snippets.htm @@ -0,0 +1,14 @@ +<div class="ctrlHolder"> + <label for="directive_snippets_id"> + {tmpl_var name='directive_snippets_id_txt'} + </label> + + <select name="directive_snippets_id" id="directive_snippets_id" class="selectInput formLengthHalf"> + <option value="0"></option> + <tmpl_loop name="records"> + <option {tmpl_if name='is_selected' op='==' value='true'}selected="selected" {/tmpl_if}value="{tmpl_var name='directive_snippets_id'}"> + {tmpl_var name='name'} + </option> + </tmpl_loop> + </select> +</div> \ No newline at end of file diff --git a/interface/web/sites/templates/web_vhost_domain_edit.htm b/interface/web/sites/templates/web_vhost_domain_edit.htm index 0e0897a5cc..6548e82748 100644 --- a/interface/web/sites/templates/web_vhost_domain_edit.htm +++ b/interface/web/sites/templates/web_vhost_domain_edit.htm @@ -219,6 +219,7 @@ {tmpl_var name='fastcgi_php_version'} </select> </div> + {tmpl_var name="directive_snippets_id"} <div class="ctrlHolder"> <p class="label">{tmpl_var name='active_txt'}</p> <div class="multiField"> @@ -249,6 +250,7 @@ adjustForm(); reloadWebIP(); reloadFastcgiPHPVersions(); + reloadDirectiveSnippets(); }); } adjustForm(true); @@ -316,6 +318,23 @@ } }); } + + function reloadDirectiveSnippets() { + jQuery.getJSON('sites/ajax_get_json.php'+ '?' + Math.round(new Date().getTime()), {server_id : serverId, type : "getdirectivesnippet"}, function(data) { + var options = '<option value="0"></option>'; + for (var i = 0, len = data.length; i < len; i++) { + var isSelected = ''; + + if ($('#directive_snippets_id').val() == i + 1) { + isSelected = 'selected="selected"'; + } + + options += '<option ' + isSelected + ' value="' + data[i]['directive_snippets_id'] + '">' + data[i]['name'] + '</option>'; + } + + $('#directive_snippets_id').html(options).change(); + }); + } function reloadWebIP() { loadOptionInto('ip_address','sites/ajax_get_ip.php?ip_type=IPv4&server_id='+serverId+'&client_group_id='+clientGroupId); @@ -340,9 +359,9 @@ } <tmpl_if name="readonly_tab"> - jQuery('div.panel_web_domain').find('fieldset').find('input,select,button').bind('click mousedown', function(e) { e.preventDefault(); }).focus(function() { $(this).blur(); }); + jQuery('div.panel_web_domain').find('fieldset').find('input,select,button').not('#directive_snippets_id').bind('click mousedown', function(e) { e.preventDefault(); }).focus(function() { $(this).blur(); }); jQuery('#dom-edit-submit').click(function() { - submitForm('pageForm','sites/web_vhost_domain_edit.php'); + submitForm('pageForm','sites/web_vhost_domain_edit.php'); }); <tmpl_else> jQuery('#dom-edit-submit').click(function() { diff --git a/interface/web/sites/web_vhost_domain_edit.php b/interface/web/sites/web_vhost_domain_edit.php index e868ece7bd..8935713063 100644 --- a/interface/web/sites/web_vhost_domain_edit.php +++ b/interface/web/sites/web_vhost_domain_edit.php @@ -191,7 +191,7 @@ class page_action extends tform_actions { if($app->functions->intval($this->dataRecord["server_id"]) > 0) { // check if server is in client's servers or add it. $chk_sid = explode(',', $client['web_servers']); - if(in_array($this->dataRecord["server_id"], $client['web_servers']) == false) { + if(in_array($this->dataRecord["server_id"], explode(',', $client['web_servers'])) == false) { if($client['web_servers'] != '') $client['web_servers'] .= ','; $client['web_servers'] .= $app->functions->intval($this->dataRecord["server_id"]); } diff --git a/server/plugins-available/apache2_plugin.inc.php b/server/plugins-available/apache2_plugin.inc.php index 2bf4dfe3a9..ec98e849c8 100644 --- a/server/plugins-available/apache2_plugin.inc.php +++ b/server/plugins-available/apache2_plugin.inc.php @@ -1030,6 +1030,12 @@ class apache2_plugin { $vhost_data['custom_php_ini_dir'] = escapeshellcmd($custom_php_ini_dir); // Custom Apache directives + if(intval($data['new']['directive_snippets_id']) > 0){ + $snippet = $app->db->queryOneRecord("SELECT * FROM directive_snippets WHERE directive_snippets_id = ? AND type = 'apache' AND active = 'y' AND customer_viewable = 'y'", intval($data['new']['directive_snippets_id'])); + if(isset($snippet['snippet'])){ + $vhost_data['apache_directives'] = $snippet['snippet']; + } + } // Make sure we only have Unix linebreaks $vhost_data['apache_directives'] = str_replace("\r\n", "\n", $vhost_data['apache_directives']); $vhost_data['apache_directives'] = str_replace("\r", "\n", $vhost_data['apache_directives']); diff --git a/server/plugins-available/nginx_plugin.inc.php b/server/plugins-available/nginx_plugin.inc.php index 57044eff43..c256ae18f6 100644 --- a/server/plugins-available/nginx_plugin.inc.php +++ b/server/plugins-available/nginx_plugin.inc.php @@ -1089,7 +1089,16 @@ class nginx_plugin { // Custom nginx directives $final_nginx_directives = array(); - $nginx_directives = $data['new']['nginx_directives']; + if(intval($data['new']['directive_snippets_id']) > 0){ + $snippet = $app->db->queryOneRecord("SELECT * FROM directive_snippets WHERE directive_snippets_id = ? AND type = 'nginx' AND active = 'y' AND customer_viewable = 'y'", intval($data['new']['directive_snippets_id'])); + if(isset($snippet['snippet'])){ + $nginx_directives = $snippet['snippet']; + } else { + $nginx_directives = $data['new']['nginx_directives']; + } + } else { + $nginx_directives = $data['new']['nginx_directives']; + } // Make sure we only have Unix linebreaks $nginx_directives = str_replace("\r\n", "\n", $nginx_directives); $nginx_directives = str_replace("\r", "\n", $nginx_directives); -- GitLab