Merge remote-tracking branch 'origin/support/3.0' into develop

This commit is contained in:
Molkobain
2022-01-17 19:21:52 +01:00
16 changed files with 159 additions and 90 deletions

View File

@@ -4231,13 +4231,20 @@ HTML;
if (!is_null($oImage->GetData()))
{
$aSize = utils::GetImageSize($oImage->GetData());
$oImage = utils::ResizeImageToFit(
$oImage,
$aSize[0],
$aSize[1],
$oAttDef->Get('storage_max_width'),
$oAttDef->Get('storage_max_height')
);
if (is_array($aSize) && $aSize[0] > 0 && $aSize[1] > 0)
{
$oImage = utils::ResizeImageToFit(
$oImage,
$aSize[0],
$aSize[1],
$oAttDef->Get('storage_max_width'),
$oAttDef->Get('storage_max_height')
);
}
else
{
IssueLog::Warning($sClass . ':' . $this->GetKey() . '/' . $sAttCode . ': Image could not be resized. Mimetype: ' . $oImage->GetMimeType() . ', filename: ' . $oImage->GetFileName());
}
}
$aOtherData = utils::ReadPostedParam("attr_{$sFormPrefix}{$sAttCode}", null, 'raw_data');
if (is_array($aOtherData))

View File

@@ -220,16 +220,15 @@ class CSVBulkExport extends TabularBulkExport
$sFormatInput = '<input type="text" size="15" name="date_format" id="csv_custom_date_time_format" title="" value="'.htmlentities($sDateTimeFormat, ENT_QUOTES, 'UTF-8').'"/>';
$oRadioCustom = InputUIBlockFactory::MakeForInputWithLabel(Dict::Format('Core:BulkExport:DateTimeFormatCustom_Format', $sFormatInput), "csv_date_format_radio", "custom", "csv_date_time_format_custom", "radio");
$oRadioCustom->SetDescription(Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip'));
$oRadioCustom->GetInput()->SetIsChecked($sDateTimeFormat !== (string)AttributeDateTime::GetFormat());
$oRadioCustom->SetBeforeInput(false);
$oRadioCustom->GetInput()->AddCSSClass('ibo-input-checkbox');
$oFieldSetDate->AddSubBlock($oRadioCustom);
$sJSTooltip = json_encode('<div class="date_format_tooltip">'.Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip').'</div>');
$oP->add_ready_script(
<<<EOF
$('#csv_custom_date_time_format').tooltip({content: function() { return $sJSTooltip; } });
$('#form_part_csv_options').on('preview_updated', function() { FormatDatesInPreview('csv', 'csv'); });
$('#csv_date_time_format_default').on('click', function() { FormatDatesInPreview('csv', 'csv'); });
$('#csv_date_time_format_custom').on('click', function() { FormatDatesInPreview('csv', 'csv'); });

View File

@@ -111,16 +111,15 @@ class ExcelBulkExport extends TabularBulkExport
$sFormatInput = '<input type="text" size="15" name="date_format" id="excel_custom_date_time_format" title="" value="'.htmlentities($sDateTimeFormat, ENT_QUOTES, 'UTF-8').'"/>';
$oRadioCustom = InputUIBlockFactory::MakeForInputWithLabel(Dict::Format('Core:BulkExport:DateTimeFormatCustom_Format', $sFormatInput), "excel_date_format_radio", "custom", "excel_date_time_format_custom", "radio");
$oRadioCustom->SetDescription(Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip'));
$oRadioCustom->GetInput()->SetIsChecked($sDateTimeFormat !== (string)AttributeDateTime::GetFormat());
$oRadioCustom->SetBeforeInput(false);
$oRadioCustom->GetInput()->AddCSSClass('ibo-input-checkbox');
$oFieldSetDate->AddSubBlock($oRadioCustom);
$sJSTooltip = json_encode('<div class="date_format_tooltip">'.Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip').'</div>');
$oP->add_ready_script(
<<<EOF
$('#excel_custom_date_time_format').tooltip({content: function() { return $sJSTooltip; } });
$('#form_part_xlsx_options').on('preview_updated', function() { FormatDatesInPreview('excel', 'xlsx'); });
$('#excel_date_time_format_default').on('click', function() { FormatDatesInPreview('excel', 'xlsx'); });
$('#excel_date_time_format_custom').on('click', function() { FormatDatesInPreview('excel', 'xlsx'); });

View File

@@ -95,15 +95,14 @@ class PDFBulkExport extends HTMLBulkExport
$sFormatInput = '<input type="text" size="15" name="date_format" id="pdf_custom_date_time_format" title="" value="'.htmlentities($sDateTimeFormat, ENT_QUOTES, 'UTF-8').'"/>';
$oRadioCustom = InputUIBlockFactory::MakeForInputWithLabel(Dict::Format('Core:BulkExport:DateTimeFormatCustom_Format', $sFormatInput), "pdf_date_format_radio", "custom", "pdf_date_time_format_custom", "radio");
$oRadioCustom->SetDescription(Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip'));
$oRadioCustom->GetInput()->SetIsChecked($sDateTimeFormat !== (string)AttributeDateTime::GetFormat());
$oRadioCustom->SetBeforeInput(false);
$oRadioCustom->GetInput()->AddCSSClass('ibo-input-checkbox');
$oFieldSetDate->AddSubBlock($oRadioCustom);
$sJSTooltip = json_encode('<div id="date_format_tooltip">'.Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip').'</div>');
$oP->add_ready_script(
<<<EOF
$('#pdf_custom_date_time_format').tooltip({content: function() { return $sJSTooltip; } });
$('#form_part_pdf_options').on('preview_updated', function() { FormatDatesInPreview('pdf', 'html'); });
$('#pdf_date_time_format_default').on('click', function() { FormatDatesInPreview('pdf', 'html'); });
$('#pdf_date_time_format_custom').on('click', function() { FormatDatesInPreview('pdf', 'html'); });

View File

@@ -84,15 +84,14 @@ class SpreadsheetBulkExport extends TabularBulkExport
$sFormatInput = '<input type="text" size="15" name="date_format" id="spreadsheet_custom_date_time_format" title="" value="'.htmlentities($sDateTimeFormat, ENT_QUOTES, 'UTF-8').'"/>';
$oRadioCustom = InputUIBlockFactory::MakeForInputWithLabel(Dict::Format('Core:BulkExport:DateTimeFormatCustom_Format', $sFormatInput), "spreadsheet_date_format_radio", "custom", "spreadsheet_date_time_format_custom", "radio");
$oRadioCustom->SetDescription(Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip'));
$oRadioCustom->GetInput()->SetIsChecked($sDateTimeFormat !== (string)AttributeDateTime::GetFormat());
$oRadioCustom->GetInput()->AddCSSClass('ibo-input-checkbox');
$oRadioCustom->SetBeforeInput(false);
$oFieldSetDate->AddSubBlock($oRadioCustom);
$sJSTooltip = json_encode('<div class="date_format_tooltip">'.Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip').'</div>');
$oP->add_ready_script(
<<<EOF
$('#spreadsheet_custom_date_time_format').tooltip({content: function() { return $sJSTooltip; } });
$('#form_part_spreadsheet_options').on('preview_updated', function() { FormatDatesInPreview('spreadsheet', 'spreadsheet'); });
$('#spreadsheet_date_time_format_default').on('click', function() { FormatDatesInPreview('spreadsheet', 'spreadsheet'); });
$('#spreadsheet_date_time_format_custom').on('click', function() { FormatDatesInPreview('spreadsheet', 'spreadsheet'); });

View File

@@ -11,4 +11,16 @@ $ibo-input--spacing-left--with-label: $ibo-spacing-300 !default;
select + label, label + select, label > select,
input + label, label + input, label > input {
margin-left: $ibo-input--spacing-left--with-label;
}
label.ibo-has-description {
&::after {
content: $ibo-field--label--description--content;
padding-left: $ibo-field--label--description--padding-left;
vertical-align: top;
cursor: pointer;
color: $ibo-field--label--description--color;
@extend %ibo-font-ral-bol-50;
}
}

View File

@@ -260,7 +260,7 @@ function SearchFormForeignKeys(id, sTargetClass, sAttCode, oSearchWidgetElmt, sF
$(this).parents('tr:first').remove(); // Remove the whole line, so that, next time the dialog gets displayed it's no longer there
}
);
theMap["sFilter"] = $('#datatable_ResultsToAdd_'+me.id).DataTable().ajax.params().filter;
theMap["sFilter"] = $('#datatable_ResultsToAdd_'+me.id+' [name="filter"]').val();
theMap["class"] = me.sTargetClass;
theMap['operation'] = 'GetFullListForeignKeysFromSelection';
$('#busy_'+me.iInputId).html('&nbsp;<img src="../images/indicator.gif"/>');

View File

@@ -1328,6 +1328,7 @@ EOF
$sFormatInput = '<input type="text" size="15" name="custom_date_time_format" id="excel_custom_date_time_format" title="" value="'.htmlentities($sCustomDateTimeFormat, ENT_QUOTES, 'UTF-8').'"/>';
$oRadioCustom = InputUIBlockFactory::MakeForInputWithLabel(Dict::Format('UI:CSVImport:CustomDateTimeFormat', $sFormatInput), "date_time_format", "custom", "radio_date_time_custom", "radio");
$oRadioCustom->SetDescription(Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip'));
$oRadioCustom->GetInput()->SetIsChecked($sDateTimeFormat !== (string)AttributeDateTime::GetFormat());
$oRadioCustom->SetBeforeInput(false);
$oRadioCustom->GetInput()->AddCSSClass('ibo-input-checkbox');
@@ -1424,11 +1425,9 @@ EOF
}
EOF
);
$sJSTooltip = json_encode('<div class="date_format_tooltip">'.Dict::S('UI:CSVImport:CustomDateTimeFormatTooltip').'</div>');
$oPage->add_ready_script(
<<<EOF
DoPreview();
$('#custom_date_time_format').tooltip({content: function() { return $sJSTooltip; } });
$('#custom_date_time_format').on('click', function() { $('#radio_date_time_custom').prop('checked', true); });
EOF
);

View File

@@ -469,6 +469,7 @@ EOF;
* @uses \CMDBSource::GetDBVersion() so needs a connection opened !
*
* @since 2.5.0 N°1260
* @since 2.6.2 2.7.0 N°2336 Call DB to get vendor and version (so CMDBSource must be init before calling this method)
* @link https://dev.mysql.com/doc/refman/5.6/en/connection-options.html#encrypted-connection-options "Command Options for Encrypted Connections"
*/
public static function GetMysqlCliTlsOptions($oConfig)

View File

@@ -2177,8 +2177,13 @@ class MFElement extends Combodo\iTop\DesignElement
if ($oExisting->getAttribute('_alteration') != 'removed') {
$sPath = MFDocument::GetItopNodePath($oNode);
$iLine = $oNode->getLineNo();
throw new MFException($sPath.' at line '.$iLine.": could not be added (already exists)", MFException::COULD_NOT_BE_ADDED,
$iLine, $sPath);
$sExistingPath = MFDocument::GetItopNodePath($oExisting);
$iExistingLine = $oExisting->getLineNo();
$sExceptionMessage = <<<EOF
`{$sPath}` at line {$iLine} could not be added : already exists in `{$sExistingPath}` at line {$iExistingLine}
EOF;
throw new MFException($sExceptionMessage, MFException::COULD_NOT_BE_ADDED, $iLine, $sPath);
}
$oExisting->ReplaceWithSingleNode($oNode);
$sFlag = 'replaced';

View File

@@ -25,6 +25,11 @@ class InputWithLabel extends UIBlock
protected $oInput;
/** @var bool Label before input ? */
protected $bBeforeInput;
/**
* @var string $sDescription for tooltip
* @since 3.0.1
*/
protected $sDescription;
/**
* @param string $sLabel
@@ -102,4 +107,32 @@ class InputWithLabel extends UIBlock
$this->sLabel = $sLabel;
return $this;
}
/**
* @since 3.0.1
* @return mixed
*/
public function GetDescription()
{
return $this->sDescription;
}
/**
* @since 3.0.1
* @param mixed $sDescription
*/
public function SetDescription($sDescription)
{
$this->sDescription = $sDescription;
return $this;
}
/**
* @since 3.0.1
* @return bool
*/
public function HasDescription(): bool
{
return strlen($this->sDescription) > 0;
}
}

View File

@@ -18,6 +18,11 @@ trait tInputLabel
protected $bIsLabelBefore = true;
/** @var string|null Label to display with the input (null for no label) */
protected $sLabel = null;
/**
* @var string $sDescription for tooltip
* @since 3.0.1
*/
protected $sDescription;
/**
* @return bool
@@ -85,4 +90,27 @@ trait tInputLabel
{
return $this->sLabel != null;
}
/**
* @return mixed
*/
public function GetDescription()
{
return $this->sDescription;
}
/**
* @param mixed $sDescription
*/
public function SetDescription($sDescription)
{
$this->sDescription = $sDescription;
return $this;
}
/**
* @return bool
*/
public function HasDescription(): bool
{
return $this->sDescription != null;
}
}

View File

@@ -1,3 +1,3 @@
{# @copyright Copyright (C) 2010-2021 Combodo SARL #}
{# @license http://opensource.org/licenses/AGPL-3.0 #}
<label for="{{ oUIBlock.GetId() }}">{{ oUIBlock.GetLabel() |raw }}</label>
<label for="{{ oUIBlock.GetId() }}" {% if oUIBlock.HasDescription() %} class="ibo-has-description" data-tooltip-content="{{ oUIBlock.GetDescription() |raw }}" data-tooltip-max-width="600px" data-tooltip-html-enabled="true"{% endif %}>{{ oUIBlock.GetLabel() |raw }}</label>

View File

@@ -1,10 +1,10 @@
{% block iboInputLabel %}
{% if oUIBlock.IsLabelBefore() %}
<label for="{{ oUIBlock.GetId() }}">{{ oUIBlock.GetLabel() |raw }}</label>
<label for="{{ oUIBlock.GetId() }}" {% if oUIBlock.HasDescription() %} class="ibo-has-description" data-tooltip-content="{{ oUIBlock.GetDescription() |raw }}" data-tooltip-max-width="600px" data-tooltip-html-enabled="true"{% endif %}>{{ oUIBlock.GetLabel() |raw }}</label>
{{ render_block(oUIBlock.GetInput()) }}
{% else %}
{{ render_block(oUIBlock.GetInput()) }}
<label for="{{ oUIBlock.GetId() }}">{{ oUIBlock.GetLabel() |raw }}</label>
<label for="{{ oUIBlock.GetId() }}" {% if oUIBlock.HasDescription() %} class="ibo-has-description" data-tooltip-content="{{ oUIBlock.GetDescription() |raw }}" data-tooltip-max-width="600px" data-tooltip-html-enabled="true"{% endif %}>{{ oUIBlock.GetLabel() |raw }}</label>
{% endif %}
{% endblock %}

View File

@@ -40,55 +40,56 @@
timeoutForLargeTests="60"
verbose="false">
<testsuites>
<testsuite name="Extensions">
<directory>../env-production/*/test</directory>
</testsuite>
<testsuite name="Core">
<directory>core</directory>
</testsuite>
<testsuite name="Webservices">
<directory>webservices</directory>
</testsuite>
<testsuite name="Tickets">
<directory>itop-tickets</directory>
</testsuite>
<testsuite name="Config">
<directory>itop-config</directory>
</testsuite>
<testsuite name="Application">
<directory>application</directory>
</testsuite>
<!--testsuite name="OQL">
<directory>OQL</directory>
</testsuite-->
<testsuite name="Sources">
<directory>sources</directory>
</testsuite>
<testsuite name="Status">
<directory>status</directory>
</testsuite>
<testsuite name="Synchro">
<directory>synchro</directory>
</testsuite>
<testsuite name="Setup">
<directory>setup</directory>
</testsuite>
<testsuite name="Integration">
<directory>integration</directory>
</testsuite>
<testsuite name="CoreExtensions">
<directory>coreExtensions</directory>
</testsuite>
</testsuites>
<testsuites>
<testsuite name="Extensions">
<directory>../env-production/*/test</directory>
</testsuite>
<testsuite name="Core">
<directory>core</directory>
</testsuite>
<testsuite name="Webservices">
<directory>webservices</directory>
</testsuite>
<testsuite name="Tickets">
<directory>itop-tickets</directory>
</testsuite>
<testsuite name="Config">
<directory>itop-config</directory>
</testsuite>
<testsuite name="Application">
<directory>application</directory>
</testsuite>
<!-- OQL : taking too long (20min+)... we should move this to nightlies ! See N°4655 -->
<!--testsuite name="OQL">
<directory>OQL</directory>
</testsuite-->
<testsuite name="Sources">
<directory>sources</directory>
</testsuite>
<testsuite name="Status">
<directory>status</directory>
</testsuite>
<testsuite name="Synchro">
<directory>synchro</directory>
</testsuite>
<testsuite name="Setup">
<directory>setup</directory>
</testsuite>
<testsuite name="Integration">
<directory>integration</directory>
</testsuite>
<testsuite name="CoreExtensions">
<directory>coreExtensions</directory>
</testsuite>
</testsuites>
<!-- Code coverage white list -->
<filter>
<whitelist>
<file>../core/apc-emulation.php</file>
<file>../core/ormlinkset.class.inc.php</file>
<file>../datamodels/2.x/itop-tickets/main.itop-tickets.php</file>
</whitelist>
</filter>
<!-- Code coverage white list -->
<filter>
<whitelist>
<file>../core/apc-emulation.php</file>
<file>../core/ormlinkset.class.inc.php</file>
<file>../datamodels/2.x/itop-tickets/main.itop-tickets.php</file>
</whitelist>
</filter>
</phpunit>

View File

@@ -13,6 +13,7 @@ use Combodo\iTop\Application\UI\Base\Component\Input\InputUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Input\Select\SelectOptionUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Input\SelectUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Input\TextArea;
use Combodo\iTop\Application\UI\Base\Component\Panel\PanelUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Title\TitleUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Layout\UIContentBlockUIBlockFactory;
@@ -122,10 +123,11 @@ function Usage(Page $oP)
function DisplayExpressionForm(WebPage $oP, $sAction, $sExpression = '', $sExceptionMessage = '')
{
$oP->AddSubBlock(TitleUIBlockFactory::MakeForPage(Dict::S('Core:BulkExport:ScopeDefinition')));
$oPanel = PanelUIBlockFactory::MakeNeutral(Dict::S('Core:BulkExport:ScopeDefinition'));
$oP->AddSubBlock($oPanel);
$oForm = FormUIBlockFactory::MakeStandard('form');
$oForm->SetAction($sAction);
$oP->AddSubBlock($oForm);
$oPanel->AddSubBlock($oForm);
$oForm->AddSubBlock(InputUIBlockFactory::MakeForHidden('interactive', '1'));
@@ -149,26 +151,11 @@ function DisplayExpressionForm(WebPage $oP, $sAction, $sExpression = '', $sExcep
$oSearch->UpdateContextFromUser();
$oQueries = new DBObjectSet($oSearch);
while ($oQuery = $oQueries->Fetch()) {
$oSelect->AddSubBlock(SelectOptionUIBlockFactory::MakeForSelectOption($oQuery->GetKey(), htmlentities($oQuery->Get('name'), ENT_QUOTES, 'UTF-8'), false));
$oSelect->AddSubBlock(SelectOptionUIBlockFactory::MakeForSelectOption($oQuery->GetKey(), $oQuery->Get('name'), false));
}
$oFieldPhraseBook->AddSubBlock($oSelect);
$oForm->AddSubBlock($oFieldPhraseBook);
/*oP->add('<table style="width:100%" class="export_parameters">');
$sExpressionHint = empty($sExceptionMessage) ? '' : '<tr><td colspan="2">'.htmlentities($sExceptionMessage, ENT_QUOTES, 'UTF-8').'</td></tr>';
$oP->add('<tr><td class="column-label"><span style="white-space: nowrap;"><input type="radio" name="query_mode" value="oql" id="radio_oql" checked><label for="radio_oql">'.Dict::S('Core:BulkExportLabelOQLExpression').'</label></span></td>');
$oP->add('<td><textarea style="width:100%" cols="70" rows="8" name="expression" id="textarea_oql" placeholder="'.Dict::S('Core:BulkExportQueryPlaceholder').'">'.htmlentities($sExpression, ENT_QUOTES, 'UTF-8').'</textarea></td></tr>');
$oP->add($sExpressionHint);
$oP->add('<tr><td class="column-label"><span style="white-space: nowrap;"><input type="radio" name="query_mode" value="phrasebook" id="radio_phrasebook"><label for="radio_phrasebook">'.Dict::S('Core:BulkExportLabelPhrasebookEntry').'</label></span></td>');
$oP->add('<td><select name="query" id="select_phrasebook">');
$oP->add('<option value="">'.Dict::S('UI:SelectOne').'</option>');
$oSearch = DBObjectSearch::FromOQL('SELECT QueryOQL');
$oSearch->UpdateContextFromUser();
$oQueries = new DBObjectSet($oSearch);
while ($oQuery = $oQueries->Fetch()) {
$oP->add('<option value="'.$oQuery->GetKey().'">'.htmlentities($oQuery->Get('name'), ENT_QUOTES, 'UTF-8').'</option>');
}
$oP->add('</select></td></tr>');*/
$oForm->AddSubBlock(ButtonUIBlockFactory::MakeForPrimaryAction(Dict::S('UI:Button:Next'), "", "", true, "next-btn"));
$oP->p('<a target="_blank" href="'.utils::GetAbsoluteUrlAppRoot().'webservices/export-v2.php">'.Dict::S('Core:BulkExportCanRunNonInteractive').'</a>');
$oP->p('<a target="_blank" href="'.utils::GetAbsoluteUrlAppRoot().'webservices/export.php">'.Dict::S('Core:BulkExportLegacyExport').'</a>');