Merge branch 'release/2.7.0' into develop

# Conflicts:
#	.make/license/gen-community-license.sh
#	setup/licenses/community-licenses.xml
This commit is contained in:
Pierre Goiffon
2020-03-27 15:20:08 +01:00
50 changed files with 577 additions and 273 deletions

View File

@@ -34,9 +34,12 @@ do
then
continue
fi
if [ "$subfolder" == "datamodels" -a $(find $l -name module*.php|wc -l) -ne 0 ]
if [ "$subfolder" == "datamodels" ]
then
continue
if [ $(find $l -name module*.php|wc -l) -ne 0 -o $(echo "$l"|grep -c "itop-portal-base") -ne 0 ]
then
continue
fi
fi
dir=$(dirname $(dirname $l))
prod=$(echo $l| sed "s|$dir/||1")

View File

@@ -0,0 +1,47 @@
<?php
/*******************************************************************************
* Tool to automate version update before release
*
* Will update version in the following files :
*
* * datamodels/2.x/.../module.*.php
* * datamodels/2.x/version.xml
* * css/css-variables.scss $version
*
* Usage :
* `php .make\release\update-versions.php "2.7.0-rc"`
*
* @since 2.7.0
******************************************************************************/
require_once (__DIR__.'/../../approot.inc.php');
require_once (__DIR__.DIRECTORY_SEPARATOR.'update.classes.inc.php');
/** @var \FileVersionUpdater[] $aFilesUpdaters */
$aFilesUpdaters = array(
new iTopVersionFileUpdater(),
new CssVariablesFileUpdater(),
new DatamodelsModulesFiles(),
);
if (count($argv) === 1)
{
echo '/!\ You must pass the new version as parameter';
exit(1);
}
$sVersionLabel = $argv[1];
if (empty($sVersionLabel))
{
echo 'Version passed as parameter is empty !';
exit(2);
}
foreach ($aFilesUpdaters as $oFileVersionUpdater)
{
$oFileVersionUpdater->UpdateAllFiles($sVersionLabel);
}

View File

@@ -0,0 +1,36 @@
<?php
/*******************************************************************************
* Tool to automate datamodel version update in XML
*
* Will update version in the following files :
*
* datamodels/2.x/.../datamodel.*.xml
*
* Usage :
* `php .make\release\update-xml.php "1.7"`
*
* @since 2.7.0
******************************************************************************/
require_once (__DIR__.'/../../approot.inc.php');
require_once (__DIR__.DIRECTORY_SEPARATOR.'update.classes.inc.php');
if (count($argv) === 1)
{
echo '/!\ You must pass the new version as parameter';
exit(1);
}
$sVersionLabel = $argv[1];
if (empty($sVersionLabel))
{
echo 'Version passed as parameter is empty !';
exit(2);
}
$oFileVersionUpdater = new DatamodelsXmlFiles();
$oFileVersionUpdater->UpdateAllFiles($sVersionLabel);

View File

@@ -0,0 +1,169 @@
<?php
/*******************************************************************************
* Classes for updater tools
*
* @see update-versions.php
* @see update-xml.php
******************************************************************************/
require_once (__DIR__.'/../../approot.inc.php');
abstract class FileVersionUpdater
{
/**
* @return string[] full path of files to modify
*/
abstract public function GetFiles();
/**
* Warnign : will consume lots of memory on larger files !
*
* @param string $sVersionLabel
* @param string $sFileContent
* @param string $sFileFullPath
*
* @return string file content with replaced values
*/
abstract public function UpdateFileContent($sVersionLabel, $sFileContent, $sFileFullPath);
public function UpdateAllFiles($sVersionLabel)
{
$aFilesToUpdate = $this->GetFiles();
$sFileUpdaterName = get_class($this);
echo "# Updater : $sFileUpdaterName\n";
foreach ($aFilesToUpdate as $sFileToUpdateFullPath)
{
try
{
$sCurrentFileContent = file_get_contents($sFileToUpdateFullPath);
$sNewFileContent = $this->UpdateFileContent($sVersionLabel, $sCurrentFileContent, $sFileToUpdateFullPath);
file_put_contents($sFileToUpdateFullPath, $sNewFileContent);
echo " - $sFileToUpdateFullPath : OK !\n";
}
catch (Exception $e)
{
echo " - $sFileToUpdateFullPath : Error :(\n";
}
}
}
}
abstract class AbstractSingleFileVersionUpdater extends FileVersionUpdater
{
private $sFileToUpdate;
public function __construct($sFileToUpdate)
{
$this->sFileToUpdate = $sFileToUpdate;
}
public function GetFiles()
{
return array(APPROOT.$this->sFileToUpdate);
}
}
class iTopVersionFileUpdater extends AbstractSingleFileVersionUpdater
{
public function __construct()
{
parent::__construct('datamodels/2.x/version.xml');
}
/**
* @inheritDoc
*/
public function UpdateFileContent($sVersionLabel, $sFileContent, $sFileFullPath)
{
return preg_replace(
'/(<version>)[^<]*(<\/version>)/',
'${1}'.$sVersionLabel.'${2}',
$sFileContent
);
}
}
class CssVariablesFileUpdater extends AbstractSingleFileVersionUpdater
{
public function __construct()
{
parent::__construct('css/css-variables.scss');
}
/**
* @inheritDoc
*/
public function UpdateFileContent($sVersionLabel, $sFileContent, $sFileFullPath)
{
return preg_replace(
'/(\$version: "v)[^"]*(";)/',
'${1}'.$sVersionLabel.'${2}',
$sFileContent
);
}
}
abstract class AbstractGlobFileVersionUpdater extends FileVersionUpdater
{
protected $sGlobPattern;
public function __construct($sGlobPattern)
{
$this->sGlobPattern = $sGlobPattern;
}
public function GetFiles()
{
return glob($this->sGlobPattern);
}
}
class DatamodelsModulesFiles extends AbstractGlobFileVersionUpdater
{
public function __construct()
{
parent::__construct(APPROOT.'datamodels/2.x/*/module.*.php');
}
/**
* @inheritDoc
*/
public function UpdateFileContent($sVersionLabel, $sFileContent, $sFileFullPath)
{
$sModulePath = realpath($sFileFullPath);
$sModuleFileName = basename($sModulePath, 1);
$sModuleName = preg_replace('/[^.]+\.([^.]+)\.php/', '$1', $sModuleFileName);
return preg_replace(
"/('$sModuleName\/)[^']+(')/",
'${1}'.$sVersionLabel.'${2}',
$sFileContent
);
}
}
class DatamodelsXmlFiles extends AbstractGlobFileVersionUpdater
{
public function __construct()
{
parent::__construct(APPROOT.'datamodels/2.x/*/datamodel.*.xml');
}
/**
* @inheritDoc
*/
public function UpdateFileContent($sVersionLabel, $sFileContent, $sFileFullPath)
{
return preg_replace(
'/(<itop_design .* version=")[^"]+(">)/',
'${1}'.$sVersionLabel.'${2}',
$sFileContent
);
}
}

View File

