summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: 2a86282)
raw | patch | inline | side by side (parent: 2a86282)
author | hickert <hickert@594d385d-05f5-0310-b6e9-bd551577e9d8> | |
Mon, 18 Oct 2010 09:08:49 +0000 (09:08 +0000) | ||
committer | hickert <hickert@594d385d-05f5-0310-b6e9-bd551577e9d8> | |
Mon, 18 Oct 2010 09:08:49 +0000 (09:08 +0000) |
git-svn-id: https://oss.gonicus.de/repositories/gosa/trunk@20076 594d385d-05f5-0310-b6e9-bd551577e9d8
23 files changed:
diff --git a/gosa-plugins/goto/admin/ConfigManagement/AddItemDialog.tpl b/gosa-plugins/goto/admin/ConfigManagement/AddItemDialog.tpl
--- /dev/null
@@ -0,0 +1,21 @@
+
+<h3>{t}Add item{/t}</h3>
+
+{t}Please specify a name for the item to add, this name has to be uniq within the item configuration.{/t}
+<br>
+
+<hr>
+
+<p>
+ <b>{$itemCfg.name}</b> - {$itemCfg.description}
+</p>
+
+{t}Name{/t}: <input type='text' name='itemName' value="{$itemName}">
+
+<hr>
+
+<div class='plugin-actions'>
+ <button name='saveItemAdd'>{msgPool type=okButton}</button>
+ <button name='cancelItemAdd'>{msgPool type=cancelButton}</button>
+</div>
+
diff --git a/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig-filter.xml b/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig-filter.xml
--- /dev/null
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<filterdef>
+ <definition>
+ <initial>true</initial>
+ <category>Device</category>
+ <scope>auto</scope>
+ <default>default</default>
+ <attribute>-</attribute>
+ </definition>
+
+ <search>
+ <tag>default</tag>
+ <label>Default filter</label>
+ <query>
+ <backend>DeviceItems</backend>
+ <filter>$</filter>
+ </query>
+ <autocomplete>
+ <attribute>cn</attribute>
+ <frequency>0.5</frequency>
+ <characters>3</characters>
+ </autocomplete>
+ </search>
+
+</filterdef>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig-list.tpl b/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig-list.tpl
--- /dev/null
@@ -0,0 +1,21 @@
+<div id="mainlist">
+
+ <div class="mainlist-header">
+ <p>{$HEADLINE} {$SIZELIMIT}</p>
+ <div class="mainlist-nav">
+ <table summary="{$HEADLINE}">
+ <tr>
+ <td>{$RELOAD}</td>
+ <td class="left-border">{t}Base{/t} {$RELEASE}</td>
+ <td class="left-border">{$ACTIONS}</td>
+ <td class="left-border">{$FILTER}</td>
+ </tr>
+ </table>
+ </div>
+ </div>
+
+ {$LIST}
+</div>
+
+<div class="clear"></div>
+
diff --git a/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig-list.xml b/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig-list.xml
--- /dev/null
@@ -0,0 +1,87 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<list>
+ <definition>
+ <departmentBrowser>false</departmentBrowser>
+ <departmentRootVisible>false</departmentRootVisible>
+ <baseMode>false</baseMode>
+ <multiSelect>true</multiSelect>
+ <template>goto/Config/DeviceConfig-list.tpl</template>
+ <label>List of items</label>
+ <defaultSortColumn>1</defaultSortColumn>
+
+ %TYPES%
+
+ </definition>
+
+ <table>
+ <layout>|20px;c|||170px;r|</layout>
+
+ <department>
+ <value>%{filter:objectType(dn,objectClass)}</value>
+ </department>
+
+ <department>
+ <value>%{filter:departmentLink(row,dn,description)}</value>
+ <span>2</span>
+ </department>
+
+ <column>
+ <value>%{filter:objectType(dn,objectClass)}</value>
+ </column>
+
+ <column>
+ <label>Name</label>
+ <sortAttribute>cn</sortAttribute>
+ <sortType>string</sortType>
+ <value>%{filter:link(row,dn,"%s",cn,pid)}</value>
+ <export>true</export>
+ </column>
+
+ <column>
+ <label>Description</label>
+ <sortAttribute>description</sortAttribute>
+ <sortType>string</sortType>
+ <value>%{filter:link(row,dn,"%s",description,pid)}</value>
+ <export>true</export>
+ </column>
+
+ <column>
+ <label>Actions</label>
+ <value>%{filter:actions(dn,row,objectClass)}</value>
+ </column>
+
+ </table>
+
+ <actionmenu>
+
+ %ITEMS%
+
+ <action>
+ <name>remove</name>
+ <type>entry</type>
+ <image>images/lists/trash.png</image>
+ <label>Remove</label>
+ </action>
+
+ </actionmenu>
+
+ <actiontriggers snapshot="false" copypaste="false">
+
+ <action>
+ <name>editEntry</name>
+ <type>entry</type>
+ <image>images/lists/edit.png</image>
+ <label>Edit item</label>
+ </action>
+
+ <action>
+ <name>remove</name>
+ <type>entry</type>
+ <image>images/lists/trash.png</image>
+ <label>Remove item</label>
+ </action>
+
+ </actiontriggers>
+
+</list>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig.tpl b/gosa-plugins/goto/admin/ConfigManagement/DeviceConfig.tpl
--- /dev/null
@@ -0,0 +1,12 @@
+<h3>{t}Device Config{/t}</h3>
+{$navigationList}
+<button name='addSubModule'>{msgPool type='addButton'}</button>
+
+<hr>
+
+<b>{$containerName}</b> <i>({$containerDescription})</i>
+
+<p>
+{$template}
+</p>
+
diff --git a/gosa-plugins/goto/admin/ConfigManagement/TemplateEngine.tpl b/gosa-plugins/goto/admin/ConfigManagement/TemplateEngine.tpl
--- /dev/null
@@ -0,0 +1,11 @@
+<h3>Bla</h3>
+
+{$template}
+
+<hr>
+
+<div class='plugin-actions'>
+ <button name='saveItemEdit'>{msgPool type=okButton}</button>
+ <button name='cancelItemEdit'>{msgPool type=cancelButton}</button>
+</div>
+
diff --git a/gosa-plugins/goto/admin/ConfigManagement/TemplateWidget_textEditor.tpl b/gosa-plugins/goto/admin/ConfigManagement/TemplateWidget_textEditor.tpl
--- /dev/null
@@ -0,0 +1,12 @@
+{if $write_protect}
+ {t}The text is write protected, due to its encoding. Editing may break it!{/t}
+ <br>
+ <button type='submit' name='editAnyway'>{t}Edit anyway{/t}</button>
+{/if}
+<textarea {if $write_protect} disabled {/if} {if !$write_protect} name="{$postName}" {/if}
+ style="width:100%;height:300px;" id="{$postName}"
+ rows="20" cols="120">{$value}</textarea>
+<div>
+ <input type="file" name="ImportFile">
+ <button type='submit' name='ImportUpload'>{t}Import text{/t}</button>
+</div>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_AddItemDialog.inc b/gosa-plugins/goto/admin/ConfigManagement/class_AddItemDialog.inc
--- /dev/null
@@ -0,0 +1,61 @@
+<?php
+
+class AddItemDialog
+{
+ private $itemCfg = NULL;
+ private $config = NULL;
+
+ private $itemName = "";
+ private $itemType = NULL;
+
+ function __construct(&$config, $itemType, $itemCfg)
+ {
+ $this->config = $config;
+ $this->itemCfg = $itemCfg;
+ $this->itemType = $itemType;
+ }
+
+ function execute()
+ {
+ $smarty = get_smarty();
+ $smarty->assign('itemCfg', set_post($this->itemCfg));
+ $smarty->assign('itemName', set_post($this->itemName));
+ return($smarty->fetch(get_template_path('goto/Config/AddItemDialog.tpl', TRUE)));
+ }
+
+ function getItemCfg()
+ {
+ return($this->itemCfg);
+ }
+
+ function getName()
+ {
+ return($this->itemName);
+ }
+
+ function getItemType()
+ {
+ return($this->itemType);
+ }
+
+ function save_object()
+ {
+ if(isset($_POST['itemName'])){
+ $this->itemName = get_post('itemName');
+ }
+ }
+
+ function check()
+ {
+ $message = array();
+ if(empty($this->itemName)){
+ $message[] = msgPool::required(_("Name"));
+ }else
+ if(!tests::is_uid($this->itemName)){
+ $message[] = msgPool::invalid(_("Name"));
+ }
+ return($message);
+ }
+}
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_DeviceConfig.inc b/gosa-plugins/goto/admin/ConfigManagement/class_DeviceConfig.inc
--- /dev/null
@@ -0,0 +1,630 @@
+<?php
+
+/*! \brief A GOsa plugin which generates a device configuration dialog
+ */
+class DeviceConfig extends management
+{
+
+ // Used to render the item-configuration dialog
+ private $TemplateEngine = NULL;
+
+ // A list of all configured items for this device.
+ private $allConfiguredItems = array();
+
+ // The currently active item
+ // Add add and remove action will be performed on this item
+ private $currentItem = array();
+
+ // A baseSelector which will be fed with a simulated
+ // department list. All entries will get a fake base
+ // which can then be used to fill the baseSelector widget.
+ private $itemContainerSelector = NULL;
+
+ // The currently selected base within management list.
+ private $base ;
+
+ // This array contains a list of all item-types we can add
+ // to the currently selected item (currentItem)
+ private $addableContainerItems = array();
+
+ // Due to the fakt that we use a fake 'base/dn' for all items
+ // we've to map this 'base/dn' to the items 'id'.
+ private $mappingBaseToID = array();
+
+ private $rootItemID;
+ private $itemConfig = array();
+ private $lastItemID = 1;
+
+ private $rpcError = FALSE;
+ private $initFailed = FALSE;
+ private $invalidInstallMethod = FALSE;
+ private $errorMessage = "";
+
+ // Some plugin related memebers which are not member of
+ // the management class. See class plugin.
+ public $initTime;
+ public $is_account = FALSE;
+ public $ignore_account = FALSE;
+ public $pl_notify;
+ public $read_only;
+
+ public $allItemConfigurations = NULL;
+
+ /*! \brief Constructs the device configuration plugin
+ * @param Config The GOsa configuration object.
+ */
+ function __construct(&$config, $dn)
+ {
+ // Load the template engine and tell her what template
+ // to use for the HTML it produces.
+ $this->TemplateEngine = new TemplateEngine($config);
+ $this->TemplateEngine->setTemplate('puppet.tpl');
+ $this->config = $config;
+
+ // Set storage points - We do not have any - We just create a fake list which lists all items
+ $this->storagePoints = array("");
+
+ // Try to initialize
+ $this->init();
+ $this->rebuildListing();
+ }
+
+
+ /*! \brief Sets the installation method to the given method.
+ * Updates the template engine and adds the initial root
+ * object for the selected method.
+ * @param The method to use.
+ * @return TRUE on success else FALSE.
+ */
+ function setInstallMethod($str)
+ {
+ $this->is_account = FALSE;
+ if(!isset($this->allItemConfigurations[$str])){
+ $this->itemConfig = array();
+ $this->invalidInstallMethod =TRUE;
+ $this->errorMessage = sprintf(_("Invalid installation method selected '%s'!"), $str);
+ msg_dialog::display(_("Setup"), $this->errorMessage, ERROR_DIALOG);
+ return(FALSE);
+ }else{
+
+ $this->itemConfig = $this->allItemConfigurations[$str]['items'];
+ $this->invalidInstallMethod =FALSE;
+ $this->TemplateEngine->load($this->itemConfig);
+
+ // Detect root item, its name is /
+ $root = NULL;
+ foreach($this->itemConfig as $key => $item){
+ if($item['name'] == '/') {
+ $root = $key;
+ break;
+ }
+ }
+ if(!$root){
+ $this->errorMessage = sprintf(_("Installation method '%s' is invalid, no root object found!"), $str);
+ msg_dialog::display(_("Setup"), $this->errorMessage , ERROR_DIALOG);
+ $this->initFailed = TRUE;
+ $this->itemConfig = array();
+ return(FALSE);
+ }
+
+ // Set current item to 'root', this is the minimum to get things running.
+ $idRoot = $this->addItem($root,'root',array());
+ $this->rootItemID = $idRoot;
+ $this->setCurrentItem($idRoot);
+ $this->setSelectedListItemID($idRoot);
+ $this->is_account = TRUE;
+ $this->rebuildListing();
+ return(TRUE);
+ }
+ }
+
+
+ /*! \brief Intializes this plugin
+ * All available installation methods will be loaded
+ * and populated.
+ */
+ function init()
+ {
+ // Reset erros
+ $this->rpcError = $this->initFailed = FALSE;
+
+ // Load configuration via rpc.
+ $rpc = $this->config->getRpcHandle();
+
+ // Populate install methods on success.
+ $res = $rpc->getSupportedInstallMethods();
+ if(!$rpc->success()){
+ $this->rpcError = TRUE;
+ $this->errorMessage = $rpc->get_error();;
+ return;
+ }
+ $this->allItemConfigurations = $res;
+ if(!count($this->allItemConfigurations)){
+ $this->errorMessage = _("No selectable install methods returned!");
+ msg_dialog::display(_("Setup"), $this->errorMessage , ERROR_DIALOG);
+ $this->initFailed = TRUE;
+ return;
+ }
+ }
+
+
+ /*! \brief Add a new child-item to the currently selected one.
+ *
+ * @param String type The 'type' of the new object, eg. 'KickstartTemplate'
+ * @param String name The 'name' of the new object.
+ * @param Array values The initial values for this object.
+ * @return
+ */
+ function addItem($type,$name, $values = array())
+ {
+ if(!isset($this->itemConfig[$type])){
+ echo "Invalid type {$type}, skipping item!<br>";
+ return;
+ }
+
+ // Add missing values with the item-type defaults.
+ $allValuesSet = TRUE;
+ foreach($this->itemConfig[$type]['options'] as $oName => $oValue){
+ if(!isset($values[$oName])){
+ $values[$oName] = (isset($oValue['default']))?$oValue['default']:"";
+ }
+ }
+
+ // Get the currently selected entry, its the parent for the newly
+ // added one.
+ $current = &$this->currentItem;
+
+ // Create a FAKE base to be able to use the management lists
+ // which are currently ldap and thus dn based.
+ $base = (isset($current['base']))? ",".$current['base'] : '';
+ $base = "{$type}={$name}{$base}";
+
+
+ if(isset($this->mappingBaseToID[$base])){
+ echo "Cannot add entry, dn already in use! {$base}<br>";
+ return(null);
+ }
+
+ // Get next free item slot.
+ $id = ($this->lastItemID ++);
+ $new = array(
+ 'base' => $base,
+ 'children' => array(),
+ 'id' => $id,
+ 'type' => $type,
+ 'name' => $name,
+ 'values' => $values);
+
+ // Append the entry to the list of all items.
+ $this->allConfiguredItems[$id] = $new;
+
+ // Create a child referenc, this creates some kind of entry tree.
+ $current['children'][$id] = &$this->allConfiguredItems[$id];
+
+ // Add entries to the list of base and id mappings
+ // this allows us to easily detect the base for an id and vice versa.
+ $this->mappingBaseToID[$id] = $base;
+ $this->mappingBaseToID[$base] = $id;
+ return($id);
+ }
+
+
+ /*! \brief Selects an item as active.
+ * All further add and remove actions will be performed
+ * on the obejcts children.
+ * @param String The 'id' of the item we want to select.
+ * @return
+ */
+ function setCurrentItem($item)
+ {
+ if(!isset($this->allConfiguredItems[$item])){
+ echo "Invalid item name {$name}! Skipping selection!";
+ return;
+ }
+
+ // Set the new item info.
+ $this->currentItem = &$this->allConfiguredItems[$item];
+ $this->currentItemType = $this->currentItem['type'];
+ $this->currentItemDescriptor = $this->itemConfig[$this->currentItem['type']];
+ }
+
+
+ /*! \brief Removes a given item ID.
+ * @param String The 'id' of the item we want to remove.
+ * @return
+ */
+ function removeItem($id, &$data = NULL)
+ {
+ if($data === NULL){
+ $data = &$this->allConfiguredItems;
+ }
+
+ // Remove the item and its children
+ if(isset($data[$id])){
+ foreach($data[$id]['children'] as $cid => $item){
+ $this->removeItem($cid, $data);
+ }
+ unset($data[$id]);
+ }
+
+ // Remove to current id from sub entries
+ foreach($data as $key => $item){
+ $this->removeItem($id, $data[$key]['children']);
+ }
+ }
+
+
+ /*! \brief Initiate item edit.
+ * An action send from the management list.
+ * @param See management::editEntry
+ * @return
+ */
+ function editEntry($action="",$target=array(),$all=array(),
+ $altTabClass ="", $altTabType = "", $altAclCategory="")
+ {
+ $this->setCurrentItem($target[0]);
+ $this->dialogObject = $this->TemplateEngine;
+ $this->skipFooter = TRUE;
+ $this->dialog = TRUE;
+
+ // Update the template engine to use another type of item and
+ // some other values.
+ $this->TemplateEngine->setValues($this->currentItemType,$this->currentItem['values']);
+ }
+
+
+ /*! \brief Save changes for the currently edited item.
+ */
+ function saveItemChanges()
+ {
+ // Save eventually changed values
+ if($this->currentItem){
+
+ // Check if everything is fine.
+ $msgs = $this->TemplateEngine->save_object();
+ $msgs = $this->TemplateEngine->check();
+ if(count($msgs)){
+ msg_dialog::displayChecks($msgs);
+ }else{
+ foreach($this->TemplateEngine->getWidgets() as $widget){
+ $this->currentItem['values'][$widget->getName()] = $widget->getValue();
+ }
+ $this->closeDialogs();
+ }
+ }
+ }
+
+
+ /*! \brief React on open requests from the management list
+ */
+ function openEntry($action="",$target=array(),$all=array(),
+ $altTabClass ="", $altTabType = "", $altAclCategory="")
+ {
+ $this->setSelectedListItemID($target[0]);
+ }
+
+
+ /*! \brief Overridden render method of class mangement.
+ * this allows us to add a release selection box.
+ */
+ function renderList()
+ {
+ // In case of an error abort here.
+ if($this->rpcError || $this->initFailed || $this->invalidInstallMethod){
+ $smarty = get_smarty();
+ $smarty->assign('initFailed', $this->initFailed);
+ $smarty->assign('rpcError', $this->rpcError);
+ $smarty->assign('invalidInstallMethod', $this->invalidInstallMethod);
+ $smarty->assign('error', $this->errorMessage);
+ return($smarty->fetch(get_template_path('goto/Config/failed.tpl', TRUE)));
+ }
+
+ // Do we represent a valid account
+ if (!$this->is_account){
+ $str = "<img alt=\"\" src=\"images/small-error.png\" align=\"middle\"> <b>".
+ msgPool::noValidExtension("GOsa")."</b>";
+ return($str);
+ }
+
+ // Collect item container list to be able to render the fake-base selector
+ if(!$this->itemContainerSelector){
+ $this->itemContainerSelector = new ItemSelector(
+ $this->getContainerList(),
+ $this->base,
+ $this->allConfiguredItems[$this->rootItemID]['base']);
+ }else{
+ $this->itemContainerSelector->setBases($this->getContainerList());
+ }
+ $this->itemContainerSelector->update(true);
+ $this->itemContainerSelector->setBase($this->base);
+
+ session::set('DEVICE_ITEMS', $this->allConfiguredItems);
+ $this->rebuildListing();
+ $filter = $this->getFilter();
+ $headpage = $this->getHeadpage();
+
+ $headpage->update();
+ $smarty = get_smarty();
+ $smarty->assign("RELEASE", $this->itemContainerSelector->render());
+ $display = $headpage->render();
+ return($this->getHeader().$display);
+ }
+
+
+ /*! \brief Build up a list of items useable for the itemSelector.
+ */
+ function getContainerList($array = NULL)
+ {
+ $array = ($array == NULL)?$this->allConfiguredItems[$this->rootItemID]: $array;
+ $ret[$array['base']] = $array['type'];
+ if(count($array['children'])){
+ foreach($array['children'] as $subItem){
+ $ret = array_merge($ret, $this->getContainerList($subItem));
+ }
+ }
+ return($ret);
+ }
+
+
+ /*! \brief Update the management class and tell her which
+ * items are available for the itemSelector (baseSelector).
+ */
+ function rebuildListing()
+ {
+ // Build filter
+ if (session::global_is_set(get_class($this)."_filter")){
+ $filter= session::global_get(get_class($this)."_filter");
+ } else {
+ $filter = new filter(get_template_path("goto/Config/DeviceConfig-filter.xml", true));
+ $filter->setObjectStorage($this->storagePoints);
+ }
+ $this->setFilter($filter);
+
+ // Load service xml file and fill in placeholders
+ $contents =file_get_contents(get_template_path("goto/Config/DeviceConfig-list.xml", true));
+
+ // Build up device-list configuration
+ $types ="";
+ $images = array();
+ $images[] = 'images/lists/edit.png';
+ $images[] = 'images/caps.png';
+ $images[] = 'images/lists/trash.png';
+ $images[] = 'images/filter.png';
+ $images[] = 'images/find.png';
+ $i = 0;
+ foreach($this->itemConfig as $type => $item){
+ $desc = $item['description'];
+ $img = $images[$i++];
+ $types .=
+ " <objectType>".
+ " <label>{$desc}</label>".
+ " <objectClass>{$type}</objectClass>".
+ " <category>Device</category>".
+ " <class>dummy</class>".
+ " <image>{$img}</image>".
+ " </objectType>";
+ }
+ $contents = preg_replace("/%TYPES%/", $types, $contents);
+
+
+ $items = "";
+ $i = 0;
+ foreach($this->addableContainerItems as $item){
+ $desc = $this->itemConfig[$item]['description'];
+ $img = $images[$i++];
+ $items .=
+ "<action>".
+ " <name>add_{$item}</name>".
+ " <type>entry</type>".
+ " <image>{$img}</image>".
+ " <label>{$desc}</label>".
+ "</action>";
+ }
+
+ if(!empty($items)){
+ $items =
+
+ "<action>".
+ " <type>sub</type>".
+ " <image>images/lists/element.png[new]</image>".
+ " <label>Create</label>".
+ " {$items}".
+ "</action>";
+ }
+
+ $contents = preg_replace("/%ITEMS%/", $items, $contents);
+
+ $headpage = new listing($contents,TRUE);
+ $headpage->setBase($this->base);
+ $headpage->setFilter($filter);
+
+ parent::__construct($this->config, $this->ui, "services", $headpage);
+
+ // Register default actions
+ $this->registerAction("new", "newEntry");
+ $this->registerAction("edit", "openEntry"); // !! We forward 'edit' to 'open' to have a department like navigation.
+ $this->registerAction("editEntry", "editEntry");
+
+ $this->registerAction("saveItemChanges", "saveItemChanges");
+ $this->registerAction("cancelItemEdit", "closeDialogs");
+ $this->registerAction("cancelItemAdd", "closeDialogs");
+ $this->registerAction("saveItemAdd", "saveItemAdd");
+ foreach($this->itemConfig as $name => $item){
+ $this->registerAction("add_{$name}", "newEntry");
+ }
+ }
+
+
+ /*! \brief This method intiates the object creation.
+ *
+ * @param String 'action' The name of the action which was the used as trigger.
+ * @param Array 'target' A list of object dns, which should be affected by this method.
+ * @param Array 'all' A combination of both 'action' and 'target'.
+ */
+ function newEntry($action="",$target=array(),$all=array(),
+ $altTabClass ="", $altTabType = "", $altAclCategory="")
+ {
+ $toAdd = preg_replace("/^add_/", "",$action);
+ $itemToAdd = $this->itemConfig[$toAdd];
+
+ $this->dialogObject = new AddItemDialog($this->config,$toAdd,$itemToAdd);
+ $this->dialog = true;
+ }
+
+
+ /*! \brief Saves newly created items and adds them as child to
+ * the currently selected item.
+ */
+ function saveItemAdd()
+ {
+ if(!$this->dialogObject instanceOf AddItemDialog) return;
+
+ $msgs = $this->dialogObject->save_object();
+ $msgs = $this->dialogObject->check();
+ if(count($msgs)){
+ msg_dialog::displayChecks($msgs);
+ }else{
+ $itemName = $this->dialogObject->getName();
+ $itemCfg = $this->dialogObject->getItemCfg();
+ $itemType = $this->dialogObject->getItemType();
+
+ $this->setCurrentItem($this->mappingBaseToID[$this->base]);
+
+ $this->addItem($itemType, $itemName);
+ $this->closeDialogs();
+
+# $this->setCurrentItem($itemName);
+# $this->dialogObject = $this->TemplateEngine;
+# $this->skipFooter = TRUE;
+# $this->dialog = TRUE;
+
+ }
+ }
+
+
+ /*! \brief Keep track of posted values, some may be interesting for us.
+ * Tell the template engine to take care of posted values too.
+ * @param String
+ * @return
+ */
+ function save_object()
+ {
+ if(isset($_POST['retryInit'])){
+ $this->init();
+ return;
+ }
+
+ // Do nothing else in case of an error
+ if($this->rpcError || $this->initFailed) return;
+
+ // Add sub-module requested.
+ if(isset($_POST['addSubModule']) && isset($_POST['subModule'])){
+ $sub = get_post('subModule');
+ if(in_array($sub, $this->currentItemDescriptor['container'])){
+
+ // Check if this is a valid item
+ if(!isset($this->itemConfig[$sub])) {
+ echo "Invalid item type '{$sub}'!";
+ $values = array();
+ }else{
+ $values = $this->itemConfig[$sub]['options'];
+ }
+ $name = 'test'.rand(0,99999);
+ $this->addItem($sub,$name,$values);
+ }
+ }
+
+ // Get the selected item-id from the item list and populate it.
+ if($this->itemContainerSelector){
+ $this->itemContainerSelector->update();
+ $id = $this->mappingBaseToID[$this->itemContainerSelector->getBase()];
+ $this->setSelectedListItemID($id);
+ }
+ }
+
+
+ /* \brief Updates the currenlty seleted item in the management list
+ */
+ function setSelectedListItemID($id)
+ {
+ $this->base = $this->mappingBaseToID[$id];
+ $type = $this->allConfiguredItems[$id]['type'];
+ $this->addableContainerItems = $this->itemConfig[$type]['container'];
+ }
+
+
+ /*! \brief Forward plugin acls
+ */
+ function set_acl_base($base)
+ {
+ $this->acl_base = $base;
+ }
+
+
+ /*! \brief Forward plugin acls
+ */
+ function set_acl_category($category)
+ {
+ $this->acl_category = $category;
+ }
+
+ function save()
+ {
+ foreach($this->allConfiguredItems as $name => $item){
+ foreach($item['values'] as $oName => $oValue){
+ if(!is_array($oValue)) $oValue = array($oValue);
+ foreach($oValue as $val){
+ echo "<br>{$name} -- <i>{$item['type']}</i>: <b>{$oName}</b>: {$val}";
+ }
+ }
+ }
+ }
+
+
+ /*! \brief Initiates the removal for the given entries
+ * and displays a confirmation dialog.
+ *
+ * @param String 'action' The name of the action which was the used as trigger.
+ * @param Array 'target' A list of object dns, which should be affected by this method.
+ * @param Array 'all' A combination of both 'action' and 'target'.
+ */
+ protected function removeEntryRequested($action="",$target=array(),$all=array())
+ {
+ foreach($target as $id){
+ $this->removeItem($id);
+ }
+ }
+
+
+ // Inject user actions
+ function detectPostActions()
+ {
+ if($this->rpcError || $this->initFailed) return(array('action' => ''));
+
+ $action = management::detectPostActions();
+ if(isset($_POST['saveItemEdit'])) $action['action'] = "saveItemChanges";
+ if(isset($_POST['saveItemAdd'])) $action['action'] = "saveItemAdd";
+ if(isset($_POST['cancelItemEdit'])) $action['action'] = "cancelItemEdit";
+ if(isset($_POST['cancelItemAdd'])) $action['action'] = "cancelItemAdd";
+ return($action);
+ }
+
+
+ function closeDialogs()
+ {
+ parent::closeDialogs();
+ $this->dialog = false;
+ }
+
+
+ function check()
+ {
+ return(array());
+ }
+
+ function getRootItemId()
+ {
+ return($this->rootItemID);
+ }
+}
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_ItemSelector.inc b/gosa-plugins/goto/admin/ConfigManagement/class_ItemSelector.inc
--- /dev/null
@@ -0,0 +1,25 @@
+<?php
+/*
+ * This code is part of GOsa (http://www.gosa-project.org)
+ * Copyright (C) 2003-2010 GONICUS GmbH
+ *
+ * ID: $$Id: class_listing.inc 15296 2010-01-26 08:27:39Z cajus $$
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+class ItemSelector extends releaseSelector {
+}
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateEngine.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateEngine.inc
--- /dev/null
@@ -0,0 +1,154 @@
+<?php
+
+/*! \brief A template engine used to render dynamic template
+ * for the GOsa-devices.
+ */
+class TemplateEngine
+{
+ private $config;
+ private $data = array();
+ private $template = "";
+ private $itemType = '';
+ private $widgets = array();
+
+
+ /*! \brief Constructs the template engine.
+ * @param Config The GOsa configuration object.
+ */
+ function __construct($config)
+ {
+ $this->config = &$config;
+ }
+
+
+ /*! \brief Load/Sets the instruction-set to use for the current
+ * device configuration.
+ * A device configruation tells us what options
+ * an item can have and what children.
+ * @param Array The instruction set to use.
+ */
+ function load($array)
+ {
+ $this->data = $array;
+ }
+
+
+ /*! \brief Set the template which will be used to generate
+ * the HTML content for this configuration session.
+ * @param String A template filename.
+ */
+ function setTemplate($tmpl)
+ {
+ $this->template = $tmpl;
+ }
+
+
+ /*! \brief Returns the list of widgets which are currently used
+ * by the template engine to render the plugin.
+ * @return Array A list of widgets.
+ */
+ function getWidgets()
+ {
+ return($this->widgets);
+ }
+
+
+ /*! \brief Sets the current item type we want to render
+ * E.g. 'KickstartTemplate' and the corresponding values.
+ *
+ * @param String The name of the item we want to render now.
+ * @param Array The initial value.
+ */
+ function setValues($name, $values)
+ {
+ // Set the current item type and reset the widget list.
+ $this->itemType = $name;
+ $this->widgets = array();
+
+ // Do nothing if something seems to be wrong.
+ if(!isset($this->data[$this->itemType])){
+ echo "Undefined item type '{$name}'!<br>";
+ return;
+ }
+
+ // Get the options provided by the item and create widget for them.
+ $data = $this->data[$this->itemType];
+ if(isset($data['options']) && count($data['options'])){
+ foreach($data['options'] as $name => $item){
+ $widgetClassName = "TemplateWidget_{$item['type']}";
+
+ // Check if the widget is available, if it is not, use a default (string).
+ if(!class_available($widgetClassName)){
+ echo "Unknown widget class {$widgetClassName}! Falling back to default widget.<br>";
+ $widgetClassName = "TemplateWidget_string";
+ }
+
+ // Prepare the value for the widget
+ $value = $values[$name];
+ $syntax = (isset($item['syntax']))? $item['syntax']: "";
+ $providedValues = (isset($item['values']))? $item['values']: array();
+
+ // Create the new widget.
+ $this->widgets[$name] = new $widgetClassName($this->config, $name,
+ $value,
+ $item['description'],
+ $syntax,
+ $item['required'],
+ $item['type'],
+ $item['display'],
+ $providedValues);
+ }
+ }
+ }
+
+
+ function execute(){
+ return($this->render());
+ }
+
+
+ /*! \brief Creates the HTML content for the given list of widgets
+ * @return String The HTML content.
+ */
+ function render()
+ {
+ $smarty = get_smarty();
+ $smarty->assign("type", $this->itemType);
+
+ // Tell smarty the HTML-content for each widget and the name that should be
+ // displayed.
+ foreach($this->widgets as $widget){
+ $smarty->assign($widget->getName(), $widget->render());
+ $smarty->assign($widget->getName()."Name", $widget->getDisplayName());
+ }
+ $template = $smarty->fetch(get_template_path("goto/Config/{$this->template}", TRUE));
+
+ $smarty->assign('template', $template);
+ return($smarty->fetch(get_template_path("goto/Config/TemplateEngine.tpl", TRUE)));
+ }
+
+
+ /*! \brief Keep track of posted values.
+ */
+ function save_object()
+ {
+ foreach($this->widgets as $widget){
+ $widget->save_object();
+ }
+ }
+
+
+ /*! \brief Check widget values and return a list of errors.
+ */
+ function check()
+ {
+ $msgs = array();
+ foreach($this->widgets as $widget){
+ $msgs = array_merge($msgs, $widget->check());
+ }
+ return($msgs);
+ }
+}
+
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget.inc
--- /dev/null
@@ -0,0 +1,122 @@
+<?php
+
+/*! \brief The base class for all template-widgets used by the
+ * device-configuration class.
+ */
+class TemplateWidget
+{
+ protected $name = "unnamed";
+ protected $value = "";
+
+ protected $description = "";
+ protected $required = "";
+ protected $type = "";
+ protected $display = "";
+ protected $syntax = "";
+ protected $values = "";
+
+ /*! \brief Constructs the template widget and sets the default values.
+ * @param Config The GOsa configuration object.
+ * @param String A name for the widget.
+ * @param String The initial value.
+ * @param String A description.
+ * @param String True/False Must-Value/Optional-Value.
+ * @param String The widget type.
+ * @param String A display name for the widget.
+ */
+ function __construct(&$config, $name, $value, $description,$syntax,$required,$type,$display, $values=array())
+ {
+ $this->config = &$config;
+ $this->name = $name;
+ $this->value = $value;
+ $this->description = $description;
+ $this->required = $required;
+ $this->type = $type;
+ $this->syntax = $syntax;
+ $this->values = $values;
+ $this->display = $display;
+ $class = get_class();
+ $this->postName = "{$class}_{$this->name}";
+ }
+
+
+ /*! \brief Returns the display-name for the current widget.
+ * @return String The display-name for the widget, this
+ * name will usually be rendered infront of input fields.
+ */
+ function getDisplayName()
+ {
+ $must = ($this->required)?"<span class='required'>*</span>":"";
+ return($this->display.$must);
+ }
+
+
+ /*! \brief Returns the description for the widget.
+ */
+ function getDescription()
+ {
+ return($this->description);
+ }
+
+
+ /*! \brief Generates the HTML code for the widget.
+ * @return The HTML content for the widget.
+ */
+ function render()
+ {
+ return("");
+ }
+
+
+ /*! \brief Keep track of posted values.
+ */
+ function save_object()
+ {
+ if(isset($_POST[$this->postName])){
+ $this->value = get_post($this->postName);
+ }
+ }
+
+
+ /*! \brief Returns the current value.
+ * @return Mixed The widgets value.
+ */
+ function getValue()
+ {
+ return($this->value);
+ }
+
+
+ /*! \brief Returns the name of the widget.
+ * @param String The widgets name.
+ */
+ function getName()
+ {
+ return($this->name);
+ }
+
+
+ /*! \brief Sets a new value for the widget.
+ * @param String The new value.
+ */
+ function setValue($value)
+ {
+ $this->value = $value;
+ }
+
+
+ /*! \brief Check the value entry using the provieded syntax.
+ * @return Array Returns a list of errors
+ */
+ function check()
+ {
+ if($this->required && empty($this->value)){
+ return(array(msgPool::required($this->display)));
+ }
+ if(!empty($this->value) && !empty($this->syntax) && !preg_match("/".$this->syntax."/", $this->value)){
+ return(array(msgPool::invalid($this->display, $this->value, "/".$this->syntax."/")));
+ }
+ return(array());
+ }
+}
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_checkbox.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_checkbox.inc
--- /dev/null
@@ -0,0 +1,19 @@
+<?php
+
+class TemplateWidget_checkbox extends TemplateWidget
+{
+ function render()
+ {
+ $str = "";
+ $str .= "<input type='checkbox' value='1' name='{$this->postName}' ";
+ if($this->value) $str .= " checked ";
+ $str .= ">";
+ return($str);
+ }
+
+ function save_object()
+ {
+ $this->value = isset($_POST[$this->postName]);
+ }
+}
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_combobox.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_combobox.inc
--- /dev/null
@@ -0,0 +1,22 @@
+<?php
+
+class TemplateWidget_combobox extends TemplateWidget
+{
+ function render()
+ {
+ $str = "";
+
+ // Build up list data
+ $str .= "<select size='1' name='{$this->postName}'>";
+ foreach($this->values as $name => $value){
+ if($name == $this->value){
+ $str .= "<option selected value=\"{$name}\">{$value}</option>\n";
+ }else{
+ $str .= "<option value=\"{$name}\">{$value}</option>\n";
+ }
+ }
+ $str .= "</select>";
+ return($str);
+ }
+}
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_file.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_file.inc
--- /dev/null
@@ -0,0 +1,34 @@
+<?php
+
+class TemplateWidget_file extends TemplateWidget
+{
+ function render()
+ {
+ $title = set_post($this->description);
+ if(mb_strlen($this->value) == 0){
+ $ret = "<i>"._("No file uploaded yet")."</i>";
+ $ret.= "<br> <input type=\"hidden\" name=\"MAX_FILE_SIZE\" value=\"2000000\">
+ <input id=\"{$this->postName}\"
+ name=\"{$this->postName}\"
+ type=\"file\"
+ size=\"20\"
+ maxlength=\"255\"
+ accept=\"*.*\"> ";
+ $ret.= "<button name='{$this->postName}_Upload'>"._("Upload")."</button>";
+ }else{
+ $ret = "<i>"._("File uploaded").": ".mb_strlen($this->value)." "._("Bytes");
+ $ret.= " <button name='{$this->postName}_Remove'>".msgPool::delButton()."</button>";
+ }
+ return($ret);
+ }
+
+ function save_object()
+ {
+ if(isset($_POST["{$this->postName}_Upload"]) && isset($_FILES[$this->postName]['tmp_name'])){
+ $this->value = file_get_contents($_FILES[$this->postName]['tmp_name']);
+ }
+ if(isset($_POST["{$this->postName}_Remove"])) $this->value ="";
+ }
+}
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_fixedList.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_fixedList.inc
--- /dev/null
@@ -0,0 +1,86 @@
+<?php
+
+class TemplateWidget_fixedList extends TemplateWidget
+{
+ protected $value = array();
+
+ function __construct(&$config, $name, $value, $description,$syntax,$required,$type,$display,$values)
+ {
+ parent:: __construct($config, $name, $value, $description,$syntax,$required,$type,$display,$values);
+
+ $this->listWidget= new sortableListing($this->value);
+ $this->listWidget->setEditable(false);
+ $this->listWidget->setDeleteable(true);
+ $this->listWidget->setColspecs(array('*'));
+ $this->listWidget->setWidth("100%");
+ $this->listWidget->setHeight("70px");
+ $this->listWidget->setAcl("rwcdm");
+ }
+
+ function getAvailableOptions()
+ {
+ $tmp = array();
+ foreach($this->values as $key => $name){
+ if(!in_array($key, $this->value)){
+ $tmp[$key]=$name;
+ }
+ }
+ return($tmp);
+ }
+
+ function render()
+ {
+ $str = "";
+
+ // Build up list data
+ $data = $this->value;
+ foreach($this->value as $key => $name){
+ $lData[$key] = array('data' => array($this->values[$name]));
+ }
+ $this->listWidget->setListData($data, $lData);
+ $this->listWidget->update();
+ $str .= $this->listWidget->render();
+ $str .= "<select size='1' name='{$this->postName}_Input'>";
+ foreach($this->getAvailableOptions() as $name => $value){
+ $str .= "<option value=\"{$name}\">{$value}</option>\n";
+ }
+ $str .= "</select>";
+ $str .= "<button name='{$this->postName}_Add'>".msgPool::addButton()."</button>";
+ return($str);
+ }
+
+ function save_object()
+ {
+ $this->listWidget->save_object();
+ $action = $this->listWidget->getAction();
+ if($action['action'] == 'delete'){
+ $id = $this->listWidget->getKey($action['targets'][0]);
+ unset($this->value[$id]);
+ $this->value = array_values($this->value);
+ }
+
+ if(isset($_POST["{$this->postName}_Add"]) && isset($_POST["{$this->postName}_Input"])){
+ $input = get_post("{$this->postName}_Input");
+
+ if(!empty($input) && !empty($this->syntax) && !preg_match("/".$this->syntax."/", $input)){
+ msg_dialog::displayChecks(array(msgPool::invalid($this->display, $input, "/".$this->syntax."/")));
+ }elseif(!empty($input)){
+ $this->value[] = $input;
+ }
+ }
+ }
+
+ /*! \brief Check the value entry using the provieded syntax.
+ * @return Array Returns a list of errors
+ */
+ function check()
+ {
+ if($this->required && empty($this->value)){
+ return(array(msgPool::required($this->display)));
+ }
+ return(array());
+ }
+}
+
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_list.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_list.inc
--- /dev/null
@@ -0,0 +1,64 @@
+<?php
+
+class TemplateWidget_list extends TemplateWidget
+{
+ function __construct(&$config, $name, $value, $description,$syntax,$required,$type,$display,$values)
+ {
+ parent:: __construct($config, $name, $value, $description,$syntax,$required,$type,$display,$values);
+
+ $this->listWidget= new sortableListing($this->value);
+ $this->listWidget->setEditable(false);
+ $this->listWidget->setDeleteable(true);
+ $this->listWidget->setColspecs(array('*'));
+ $this->listWidget->setWidth("100%");
+ $this->listWidget->setHeight("70px");
+ $this->listWidget->setAcl("rwcdm");
+ }
+
+
+ function render()
+ {
+ $str = "";
+ $this->listWidget->setListData($this->value);
+ $this->listWidget->update();
+ $str .= $this->listWidget->render();
+ $str .= "<input type='text' name='{$this->postName}_Input'>";
+ $str .= "<button name='{$this->postName}_Add'>".msgPool::addButton()."</button>";
+ return($str);
+ }
+
+ function save_object()
+ {
+ $this->listWidget->save_object();
+ $action = $this->listWidget->getAction();
+ if($action['action'] == 'delete'){
+ $id = $this->listWidget->getKey($action['targets'][0]);
+ unset($this->value[$id]);
+ $this->value = array_values($this->value);
+ }
+
+ if(isset($_POST["{$this->postName}_Add"]) && isset($_POST["{$this->postName}_Input"])){
+ $input = get_post("{$this->postName}_Input");
+
+ if(!empty($input) && !empty($this->syntax) && !preg_match("/".$this->syntax."/", $input)){
+ msg_dialog::displayChecks(array(msgPool::invalid($this->display, $input, "/".$this->syntax."/")));
+ }elseif(!empty($input)){
+ $this->value[] = $input;
+ }
+ }
+ }
+
+ /*! \brief Check the value entry using the provieded syntax.
+ * @return Array Returns a list of errors
+ */
+ function check()
+ {
+ if($this->required && empty($this->value)){
+ return(array(msgPool::required($this->display)));
+ }
+ return(array());
+ }
+}
+
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_string.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_string.inc
--- /dev/null
@@ -0,0 +1,18 @@
+<?php
+
+class TemplateWidget_string extends TemplateWidget
+{
+ function render()
+ {
+ $desc = set_post($this->description);
+ $value = set_post($this->value);
+
+ $name = " name=\"{$this->postName}\" ";
+ $value = " value=\"{$value}\" ";
+ $title = (empty($this->description))?"": " title=\"{$desc}\"";
+
+ return("<input type='text' {$title} {$name} {$value }>");
+ }
+}
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_textEditor.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_textEditor.inc
--- /dev/null
@@ -0,0 +1,75 @@
+<?php
+
+class TemplateWidget_textEditor extends TemplateWidget
+{
+ protected $value = array();
+ protected $write_protect = FALSE;
+
+ function __construct(&$config, $name, $value, $description,$syntax,$required,$type,$display,$values)
+ {
+ parent:: __construct($config, $name, $value, $description,$syntax,$required,$type,$display,$values);
+
+ // Keep an eye on dangerous encodings, we may break scripts while editing.
+ $this->mb_extension = function_exists("mb_detect_encoding");
+ if($this->mb_extension){
+ $this->enc_before_edit = mb_detect_encoding($this->value);
+ if($this->enc_before_edit != "ASCII"){
+ $this->write_protect = TRUE;
+ }
+ }
+ }
+
+
+ function render()
+ {
+ $smarty = get_smarty();
+ $smarty->assign("postName", set_post($this->postName));
+ $smarty->assign("write_protect", set_post($this->write_protect));
+ $smarty->assign("value", set_post($this->value));
+ return($smarty->fetch(get_template_path("TemplateWidget_textEditor.tpl", TRUE, dirname(__FILE__))));
+ }
+
+
+ function save_object()
+ {
+ TemplateWidget::save_object();
+ if(isset($_POST['editAnyway'])) $this->write_protect = FALSE;
+
+ if(isset($_POST['ImportUpload'])){
+ if(($_FILES['ImportFile']['error']!=0)){
+ msg_dialog::display(_("Error"), msgPool::incorrectUpload(), ERROR_DIALOG);
+ }elseif(($_FILES['ImportFile']['size']==0)){
+ msg_dialog::display(_("Error"), msgPool::incorrectUpload(_("file is empty")), ERROR_DIALOG);
+ }else{
+ $str = file_get_contents($_FILES['ImportFile']['tmp_name']);
+ $this->value = $str;
+
+ // Check encoding again
+ if($this->mb_extension){
+ $this->enc_before_edit = mb_detect_encoding($this->value);
+ if($this->enc_before_edit != "ASCII"){
+ $this->write_protect = TRUE;
+ }
+ }
+ }
+ }
+ $this->enc_after_edit = mb_detect_encoding($this->value);
+ }
+
+
+ /*! \brief Check the value entry using the provieded syntax.
+ * @return Array Returns a list of errors
+ */
+ function check()
+ {
+ $msgs = TemplateWidget::check();
+ if($this->mb_extension && !$this->write_protect && $this->enc_after_edit !== $this->enc_before_edit ){
+ $msg = sprintf(_("The text encodig has changed from '%s' to '%s'. Do you really want to save?"),
+ "<i>".$this->enc_before_edit."</i>","<i>".$this->enc_after_edit."</i>");
+ $msgs[] = $msg;
+ $this->enc_before_edit = $this->enc_after_edit;
+ }
+ return($msgs);
+ }
+}
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_textarea.inc b/gosa-plugins/goto/admin/ConfigManagement/class_TemplateWidget_textarea.inc
--- /dev/null
@@ -0,0 +1,16 @@
+<?php
+
+class TemplateWidget_textarea extends TemplateWidget
+{
+ function render()
+ {
+ $title = set_post($this->description);
+ return("<textarea title=\"{$title}\"
+ style='width:100%'
+ rows=4 type='text'
+ name=\"{$this->postName}\">".set_post($this->value)."</textarea>");
+ }
+
+}
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/class_filterDeviceItems.inc b/gosa-plugins/goto/admin/ConfigManagement/class_filterDeviceItems.inc
--- /dev/null
@@ -0,0 +1,57 @@
+<?php
+
+class filterDeviceItems {
+
+ static function query($base, $scope, $filter, $attributes, $category, $objectStorage= "")
+ {
+ // Walk through the data array till we reach the correct level, then
+ // create the list of entries.
+ $data = session::get('DEVICE_ITEMS');
+ foreach($data as $id => $item){
+ if($item['base'] == $base){
+ $data = $item['children'];
+ break;;
+ }
+ }
+
+ // Prepare filter, strip out regex regex related chars, except for *
+ $filter = preg_replace('/\*/','____STAR____', $filter);
+ $filter = preg_quote($filter,'/');
+ $filter = preg_replace('/____STAR____/','.*', $filter);
+
+ // Add entries
+ $ret = array();
+ foreach($data as $item){
+ filterDeviceItems::addEntry($ret, $item, $scope == 'sub', $filter);
+ }
+ return($ret);
+ }
+
+ static function addEntry(&$ret, $item, $recursive = FALSE, $filter)
+ {
+ if(preg_match("/".$filter."/",$item['name'])){
+ $entry = array();
+ $entry['dn'] = $item['id'];
+ $entry[] = 'dn';
+ $entry['cn'] = array($item['name'], 'count' => 1);
+ $entry[] = 'cn';
+ $entry['id'] = array($item['id'], 'count' => 1);
+ $entry[] = 'id';
+ $entry['description'] = array($item['type'], 'count' => 1);
+ $entry[] = 'description';
+ $entry['objectClass'] = array($item['type'],'count' => 1);
+ $entry[] = 'objectClass';
+ $entry['count'] = 5;
+ $ret[] = $entry;
+ }
+
+ if($recursive && isset($item['children']) && count($item['children'])){
+ foreach($item['children'] as $item){
+ filterDeviceItems::addEntry($ret, $item, $recursive,$filter);
+ }
+ }
+
+ }
+}
+
+?>
diff --git a/gosa-plugins/goto/admin/ConfigManagement/failed.tpl b/gosa-plugins/goto/admin/ConfigManagement/failed.tpl
--- /dev/null
@@ -0,0 +1,12 @@
+{if $rpcError}
+ <h3>{t}Error{/t}</h3>
+ {msgPool type=rpcError p1=$error}
+ <button name='retryInit'>{t}Retry{/t}</button>
+{elseif $initFailed}
+ <h3>{t}Communication failed{/t}</h3>
+ {msgPool type=rpcError p1=$error}
+ <button name='retryInit'>{t}Retry{/t}</button>
+{elseif $invalidInstallMethod}
+ <h3>{t}Configuration error {/t}</h3>
+ {msgPool type=rpcError p1=$error}
+{/if}
diff --git a/gosa-plugins/goto/admin/ConfigManagement/puppet.tpl b/gosa-plugins/goto/admin/ConfigManagement/puppet.tpl
--- /dev/null
@@ -0,0 +1,39 @@
+{if $type == 'PuppetModule'}
+ <table width="100%">
+ <tr>
+ <td style="width:50%; vertical-align: top;">
+ <table>
+ <tr>
+ <td>{$nameName}</td>
+ <td>{$name}</td>
+ </tr>
+ <tr>
+ <td>{$descriptionName}</td>
+ <td>{$description}</td>
+ </tr>
+ <tr>
+ <td>{$versionName}</td>
+ <td>{$version}</td>
+ </tr>
+ </table>
+ </td>
+ <td style="width:50%; vertical-align: top;">
+ {$dependencyName}:<br>
+ {$dependency}
+ </td>
+ </tr>
+ </table>
+{/if}
+{if $type == 'PuppetTemplate'}
+ <table>
+ <tr>
+ <td>{$nameName}</td>
+ <td>{$name}</td>
+ </tr>
+ <tr>
+ <td>{$dataName}</td>
+ <td>{$data}</td>
+ </tr>
+ </table>
+ <input type='submit'>
+{/if}