@@ -46,8 +46,6 @@ abstract class Dashboard
protected $aCells;
/** @var \ModelReflection $oMetaModel */
protected $oMetaModel;
/** @var bool $bCustomized */
protected $bCustomized;
/**
* Dashboard constructor.
@@ -63,7 +61,6 @@ abstract class Dashboard
$this->aCells = array();
$this->oDOMNode = null;
$this->sId = $sId;
$this->bCustomized = false;
}
/**
@@ -338,6 +335,25 @@ abstract class Dashboard
}
/**
* @return mixed
*/
public function GetId()
{
return $this->sId;
}
/**
* Return a sanitize ID for usages in XML/HTML attributes
*
* @return string
* @since 2.7.0
*/
public function GetSanitizedId()
{
return utils::Sanitize($this->GetId(), '', 'element_identifier');
}
/**
* @return string
*/
@@ -402,24 +418,6 @@ abstract class Dashboard
$this->iAutoReloadSec = max(MetaModel::GetConfig()->Get('min_reload_interval'), (int)$iAutoReloadSec);
}
/**
* @return bool
* @since 2.7.0
*/
public function GetCustomFlag()
{
return $this->bCustomized;
}
/**
* @param bool $bCustomized
* @since 2.7.0
*/
public function SetCustomFlag($bCustomized)
{
$this->bCustomized = $bCustomized;
}
/**
* @param \Dashlet $oDashlet
*/
@@ -539,7 +537,7 @@ EOF
$oPage->add('<div class="dashboard-title-line"><div class="dashboard-title">'.htmlentities(Dict::S($this->sTitle), ENT_QUOTES, 'UTF-8', false).'</div></div>');
/** @var \DashboardLayoutMultiCol $oLayout */
$oLayout = new $this->sLayoutClass;
$oLayout = new $this->sLayoutClass();
foreach($this->aCells as $iCellIdx => $aDashlets)
{
@@ -591,19 +589,21 @@ EOF
// Toolbox/palette to edit the properties of each dashlet
$oPage->add('<div class="ui-widget-content ui-corner-all"><div class="ui-widget-header ui-corner-all" style="text-align:center; padding: 2px;">'.Dict::S('UI:DashboardEdit:DashletProperties').'</div>');
/** @var \DashboardLayoutMultiCol $oLayout */
$oLayout = new $this->sLayoutClass();
$oPage->add('<div id="dashlet_properties" style="text-align:center">');
foreach($this->aCells as $aCell)
foreach($this->aCells as $iCellIdx => $aCell)
{
/** @var \Dashlet $oDashlet */
foreach($aCell as $oDashlet)
{
$sId = $oDashlet->GetID();
if ($oDashlet->IsVisible())
{
$oPage->add('<div class="dashlet_properties" id="dashlet_properties_'.$sId.'" style="display:none">');
$oPage->add('<div class="dashlet_properties" id="dashlet_properties_'.$oDashlet->GetID().'" style="display:none">');
$oForm = $oDashlet->GetForm();
$this->SetFormParams($oForm, $aExtraParams);
$oForm->RenderAsPropertySheet($oPage, false, '.itop-dashboard');
$oForm->RenderAsPropertySheet($oPage, false, '.itop-dashboard');
$oPage->add('</div>');
}
}
@@ -664,20 +664,16 @@ EOF
}
/**
* Prepare dashlet for rendering:
* - Fix ID to unique within the dashboard
* Prepare dashlet for rendering (eg. change its ID or another processing).
* Meant to be overloaded.
*
* @param \Dashlet $oDashlet
* @param array $aCoordinates Contains x, y (starting from 0)
* @param array $aCoordinates
* @param array $aExtraParams
*
* @return void
*/
protected function PrepareDashletForRendering(Dashlet $oDashlet, $aCoordinates, $aExtraParams = array())
{
$sDashletIdOrig = $oDashlet->GetID();
$sDashboardSanitizedId = utils::Sanitize($this->GetId(), '', 'element_identifier');
$sDashletIdNew = static::GetDashletUniqueId($this->GetCustomFlag(), $sDashboardSanitizedId, $aCoordinates[1], $aCoordinates[0], $sDashletIdOrig);
$oDashlet->SetID($sDashletIdNew);
}
abstract protected function PrepareDashletForRendering(Dashlet $oDashlet, $aCoordinates, $aExtraParams = array());
/**
* @param \DesignerForm $oForm
@@ -711,20 +707,20 @@ EOF
* @param string $sDashboardDivId
* @param int $iRow
* @param int $iCol
* @param string $sDashletIdOrig
* @param string $sDashletOrigId
*
* @return string
*
* @since 2.7.0 N°2735
*/
public static function GetDashletUniqueId($bIsCustomized, $sDashboardDivId, $iRow, $iCol, $sDashletIdOrig)
public static function GetDashletUniqueId($bIsCustomized, $sDashboardDivId, $iRow, $iCol, $sDashletOrigId)
{
if(strpos($sDashletIdOrig, 'IDrow') !== false)
if(strpos($sDashletOrigId, '_ID_row') !== false)
{
return $sDashletIdOrig;
return $sDashletOrigId;
}
$sDashletId = $sDashboardDivId."_IDrow$iRow-col$iCol-$sDashletIdOrig";
$sDashletId = $sDashboardDivId."_ID_row".$iRow."_col".$iCol."_".$sDashletOrigId;
if ($bIsCustomized)
{
$sDashletId = 'CUSTOM_'.$sDashletId;
@@ -732,14 +728,6 @@ EOF
return $sDashletId;
}
/**
* @return mixed
*/
public function GetId()
{
return $this->sId;
}
}
/**
@@ -751,6 +739,8 @@ class RuntimeDashboard extends Dashboard
private $sDefinitionFile = '';
/** @var null $sReloadURL */
private $sReloadURL = null;
/** @var bool $bCustomized */
protected $bCustomized;
/**
* @inheritDoc
@@ -759,6 +749,25 @@ class RuntimeDashboard extends Dashboard
{
parent::__construct($sId);
$this->oMetaModel = new ModelReflectionRuntime();
$this->bCustomized = false;
}
/**
* @return bool
* @since 2.7.0
*/
public function GetCustomFlag()
{
return $this->bCustomized;
}
/**
* @param bool $bCustomized
* @since 2.7.0
*/
public function SetCustomFlag($bCustomized)
{
$this->bCustomized = $bCustomized;
}
/**
@@ -1498,7 +1507,9 @@ JS
protected function PrepareDashletForRendering(Dashlet $oDashlet, $aCoordinates, $aExtraParams = array())
{
$sDashletIdOrig = $oDashlet->GetID();
parent::PrepareDashletForRendering($oDashlet, $aCoordinates);
$sDashboardSanitizedId = $this->GetSanitizedId();
$sDashletIdNew = static::GetDashletUniqueId($this->GetCustomFlag(), $sDashboardSanitizedId, $aCoordinates[1], $aCoordinates[0], $sDashletIdOrig);
$oDashlet->SetID($sDashletIdNew);
$this->UpdateDashletUserPrefs($oDashlet, $sDashletIdOrig, $aExtraParams);
}

View File

@@ -616,12 +616,12 @@ class DashletUnknown extends Dashlet
{
$aInfos = static::GetInfo();
$sIconUrl = utils::GetAbsoluteUrlAppRoot().$aInfos['icon'];
$sIconUrl = utils::HtmlEntities(utils::GetAbsoluteUrlAppRoot().$aInfos['icon']);
$sExplainText = ($bEditMode) ? Dict::Format('UI:DashletUnknown:RenderText:Edit', $this->GetDashletType()) : Dict::S('UI:DashletUnknown:RenderText:View');
$oPage->add('<div class="dashlet-content">');
$oPage->add('<div class="dashlet-ukn-image"><img src="'.utils::HtmlEntities($sIconUrl).'" /></div>');
$oPage->add('<div class="dashlet-ukn-image"><img src="'.$sIconUrl.'" /></div>');
$oPage->add('<div class="dashlet-ukn-text">'.$sExplainText.'</div>');
$oPage->add('</div>');
@@ -636,12 +636,12 @@ class DashletUnknown extends Dashlet
{
$aInfos = static::GetInfo();
$sIconUrl = utils::GetAbsoluteUrlAppRoot().$aInfos['icon'];
$sIconUrl = utils::HtmlEntities(utils::GetAbsoluteUrlAppRoot().$aInfos['icon']);
$sExplainText = Dict::Format('UI:DashletUnknown:RenderNoDataText:Edit', $this->GetDashletType());
$oPage->add('<div class="dashlet-content">');
$oPage->add('<div class="dashlet-ukn-image"><img src="'.utils::HtmlEntities($sIconUrl).'" /></div>');
$oPage->add('<div class="dashlet-ukn-image"><img src="'.$sIconUrl.'" /></div>');
$oPage->add('<div class="dashlet-ukn-text">'.$sExplainText.'</div>');
$oPage->add('</div>');
@@ -777,12 +777,12 @@ class DashletProxy extends DashletUnknown
{
$aInfos = static::GetInfo();
$sIconUrl = utils::GetAbsoluteUrlAppRoot().$aInfos['icon'];
$sIconUrl = utils::HtmlEntities(utils::GetAbsoluteUrlAppRoot().$aInfos['icon']);
$sExplainText = Dict::Format('UI:DashletProxy:RenderNoDataText:Edit', $this->GetDashletType());
$oPage->add('<div class="dashlet-content">');
$oPage->add('<div class="dashlet-pxy-image"><img src="'.utils::HtmlEntities($sIconUrl).'" /></div>');
$oPage->add('<div class="dashlet-pxy-image"><img src="'.$sIconUrl.'" /></div>');
$oPage->add('<div class="dashlet-pxy-text">'.$sExplainText.'</div>');
$oPage->add('</div>');
@@ -863,7 +863,7 @@ class DashletPlainText extends Dashlet
*/
public function Render($oPage, $bEditMode = false, $aExtraParams = array())
{
$sText = htmlentities($this->aProperties['text'], ENT_QUOTES, 'UTF-8');
$sText = utils::HtmlEntities($this->aProperties['text']);
$sText = str_replace(array("\r\n", "\n", "\r"), "<br/>", $sText);
$sId = 'plaintext_'.($bEditMode? 'edit_' : '').$this->sId;
@@ -919,7 +919,7 @@ class DashletObjectList extends Dashlet
$sShowMenu = $this->aProperties['menu'] ? '1' : '0';
$oPage->add('<div class="dashlet-content">');
$sHtmlTitle = htmlentities(Dict::S($sTitle), ENT_QUOTES, 'UTF-8'); // done in the itop block
$sHtmlTitle = utils::HtmlEntities(Dict::S($sTitle)); // done in the itop block
if ($sHtmlTitle != '')
{
$oPage->add('<h1>'.$sHtmlTitle.'</h1>');
@@ -965,7 +965,7 @@ class DashletObjectList extends Dashlet
$bShowMenu = $this->aProperties['menu'];
$oPage->add('<div class="dashlet-content">');
$sHtmlTitle = htmlentities($this->oModelReflection->DictString($sTitle), ENT_QUOTES, 'UTF-8'); // done in the itop block
$sHtmlTitle = utils::HtmlEntities($this->oModelReflection->DictString($sTitle)); // done in the itop block
if ($sHtmlTitle != '')
{
$oPage->add('<h1>'.$sHtmlTitle.'</h1>');
@@ -1258,7 +1258,7 @@ abstract class DashletGroupBy extends Dashlet
case 'table':
default:
$sHtmlTitle = htmlentities(Dict::S($sTitle), ENT_QUOTES, 'UTF-8'); // done in the itop block
$sHtmlTitle = utils::HtmlEntities(Dict::S($sTitle)); // done in the itop block
$sType = 'count';
$aParams = array(
'group_by' => $this->sGroupByExpr,
@@ -1695,7 +1695,7 @@ class DashletGroupByPie extends DashletGroupBy
$sBlockId = 'block_fake_'.$this->sId.($bEditMode ? '_edit' : ''); // make a unique id (edition occuring in the same DOM)
$HTMLsTitle = ($sTitle != '') ? '<h1 style="text-align:center">'.htmlentities($sTitle, ENT_QUOTES, 'UTF-8').'</h1>' : '';
$HTMLsTitle = ($sTitle != '') ? '<h1 style="text-align:center">'.utils::HtmlEntities($sTitle).'</h1>' : '';
$oPage->add("<div style=\"background-color:#fff;padding:0.25em;\">$HTMLsTitle<div id=\"$sBlockId\" style=\"background-color:#fff;\"></div></div>");
$aDisplayValues = $this->MakeSimulatedData();
@@ -1767,7 +1767,7 @@ class DashletGroupByBars extends DashletGroupBy
$sBlockId = 'block_fake_'.$this->sId.($bEditMode ? '_edit' : ''); // make a unique id (edition occuring in the same DOM)
$HTMLsTitle = ($sTitle != '') ? '<h1 style="text-align:center">'.htmlentities($sTitle, ENT_QUOTES, 'UTF-8').'</h1>' : '';
$HTMLsTitle = ($sTitle != '') ? '<h1 style="text-align:center">'.utils::HtmlEntities($sTitle).'</h1>' : '';
$oPage->add("<div style=\"background-color:#fff;padding:0.25em;\">$HTMLsTitle<div id=\"$sBlockId\" style=\"background-color:#fff;\"></div></div>");
$aDisplayValues = $this->MakeSimulatedData();
@@ -1916,16 +1916,16 @@ class DashletHeaderStatic extends Dashlet
*/
public function Render($oPage, $bEditMode = false, $aExtraParams = array())
{
$sTitle = $this->aProperties['title'];
$sTitle = utils::HtmlEntities($this->aProperties['title']);
$sIcon = $this->aProperties['icon'];
$oIconSelect = $this->oModelReflection->GetIconSelectionField('icon');
$sIconPath = $oIconSelect->MakeFileUrl($sIcon);
$sIconPath = utils::HtmlEntities($oIconSelect->MakeFileUrl($sIcon));
$oPage->add('<div class="dashlet-content">');
$oPage->add('<div class="main_header">');
$oPage->add('<img src="'.utils::HtmlEntities($sIconPath).'">');
$oPage->add('<img src="'.$sIconPath.'">');
$oPage->add('<h1>'.$this->oModelReflection->DictString($sTitle).'</h1>');
$oPage->add('</div>');
@@ -2046,14 +2046,14 @@ class DashletHeaderDynamic extends Dashlet
*/
public function Render($oPage, $bEditMode = false, $aExtraParams = array())
{
$sTitle = $this->aProperties['title'];
$sTitle = utils::HtmlEntities($this->aProperties['title']);
$sIcon = $this->aProperties['icon'];
$sSubtitle = $this->aProperties['subtitle'];
$sSubtitle = utils::HtmlEntities($this->aProperties['subtitle']);
$sQuery = $this->aProperties['query'];
$sGroupBy = $this->aProperties['group_by'];
$oIconSelect = $this->oModelReflection->GetIconSelectionField('icon');
$sIconPath = $oIconSelect->MakeFileUrl($sIcon);
$sIconPath = utils::HtmlEntities($oIconSelect->MakeFileUrl($sIcon));
$aValues = $this->GetValues();
if (count($aValues) > 0)
@@ -2081,7 +2081,7 @@ class DashletHeaderDynamic extends Dashlet
$oPage->add('<div class="dashlet-content">');
$oPage->add('<div class="main_header">');
$oPage->add('<img src="'.utils::HtmlEntities($sIconPath).'">');
$oPage->add('<img src="'.$sIconPath.'">');
if (isset($aExtraParams['query_params']))
{
@@ -2110,9 +2110,9 @@ class DashletHeaderDynamic extends Dashlet
*/
public function RenderNoData($oPage, $bEditMode = false, $aExtraParams = array())
{
$sTitle = $this->aProperties['title'];
$sTitle = utils::HtmlEntities($this->aProperties['title']);
$sIcon = $this->aProperties['icon'];
$sSubtitle = $this->aProperties['subtitle'];
$sSubtitle = utils::HtmlEntities($this->aProperties['subtitle']);
$sQuery = $this->aProperties['query'];
$sGroupBy = $this->aProperties['group_by'];
@@ -2120,12 +2120,12 @@ class DashletHeaderDynamic extends Dashlet
$sClass = $oQuery->GetClass();
$oIconSelect = $this->oModelReflection->GetIconSelectionField('icon');
$sIconPath = $oIconSelect->MakeFileUrl($sIcon);
$sIconPath = utils::HtmlEntities($oIconSelect->MakeFileUrl($sIcon));
$oPage->add('<div class="dashlet-content">');
$oPage->add('<div class="main_header">');
$oPage->add('<img src="'.utils::HtmlEntities($sIconPath).'">');
$oPage->add('<img src="'.$sIconPath.'">');
$sBlockId = 'block_fake_'.$this->sId.($bEditMode ? '_edit' : ''); // make a unique id (edition occuring in the same DOM)
@@ -2156,8 +2156,8 @@ class DashletHeaderDynamic extends Dashlet
$sTitle = $this->oModelReflection->DictString($sTitle);
$sSubtitle = $this->oModelReflection->DictFormat($sSubtitle, $iTotal);
$oPage->add('<h1>'.$sTitle.'</h1>');
$oPage->add('<a class="summary">'.$sSubtitle.'</a>');
$oPage->add('<h1>'.utils::HtmlEntities($sTitle).'</h1>');
$oPage->add('<a class="summary">'.utils::HtmlEntities($sSubtitle).'</a>');
$oPage->add('</div>');
$oPage->add('</div>');

View File

@@ -316,7 +316,7 @@ class LoginWebPage extends NiceWebPage
{
$aVars['bBadToken'] = false;
// Trash the token and change the password
$oUser->Set('reset_pwd_token', '');
$oUser->Set('reset_pwd_token', new ormPassword());
$oUser->AllowWrite(true);
$oUser->SetPassword($sNewPwd); // Does record the change into the DB
$aVars['sUrl'] = utils::GetAbsoluteUrlAppRoot();

View File

@@ -304,7 +304,7 @@ EOF
$sLinkTarget .= ' target="_blank"';
}
$sURL = '"'.$oMenu->GetHyperlink($aExtraParams).'"'.$sLinkTarget;
$sTitle = $oMenu->GetTitle();
$sTitle = utils::HtmlEntities($oMenu->GetTitle());
$sItemHtml .= "<a href={$sURL}>{$sTitle}</a>";
}
else
@@ -922,7 +922,7 @@ class OQLMenuNode extends MenuNode
$oBlock->Display($oPage, 0);
}
$oPage->add("<p class=\"page-header\">$sIcon ".Dict::S($sTitle)."</p>");
$oPage->add("<p class=\"page-header\">$sIcon ".utils::HtmlEntities(Dict::S($sTitle))."</p>");
$aParams = array_merge(array('table_id' => $sUsageId), $aExtraParams);
$oBlock = new DisplayBlock($oSearch, 'list', false /* Asynchronous */, $aParams);

View File

@@ -5701,10 +5701,14 @@ abstract class MetaModel
{
$sChangeList = implode(', ', $aChangeList);
$aCondensedQueries[] = "ALTER TABLE `$sTable` $sChangeList";
}
foreach($aPostTableAlteration as $sTable => $aChangeList)
{
$aCondensedQueries = array_merge($aCondensedQueries, $aChangeList);
// Add request right after the ALTER TABLE
if (isset($aPostTableAlteration[$sTable]))
{
foreach ($aPostTableAlteration[$sTable] as $sQuery)
{
$aCondensedQueries[] = $sQuery;
}
}
}
return array($aErrors, $aSugFix, $aCondensedQueries);

View File

@@ -17,7 +17,7 @@
*/
// Beware the version number MUST be enclosed with quotes otherwise v2.3.0 becomes v2 0.3 .0
$version: "v2.7.0-beta2";
$version: "v2.7.0";
$approot-relative: "../../../../../" !default; // relative to env-***/branding/themes/***/main.css
// Base colors

View File

@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<itop_design version="1.7">
<itop_design xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.7">
<constants>
</constants>
<classes>

View File

@@ -38,6 +38,8 @@ Dict::Add('DE DE', 'German', 'Deutsch', array(
'Class:UserLocal/Attribute:expiration/Value:force_expire+' => '',
'Class:UserLocal/Attribute:password_renewed_date' => 'Passworterneuerung',
'Class:UserLocal/Attribute:password_renewed_date+' => 'Letztes Änderungsdatum',
'Error:UserLocalPasswordValidator:UserPasswordPolicyRegex:ValidationFailed' => 'Das Passwort muss mindestens 8 Zeichen lang sein und Großbuchstaben, Kleinbuchstaben, Zahlen und Sonderzeichen enthalten.',
'UserLocal:password:expiration' => 'Die folgenden Felder benötigen eine iTop Erweiterung'
));

View File

@@ -249,6 +249,14 @@ class UserLocal extends UserInternal
$config = MetaModel::GetConfig();
}
//if the $proposedValue is an ormPassword, then it cannot be checked
//this if is even more permissive as we can only check against strings
if (!is_string($proposedValue) && !empty($proposedValue))
{
$this->m_oPasswordValidity = new UserLocalPasswordValidity(true);
return;
}
if (null == $aValidatorCollection)
{
$aValidatorCollection = MetaModel::EnumPlugins('iModuleExtension', 'UserLocalPasswordValidator');

View File

@@ -104,10 +104,6 @@ class DatabaseAnalyzer
*/
public function CheckIntegrity($aClassSelection)
{
// Getting and setting time limit are not symetric:
// www.php.net/manual/fr/function.set-time-limit.php#72305
$iPreviousTimeLimit = ini_get('max_execution_time');
$aErrorsAndFixes = array();
if (empty($aClassSelection))
@@ -125,13 +121,10 @@ class DatabaseAnalyzer
$aClassSelection = array_unique($aClassSelection);
}
foreach($aClassSelection as $sClass)
foreach ($aClassSelection as $sClass)
{
// Check uniqueness rules
if (method_exists('MetaModel', 'GetUniquenessRules'))
{
$this->CheckUniquenessRules($sClass, $aErrorsAndFixes);
}
$this->CheckUniquenessRules($sClass, $aErrorsAndFixes);
if (!MetaModel::HasTable($sClass))
{
@@ -144,13 +137,16 @@ class DatabaseAnalyzer
if (!MetaModel::IsStandaloneClass($sClass))
{
$sRootTable = MetaModel::DBGetTable($sRootClass);
$sRootKey = MetaModel::DBGetKey($sRootClass);
if (!MetaModel::IsRootClass($sClass))
{
$sRootTable = MetaModel::DBGetTable($sRootClass);
$sRootKey = MetaModel::DBGetKey($sRootClass);
$this->CheckRecordsInRootTable($sTable, $sKeyField, $sRootTable, $sRootKey, $sClass, $aErrorsAndFixes);
$this->CheckRecordsInChildTable($sRootClass, $sClass, $sRootTable, $sRootKey, $sTable, $sKeyField, $aErrorsAndFixes);
if (!MetaModel::IsLeafClass($sClass))
{
$this->CheckIntermediateFinalClass($sRootClass, $sClass, $sRootTable, $sRootKey, $sTable, $sKeyField, $aErrorsAndFixes);
}
}
}
@@ -174,10 +170,6 @@ class DatabaseAnalyzer
}
$this->CheckUsers($aErrorsAndFixes);
if (!is_null($this->iTimeLimitPerOperation))
{
set_time_limit($iPreviousTimeLimit);
}
return $aErrorsAndFixes;
}
@@ -317,6 +309,33 @@ class DatabaseAnalyzer
$this->ExecQuery($sSelWrongRecs, $sFixItRequest, Dict::Format('DBAnalyzer-Integrity-OrphanRecord', $sRootTable, $sTable), $sRootClass, $aErrorsAndFixes);
}
/**
* Check that the "finalclass" field is correct for all the classes of the hierarchy
*
* @param $sRootClass
* @param $sClass
* @param $sRootTable
* @param $sRootKey
* @param $sTable
* @param $sKeyField
* @param $aErrorsAndFixes
*
* @throws \CoreException
*/
private function CheckIntermediateFinalClass($sRootClass, $sClass, $sRootTable, $sRootKey, $sTable, $sKeyField, &$aErrorsAndFixes)
{
$sField = MetaModel::DBGetClassField($sClass);
$sRootField = MetaModel::DBGetClassField($sRootClass);
$sSelWrongRecs = <<<SQL
SELECT `$sTable`.`$sKeyField` AS id
FROM `$sTable`
JOIN `$sRootTable` ON `$sRootTable`.`$sRootKey` = `$sTable`.`$sKeyField`
WHERE `$sTable`.`$sField` != `$sRootTable`.`$sRootField`
SQL;
// Copy the finalclass of the root table
$sFixItRequest = "UPDATE `$sTable`,`$sRootTable` SET `$sTable`.`$sField` = `$sRootTable`.`$sRootField` WHERE `$sTable`.`$sKeyField` = `$sRootTable`.`$sRootKey`";
$this->ExecQuery($sSelWrongRecs, $sFixItRequest, Dict::Format('DBAnalyzer-Integrity-FinalClass', $sField, $sTable, $sRootTable), $sClass, $aErrorsAndFixes);
}
/**
* Check that any external field is pointing to an existing object
*
@@ -455,6 +474,8 @@ class DatabaseAnalyzer
}
/**
* Check user accounts without profile
*
* @param $aErrorsAndFixes
*
* @throws \CoreException
@@ -462,7 +483,6 @@ class DatabaseAnalyzer
*/
private function CheckUsers(&$aErrorsAndFixes)
{
// Check user accounts without profile
$sUserTable = MetaModel::DBGetTable('User');
$sLinkTable = MetaModel::DBGetTable('URP_UserProfile');
$sSelect = "SELECT DISTINCT u.id AS id, u.`login` AS value";

View File

@@ -52,6 +52,8 @@ Dict::Add('EN US', 'English', 'English', array(
'DBAnalyzer-Integrity-InvalidValue' => 'Invalid value for %1$s (column: `%2$s.%3$s`)',
'DBAnalyzer-Integrity-UsersWithoutProfile' => 'Some user accounts have no profile at all',
'DBAnalyzer-Fetch-Count-Error' => 'Fetch count error in `%1$s`, %2$d entries fetched / %3$d counted',
'DBAnalyzer-Integrity-FinalClass' => 'Field `%2$s`.`%1$s` must have the same value than `%3$s`.`%1$s`',
'DBAnalyzer-Integrity-RootFinalClass' => 'Field `%2$s`.`%1$s` must contains a valid class',
));
// Database Info

View File

@@ -47,6 +47,8 @@ Dict::Add('FR FR', 'French', 'Français', array(
'DBAnalyzer-Integrity-InvalidValue' => 'Valeur invalide pour %1$s (colonne: `%2$s.%3$s`)',
'DBAnalyzer-Integrity-UsersWithoutProfile' => 'Certains comptes utilisateurs n\'ont aucun profile',
'DBAnalyzer-Fetch-Count-Error' => 'Erreur de récupération dans `%1$s`, %2$d enregistrements récupérés / %3$d comptés',
'DBAnalyzer-Integrity-FinalClass' => 'Le champ `%2$s`.`%1$s` doit avoir la même valeur que `%3$s`.`%1$s`',
'DBAnalyzer-Integrity-RootFinalClass' => 'Le champ `%2$s`.`%1$s` doit contenir une classe valide',
));
// Database Info

View File

@@ -62,6 +62,7 @@ Dict::Add('DE DE', 'German', 'Deutsch', array(
'Class:Attachment/Attribute:contents+' => '',
));
Dict::Add('DE DE', 'German', 'Deutsch', array(
'Attachments:File:Thumbnail' => 'Icon',
'Attachments:File:Name' => 'Dateiname',
@@ -81,4 +82,4 @@ Dict::Add('DE DE', 'German', 'Deutsch', array(
'Class:Attachment/Attribute:user_id+' => '',
'Class:Attachment/Attribute:contact_id' => 'Kontakt ID',
'Class:Attachment/Attribute:contact_id+' => '',
));
));

View File

@@ -1890,7 +1890,7 @@ Dict::Add('IT IT', 'Italian', 'Italiano', array(
'Server:otherinfo' => 'Other information~~',
'Server:power' => 'Power supply~~',
'Person:info' => 'General information~~',
'UserLocal:info' => 'General information~~',
'UserLocal:info' => 'General information~~',
'Person:personal_info' => 'Personal information~~',
'Person:notifiy' => 'Notification~~',
'Class:Subnet/Tab:IPUsage' => 'Utilizzo IP',

View File

@@ -1902,7 +1902,7 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'Server:otherinfo' => 'Andere informatie',
'Server:power' => 'Stroomtoevoer',
'Person:info' => 'Globale informatie',
'UserLocal:info' => 'Globale informatie~~',
'UserLocal:info' => 'Globale informatie',
'Person:personal_info' => 'Persoonlijke informatie',
'Person:notifiy' => 'Notificeer',
'Class:Subnet/Tab:IPUsage' => 'IP-gebruik',

View File

@@ -20,28 +20,29 @@
* You should have received a copy of the GNU Affero General Public License
* along with iTop. If not, see <http://www.gnu.org/licenses/>
*/
Dict::Add('DE DE', 'German', 'Deutsch', array(
'iTopUpdate:UI:PageTitle' => 'Anwendungsupgrade',
'itop-core-update:UI:SelectUpdateFile' => 'Upgrade-Datei hochladen',
'itop-core-update:UI:ConfirmUpdate' => 'Confirm Upgrade',
'itop-core-update:UI:UpdateCoreFiles' => 'Upgrade der iTop-Core-Dateien',
'iTopUpdate:UI:MaintenanceModeActive' => 'Die Anwendung läuft im Wartungsmodus, Benutzerzugriffe sind nicht möglich. Führen sie erneut ein Setup oder Restore der Anwendung aus, um in den normalen Betriebsmodus zurückzukehren.',
'itop-core-update:UI:UpdateDone' => 'Upgrade abgeschlossen',
'iTopUpdate:UI:MaintenanceModeActive' => 'Die Anwendung läuft im Wartungsmodus, Benutzerzugriffe sind nicht möglich. Führen sie erneut ein Setup oder Restore der Anwendung aus, um in den normalen Betriebsmodus zurückzukehren.',
'itop-core-update:UI:UpdateDone' => 'Upgrade abgeschlossen',
'itop-core-update/Operation:SelectUpdateFile/Title' => 'Upgrade',
'itop-core-update/Operation:ConfirmUpdate/Title' => 'Upgrade bestätigen',
'itop-core-update/Operation:UpdateCoreFiles/Title' => 'Anwendungsupgrade',
'itop-core-update/Operation:SelectUpdateFile/Title' => 'Upgrade',
'itop-core-update/Operation:ConfirmUpdate/Title' => 'Upgrade bestätigen',
'itop-core-update/Operation:UpdateCoreFiles/Title' => 'Anwendungsupgrade',
'itop-core-update/Operation:UpdateDone/Title' => 'Application Upgrade Done~~',
'iTopUpdate:UI:SelectUpdateFile' => 'Upgrade-Datei hochladen',
'iTopUpdate:UI:CheckUpdate' => 'Upgrade-Datei überprüfen',
'iTopUpdate:UI:ConfirmInstallFile' => 'Installation von %1$s',
'iTopUpdate:UI:DoUpdate' => 'Upgrade',
'iTopUpdate:UI:CurrentVersion' => 'Installierte Version',
'iTopUpdate:UI:NewVersion' => 'Newly installed version~~',
'iTopUpdate:UI:Back' => 'Zurück',
'iTopUpdate:UI:Cancel' => 'Abbrechen',
'iTopUpdate:UI:Continue' => 'Weiter',
'iTopUpdate:UI:RunSetup' => 'Setuplauf',
'iTopUpdate:UI:RunSetup' => 'Setuplauf',
'iTopUpdate:UI:WithDBBackup' => 'Datenbankbackup',
'iTopUpdate:UI:WithFilesBackup' => 'Backup der Anwendungsdateien',
'iTopUpdate:UI:WithoutBackup' => 'Kein geplantes Backup',
@@ -49,7 +50,7 @@ Dict::Add('DE DE', 'German', 'Deutsch', array(
'iTopUpdate:UI:DoFilesArchive' => 'Anwendungsdateien archivieren',
'iTopUpdate:UI:UploadArchive' => 'Archivpaket hochladen',
'iTopUpdate:UI:ServerFile' => 'Pfad zu Archivpaket, dass bereits auf dem Server liegt',
'iTopUpdate:UI:WarningReadOnlyDuringUpdate' => 'Während des Upgrades läuft die Anwendung im read-only Modus',
'iTopUpdate:UI:WarningReadOnlyDuringUpdate' => 'Während des Upgrades läuft die Anwendung im read-only Modus',
'iTopUpdate:UI:Status' => 'Status',
'iTopUpdate:UI:Action' => 'Update',
@@ -80,9 +81,9 @@ Dict::Add('DE DE', 'German', 'Deutsch', array(
'iTopUpdate:UI:SetupMessage:Backup' => 'Datenbankbackup',
'iTopUpdate:UI:SetupMessage:FilesArchive' => 'Archivierung der Anwendungsdaten',
'iTopUpdate:UI:SetupMessage:CopyFiles' => 'Kopieren neuer Dateien',
'iTopUpdate:UI:SetupMessage:CheckCompile' => 'Prüfung des Anwendungsupgrades',
'iTopUpdate:UI:SetupMessage:Compile' => 'Upgrade von Anwendung und Datenbank',
'iTopUpdate:UI:SetupMessage:UpdateDatabase' => 'Upgrade Datenbank',
'iTopUpdate:UI:SetupMessage:CheckCompile' => 'Prüfung des Anwendungsupgrades',
'iTopUpdate:UI:SetupMessage:Compile' => 'Upgrade von Anwendung und Datenbank',
'iTopUpdate:UI:SetupMessage:UpdateDatabase' => 'Upgrade Datenbank',
'iTopUpdate:UI:SetupMessage:ExitMaintenance' => 'Wartungsmodus deaktivert',
'iTopUpdate:UI:SetupMessage:UpdateDone' => 'Upgrade abgeschlossen',

View File

@@ -39,8 +39,8 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'iTopUpdate:UI:CheckUpdate' => 'Verifieer upgrade-bestand',
'iTopUpdate:UI:ConfirmInstallFile' => 'Er zal een upgrade uitgevoerd worden met %1$s',
'iTopUpdate:UI:DoUpdate' => 'Upgrade',
'iTopUpdate:UI:CurrentVersion' => 'Versienummer huidige installatie',
'iTopUpdate:UI:NewVersion' => 'Newly installed version~~',
'iTopUpdate:UI:CurrentVersion' => 'Huidige versie',
'iTopUpdate:UI:NewVersion' => 'Nieuwe versie',
'iTopUpdate:UI:Back' => 'Vorige',
'iTopUpdate:UI:Cancel' => 'Annuleer',
'iTopUpdate:UI:Continue' => 'Volgende',
@@ -83,7 +83,7 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'iTopUpdate:UI:SetupMessage:Backup' => 'Maken van backup database',
'iTopUpdate:UI:SetupMessage:FilesArchive' => 'Archiveren van de toepassingsbestanden',
'iTopUpdate:UI:SetupMessage:CopyFiles' => 'Kopiëren van nieuwe versies van bestanden',
'iTopUpdate:UI:SetupMessage:CheckCompile' => 'Check application upgrade~~',
'iTopUpdate:UI:SetupMessage:CheckCompile' => 'Controleren van de upgrade van de toepassing',
'iTopUpdate:UI:SetupMessage:Compile' => 'Upgraden van toepassing en database',
'iTopUpdate:UI:SetupMessage:UpdateDatabase' => 'Upgraden van database',
'iTopUpdate:UI:SetupMessage:ExitMaintenance' => 'Deactiveren van onderhoudsmode',

View File

@@ -1,3 +1,3 @@
<?xml version="1.0" encoding="UTF-8"?>
<itop_design version="1.7">
<itop_design xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.7">
</itop_design>

View File

@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<itop_design version="1.6">
<itop_design xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.7">
<classes>
<class id="Ticket">
<methods>

View File

@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<itop_design version="1.7">
<itop_design xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.7">
<constants>
</constants>
<classes>

View File

@@ -16,7 +16,6 @@
*
* You should have received a copy of the GNU Affero General Public License
*/
// Portal
Dict::Add('DE DE', 'German', 'Deutsch', array(
'Page:DefaultTitle' => '%1$s - Benutzer Portal',
@@ -126,7 +125,7 @@ Dict::Add('DE DE', 'German', 'Deutsch', array(
'Brick:Portal:Object:Form:View:Title' => '%1$s : %2$s',
'Brick:Portal:Object:Form:Stimulus:Title' => 'Bitte folgende Informationen eintragen:',
'Brick:Portal:Object:Form:Message:Saved' => 'gespeichert',
'Brick:Portal:Object:Form:Message:ObjectSaved' => '%1$s gespeichert',
'Brick:Portal:Object:Form:Message:ObjectSaved' => '%1$s gespeichert',
'Brick:Portal:Object:Search:Regular:Title' => 'Select %1$s (%2$s)',
'Brick:Portal:Object:Search:Hierarchy:Title' => 'Select %1$s (%2$s)',
'Brick:Portal:Object:Copy:TextToCopy' => '%1$s: %2$s',

View File

@@ -80,8 +80,6 @@ class ObjectFormManager extends FormManager
protected $aFormProperties;
/** @var array $aCallbackUrls */
protected $aCallbackUrls = array();
/** @var boolean $bIsSubmittable */
protected $bIsSubmittable = true;
/**
* Creates an instance of \Combodo\iTop\Portal\Form\ObjectFormManager from JSON data that must contain at least :
@@ -222,29 +220,7 @@ class ObjectFormManager extends FormManager
return $this;
}
/**
*
* @return string
*/
public function GetIsSubmittable()
{
return $this->bIsSubmittable;
}
/**
*
* @param boolean $bIsSubmittable
*
* @return $this
*/
public function SetIsSubmittable($bIsSubmittable)
{
$this->bIsSubmittable = $bIsSubmittable;
return $this;
}
/**
*
* @return string
@@ -663,8 +639,7 @@ class ObjectFormManager extends FormManager
// Failsafe for AttributeType that would not have MakeFormField and therefore could not be used in a form
if ($oField !== null)
{
// If a form is in edit mode and can't be submitted to update an object (only transitions available), we have no reason to allow fields to be editable
if ($this->sMode !== static::ENUM_MODE_VIEW && $this->GetIsSubmittable())
if ($this->sMode !== static::ENUM_MODE_VIEW)
{
// Field dependencies
$aFieldDependencies = $oAttDef->GetPrerequisiteAttributes();

View File

@@ -277,8 +277,7 @@ class ObjectFormHandlerHelper
->SetMode($sMode)
->SetActionRulesToken($sActionRulesToken)
->SetRenderer($oFormRenderer)
->SetFormProperties($aFormProperties)
->SetIsSubmittable(isset($aFormData['buttons']['submit']) || ($sMode === self::ENUM_MODE_CREATE));
->SetFormProperties($aFormProperties);
$oFormManager->Build();

View File

@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<itop_design version="1.7">
<itop_design xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.7">
<portals>
<portal id="itop-portal" _delta="define"><!-- ID must match module_design[id] -->
<url>pages/exec.php?exec_module=itop-portal-base&amp;exec_page=index.php&amp;portal_id=itop-portal</url><!-- portal_id must match module_design[id] -->

View File

@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<itop_design version="1.6">
<itop_design xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.7">
<classes/>
<user_rights>
<groups>

View File

@@ -1,4 +1,4 @@
<?xml version="1.0" encoding="UTF-8"?>
<information>
<version>2.7.0-beta2</version>
<version>2.7.0</version>
</information>

View File

@@ -544,6 +544,8 @@ Dict::Add('CS CZ', 'Czech', 'Čeština', array(
'Class:Trigger/Attribute:action_list+' => 'Akce prováděné, když je aktivován trigger',
'Class:Trigger/Attribute:finalclass' => 'Typ',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -542,6 +542,8 @@ Dict::Add('DA DA', 'Danish', 'Dansk', array(
'Class:Trigger/Attribute:action_list+' => '',
'Class:Trigger/Attribute:finalclass' => 'Type',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -202,7 +202,7 @@ Operatoren:<br/>
'Core:AttributeTag' => 'Tags',
'Core:AttributeTag+' => 'Tags',
'Core:Context=REST/JSON' => 'REST',
'Core:Context=Synchro' => 'Synchro',
'Core:Context=Setup' => 'Setup',
@@ -541,6 +541,8 @@ Dict::Add('DE DE', 'German', 'Deutsch', array(
'Class:Trigger/Attribute:action_list+' => 'Aktionen, die ausgeführt werden, wenn der Trigger aktiviert ist',
'Class:Trigger/Attribute:finalclass' => 'Typ',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -804,12 +804,12 @@ Dict::Add('EN US', 'English', 'English', array(
'UI:Delete:ConfirmDeletionOf_Name' => 'Deletion of %1$s',
'UI:Delete:ConfirmDeletionOf_Count_ObjectsOf_Class' => 'Deletion of %1$d objects of class %2$s',
'UI:Delete:CannotDeleteBecause' => 'Could not be deleted: %1$s',
'UI:Delete:ShouldBeDeletedAtomaticallyButNotPossible' => 'Should be automaticaly deleted, but this is not feasible: %1$s',
'UI:Delete:ShouldBeDeletedAtomaticallyButNotPossible' => 'Should be automatically deleted, but this is not feasible: %1$s',
'UI:Delete:MustBeDeletedManuallyButNotPossible' => 'Must be deleted manually, but this is not feasible: %1$s',
'UI:Delete:WillBeDeletedAutomatically' => 'Will be automaticaly deleted',
'UI:Delete:WillBeDeletedAutomatically' => 'Will be automatically deleted',
'UI:Delete:MustBeDeletedManually' => 'Must be deleted manually',
'UI:Delete:CannotUpdateBecause_Issue' => 'Should be automatically updated, but: %1$s',
'UI:Delete:WillAutomaticallyUpdate_Fields' => 'will be automaticaly updated (reset: %1$s)',
'UI:Delete:WillAutomaticallyUpdate_Fields' => 'will be automatically updated (reset: %1$s)',
'UI:Delete:Count_Objects/LinksReferencing_Object' => '%1$d objects/links are referencing %2$s',
'UI:Delete:Count_Objects/LinksReferencingTheObjects' => '%1$d objects/links are referencing some of the objects to be deleted',
'UI:Delete:ReferencesMustBeDeletedToEnsureIntegrity' => 'To ensure Database integrity, any reference should be further eliminated',

View File

@@ -542,6 +542,8 @@ Dict::Add('ES CR', 'Spanish', 'Español, Castellaño', array(
'Class:Trigger/Attribute:action_list+' => 'Acciones realizadas cuando se activó el disparador',
'Class:Trigger/Attribute:finalclass' => 'Clase',
'Class:Trigger/Attribute:finalclass+' => 'Clase',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -540,6 +540,8 @@ Dict::Add('HU HU', 'Hungarian', 'Magyar', array(
'Class:Trigger/Attribute:action_list+' => '',
'Class:Trigger/Attribute:finalclass' => 'Típus',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -542,6 +542,8 @@ Dict::Add('IT IT', 'Italian', 'Italiano', array(
'Class:Trigger/Attribute:action_list+' => 'Azioni eseguite quando il trigger viene attivato ',
'Class:Trigger/Attribute:finalclass' => 'Tipo',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -540,6 +540,8 @@ Dict::Add('JA JP', 'Japanese', '日本語', array(
'Class:Trigger/Attribute:action_list+' => 'トリガーが発行された場合に動作するアクション',
'Class:Trigger/Attribute:finalclass' => 'タイプ',
'Class:Trigger/Attribute:finalclass+' => 'タイプ',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -210,12 +210,12 @@ Operators:<br/>
'Core:AttributeTag' => 'Tags',
'Core:AttributeTag+' => 'Tags',
'Core:Context=REST/JSON' => 'REST~~',
'Core:Context=Synchro' => 'Synchro~~',
'Core:Context=Setup' => 'Setup~~',
'Core:Context=GUI:Console' => 'Console~~',
'Core:Context=CRON' => 'CRON~~',
'Core:Context=GUI:Portal' => 'Portal~~',
'Core:Context=REST/JSON' => 'REST',
'Core:Context=Synchro' => 'Synchro',
'Core:Context=Setup' => 'Setup',
'Core:Context=GUI:Console' => 'Console',
'Core:Context=CRON' => 'CRON',
'Core:Context=GUI:Portal' => 'Portaal',
));
@@ -548,6 +548,8 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'Class:Trigger/Attribute:action_list+' => 'Acties uitgevoerd nadat de trigger is geactiveerd',
'Class:Trigger/Attribute:finalclass' => 'Type',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -349,14 +349,14 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'BooleanLabel:yes' => 'Ja',
'BooleanLabel:no' => 'Nee',
'UI:Login:Title' => 'Aanmelden in '.ITOP_APPLICATION_SHORT,
'UI:Login:Title' => 'Aanmelden in ITOP_APPLICATION_SHORT',
'Menu:WelcomeMenu' => 'Welkom', // Duplicated into itop-welcome-itil (will be removed from here...)
'Menu:WelcomeMenu+' => 'Welkom in '.ITOP_APPLICATION_SHORT, // Duplicated into itop-welcome-itil (will be removed from here...)
'Menu:WelcomeMenu+' => 'Welkom in ITOP_APPLICATION_SHORT', // Duplicated into itop-welcome-itil (will be removed from here...)
'Menu:WelcomeMenuPage' => 'Welkom', // Duplicated into itop-welcome-itil (will be removed from here...)
'Menu:WelcomeMenuPage+' => 'Welkom in '.ITOP_APPLICATION_SHORT, // Duplicated into itop-welcome-itil (will be removed from here...)
'UI:WelcomeMenu:Title' => 'Welkom in '.ITOP_APPLICATION_SHORT,
'Menu:WelcomeMenuPage+' => 'Welkom in ITOP_APPLICATION_SHORT', // Duplicated into itop-welcome-itil (will be removed from here...)
'UI:WelcomeMenu:Title' => 'Welkom in ITOP_APPLICATION_SHORT',
'UI:WelcomeMenu:LeftBlock' => '<p>'.ITOP_APPLICATION_SHORT.' is een compleet en open source portaal voor IT-operaties.</p>
'UI:WelcomeMenu:LeftBlock' => '<p>ITOP_APPLICATION_SHORT is een compleet en open source portaal voor IT-operaties.</p>
<ul>Op maat van jouw IT-omgeving:
<li>Complete CMDB (Configuration Management Database) voor het documenteren en beheren van de IT-inventaris.</li>
<li>Incident Management-module voor het vinden van en communiceren over alle problemen die optreden .</li>
@@ -367,14 +367,14 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
</ul>
<p>Alle modules kunnen volledig onafhankelijk van elkaar worden opgezet, stap voor stap.</p>',
'UI:WelcomeMenu:RightBlock' => '<p>'.ITOP_APPLICATION_SHORT.' is gericht op serviceproviders. Het zorgt ervoor dat IT-engineers gemakkelijk meerdere klanten of organisaties kunnen beheren.
<ul>'.ITOP_APPLICATION_SHORT.' zorgt dankzij een uitgebreide set van bedrijfsprocessen voor een reeks voordelen:
'UI:WelcomeMenu:RightBlock' => '<p>ITOP_APPLICATION_SHORT is gericht op serviceproviders. Het zorgt ervoor dat IT-engineers gemakkelijk meerdere klanten of organisaties kunnen beheren.
<ul>ITOP_APPLICATION_SHORT zorgt dankzij een uitgebreide set van bedrijfsprocessen voor een reeks voordelen:
<li>De efficientië van het IT-management versterkt.</li>
<li>De prestaties van IT-operaties verbetert.</li>
<li>De klanttevredenheid verhoogt en leidinggevenden inzicht biedt in hun bedrijfsperformantie.</li>
</ul>
</p>
<p>'.ITOP_APPLICATION_SHORT.' is klaar om geïntegreerd te worden met jouw huidige infrastructuur rond IT-management.</p>
<p>ITOP_APPLICATION_SHORT is klaar om geïntegreerd te worden met jouw huidige infrastructuur rond IT-management.</p>
<p>
<ul>De adoptie van dit IT-operationele portaal zal je helpen met:
<li>Het beter beheren van een steeds complexere IT-omgeving.</li>
@@ -438,7 +438,7 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:Error:IncorrectLinkDefinition_LinkedClass_Class' => 'Incorrecte linkdefinitie: de klasse %1$s om objecten te beheren werd niet gevonden als externe sleutel (key) in de klasse %2$s',
'UI:Error:Object_Class_Id_NotFound' => 'Object: %1$s:%2$d niet gevonden',
'UI:Error:WizardCircularReferenceInDependencies' => 'Fout: cirkelverwijzing in de afhankelijke variabelen tussen de velden. Controleer het datamodel.',
'UI:Error:UploadedFileTooBig' => 'Het geüploade bestand is te groot. De maximale grootte is %1$s. Contacteer jouw '.ITOP_APPLICATION_SHORT.'-beheerder om deze limiet aan te passen. (Controleer de PHP-configuratie voor "upload_max_filesize" en "post_max_size" op de server).',
'UI:Error:UploadedFileTooBig' => 'Het geüploade bestand is te groot. De maximale grootte is %1$s. Contacteer jouw ITOP_APPLICATION_SHORT-beheerder om deze limiet aan te passen. (Controleer de PHP-configuratie voor "upload_max_filesize" en "post_max_size" op de server).',
'UI:Error:UploadedFileTruncated.' => 'Het geüploade bestand is ingekort!',
'UI:Error:NoTmpDir' => 'De tijdelijke opslagruimte is niet gedefinieerd.',
'UI:Error:CannotWriteToTmp_Dir' => 'Niet mogelijk om het tijdelijke bestand naar een tijdelijke map weg te schrijven. upload_tmp_dir = "%1$s".',
@@ -520,14 +520,14 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:SearchValue:CheckAll' => 'Vink alles aan',
'UI:SearchValue:UncheckAll' => 'Vink alles uit',
'UI:SelectOne' => '-- selecteer --',
'UI:Login:Welcome' => 'Welkom in '.ITOP_APPLICATION_SHORT.'!',
'UI:Login:Welcome' => 'Welkom in ITOP_APPLICATION_SHORT!',
'UI:Login:IncorrectLoginPassword' => 'Ongeldige gebruikersnaam of wachtwoord, probeer opnieuw.',
'UI:Login:IdentifyYourself' => 'Identificeer jezelf voordat je verder gaat',
'UI:Login:UserNamePrompt' => 'Gebruikersnaam',
'UI:Login:PasswordPrompt' => 'Wachtwoord',
'UI:Login:ForgotPwd' => 'Wachtwoord vergeten?',
'UI:Login:ForgotPwdForm' => 'Wachtwoord vergeten',
'UI:Login:ForgotPwdForm+' => ITOP_APPLICATION_SHORT.' kan je een e-mail sturen waarin de instructies voor het resetten van jouw account staan.',
'UI:Login:ForgotPwdForm+' => 'ITOP_APPLICATION_SHORT kan je een e-mail sturen waarin de instructies voor het resetten van jouw account staan.',
'UI:Login:ResetPassword' => 'Stuur nu!',
'UI:Login:ResetPwdFailed' => 'E-mail sturen mislukt: %1$s',
'UI:Login:SeparatorOr' => 'Of',
@@ -540,8 +540,8 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:ResetPwd-Error-NoEmail' => 'Er ontbreekt een e-mailadres. Neem contact op met jouw beheerder.',
'UI:ResetPwd-Error-Send' => 'Er is een technisch probleem bij het verzenden van de e-mail. Neem contact op met jouw beheerder.',
'UI:ResetPwd-EmailSent' => 'Kijk in jouw mailbox (eventueel bij ongewenste mail) en volg de instructies...',
'UI:ResetPwd-EmailSubject' => 'Reset jouw '.ITOP_APPLICATION_SHORT.'-wachtwoord',
'UI:ResetPwd-EmailBody' => '<body><p>Je hebt een reset van jouw '.ITOP_APPLICATION_SHORT.'-wachtwoord aangevraagd.</p><p>Klik op deze link (eenmalig te gebruiken) om <a href="%1$s">een nieuw wachtwoord in te voeren</a></p>.',
'UI:ResetPwd-EmailSubject' => 'Reset jouw ITOP_APPLICATION_SHORT-wachtwoord',
'UI:ResetPwd-EmailBody' => '<body><p>Je hebt een reset van jouw ITOP_APPLICATION_SHORT-wachtwoord aangevraagd.</p><p>Klik op deze link (eenmalig te gebruiken) om <a href="%1$s">een nieuw wachtwoord in te voeren</a></p>.',
'UI:ResetPwd-Title' => 'Reset wachtwoord',
'UI:ResetPwd-Error-InvalidToken' => 'Sorry. Jouw wachtwoord is al gereset, of je hebt al meerdere e-mails ontvangen. Zorg ervoor dat je de link in de laatst ontvangen e-mail gebruikt.',
@@ -549,24 +549,24 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:ResetPwd-Ready' => 'Het wachtwoord is veranderd',
'UI:ResetPwd-Login' => 'Klik hier om in te loggen',
'UI:Login:About' => ITOP_APPLICATION,
'UI:Login:About' => 'ITOP_APPLICATION',
'UI:Login:ChangeYourPassword' => 'Verander jouw wachtwoord',
'UI:Login:OldPasswordPrompt' => 'Oud wachtwoord',
'UI:Login:NewPasswordPrompt' => 'Nieuw wachtwoord',
'UI:Login:RetypeNewPasswordPrompt' => 'Herhaal nieuwe wachtwoord',
'UI:Login:IncorrectOldPassword' => 'Fout: het oude wachtwoord is incorrect',
'UI:LogOffMenu' => 'Log uit',
'UI:LogOff:ThankYou' => 'Bedankt voor het gebruiken van '.ITOP_APPLICATION,
'UI:LogOff:ThankYou' => 'Bedankt voor het gebruiken van ITOP_APPLICATION',
'UI:LogOff:ClickHereToLoginAgain' => 'Klik hier om in te loggen',
'UI:ChangePwdMenu' => 'Verander wachtwoord',
'UI:Login:PasswordChanged' => 'Wachtwoord met succes aangepast',
'UI:AccessRO-All' => ITOP_APPLICATION.' is alleen-lezen',
'UI:AccessRO-Users' => ITOP_APPLICATION.' is alleen-lezen voor eindgebruikers',
'UI:AccessRO-All' => 'ITOP_APPLICATION is alleen-lezen',
'UI:AccessRO-Users' => 'ITOP_APPLICATION is alleen-lezen voor eindgebruikers',
'UI:ApplicationEnvironment' => 'Omgeving van de applicatie: %1$s',
'UI:Login:RetypePwdDoesNotMatch' => 'Het nieuwe wachtwoord en de herhaling van het nieuwe wachtwoord komen niet overeen',
'UI:Button:Login' => 'Ga naar '.ITOP_APPLICATION,
'UI:Login:Error:AccessRestricted' => 'Geen toegang tot '.ITOP_APPLICATION_SHORT.'. Neem contact op met een '.ITOP_APPLICATION_SHORT.'-beheerder.',
'UI:Login:Error:AccessAdmin' => 'Alleen toegankelijk voor mensen met beheerdersrechten. Neem contact op met een '.ITOP_APPLICATION_SHORT.'-beheerder',
'UI:Button:Login' => 'Ga naar ITOP_APPLICATION',
'UI:Login:Error:AccessRestricted' => 'Geen toegang tot ITOP_APPLICATION_SHORT. Neem contact op met een ITOP_APPLICATION_SHORT-beheerder.',
'UI:Login:Error:AccessAdmin' => 'Alleen toegankelijk voor mensen met beheerdersrechten. Neem contact op met een ITOP_APPLICATION_SHORT-beheerder',
'UI:Login:Error:WrongOrganizationName' => 'Onbekende organisatie',
'UI:Login:Error:MultipleContactsHaveSameEmail' => 'Meerdere contacten hebben hetzelfde e-mailadres',
'UI:Login:Error:NoValidProfiles' => 'Geen geldig profiel opgegeven',
@@ -579,7 +579,7 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:CSVImport:DataLine1' => 'Dataregel 1',
'UI:CSVImport:DataLine2' => 'Dataregel 2',
'UI:CSVImport:idField' => 'id (Primaire sleutel (key))',
'UI:Title:BulkImport' => ITOP_APPLICATION_SHORT.' - Bulk import',
'UI:Title:BulkImport' => 'ITOP_APPLICATION_SHORT - Bulk import',
'UI:Title:BulkImport+' => 'CSV Import Wizard',
'UI:Title:BulkSynchro_nbItem_ofClass_class' => 'Synchronisatie van %1$d objecten van klasse "%2$s"',
'UI:CSVImport:ClassesSelectOne' => '-- selecteer een --',
@@ -676,9 +676,9 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:CSVExport:AdvancedMode' => 'Geavanceerde mode',
'UI:CSVExport:AdvancedMode+' => 'In geavanceerde mode worden verscheidene kolommen toegevoegd aan de export: id van het object, id van de externe codes en hun reconciliation-attributen.',
'UI:CSVExport:LostChars' => 'Tekstcoderingsprobleem',
'UI:CSVExport:LostChars+' => 'Het gedownloade bestand zal worden gecodeerd in %1$s. '.ITOP_APPLICATION_SHORT.' heeft een aantal karakters gedetecteerd die niet compatibel zijn met dit formaat. Deze karakters zullen worden vervangen door een ander karakter (bijvoorbeeld karakters met accent kunnen het accent verliezen), of ze zullen worden verwijderd. Je kan data kopiëren en plakken van jouw webbrowser. Ook kan je de beheerder contacteren om de codes te veranderen (Zie parameter \'csv_file_default_charset\').',
'UI:CSVExport:LostChars+' => 'Het gedownloade bestand zal worden gecodeerd in %1$s. ITOP_APPLICATION_SHORT heeft een aantal karakters gedetecteerd die niet compatibel zijn met dit formaat. Deze karakters zullen worden vervangen door een ander karakter (bijvoorbeeld karakters met accent kunnen het accent verliezen), of ze zullen worden verwijderd. Je kan data kopiëren en plakken van jouw webbrowser. Ook kan je de beheerder contacteren om de codes te veranderen (Zie parameter \'csv_file_default_charset\').',
'UI:Audit:Title' => ITOP_APPLICATION_SHORT.' - CMDB Audit',
'UI:Audit:Title' => 'ITOP_APPLICATION_SHORT - CMDB Audit',
'UI:Audit:InteractiveAudit' => 'Interactieve Audit',
'UI:Audit:HeaderAuditRule' => 'Auditregel',
'UI:Audit:HeaderNbObjects' => '# objecten',
@@ -687,7 +687,7 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:Audit:ErrorIn_Rule_Reason' => 'OQL-fout in de regel %1$s: %2$s.',
'UI:Audit:ErrorIn_Category_Reason' => 'OQL-fout in de categorie %1$s: %2$s.',
'UI:RunQuery:Title' => ITOP_APPLICATION_SHORT.' - Evaluatie van OQL-query',
'UI:RunQuery:Title' => 'ITOP_APPLICATION_SHORT - Evaluatie van OQL-query',
'UI:RunQuery:QueryExamples' => 'Voorbeelden van query\'s',
'UI:RunQuery:HeaderPurpose' => 'Doel',
'UI:RunQuery:HeaderPurpose+' => 'Uitleg over de query',
@@ -704,7 +704,7 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:RunQuery:Error' => 'Er trad een fout op tijdens het uitvoeren van deze query: %1$s',
'UI:Query:UrlForExcel' => 'URL om te gebruiken voor MS Excel-webquery\'s',
'UI:Query:UrlV1' => 'De lijst van velden is leeg gelaten. De pagina <em>export-V2.php</em> kan niet aangeroepen worden zonder deze informatie.Daarom verwijst de onderstaande link naar de oude export-pagina: <em>export.php</em>. Deze verouderde versie heeft enkele beperkingen: de lijst van geëxporteerde velden kan verschillen afhankelijk van het gekozen export-formaat en het datamodel van iTop. Als je wil dat de lijst van geëxporteerde kolommen hetzelfde blijft over lange tijd, dan moet je een waarde opgeven voor het attribuut "Velden" en de pagina <em>export-V2.php</em> gebruiken.',
'UI:Schema:Title' => ITOP_APPLICATION_SHORT.' objecten-schema',
'UI:Schema:Title' => 'ITOP_APPLICATION_SHORT objecten-schema',
'UI:Schema:CategoryMenuItem' => 'Categorie <b>%1$s</b>',
'UI:Schema:Relationships' => 'Relaties',
'UI:Schema:AbstractClass' => 'Abstracte klasse: objecten van deze klasse kunnen niet worden geïnstantieerd.',
@@ -819,9 +819,9 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:Delete:PleaseDoTheManualOperations' => 'Verricht eerst de handmatige handelingen die hierboven staan voordat je dit object verwijdert',
'UI:Delect:Confirm_Object' => 'Bevestig dat je %1$s wil verwijderen.',
'UI:Delect:Confirm_Count_ObjectsOf_Class' => 'Bevestig dat je de volgende %1$d objecten van klasse %2$s wilt verwijderen.',
'UI:WelcomeToITop' => 'Welkom in '.ITOP_APPLICATION,
'UI:DetailsPageTitle' => ITOP_APPLICATION_SHORT.' - %1$s - %2$s details',
'UI:ErrorPageTitle' => ITOP_APPLICATION_SHORT.' - Fout',
'UI:WelcomeToITop' => 'Welkom in ITOP_APPLICATION',
'UI:DetailsPageTitle' => 'ITOP_APPLICATION_SHORT - %1$s - %2$s details',
'UI:ErrorPageTitle' => 'ITOP_APPLICATION_SHORT - Fout',
'UI:ObjectDoesNotExist' => 'Sorry, dit object bestaat niet (of je bent niet gemachtigd het te bekijken).',
'UI:ObjectArchived' => 'Dit object werd gearchiveerd. Gelieve de Archief-mode in te schakelen of je beheerder te contacteren.',
'Tag:Archived' => 'Gearchiveerd',
@@ -831,7 +831,7 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'Tag:Synchronized' => 'Gesynchroniseerd',
'ObjectRef:Archived' => 'Gearchiveerd',
'ObjectRef:Obsolete' => 'Buiten dienst',
'UI:SearchResultsPageTitle' => ITOP_APPLICATION_SHORT.' - Zoekresultaten',
'UI:SearchResultsPageTitle' => 'ITOP_APPLICATION_SHORT - Zoekresultaten',
'UI:SearchResultsTitle' => 'Zoekresultaten',
'UI:SearchResultsTitle+' => 'Volledige tekst - zoekresultaten',
'UI:Search:NoSearch' => 'Geen zoekopdracht',
@@ -841,28 +841,28 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'UI:FullTextSearchTitle_Text' => 'Resultaten voor "%1$s":',
'UI:Search:Count_ObjectsOf_Class_Found' => '%1$d object(en) van klasse %2$s gevonden.',
'UI:Search:NoObjectFound' => 'Geen object gevonden.',
'UI:ModificationPageTitle_Object_Class' => ITOP_APPLICATION_SHORT.' - %1$s - %2$s aanpassing',
'UI:ModificationPageTitle_Object_Class' => 'ITOP_APPLICATION_SHORT - %1$s - %2$s aanpassing',
'UI:ModificationTitle_Class_Object' => 'Aanpassen van %1$s: <span class="hilite">%2$s</span>',
'UI:ClonePageTitle_Object_Class' => ITOP_APPLICATION_SHORT.' - Kloon %1$s - %2$s aanpassing',
'UI:ClonePageTitle_Object_Class' => 'ITOP_APPLICATION_SHORT - Kloon %1$s - %2$s aanpassing',
'UI:CloneTitle_Class_Object' => 'Klonen van %1$s: <span class="hilite">%2$s</span>',
'UI:CreationPageTitle_Class' => ITOP_APPLICATION_SHORT.' - Nieuwe %1$s aangemaakt',
'UI:CreationPageTitle_Class' => 'ITOP_APPLICATION_SHORT - Nieuwe %1$s aangemaakt',
'UI:CreationTitle_Class' => '%1$s aanmaken',
'UI:SelectTheTypeOf_Class_ToCreate' => 'Selecteer het type %1$s dat moet worden aangemaakt:',
'UI:Class_Object_NotUpdated' => 'Geen verandering waargenomen, %1$s (%2$s) is <strong>niet</strong> aangepast.',
'UI:Class_Object_Updated' => '%1$s (%2$s) aangepast.',
'UI:BulkDeletePageTitle' => ITOP_APPLICATION_SHORT.' - Meerdere objecten verwijderen',
'UI:BulkDeletePageTitle' => 'ITOP_APPLICATION_SHORT - Meerdere objecten verwijderen',
'UI:BulkDeleteTitle' => 'Selecteer de objecten die je wilt verwijderen:',
'UI:PageTitle:ObjectCreated' => 'Object Aangemaakt.',
'UI:Title:Object_Of_Class_Created' => '%1$s - %2$s aangemaakt.',
'UI:Apply_Stimulus_On_Object_In_State_ToTarget_State' => 'Bezig met het toepassen van %1$s op object: %2$s in fase %3$s tot doelfase: %4$s.',
'UI:ObjectCouldNotBeWritten' => 'Het object kon niet geschreven worden: %1$s',
'UI:PageTitle:FatalError' => ITOP_APPLICATION_SHORT.' - Fatale Fout',
'UI:PageTitle:FatalError' => 'ITOP_APPLICATION_SHORT - Fatale Fout',
'UI:SystemIntrusion' => 'Toegang geweigerd. Je hebt een actie aangevraagd waarvoor je niet gemachtigd bent.',
'UI:FatalErrorMessage' => 'Fatale fout, '.ITOP_APPLICATION_SHORT.' kan niet doorgaan.',
'UI:FatalErrorMessage' => 'Fatale fout, ITOP_APPLICATION_SHORT kan niet doorgaan.',
'UI:Error_Details' => 'Fout: %1$s.',
'UI:PageTitle:ClassProjections' => ITOP_APPLICATION_SHORT.' gebruikersbeheer - klasse-projecties',
'UI:PageTitle:ProfileProjections' => ITOP_APPLICATION_SHORT.' gebruikersbeheer - profiel-projecties',
'UI:PageTitle:ClassProjections' => 'ITOP_APPLICATION_SHORT gebruikersbeheer - klasse-projecties',
'UI:PageTitle:ProfileProjections' => 'ITOP_APPLICATION_SHORT gebruikersbeheer - profiel-projecties',
'UI:UserManagement:Class' => 'Klasse',
'UI:UserManagement:Class+' => 'Klasse van objecten',
'UI:UserManagement:ProjectedObject' => 'Object',
@@ -963,8 +963,8 @@ Dict::Add('NL NL', 'Dutch', 'Nederlands', array(
'Menu:NotificationsMenu+' => 'Configuratie van de meldingen', // Duplicated into itop-welcome-itil (will be removed from here...)
'UI:NotificationsMenu:Title' => 'Configuratie van <span class="hilite">Meldingen</span>',
'UI:NotificationsMenu:Help' => 'Help',
'UI:NotificationsMenu:HelpContent' => '<p>In '.ITOP_APPLICATION_SHORT.' zijn de meldingen volledig aan te passen. Ze zijn gebaseerd op twee sets van objecten: <i>triggers and actions</i>.</p>
<p><i><b>Triggers</b></i> bepalen wanneer er een melding is. Er zijn verschillende triggers als onderdeel van '.ITOP_APPLICATION_SHORT.' core, maar andere kunnen door middel van uitbreidingen worden toegevoegd.
'UI:NotificationsMenu:HelpContent' => '<p>In ITOP_APPLICATION_SHORT zijn de meldingen volledig aan te passen. Ze zijn gebaseerd op twee sets van objecten: <i>triggers and actions</i>.</p>
<p><i><b>Triggers</b></i> bepalen wanneer er een melding is. Er zijn verschillende triggers als onderdeel van ITOP_APPLICATION_SHORT core, maar andere kunnen door middel van uitbreidingen worden toegevoegd.
<p>Sommige triggers worden uitgevoerd:</p>
@@ -1072,8 +1072,8 @@ Bij die koppeling wordt aan elke actie een volgorde-nummer gegeven. Dit bepaalt
'UI:RelationTooltip:Redundancy' => 'Redundantie',
'UI:RelationTooltip:ImpactedItems_N_of_M' => '# geïmpacteerde items: %1$d / %2$d',
'UI:RelationTooltip:CriticalThreshold_N_of_M' => 'Kritische drempelwaarde: %1$d / %2$d',
'Portal:Title' => ITOP_APPLICATION_SHORT.' gebruikersportaal',
'Portal:NoRequestMgmt' => 'Beste %1$s, je bent naar deze pagina doorverwezen omdat jouw account is geconfigureerd met het profiel "Portal user". Helaas is '.ITOP_APPLICATION_SHORT.' niet geïnstalleerd met de optie "Request Management". Neem contact op met jouw beheerder.',
'Portal:Title' => 'ITOP_APPLICATION_SHORT gebruikersportaal',
'Portal:NoRequestMgmt' => 'Beste %1$s, je bent naar deze pagina doorverwezen omdat jouw account is geconfigureerd met het profiel "Portal user". Helaas is ITOP_APPLICATION_SHORT niet geïnstalleerd met de optie "Request Management". Neem contact op met jouw beheerder.',
'Portal:Refresh' => 'Herlaad',
'Portal:Back' => 'Vorige',
'Portal:WelcomeUserOrg' => 'Welkom %1$s, van %2$s',
@@ -1157,7 +1157,7 @@ Bij die koppeling wordt aan elke actie een volgorde-nummer gegeven. Dit bepaalt
'UI:Favorites:ShowObsoleteData+' => 'Toon "Buiten dienst"-data in zoekresultaten en in keuzelijsten.',
'UI:NavigateAwayConfirmationMessage' => 'Bewerkingen zullen worden genegeerd.',
'UI:CancelConfirmationMessage' => 'Je zult jouw aanpassingen verliezen. Wil je toch doorgaan?',
'UI:AutoApplyConfirmationMessage' => 'Sommige veranderingen zijn nog niet doorgevoerd. Wil je dat '.ITOP_APPLICATION_SHORT.' deze meeneemt?',
'UI:AutoApplyConfirmationMessage' => 'Sommige veranderingen zijn nog niet doorgevoerd. Wil je dat ITOP_APPLICATION_SHORT deze meeneemt?',
'UI:Create_Class_InState' => 'Maak %1$s aan in deze fase: ',
'UI:OrderByHint_Values' => 'Sorteervolgorde: %1$s',
'UI:Menu:AddToDashboard' => 'Voeg toe aan dashboard...',
@@ -1221,7 +1221,7 @@ Bij die koppeling wordt aan elke actie een volgorde-nummer gegeven. Dit bepaalt
'UI:DashletUnknown:Label' => 'Onbekend',
'UI:DashletUnknown:Description' => 'Onbekende dashlet (mogelijk verwijderd)',
'UI:DashletUnknown:RenderText:View' => 'Kan deze dashlet niet weergeven.',
'UI:DashletUnknown:RenderText:Edit' => 'Kan deze dashlet niet weergeven (klasse "%1$s"). Controleer bij je '.ITOP_APPLICATION_SHORT.'-beheerder of dit nog beschikbaar is.',
'UI:DashletUnknown:RenderText:Edit' => 'Kan deze dashlet niet weergeven (klasse "%1$s"). Controleer bij je ITOP_APPLICATION_SHORT-beheerder of dit nog beschikbaar is.',
'UI:DashletUnknown:RenderNoDataText:Edit' => 'Geen voorbeeld mogelijk van deze dashlet (klasse "%1$s").',
'UI:DashletUnknown:Prop-XMLConfiguration' => 'Configuratie (getoond als ruwe XML)',
@@ -1401,8 +1401,8 @@ Bij die koppeling wordt aan elke actie een volgorde-nummer gegeven. Dit bepaalt
'UI:AddAnExisting_Class' => 'Voeg objecten van type %1$s toe...',
'UI:SelectionOf_Class' => 'Selectie van objecten van type %1$s',
'UI:AboutBox' => 'Over '.ITOP_APPLICATION_SHORT.'...',
'UI:About:Title' => 'Over '.ITOP_APPLICATION_SHORT,
'UI:AboutBox' => 'Over ITOP_APPLICATION_SHORT...',
'UI:About:Title' => 'Over ITOP_APPLICATION_SHORT',
'UI:About:DataModel' => 'Datamodel',
'UI:About:Support' => 'Support informatie',
'UI:About:Licenses' => 'Licenties',
@@ -1427,7 +1427,7 @@ Bij die koppeling wordt aan elke actie een volgorde-nummer gegeven. Dit bepaalt
'ExcelExport:PreparingExport' => 'Export aan het voorbereiden...',
'ExcelExport:Statistics' => 'Statistieken',
'portal:legacy_portal' => 'Portaal voor eindgebruikers',
'portal:backoffice' => ITOP_APPLICATION_SHORT.' Back-Office User Interface',
'portal:backoffice' => 'ITOP_APPLICATION_SHORT Back-Office User Interface',
'UI:CurrentObjectIsLockedBy_User' => 'Het object is vergrendeld omdat het momenteel aangepast wordt door %1$s.',
'UI:CurrentObjectIsLockedBy_User_Explanation' => 'Het object wordt aangepast door %1$s. Jouw wijzigingen kunnen niet opgeslagen worden omdat ze een conflict kunnen veroorzaken.',

View File

@@ -542,6 +542,8 @@ Dict::Add('PT BR', 'Brazilian', 'Brazilian', array(
'Class:Trigger/Attribute:action_list+' => 'Ações executadas quando o gatilho é ativado',
'Class:Trigger/Attribute:finalclass' => 'Tipo',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -529,6 +529,8 @@ Dict::Add('RU RU', 'Russian', 'Русский', array(
'Class:Trigger/Attribute:action_list+' => 'Действия, выполняемые при срабатывании триггера',
'Class:Trigger/Attribute:finalclass' => 'Тип',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -539,6 +539,8 @@ Dict::Add('SK SK', 'Slovak', 'Slovenčina', array(
'Class:Trigger/Attribute:action_list+' => '',
'Class:Trigger/Attribute:finalclass' => 'Typ',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -550,6 +550,8 @@ Dict::Add('TR TR', 'Turkish', 'Türkçe', array(
'Class:Trigger/Attribute:action_list+' => 'Tetiklenen işlemler',
'Class:Trigger/Attribute:finalclass' => 'Tip',
'Class:Trigger/Attribute:finalclass+' => '',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -541,6 +541,8 @@ Dict::Add('ZH CN', 'Chinese', '简体中文', array(
'Class:Trigger/Attribute:action_list+' => 'Actions performed when the trigger is activated',
'Class:Trigger/Attribute:finalclass' => '触发器子类别',
'Class:Trigger/Attribute:finalclass+' => 'Name of the final class',
'Class:Trigger/Attribute:context' => 'Context~~',
'Class:Trigger/Attribute:context+' => 'Context to allow the trigger to start~~',
));
//

View File

@@ -144,29 +144,27 @@ $(function()
}
});
},
// We need a unique dashlet id, we will get it using an ajax query
_get_dashletid_ajax: function(options, sTempDashletId)
{
var me = this;
var $container = options.container;
var oParams = this.options.new_dashletid_parameters;
oParams.dashboardid = me.options.dashboard_id;
oParams.iRow = $container.closest("tr").data("dashboard-row-index");
oParams.iCol = $container.data("dashboard-column-index");
oParams.dashletid = sTempDashletId;
$.post(this.options.new_dashletid_endpoint, oParams, function(data) {
var sFinalDashletId = data;
me.add_dashlet_prepare(options, sFinalDashletId);
});
},
add_dashlet: function(options)
{
var $container = options.container,
iNumberOfExistingDashletsInDashboard = $container.closest("table").find("div.dashlet").length,
sTempDashletId = iNumberOfExistingDashletsInDashboard+1;
var $container = options.container;
var aDashletsIds = $container.closest("table").find("div.dashlet").map(function(){
// Note:
// - At runtime a unique dashlet ID is generated (see \Dashboard::GetDashletUniqueId) to avoid JS widget collisions
// - At design time, the dashlet ID is not touched (same as in the XML datamodel)
var sDashletUniqueId = $(this).attr("id");
var sDashletIdParts = sDashletUniqueId.split('_');
var sDashletOrigId = sDashletIdParts[sDashletIdParts.length - 1];
return isNaN(sDashletOrigId) ? 0 : parseInt(sDashletOrigId);
}).get();
// Note: Use of .apply() to be compatible with IE10
var iHighestDashletOrigId = Math.max.apply(null, aDashletsIds);
this._get_dashletid_ajax(options, sTempDashletId);
this._get_dashletid_ajax(options, iHighestDashletOrigId + 1);
},
// Get the real dashlet ID from the temporary ID
_get_dashletid_ajax: function(options, sTempDashletId)
{
// Do nothing, meant for overloading
},
add_dashlet_prepare: function(options, sFinalDashletId)
{
@@ -333,6 +331,22 @@ $(function()
}
});
},
// We need a unique dashlet id, we will get it using an ajax query
_get_dashletid_ajax: function(options, sTempDashletId)
{
var me = this;
var $container = options.container;
var oParams = this.options.new_dashletid_parameters;
oParams.dashboardid = me.options.dashboard_id;
oParams.iRow = $container.closest("tr").data("dashboard-row-index");
oParams.iCol = $container.data("dashboard-column-index");
oParams.dashletid = sTempDashletId;
$.post(this.options.new_dashletid_endpoint, oParams, function(data) {
var sFinalDashletId = data;
me.add_dashlet_prepare(options, sFinalDashletId);
});
},
add_dashlet_ajax: function(options, sDashletId)
{
var oParams = this.options.new_dashlet_parameters;

View File

@@ -281,8 +281,16 @@ $(function()
},
_on_upload_error: function(data, status, e)
{
alert(e);
this.oUploadDlg.closest('.ui-dialog').find('.ui-button').button('enable');
if(data.responseText.indexOf('login-body') !== false)
{
alert('Sorry, your session has expired. In order to continue, the whole page has to be loaded again.');
this.oUploadDlg.dialog('close');
}
else
{
alert(e);
this.oUploadDlg.closest('.ui-dialog').find('.ui-button').button('enable');
}
}
});
});

View File

@@ -1197,7 +1197,7 @@ EOF
break;
case 'dashboard_editor':
$sId = utils::ReadParam('id', '', false, 'raw_data');
$sId = utils::ReadParam('id', '', false, 'element_identifier');
$aExtraParams = utils::ReadParam('extra_params', array(), false, 'raw_data');
$aExtraParams['dashboard_div_id'] = utils::Sanitize($sId, '', 'element_identifier');
$sDashboardFile = utils::ReadParam('file', '', false, 'raw_data');
@@ -1217,10 +1217,11 @@ EOF
case 'new_dashlet_id':
$sDashboardDivId = utils::ReadParam("dashboardid");
$bIsCustomized = true; // Only called at runtime when customizing a dashboard
$iRow = utils::ReadParam("iRow");
$iCol = utils::ReadParam("iCol");
$sDashletIdOrig = utils::ReadParam("dashletid");
$sFinalDashletId = Dashboard::GetDashletUniqueId(true, $sDashboardDivId, $iRow, $iCol, $sDashletIdOrig);
$sFinalDashletId = Dashboard::GetDashletUniqueId($bIsCustomized, $sDashboardDivId, $iRow, $iCol, $sDashletIdOrig);
$oPage = new ajax_page('');
$oPage->add($sFinalDashletId);
break;

View File

@@ -751,6 +751,10 @@ class iTopDesignFormat
// -- 2314 : remove "themes" nodes
$sPath = "/itop_design/branding/themes";
$this->RemoveNodeFromXPath($sPath);
// -- 2746 - remove attributes Enum Set
$sPath = "/itop_design/classes/class/class/fields/field[@xsi:type='AttributeEnumSet']";
$this->RemoveNodeFromXPath($sPath);
}
/**

View File

@@ -1936,33 +1936,6 @@ to represent the company, product, or service to which they refer.**
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
]]></text>
</license>
<license>
<product scope="datamodels">itop-portal-base/portal</product>
<author/>
<license_type>AGPLv3</license_type>
<text><![CDATA[
Copyright (c) Nils Adermann, Jordi Boggiano
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is furnished
to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
]]></text>
</license>
<license>
@@ -2777,7 +2750,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.</pre>
<license>
<product scope="lib">combodo/tcpdf</product>
<author>Nicola Asuni - Combodo</author>
<license_type>LGPL-3.0-only</license_type>
<license_type>LGPL-3.0-only</license_type>
<text><![CDATA[
**********************************************************************
* TCPDF LICENSE
@@ -2787,9 +2760,8 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.</pre>
under the terms of the GNU Lesser General Public License as
published by the Free Software Foundation, either version 3 of the
License, or (at your option) any later version.
2002-2019 Nicola Asuni - Tecnick.com LTD
2002-2019 Nicola Asuni - Tecnick.com LTD
**********************************************************************
**********************************************************************
@@ -3641,11 +3613,11 @@ Public License instead of this License. But first, please read
**********************************************************************
]]></text>
</license>
<license>
<product scope="lib">nikic/php-parser</product>
<author>Nikita Popov</author>
<license_type>BSD-3-Clause</license_type>
<text><![CDATA[
<license>
<product scope="lib">nikic/php-parser</product>
<author>Nikita Popov</author>
<license_type>BSD-3-Clause</license_type>
<text><![CDATA[
Copyright (c) 2011-2018 by Nikita Popov.
Some rights reserved.
@@ -3678,8 +3650,8 @@ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
]]></text>
</license>
<license>
</license>
<license>
<product scope="lib">paragonie/random_compat</product>
<author>Paragon Initiative Enterprises</author>
<license_type>MIT</license_type>