Compare commits

...

2409 Commits

Author SHA1 Message Date
Eric Espie
8141723869 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	approot.inc.php
#	css/css-variables.scss
#	datamodels/2.x/authent-cas/module.authent-cas.php
#	datamodels/2.x/authent-external/module.authent-external.php
#	datamodels/2.x/authent-ldap/module.authent-ldap.php
#	datamodels/2.x/authent-local/module.authent-local.php
#	datamodels/2.x/combodo-db-tools/module.combodo-db-tools.php
#	datamodels/2.x/itop-attachments/module.itop-attachments.php
#	datamodels/2.x/itop-backup/module.itop-backup.php
#	datamodels/2.x/itop-bridge-virtualization-storage/module.itop-bridge-virtualization-storage.php
#	datamodels/2.x/itop-change-mgmt-itil/module.itop-change-mgmt-itil.php
#	datamodels/2.x/itop-change-mgmt/module.itop-change-mgmt.php
#	datamodels/2.x/itop-config-mgmt/module.itop-config-mgmt.php
#	datamodels/2.x/itop-config/module.itop-config.php
#	datamodels/2.x/itop-core-update/module.itop-core-update.php
#	datamodels/2.x/itop-datacenter-mgmt/module.itop-datacenter-mgmt.php
#	datamodels/2.x/itop-endusers-devices/module.itop-endusers-devices.php
#	datamodels/2.x/itop-files-information/module.itop-files-information.php
#	datamodels/2.x/itop-full-itil/module.itop-full-itil.php
#	datamodels/2.x/itop-hub-connector/module.itop-hub-connector.php
#	datamodels/2.x/itop-incident-mgmt-itil/module.itop-incident-mgmt-itil.php
#	datamodels/2.x/itop-knownerror-mgmt/module.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-oauth-client/module.itop-oauth-client.php
#	datamodels/2.x/itop-portal-base/module.itop-portal-base.php
#	datamodels/2.x/itop-portal/module.itop-portal.php
#	datamodels/2.x/itop-problem-mgmt/module.itop-problem-mgmt.php
#	datamodels/2.x/itop-profiles-itil/module.itop-profiles-itil.php
#	datamodels/2.x/itop-request-mgmt-itil/module.itop-request-mgmt-itil.php
#	datamodels/2.x/itop-request-mgmt/module.itop-request-mgmt.php
#	datamodels/2.x/itop-service-mgmt-provider/module.itop-service-mgmt-provider.php
#	datamodels/2.x/itop-service-mgmt/module.itop-service-mgmt.php
#	datamodels/2.x/itop-sla-computation/module.itop-sla-computation.php
#	datamodels/2.x/itop-storage-mgmt/module.itop-storage-mgmt.php
#	datamodels/2.x/itop-tickets/module.itop-tickets.php
#	datamodels/2.x/itop-virtualization-mgmt/module.itop-virtualization-mgmt.php
#	datamodels/2.x/itop-welcome-itil/module.itop-welcome-itil.php
#	datamodels/2.x/version.xml
2024-09-26 17:37:07 +02:00
denis.flaven@combodo.com
8cb701bda3 🔖 Prepare 2.7.11 version 2024-09-26 16:53:24 +02:00
jf-cbd
1b29746806 Rename github token 2024-09-23 17:14:41 +02:00
jf-cbd
fb9c317256 Add an action in the workflow to automatically add pull requests to the Combodo PRs dashboard 2024-09-23 14:43:33 +02:00
jf-cbd
1aef576403 N°7604 - Security hardening 2024-07-04 13:52:19 +02:00
jf-cbd
96e1388dde N°7603 - Security hardening + UI blocks examples updated 2024-07-04 10:56:08 +02:00
Timothee
69c8791fc5 Fix merge conflit resolution d3b9965283 2024-07-03 16:48:08 +02:00
Eric Espie
cddc452693 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-06-24 13:55:29 +02:00
Eric Espie
0904a21e3f Cleanup ItopTestCase 2024-06-24 11:50:37 +02:00
Timothee
1f1a2b660f N°7581 Improve error message readability during object creation/modification in the portal (regression introduced with N°7545) 2024-06-21 12:36:52 +02:00
Molkobain
33a906f11a Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-06-21 11:29:18 +02:00
Molkobain
82d11eeb47 N°7127 - Upgrade handlebars.js to v4.7.8 2024-06-21 11:19:39 +02:00
Eric Espie
2596a150bf Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-06-20 11:07:36 +02:00
Eric Espie
142d6c8993 N°7533 - Detect and warns on Galera clusters 2024-06-20 11:06:57 +02:00
Timothee
c4fc0ed982 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-06-17 16:51:30 +02:00
Timothee
320922a13d N°7545 Correctly display error message 2024-06-17 16:49:33 +02:00
Eric Espie
d3b9965283 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/cmdbsource.class.inc.php
2024-06-12 16:48:06 +02:00
Eric Espie
f03d731b1d N°7533 - Prevent installation of iTop on Galera clusters 2024-06-12 16:14:23 +02:00
Eric Espie
63cf78f64d Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	pages/preferences.php
2024-05-29 18:18:55 +02:00
Eric Espie
8be7628668 N°7548 - Code hardening 2024-05-29 18:11:36 +02:00
Eric Espie
f632cf3155 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-05-21 15:07:08 +02:00
Eric Espie
62caf16153 N°7364 - Code hardening 2024-05-21 14:20:30 +02:00
odain
163a3afc0f N°7426 - no session created - replace php_sapi_name() by PHP_SAPI in unattended 2024-05-16 15:31:08 +02:00
odain
d98e35d918 Merge branch 'support/2.7' into support/3.0 2024-05-16 14:13:24 +02:00
odain
f8b54be896 N°7426 - no session created - replace php_sapi_name() by PHP_SAPI 2024-05-16 14:10:54 +02:00
Romain Quetiez
c6f3e36451 Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	tests/php-unit-tests/src/BaseTestCase/ItopTestCase.php
#	tests/php-unit-tests/unitary-tests/core/iTopConfigParserTest.php
2024-05-16 10:09:11 +02:00
Romain Quetiez
53dc452d61 Avoid unnecessary custom test environment compilations (base compilation of file modification time) 2024-05-16 09:53:04 +02:00
Romain Quetiez
ccaf2dc5b7 Make the tests compatible with windows (and linux) 2024-05-16 09:53:04 +02:00
Molkobain
46738d4ba4 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-05-07 10:38:50 +02:00
Molkobain
5d5df5ad1a N°7255 - Fix misc. stylesheets not working in portal since N°7047 2024-05-07 10:37:39 +02:00
jf-cbd
61469a28b9 N°7445 - Invalid Unicode escape sequence on dashlet Header with statistics 2024-04-30 10:56:09 +02:00
jf-cbd
dbcbb187b2 N°7445 - Invalid Unicode escape sequence on dashlet Header with statistics 2024-04-30 08:13:37 +02:00
jf-cbd
93bba66323 N°7445 - Invalid Unicode escape sequence on dashlet Header with statistics 2024-04-30 08:03:14 +02:00
Molkobain
cab6394cba Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-04-29 13:58:13 +02:00
Molkobain
32140b360f Cherry pick fixes from 59a955f4 2024-04-29 11:45:09 +02:00
jf-cbd
e657052d17 Merge remote-tracking branch 'refs/remotes/origin/support/2.7' into support/3.0 2024-04-24 11:58:13 +02:00
jf-cbd
d85767a838 Update test to run only on commmunity builds 2024-04-24 11:14:40 +02:00
jf-cbd
e5a8bd61b0 Merge remote-tracking branch 'refs/remotes/origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-hub-connector/launch.php
2024-04-23 14:03:15 +02:00
jf-cbd
eeec57536b Security hardening 2024-04-23 11:55:39 +02:00
jf-cbd
514e0b80a5 N°7445 - Invalid Unicode escape sequence on dashlet Header with statistics 2024-04-19 11:17:09 +02:00
Molkobain
35f4ab4941 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-04-19 09:22:32 +02:00
Molkobain
16ff6341d0 N°7455 - Fix regression from 4c784886, wrong class tested 2024-04-19 09:14:53 +02:00
Molkobain
ac826cb9f1 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-04-18 18:48:24 +02:00
Molkobain
9dab8679d6 N°7448 - Update dictionary entry 2024-04-18 18:44:20 +02:00
Molkobain
f737bcb9a0 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-04-18 18:16:24 +02:00
Molkobain
4c78488644 N°7455 - Ensure form renderer class extends FormRenderer 2024-04-18 18:15:02 +02:00
odain
77cc4672b0 Merge branch 'support/2.7' into support/3.0 2024-04-15 10:20:49 +02:00
odain
b65e931c4c N°7439 - setup wizard broken on essential targets after fresh install via unattended CLI 2024-04-15 09:57:54 +02:00
odain
dfbfab7005 N°7407 - adapt test to 3.0 test SDK evolutions 2024-04-12 17:17:03 +02:00
odain
aa831b632c Merge branch 'support/2.7' into support/3.0 2024-04-12 17:16:22 +02:00
odain
6cb3519308 N°7407 - test readability 2024-04-12 16:59:56 +02:00
odain
cfb9fae648 N°7407 - fix previous commit 2024-04-12 16:49:11 +02:00
odain
f4e791734f N°7407 - remove phpunit annotation 2024-04-12 14:49:20 +02:00
odain
6653ab0668 N°7407 - fix missing extension installation via unattended from production-modules or extension folder 2024-04-12 13:25:40 +02:00
odain
7ab258ba03 N°7439 - setup wizard broken on essential targets 2024-04-12 11:32:04 +02:00
odain
b5af30a93f N°7407 - refactor unattended tests to make work anywhere 2024-04-12 11:32:04 +02:00
Molkobain
ce5c05234d Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-04-12 10:02:19 +02:00
Molkobain
bbfa601ab1 N°7446 - Add temporary workaround to fix an issue due to DB views creation. 2024-04-12 09:59:14 +02:00
odain
83764deedb Merge branch 'support/2.7' into support/3.0 2024-04-11 18:55:00 +02:00
odain
172b1cb1ff N°7407 - add phpunit annotation to exclude tests on top of targets 2024-04-11 18:54:43 +02:00
Molkobain
e1374a0e6b Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-04-11 16:56:25 +02:00
Molkobain
ca356859a3 N°7446 - Add comment for better understanding 2024-04-11 16:55:48 +02:00
Molkobain
5efe294895 N°7446 - Fix custom datamodel test class not creating DB tables correctly 2024-04-11 16:50:27 +02:00
odain
18d0b88531 N°7407 - fix merge 2024-04-10 14:11:58 +02:00
odain
3139a0b610 Merge branch 'support/2.7' into support/3.0 2024-04-10 14:06:41 +02:00
odain
e0170ccc7e N°7407 - InstallationFileServiceTest relies on local installation.xml to reduce maintenance 2024-04-10 14:05:39 +02:00
odain
367aac3e04 Merge branch 'support/2.7' into support/3.0 2024-04-09 11:06:17 +02:00
odain
3b78885f38 N°7407 - unattended test cleanup for PHP 8.x deprecations 2024-04-09 11:06:03 +02:00
odain
f14b4c32be N°7407 - adapt unattended test to 3.0 installation.xml choices 2024-04-09 10:46:44 +02:00
Molkobain
6a30d6caa9 N°7438 - Dashboard: Fix crash when closing the editor modal 2024-04-09 10:40:06 +02:00
odain
a51242dc36 N°7407 - remove 2.7 requires in unattended service 2024-04-09 10:08:43 +02:00
odain
64ba706083 Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	setup/applicationinstaller.class.inc.php
#	setup/modulediscovery.class.inc.php
#	setup/runtimeenv.class.inc.php
#	setup/unattended-install/unattended-install.php
#	tests/setup_params/default-params.xml
2024-04-09 10:07:40 +02:00
odain
ed562c9f73 N°7407 - fix unattended test enhancement 2024-04-09 10:02:06 +02:00
odain-cbd
85c576a986 N°7407 - N°7306 - Ease iTop installation via unattended CLI by using installation.xml choices (#641)
* N°7306 - Use iTop configuration settings to run unattended installation (instead of XML file settings)

* 7306 - fix infinite loop with db_tls.ca null

* 7306 - complete fields to use from itop configuration instead of XML setup

* fix using default language from conf

* 6365 - temp work

* 6365 - add option to select modules from installation.xml

* 6365-select modules option in unattended install

* 6365 - pass env to service + debug failed test

* 6365 - debug ci again + separate process annotation

* 6365 - fix test + cleanup

* 6365 - ci using use_installation_xml mode

* 6365 - ci using use_installation_xml mode

* 6365 - pass selected_modules to unattended

* N°6365 - Compute selected modules based on selected extensions coming from XML setup

* switch constr parameters and fix call from unattended cli

* 6365 - use use_installation_xml for unattended install only when no selected modules already provided

* test ci XML setup including selected extensions but no modules

* test ci installing iTop without selected modules/extenesions: guess via installation.xml

* same but without even providing XML setup - comment it in ci_description.ini

* 7306 - cleanup requires

* use infra master

* N°6365 - make current unattended CLI work with any iTop version (CLIPage compatibility)

* N°6365 - log which modules will be installed during setup

* N°6365 - unattended documentation + bash helper

* 6365- fix warning due to copies index access

* 6365 - enhance traces feedback to understant which and how modules are computes

* 6365 - enhance bash CLI + doc

* 6365 - fix require clipage compatibility

* 6365 - add return for better cli ouput

* 6365 - enhance ouput messages

* Document the usage and harmonize argument names (still not perfect)

* 6365 - fix use of new param param-file

* 6365 - fix test + vardump cleanup

* N°6365 - use underscore for unattended install options as advices in the PR

* 6365 -enhance test by using PHP_BINARY

---------

Co-authored-by: Romain Quetiez <romain.quetiez@combodo.com>
2024-04-09 10:00:58 +02:00
odain
ff1305165e N°5120 - PR merge adaptation to CLIPage 2024-04-02 14:42:21 +02:00
Molkobain
65c706fdfe Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-04-02 10:37:08 +02:00
odain-cbd
5a34c76cc4 N°5120 - Unattended install : use cty toolkit version (#624)
* N°5120 - Unattended install : use cty toolkit version

* N°5120 - CLI mode validation

* 5120 - bring CI enhancements

* 5120 - bring back saas use-itop-config option: to read db settings from conf directly

* 5120 - move unattended script in setup folder/unattended-install

* 5120 - use-itop-config option: take db_tls_enabled and db_tls_ca into account

* 5120 - move test

* 5120 - put ci enhancements back - logs and conf preservation with install mode

* 5120 - keep PR simple - remove saas use-itop-config option for now

* 5120 - remove ci enhancement to preserve configuration

* Update setup/unattended-install/README.md

Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>

* 5120 - documentation

* 5120 - fix log level

* 5120 - fix test

* fix phpunit test comment

---------

Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>
2024-03-29 11:09:27 +01:00
Molkobain
bdfd956825 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	css/setup.css
#	setup/setuppage.class.inc.php
2024-03-21 15:37:33 +01:00
Molkobain
da99a250bf N°7075 - Add check for Content Security Policies (CSP) in the setup 2024-03-21 14:20:22 +01:00
Pierre Goiffon
f4b9a9a5fe N°6455 Fix datepicker widget icon on button
The buttonText is now escaped

(cherry picked from commit fa5d03fc6e)
2024-03-18 18:19:30 +01:00
jf-cbd
5c46b4ef4a Added modules to GetLtsCompatibleModulesList (Dictionnarie tests) 2024-03-14 16:59:32 +01:00
Pierre Goiffon
a97935ca01 N°7336 DeprecatedCallsLog robustness (#632)
Was creating PHP notices when deprecated method caller wasn't a class/method
Found in iTop 3.2.0-dev with itop-object-copier copy.php : it is calling WebPage::add_linked_script directly inside the copy.php script (no class nor function)

Co-authored-by: odain <olivier.dain@combodo.com>
2024-03-13 15:38:21 +01:00
Molkobain
efd7fb0f59 N°7331 - Fix wrong file extension in .htaccess file 2024-03-13 15:16:46 +01:00
Pierre Goiffon
a4edf8cb21 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/php-unit-tests/unitary-tests/setup/SetupUtilsTest.php
2024-03-13 09:59:28 +01:00
Pierre Goiffon
dbd5ba0377 N°7302 Fix SetupUtilsTest::testHumanReadableSize 2024-03-13 09:56:31 +01:00
Pierre Goiffon
5d6f293956 N°7302 Report SetupUtilsTest::testHumanReadableSize in the 2.7 branch 2024-03-13 09:48:46 +01:00
Pierre Goiffon
65e6c84477 N°7302 Fix SetupUtilsTest::testHumanReadableSize 2024-03-13 09:37:34 +01:00
Pierre Goiffon
a337ef3d88 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	setup/modelfactory.class.inc.php
#	setup/setuputils.class.inc.php
2024-03-13 09:27:06 +01:00
Pierre Goiffon
986c24d777 N°7302 Fix unit name in \SetupUtils::HumanReadableSize (#626) 2024-03-12 18:09:29 +01:00
Pierre Goiffon
763112c179 N°7344 rest.php core/get : add try/catch around query execution (#622)
Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>
Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2024-03-12 18:08:04 +01:00
Pierre Goiffon
a5efd981d8 N°7343 Catch ParseError when loading dict files in setup (#615) 2024-03-12 18:05:38 +01:00
Pierre Goiffon
289ca7b505 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-03-12 17:34:51 +01:00
Pierre Goiffon
2922b22478 \DBObject::GetSearchForUniquenessRule remove wrong @api 2024-03-12 17:34:28 +01:00
Pierre Goiffon
2af05a437e N°4314 - Fix Uniqueness rules not working with Silo
(cherry picked from commit e8c11f38d2)
2024-03-12 17:32:56 +01:00
vdumas
71d9536bc4 N°7268 Method SetComputedDate fails on Date only attribute
(cherry picked from commit b6caa51552)
(cherry picked from commit c8810708ef)
2024-03-12 17:29:04 +01:00
Molkobain
6377a738c5 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-03-11 21:18:53 +01:00
Molkobain
a9f8dcc5e8 N°7122 N°4164 - Portal: Hide log off button when user can't actually log off (eg. SSO using SAML or other providers) (#599)
* N°7122 N°4164 - Portal: Hide log off button when user can't actually log off (eg. SSO using SAML or other providers)

* N°7122 - Fix typo

Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>

---------

Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>
2024-03-11 21:13:09 +01:00
Pierre Goiffon
969a301cbb Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-03-11 16:40:01 +01:00
Pierre Goiffon
c325294e17 N°6599 Update moment from 2.22.2 to 2.30.1 2024-03-11 16:39:05 +01:00
Pierre Goiffon
a29b0a8e33 N°6455 Update JQuery-UI from 1.12.1 to 1.13.2 2024-03-08 11:13:32 +01:00
Pierre Goiffon
f78b57521a Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-03-07 11:11:19 +01:00
Pierre Goiffon
da490739be 💡 Fix \CMDBSource::Query phpdoc block 2024-03-07 11:10:53 +01:00
Pierre Goiffon
48de13b5cf Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-03-04 08:32:59 +01:00
Pierre Goiffon
b867faa355 Fix DBObjectTest
Error was "Class 'Combodo\iTop\Test\UnitTest\Core\DBObjectSet' not found"
2024-03-04 08:09:35 +01:00
Pierre Goiffon
e878938e25 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-03-01 17:26:05 +01:00
jf-cbd
7453cc184f ✏️ fix a typo 2024-03-01 17:25:08 +01:00
Anne-Cath
f3abe1ff13 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	pages/audit.php
2024-02-29 16:50:04 +01:00
Anne-Catherine
473cf004b6 N°6968 - Audit duration : add of a rule multiplie by 4 the time of response (#575) 2024-02-29 16:33:04 +01:00
Pierre Goiffon
24f1cf8ca1 💡 Fix deprecated in JSDoc 2024-02-28 16:43:40 +01:00
Pierre Goiffon
102a4a0c75 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/attributedef.class.inc.php
2024-02-20 12:11:02 +01:00
Pierre Goiffon
f6fec506b1 💡 Some PHPDoc hints on value types to pass to DBObject::Set 2024-02-20 12:10:00 +01:00
Pierre Goiffon
3b9f281afd N°7246 DictionariesConsistencyTest : remove combodo-approval-light
We have an invalid CS dict in the 1.2.3 module version
2024-02-20 09:27:15 +01:00
Pierre Goiffon
ec465174f7 N°7246 DictionariesConsistencyTest : remove syntax incompatible with PHP < 7.3 2024-02-20 09:11:47 +01:00
Molkobain
31bd763b90 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-02-19 09:49:26 +01:00
Molkobain
5c12151c26 📝 Update PR template 2024-02-19 09:46:12 +01:00
Pierre Goiffon
9777ac1a5c N°7246 DictionariesConsistencyTest : don't test extensions modules in old iTop builds 2024-02-15 14:39:00 +01:00
Pierre Goiffon
dd27a3ebb4 N°7246 Fix dict files : translated keys with tildes in /dictionaries/** 2024-02-15 10:50:08 +01:00
Pierre Goiffon
54439ad529 N°7249 DictionariesConsistencyTest : also scan /dictionaries sub-directories
Since 3.0.0 we introduced sub directories
2024-02-15 10:46:42 +01:00
Pierre Goiffon
8f7bf00551 N°7246 DictionariesConsistencyTest : add /extensions for local debugging 2024-02-15 09:46:14 +01:00
Pierre Goiffon
c020de59a7 📝 tests README : retrofit of the support/3.2 version 2024-02-14 15:16:58 +01:00
Pierre Goiffon
aa53de467d Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-02-14 11:39:42 +01:00
Pierre Goiffon
bc6efc99ed N°7246 Fix dict files : remove keys defined multiple times in the same file 2024-02-14 11:20:02 +01:00
Pierre Goiffon
bb3ab76205 N°7246 Fix dict files : missing constants in dict labels 2024-02-14 11:20:02 +01:00
Pierre Goiffon
0b1bdfff55 N°7246 Fix dict files : translated keys with tildes
Note that there were some keys in EN files with tildes at the end
2024-02-14 11:20:02 +01:00
Pierre Goiffon
77c0cdf5aa N°7246 📝 test README : add markTestAsSkipped restrictions 2024-02-14 11:20:02 +01:00
Pierre Goiffon
af9fb74c54 N°7246 Add new tests methods in DictionariesConsistencyTest (#610)
Adding following checks:
* no duplicate key in the same file
* for each value different than its EN counterpart, no tildes at the end
* good use of iTop name constants (ITOP_APPLICATION_SHORT, ITOP_APPLICATION, ITOP_VERSION_NAME), eg `'my value ITOP_APPLICATION'` instead of `'my value '.ITOP_APPLICATION`
2024-02-14 11:20:02 +01:00
Pierre Goiffon
5d6c4939f6 N°7245 Bettor logs on RunTimeEnvironment::CallInstallerHandlers exceptions (#606) 2024-02-14 11:01:12 +01:00
Pierre Goiffon
51d0d16a11 N°7052 synchro_import.php: fix undefined offset notices (#583)
Regression brought by #269
2024-02-14 09:53:31 +01:00
Pierre Goiffon
b0634c9fbc N°7232 Fix regression on UI:RunQuery:Error
In the UI:RunQuery:Error key, the placeholder was removed when we migrated run_query.php to using UiBlock and Panel.
But it was restored by mistake in f65c6904 (N°5491 in 3.0.4 / 3.1.1)
This was the only key modified for this bug in a EN file.
2024-02-09 13:30:47 +01:00
Pierre Goiffon
c951a33646 📝 Update js/README.md file locations 2024-02-09 12:04:21 +01:00
Pierre Goiffon
ed694b09b0 💡 Update test PHPDoc 2024-02-08 11:34:13 +01:00
Molkobain
3868d57d28 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-01-24 15:11:29 +01:00
Molkobain
1b3a2c8470 N°5775 - Show error message to user in case of issue during token generation 2024-01-24 14:49:51 +01:00
Dennis Lassiter
618d8e6468 N°5775 - Allow configuration of OAuth client on MS Azure with single tenant (#553)
* Add Tenant-Support for Azure OAuthClient

* Improvement: Make tenant required

* Improvment: Removed check for null-value

Since last commit, the "tenant"-field either set to a custom value or "common" by default. It is not allowed to be null

* Add field description

---------

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2024-01-24 14:38:54 +01:00
Molkobain
f54d1273c9 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-01-16 19:46:55 +01:00
Molkobain
01a955a16f 📝 Add PR template 2024-01-16 19:42:39 +01:00
Pierre Goiffon
a5aac0caad N°7143 Woops removed forgotten echo 2024-01-16 10:25:28 +01:00
Pierre Goiffon
31e29506fa N°7143 DictionariesConsistencyTest::testNoDictFileInDatamodelsModuleRootDirectory Add exclusion list to remove modules that must be compatible with iTop 2.7 2024-01-16 10:18:50 +01:00
Anne-Cath
3f3b0cbe55 Fix merge support/2.7 to support/3.0 2024-01-15 16:25:10 +01:00
Anne-Cath
dab03e5b5d Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/cmdbabstract.class.inc.php
2024-01-15 15:56:24 +01:00
Anne-Catherine
87582a021b N°6993 - Error message on bulk transition on object containing a null blob (#596) 2024-01-15 15:49:19 +01:00
Pierre Goiffon
8ef04bedf2 N°7143 Move datamodels/2.x dict files to dictionaries subdir
New phpunit method to ensure it won't happen again
2024-01-15 15:35:15 +01:00
Pierre Goiffon
9eeb4b8751 N°7143 itop-hub-connector dic files: fix buggy br tags 2024-01-15 15:35:15 +01:00
Pierre Goiffon
ae3d0f9444 N°7143 Fix bytes unit in attachments EN dict 2024-01-15 15:35:15 +01:00
Molkobain
2ed0666c3b N°7085 - Remove comment about annotation as on support/3.0 branch not using runTestsInSeparateProcesses is the standard 2024-01-12 10:53:24 +01:00
odain
a61b117f71 Merge branch 'support/2.7' into support/3.0 2024-01-12 08:56:25 +01:00
odain
9830178a47 N°7085 - ci restore runTestsInSeparateProcesses 2024-01-12 08:36:15 +01:00
odain
83ac219ec9 Merge branch 'support/2.7' into support/3.0 2024-01-12 08:19:05 +01:00
odain-cbd
c140ebcb6b N°7085 - Fix infinite loop in login page until fatal error occurs (#592)
* N°7085 - login page infinite loop until fatal error- add Config->AddAllowedLoginTypes

* N°7085 - reproduce issue via a test

* N°7085-fix infinite loop

* N°7085 - ci: fix config file rights in tearDown

* N°7085 - ci: fix config file rights in tearDown (again)

* N°7085 - ci: fix config file content

* N°7085 - ci : add runTestsInSeparateProcesses

* Update core/config.class.inc.php

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>

* N°7085 - exit -1 + enhance log message

* PR feedbacks from Romain regarding LoginTest annotations

---------

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2024-01-12 08:13:40 +01:00
Molkobain
b181914d25 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2024-01-11 22:04:48 +01:00
Molkobain
7a0a4e377b N°7137 - Fix regression from 7fffbb60, missing "default_value" parameter 2024-01-11 16:40:40 +01:00
Thomas Casteleyn
7fffbb60e9 N°7137 - DataSynchro: Remove "Organization" as default value for SynchroReplica->dest_class (#551) 2024-01-11 15:38:02 +01:00
Pierre Goiffon
b8892e9651 🔖 Prepare 3.0.4 version 2024-01-05 17:34:39 +01:00
Pierre Goiffon
8cde0ce5c5 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	approot.inc.php
#	css/css-variables.scss
#	datamodels/2.x/authent-cas/module.authent-cas.php
#	datamodels/2.x/authent-external/module.authent-external.php
#	datamodels/2.x/authent-ldap/module.authent-ldap.php
#	datamodels/2.x/authent-local/module.authent-local.php
#	datamodels/2.x/combodo-db-tools/module.combodo-db-tools.php
#	datamodels/2.x/itop-attachments/module.itop-attachments.php
#	datamodels/2.x/itop-backup/module.itop-backup.php
#	datamodels/2.x/itop-bridge-virtualization-storage/module.itop-bridge-virtualization-storage.php
#	datamodels/2.x/itop-change-mgmt-itil/module.itop-change-mgmt-itil.php
#	datamodels/2.x/itop-change-mgmt/module.itop-change-mgmt.php
#	datamodels/2.x/itop-config-mgmt/module.itop-config-mgmt.php
#	datamodels/2.x/itop-config/module.itop-config.php
#	datamodels/2.x/itop-core-update/module.itop-core-update.php
#	datamodels/2.x/itop-datacenter-mgmt/module.itop-datacenter-mgmt.php
#	datamodels/2.x/itop-endusers-devices/module.itop-endusers-devices.php
#	datamodels/2.x/itop-files-information/module.itop-files-information.php
#	datamodels/2.x/itop-full-itil/module.itop-full-itil.php
#	datamodels/2.x/itop-hub-connector/module.itop-hub-connector.php
#	datamodels/2.x/itop-incident-mgmt-itil/module.itop-incident-mgmt-itil.php
#	datamodels/2.x/itop-knownerror-mgmt/module.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-oauth-client/module.itop-oauth-client.php
#	datamodels/2.x/itop-portal-base/module.itop-portal-base.php
#	datamodels/2.x/itop-portal/module.itop-portal.php
#	datamodels/2.x/itop-problem-mgmt/module.itop-problem-mgmt.php
#	datamodels/2.x/itop-profiles-itil/module.itop-profiles-itil.php
#	datamodels/2.x/itop-request-mgmt-itil/module.itop-request-mgmt-itil.php
#	datamodels/2.x/itop-request-mgmt/module.itop-request-mgmt.php
#	datamodels/2.x/itop-service-mgmt-provider/module.itop-service-mgmt-provider.php
#	datamodels/2.x/itop-service-mgmt/module.itop-service-mgmt.php
#	datamodels/2.x/itop-sla-computation/module.itop-sla-computation.php
#	datamodels/2.x/itop-storage-mgmt/module.itop-storage-mgmt.php
#	datamodels/2.x/itop-tickets/module.itop-tickets.php
#	datamodels/2.x/itop-virtualization-mgmt/module.itop-virtualization-mgmt.php
#	datamodels/2.x/itop-welcome-itil/module.itop-welcome-itil.php
#	datamodels/2.x/version.xml
2024-01-05 17:26:28 +01:00
Pierre Goiffon
2fd9523c16 🔖 Prepare 2.7.10 version 2024-01-05 15:50:41 +01:00
Pierre Goiffon
48c4e2d13d Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/ajaxwebpage.class.inc.php
#	application/webpage.class.inc.php
#	application/xmlpage.class.inc.php
#	core/config.class.inc.php
2024-01-05 10:58:51 +01:00
Pierre Goiffon
a4f6f6e877 N°4368 Fix CORB blocking regression (#598)
Don't send X-Content-Type-Options HTTP header for certain WebPage impl to workaround CORB blocking
To disable globally this new behavior introduced in 9865bf07, set the `security.enable_header_xcontent_type_options` config parameter to false

Thanks @Molkobain for the review !
2024-01-05 10:41:18 +01:00
Pierre Goiffon
6042e7f74d Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/php-unit-tests/post-build-integration-tests/SetupCssIntegrityChecklistTest.php
#	tests/php-unit-tests/unitary-tests/core/CMDBSource/CMDBSourceTest.php
2024-01-03 10:43:41 +01:00
Molkobain
94c604a6af N°3062 - Fix setup.css compilation test to ensure that it is versioned correctly. 2023-12-21 12:00:26 +01:00
Pierre Goiffon
f84e2060be N°7077 Hungarian translations based on iTop 3.0.2-1 (#584)
Many thanks to Csaba TARJÁNYI (@tacsaby) !
2023-12-20 15:52:41 +01:00
Pierre Goiffon
6995a3c641 N°6889 backup mysqldump call : restore possibility to connect using socket protocol (#591)
With previous fix (N°6123) we forced to use the tcp protocol each time. This was blocking for users wanting to connect using the socket protocol on localhost.

Now for localhost we will : 
- send both port and protocol arguments if the `db_host` config parameter does contain a port
- don't send any of the port or protocol arguments if `db_host` doesn't contain a port
2023-12-20 15:19:50 +01:00
Pierre Goiffon
4ee70cb95a Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/ajaxwebpage.class.inc.php
#	application/csvpage.class.inc.php
#	application/itopwebpage.class.inc.php
#	application/webpage.class.inc.php
#	application/xmlpage.class.inc.php
#	datamodels/2.x/itop-hub-connector/hubconnectorpage.class.inc.php
#	pages/ajax.document.php
#	pages/ajax.render.php
#	sources/application/TwigBase/Controller/Controller.php
#	webservices/export-v2.php
2023-12-19 18:38:45 +01:00
Pierre Goiffon
9865bf0779 N°4368 add sending X-Content-Type-Options HTTP header
Replace in consumers the \WebPage::add_xframe_options call by \WebPage::add_http_headers
2023-12-19 18:25:26 +01:00
Pierre Goiffon
f63f3bb547 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-12-08 17:20:48 +01:00
Pierre Goiffon
d5449cca42 💡 iTopMutex: add link to mysql doc 2023-12-08 17:20:37 +01:00
Molkobain
181c180824 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-12-06 16:28:27 +01:00
Molkobain
5d38d22c50 N°7023 - Fix regression from the initial fix that throw exceptions even for ext. keys set programatically (eg. ComputeValues), which we still want to allow 2023-12-06 16:27:37 +01:00
Molkobain
974c155855 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-12-04 23:16:35 +01:00
Pierre Goiffon
99d69493d1 N°7023 - Update tests so that we are now checking negative ext. keys 2023-12-04 22:36:26 +01:00
Molkobain
c9bb628c30 N°7023 - Improve debug message on portal \DBObject::CheckChangedExtKeysValues() call 2023-12-04 22:36:09 +01:00
Molkobain
08e8d15d78 N°7023 - Fix check to write error when adding a contact on a new user request on the end-users portal 2023-12-04 22:35:07 +01:00
Molkobain
bed1db9c51 N°938 - Update compiled portal stylesheet in minified version 2023-11-24 17:07:02 +01:00
Molkobain
7e3e8e43a8 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-portal-base/portal/public/css/portal.css
#	datamodels/2.x/itop-portal-base/portal/templates/layout.html.twig
2023-11-24 16:45:04 +01:00
Molkobain
7b59df216b N°7005 - Fix portal stylesheets not being re-compiled when outdated
Stylesheets should remain as a relative path in the portal configuration, only when consumed by the TWIG should they become URLs

Note that if not absolute, URLs will be append to ITOP/pages/
2023-11-24 16:40:58 +01:00
Molkobain
cb5eab812e N°938 - Update compiled portal stylesheet 2023-11-24 16:22:36 +01:00
Anne-Cath
484a0bb6b6 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-11-24 15:19:05 +01:00
Anne-Catherine
c9b73a7fe2 N°938 - Improve print of portal object page and portal dashboard page (#537)
N°938 - Improve print of portal object page and portal dashboard page
2023-11-24 15:17:42 +01:00
Pierre Goiffon
6f1de11c59 N°6976 Fix DeprecatedCallsLog error handler never set (#576)
Caused by N°6274 (disabling error handler when running phpunit)
There is now a test testing the handler is really fixed when not in the phpunit context
Also a TRACE log is made on setting the handler
2023-11-23 15:54:10 +01:00
Molkobain
e02b6ee14a Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-11-23 14:25:16 +01:00
Molkobain
3b2da39469 N°6989 - Security hardening 2023-11-22 18:02:50 +01:00
odain
c5b43f3157 Merge branch 'support/2.7' into support/3.0 2023-11-22 11:10:06 +01:00
odain
fc22d91232 N°6949 - Run subset of itop core unit tests after the setup when validating a module github code 2023-11-22 10:14:58 +01:00
Pierre Goiffon
3068a6a360 N°6951 Fix autoloader 2023-11-21 11:01:16 +01:00
Stephen Abello
083a0b79bf N°6951 - Security hardening 2023-11-21 10:08:46 +01:00
Stephen Abello
e22220b4fe Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	core/csvbulkexport.class.inc.php
#	core/excelbulkexport.class.inc.php
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_files.php
#	lib/composer/autoload_real.php
#	lib/composer/autoload_static.php
2023-11-21 09:47:14 +01:00
Stephen Abello
b10bcb976d N°6951 - Security hardening 2023-11-21 09:42:11 +01:00
Pierre Goiffon
154a20b757 💡 Fix ItopCustomDatamodelTestCase since phpdoc
See https://docs.phpdoc.org/guide/references/phpdoc/tags/since.html#since
2023-11-21 09:21:30 +01:00
Pierre Goiffon
79c24dfc96 N°6975 Fix ItopCustomDatamodelTestCase removing symlinks flag (#574) 2023-11-21 09:20:11 +01:00
Pierre Goiffon
b9d960e89e N°6458 Fix ItopDataTestCase::$bIsUsingSilo visibility 2023-11-16 15:35:04 +01:00
Pierre Goiffon
8540ec644a N°6458 Improve ItopDataTestCase tests speed
What was measured :
- 1'54 with previous code (always doing a reset in tearDown)
- 1'44 without any ResetMetaModelQueyCacheGetObject call (but 3 tests are failing)
- 1'44 with new optin mechanism + don't call Logoff if no current user logged
2023-11-16 15:23:18 +01:00
Pierre Goiffon
5b19593ede 📝 README tests : add prerequisites 2023-11-16 14:38:15 +01:00
Pierre Goiffon
0915081f50 ItopDataTestCase fix cached SQL queries with silo 2023-11-16 11:57:29 +01:00
Pierre Goiffon
a23d629e31 ItopDataTestCase fix using non existing EventService (added in 3.1.0) 2023-11-16 11:23:07 +01:00
Pierre Goiffon
47ccd7589f Fix TriggerTest relying on hardcoded admin user id 2023-11-16 11:16:59 +01:00
Pierre Goiffon
7521fc3006 N°6458 Tests : remove processIsolation
Was caused by cached User instances in UserRights + same login for each created User objects instances
2023-11-16 10:56:47 +01:00
Pierre Goiffon
c955fe00b7 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/cmdbabstract.class.inc.php
#	application/utils.inc.php
#	core/coreexception.class.inc.php
#	core/userrights.class.inc.php
#	datamodels/2.x/itop-portal-base/portal/src/Form/ObjectFormManager.php
#	tests/php-unit-tests/README.md
#	tests/php-unit-tests/unitary-tests/core/DBObjectTest.php
2023-11-15 15:03:04 +01:00
Pierre Goiffon
5a43448644 N°6458 Security hardening 2023-11-15 11:14:07 +01:00
Pierre Goiffon
a2b9583379 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-11-13 16:25:53 +01:00
Pierre Goiffon
77409eed99 🎨 DBObject small phpdoc fixes 2023-11-13 16:25:37 +01:00
Stephen Abello
09be84f69d N°6908 - Security hardening 2023-11-13 11:19:02 +01:00
Romain Quetiez
d9bdcfeae3 N°6658 - Fix regression: do not reset current user's profile cache 2023-11-10 15:57:08 +01:00
Pierre Goiffon
d725ba3d84 N°6765 Avoid behat scenario loading issues on portal modal (#569)
- New CombodoJsActivity API
- Replace existing calls in NiceWebPage (ready scripts)
- Add calls in ready block in portal object create template (used in both create and edit)
2023-11-10 15:10:37 +01:00
Molkobain
8a3d81c430 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-11-08 14:59:06 +01:00
Anne-Catherine
83a70daf68 N°6887 - Fix excessive OQL requests to display user's grant matrix (#564)
* N°6887 - Fix excessive OQL requests to display user's grant matrix

* N°6887 - Rename variable and add PHPDoc

---------

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2023-11-08 14:57:28 +01:00
Molkobain
cbb37f27d7 N°6866 - Fix issue when creating new fields in Request Template in French 2023-10-31 11:10:54 +01:00
Molkobain
e21dc4d21c Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-10-30 16:55:45 +01:00
Molkobain
a49a4e6c2b N°6886 - Add OAuth tests folder to removable directories list 2023-10-30 16:54:28 +01:00
Romain Quetiez
8fa9336568 Fix regression introduced with the optimization done in 15148f7, and seen only in the context of the CI 2023-10-27 11:21:56 +02:00
Romain Quetiez
15148f7d1d Fix regression introduced with the optimization done in 798cd10, and seen only if APC is enabled 2023-10-27 10:43:13 +02:00
Romain Quetiez
7e8589ba95 Fix regression introduced with the optimization done in d641504. Cope with the fact that sometimes the admin account already exists, sometimes not. 2023-10-27 09:21:36 +02:00
Romain Quetiez
fba668207f Optimize tests execution time (test rework and defensive cleanup) 2023-10-26 21:35:52 +02:00
Romain Quetiez
798cd10d6b Optimize tests execution time (no need for process isolation as long as we leave the premises clean) 2023-10-26 21:23:47 +02:00
Romain Quetiez
442721bcb5 Optimize tests execution time (no need for process isolation as long as we leave the premises clean) 2023-10-26 21:22:54 +02:00
Romain Quetiez
1a9049d277 Optimize tests execution time (no need for process isolation as long as we leave the premises clean) 2023-10-26 21:16:24 +02:00
Romain Quetiez
c0931af91a Optimize tests execution time (no need for process isolation as long as we leave the premises clean, set file modification date instead of waiting for 1 second) 2023-10-26 21:15:57 +02:00
Romain Quetiez
29e9a06dc1 Optimize tests execution time (no need for process isolation as long as we leave the premises clean) 2023-10-26 21:10:47 +02:00
Romain Quetiez
d6415042ae Optimize tests execution time (no need for process isolation as long as we leave the premises clean) 2023-10-26 21:10:07 +02:00
Romain Quetiez
90006667fe Optimize tests execution time (copy fixture files only when necessary) 2023-10-26 20:58:26 +02:00
Romain Quetiez
fd351df08b Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-10-26 20:53:24 +02:00
Romain Quetiez
7419749ba6 Prerequisites for boosting tests 2023-10-26 20:51:28 +02:00
Romain Quetiez
73bed04555 Twig tests not executed 2023-10-26 10:47:11 +02:00
Romain Quetiez
8893cdac1d Optimize tests execution time (no need for process isolation as long as we leave the premises clean) 2023-10-26 10:44:37 +02:00
Romain Quetiez
7f245a15be Optimize tests execution time (suppress meaningless test and merge two test in one, while preserving test coverage) 2023-10-25 23:01:05 +02:00
Romain Quetiez
b5c46ccd4a Optimize tests execution time (x10 / no need for a systematic check of date formats, which was ok as a first approach) 2023-10-25 22:59:03 +02:00
Romain Quetiez
7fbc211c43 Optimize tests execution time (x50 / eval is way faster than exec) 2023-10-25 22:57:03 +02:00
Romain Quetiez
cf774cdb90 Explain why process isolation is a must 2023-10-25 22:18:05 +02:00
Romain Quetiez
722a58491c Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/php-unit-tests/src/BaseTestCase/ItopTestCase.php
2023-10-25 22:08:08 +02:00
Romain Quetiez
037dfe1df6 Optimize tests execution time 2023-10-25 17:51:12 +02:00
Romain Quetiez
0b26d45014 Prerequisites for boosting tests 2023-10-25 17:50:41 +02:00
Molkobain
b9c566238a Merge remote-tracking branch 'origin/support/2.7' into support/3.0
Remove PHPUnit annotations as from support/3.0 and newer they are no longer necessary
2023-10-23 15:09:49 +02:00
Molkobain
4fd8177165 N°3715 - Fix unit tests 2023-10-23 14:55:06 +02:00
Anne-Cath
0cc0f39d9e Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-10-20 17:04:26 +02:00
Anne-Catherine
a2cdf214f0 N°3715 - Export above 1000 entries ignore obsolete data from user preference (#468)
* N°3715 - Export above 10000 entries ignore obsolete data from user preference
2023-10-20 17:02:16 +02:00
Anne-Cath
4f75d012e5 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-10-20 16:54:37 +02:00
Anne-Catherine
013173019f N°2909 - Search on Enum, Date, TagSet,... with index fails (#496) 2023-10-20 16:45:35 +02:00
Stephen Abello
fadfd94bac Merge branch 'support/2.7' into support/3.0 2023-10-17 09:19:16 +02:00
Stephen Abello
9469681a0c N°6777 - Security hardening 2023-10-17 09:12:40 +02:00
Pierre Goiffon
da27ddba82 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/utils.inc.php
#	pages/ajax.render.php
2023-10-13 17:27:03 +02:00
Pierre Goiffon
c72cb7e70e N°6606 security hardening 2023-10-13 17:15:37 +02:00
Pierre Goiffon
9df92665e0 N°6606 Backport of utils::ENUM_SANITIZATION_FILTER_* constants
Were introduced in 3.0.0, but not added to the support/2.7 branch
2023-10-13 17:10:35 +02:00
Stephen Abello
3647291475 N°6778 - Security hardening 2023-10-02 15:06:17 +02:00
Molkobain
6dc6392fab Merge remote-tracking branch 'origin/support/3.0.3' into support/3.0 2023-09-26 22:20:02 +02:00
Anne-Catherine
e793b02f8b N°6766 - Fix dependent fields not updated due to WizardHelper.UpdateFields() being triggered too early (#548)
* N°6766 - Javascript : function WizardHelper.UpdateFields triggered to early does not update fields

* N°6766 - Code review

---------

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2023-09-26 12:25:56 +02:00
Molkobain
fc6e98b534 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-09-20 16:12:51 +02:00
Molkobain
8ecebee511 PHP unit tests: Fix typo for "final private" methods as they can't be both 2023-09-20 16:11:39 +02:00
Pierre Goiffon
2690fa3315 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-09-19 12:27:19 +02:00
Pierre Goiffon
35cd965360 N°6629 Update ci_description php_version 2023-09-19 12:25:40 +02:00
Pierre Goiffon
83a5b98f82 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-09-19 09:58:40 +02:00
Pierre Goiffon
e5dd51f637 N°6600 Portal download attachment : don't display anymore SQL query on attachment not found error (#525) 2023-09-19 09:54:43 +02:00
Molkobain
4923418f58 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-09-19 08:39:41 +02:00
Molkobain
0a6c82dfe1 N°6752 - PHP unit tests: Fix typo in postbuild_integration.xml.dist 2023-09-19 08:37:46 +02:00
Molkobain
2dd7f5cada Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-09-18 15:37:32 +02:00
Molkobain
24c0f4950f Add missing .htaccess / web.config files in .gitignore for /extensions folder 2023-09-18 15:26:06 +02:00
Molkobain
d4dbbc59d4 N°6754 - PHP unit tests: Add local PHPUnit XML files to .gitignore 2023-09-18 15:23:52 +02:00
Molkobain
dc0cd44c79 N°6752 - PHP unit tests: Migrate usages of unitestautoload.php to composer autoloader 2023-09-18 15:14:44 +02:00
Pierre Goiffon
f3c4fcb0f5 💡 Pages files : add depreciation version 2023-09-18 15:07:32 +02:00
odain
6046f44f56 Merge branch 'support/2.7' into support/3.0 2023-09-15 10:08:08 +02:00
odain
6c6131ce03 N°5491 - test enhancement to reduce false positive 2023-09-15 10:07:42 +02:00
Stephen Abello
343e87a8d4 N°6581 - Security hardening 2023-09-15 09:55:51 +02:00
odain-cbd
e76728b2bf N°5491 - Inconsistent dictionnary entries regarding arguments to pass to Dict::Format-test first (#545) 2023-09-13 12:02:49 +02:00
odain
f65c690462 N°5491-fix test 2023-09-13 10:03:05 +02:00
odain
ecf8bc42fa Merge branch 'support/2.7' into support/3.0 2023-09-13 10:01:15 +02:00
Pierre Goiffon
ea8509db1f N°6709 Use ItopTestCase::RequireOnceCurrentModuleFile in GetAppRoot 2023-09-07 14:47:36 +02:00
Pierre Goiffon
df25ce76b6 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-09-07 14:43:29 +02:00
Pierre Goiffon
e946fc65fc N°6709 New ItopTestCase::RequireOnceCurrentModuleFile 2023-09-07 14:38:19 +02:00
Pierre Goiffon
dbe2f66539 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-09-06 09:07:45 +02:00
Pierre Goiffon
0d8ff7bbac N°6629 Set commit tests back to Mysql
For now we have perf issues on Jenkins with MariaDB (see N°6694)
2023-09-04 10:25:41 +02:00
Eric Espie
61a9a4ac65 Fix unit tests for MariaDB 2023-09-01 09:29:21 +02:00
acognet
1f4dcc4f9e N°5136 - Relations: Fix "Select All objects" adding obsolete objects even if "show obsolete data" param. not activated - Merge from support/2.7 2023-08-31 16:04:03 +02:00
acognet
e86309669e Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	pages/ajax.render.php
2023-08-31 15:56:16 +02:00
Pierre Goiffon
6ebcd44bb1 💡 N°6658 Add more comments and since tags 2023-08-31 15:34:44 +02:00
Anne-Catherine
bf768311c2 N°5136 - "Select All objects" add obsolete objects even if the parameter show obsolete data is not activated (#467) 2023-08-31 15:13:20 +02:00
Molkobain
d130959692 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/metamodel.class.php
2023-08-18 10:14:51 +02:00
Molkobain
a8c689c6c0 N°6436 - Add unit test to ensure that we don't lose an API during merge between branches 2023-08-18 09:55:45 +02:00
Molkobain
1990ccb5d8 N°6436 - Move interfaces enumeration from 1 line to 1 line / interface (and re-ordered them) for easier merges in newer branches 2023-08-18 09:52:55 +02:00
Molkobain
e107be56e4 N°6097 - Tests: Fix missing hook entry in PHPUnit XML file that led to compiled environment being re-build for each test case 2023-08-18 09:51:15 +02:00
Molkobain
f6653e1594 N°6436 - Restore 3.0 APIs lost during 6433678d merge 2023-08-17 17:47:46 +02:00
Romain Quetiez
65bb76b9e3 N°6658 - Boost PHPUnit tests execution 2023-08-17 17:27:55 +02:00
Molkobain
d951d3b872 💚 Fix typo in extended class name 2023-08-11 09:05:30 +02:00
Molkobain
ccceb870e3 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/php-unit-tests/src/BaseTestCase/ItopDataTestCase.php
#	tests/php-unit-tests/src/BaseTestCase/ItopTestCase.php
2023-08-10 15:53:05 +02:00
Molkobain
ed6df77cbb N°6097 - Tests: Optimize performances by creating custom env. only once and re-using it across test classes 2023-08-10 15:45:39 +02:00
Molkobain
1ad28312ec N°6097 - Tests: Introduce autoloader for "utility" classes and move them to a sub-folder for better organization as folder was still messy
Note that unittestautoload.php is now useless. We just keep for now until everything is migrated (projects / branches / modules)
2023-08-10 15:45:39 +02:00
Molkobain
f002aa04cd N°6097 - Tests: Enable PHP unit tests on a custom DataModel 2023-08-10 15:45:39 +02:00
Molkobain
b86d70623e N°6097 - Tests: Temporarily add test case for the new ItopCustomDatamodelTestCase class 2023-08-10 15:45:39 +02:00
Molkobain
fe3467309d N°6097 - Tests: Refactor base test classes for better extensibility 2023-08-10 15:45:39 +02:00
Molkobain
851ab9c356 N°6097 - Add \utils::GetDataPath() method to avoid duplicating manual path build 2023-08-10 15:45:39 +02:00
Molkobain
aef3c2e609 N°6097 - Fix \CMDBSource::DropDB() not resetting cache like \CMDBSource::DropTable() which can lead to errors when trying to re-create it afterwards 2023-08-10 15:45:39 +02:00
Pierre Goiffon
f04fc546b5 N°6643 Fix TypeError in \CMDBSource::LogDeadLock 2023-08-10 14:34:09 +02:00
Pierre Goiffon
13ad98b9b3 Add other integration tests in the beforeSetup group
All of those tests can be ran without a running iTop instance, and are blocking
2023-08-08 15:34:27 +02:00
Pierre Goiffon
4be54fdd65 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-08-08 15:33:36 +02:00
Pierre Goiffon
6d13397ba1 Add other integration tests in the beforeSetup group
All of those tests can be ran without a running iTop instance, and are blocking
2023-08-08 15:33:09 +02:00
Pierre Goiffon
d64a91d4ce Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/metamodel.class.php
2023-08-04 14:58:22 +02:00
Pierre Goiffon
c0c8a13864 💡 \MetaModel::GetObject : remove documented throw Exception 2023-08-04 14:55:38 +02:00
Pierre Goiffon
d2eef06276 AttributeURLTest : remove useless separateProcess annotations 2023-08-03 11:08:47 +02:00
Pierre Goiffon
880a824f2f N°6562 Replace new DOMText() by \DOMDocument::createTextNode
Because init using constructor outputs a read only node, see https://www.php.net/manual/en/domelement.construct.php
Thanks @Hipska
See conversation in 734a788
2023-08-03 09:40:39 +02:00
Pierre Goiffon
7aa478d6ff N°6562 💡 Fix comment
Thanks @Molkobain !
2023-08-02 10:35:30 +02:00
Pierre Goiffon
734a788340 N°6562 Fix DOMNode->textContent write
This attribute is read only
Causes layout issues on PHP 8.1.21 and 8.2.8
2023-08-01 14:22:56 +02:00
Pierre Goiffon
e5b6e2eb8c N°4354 N°6587 Add test to cover $oUser->Get('profile_list') VS security.hide_administrators config param 2023-07-27 16:42:56 +02:00
Pierre Goiffon
1682a85cc0 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-07-26 12:07:35 +02:00
Pierre Goiffon
cd9beec313 Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2023-07-26 12:07:09 +02:00
Pierre Goiffon
8295eaed90 Merge remote-tracking branch 'origin/support/2.5' into support/2.6 2023-07-26 12:06:32 +02:00
Eric Espie
829b648dd2 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-07-25 17:55:45 +02:00
Eric Espie
5475b9fbbe N°3454 - MoveToProd in 2 steps - fix utils::GetCurrentModuleName() 2023-07-25 17:44:43 +02:00
Eric Espie
6f8e7c7002 N°3454 - MoveToProd in 2 steps - fix utils::GetCurrentModuleUrl() 2023-07-25 17:20:37 +02:00
Pierre Goiffon
772368ef8a 💡 PHPDoc for object list panels 2023-07-24 15:38:57 +02:00
Pierre Goiffon
a57b6471c9 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-07-24 11:59:40 +02:00
Pierre Goiffon
bc7c1b4744 N°6590 Fix DictionariesConsistencyTest for PL dict files 2023-07-24 11:14:37 +02:00
Eric Espie
046e857768 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/config.class.inc.php
2023-07-19 15:19:06 +02:00
Eric Espie
4d8246c4d8 N°6436 - Integrate Performance Audit pre requisite in iTop Pro 2.7.9 (changed config variable name) 2023-07-19 15:13:43 +02:00
Eric Espie
5c61d725e1 N°6436 - Integrate Performance Audit pre requisite in iTop Pro 2.7.9 (changed config variable name) 2023-07-19 15:06:00 +02:00
Eric Espie
00b070b3cf Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/kpi.class.inc.php
2023-07-19 10:44:22 +02:00
Eric Espie
2c4cad4dac N°6436 - Integrate Performance Audit pre requisite in iTop Pro 2.7.9 (avoid unnecessary calls) 2023-07-19 10:37:41 +02:00
Stephen Abello
89145593ef N°6552 - Security hardening 2023-07-19 09:25:48 +02:00
Eric Espie
b2e80d37dd N°6436 - typo 2023-07-18 14:48:32 +02:00
Eric Espie
6432678de9 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/cmdbabstract.class.inc.php
#	application/utils.inc.php
#	bootstrap.inc.php
#	composer.json
#	core/MyHelpers.class.inc.php
#	core/cmdbsource.class.inc.php
#	core/config.class.inc.php
#	core/dbobject.class.php
#	core/kpi.class.inc.php
#	core/metamodel.class.php
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_real.php
#	lib/composer/autoload_static.php
2023-07-18 14:36:58 +02:00
Molkobain
71ed784c60 N°6532 - Fix missing "/" in path
(cherry picked from commit 32fd75bc4b)
2023-07-18 09:40:34 +02:00
Eric Espie
da45651121 Merge branch 'feature/6548_Hide_DBHost_and_DBUser_in_log' into support/2.7 2023-07-18 09:34:48 +02:00
Eric Espie
d388ce9a06 Merge branch 'feature/6548_Hide_DBHost_and_DBUser_in_log' into support/2.7 2023-07-18 09:17:40 +02:00
Eric Espie
47e71d8838 Merge branch 'feature/6436-Integrate_Performance_Audit_extensibility' into support/2.7 2023-07-18 09:17:05 +02:00
Stephen Abello
2b5973ec67 N°6436 - Integrate Performance Audit pre requisite in iTop Pro 2.7.9 2023-07-18 09:15:37 +02:00
Eric Espie
78396d8e4a 6548 - [ER] Hide DBHost and DBUser in log 2023-07-10 17:37:27 +02:00
Pierre Goiffon
40d63a2fa4 N°3663 💡 Fix depreciation comment in core/coreexception.class.inc.php 2023-07-07 10:24:15 +02:00
Pierre Goiffon
556b9ad89a N°6532 Fix "failed to open stream" error on require_once approot in coreexception.class.inc.php
Was occurring in TemplateFieldValueTest templates-base phpunit test
2023-07-07 09:31:34 +02:00
Stephen Abello
9afc22bd8f N°6123 - Add tests and comments 2023-07-07 09:29:15 +02:00
Pierre Goiffon
a010239efb Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-07-06 15:48:42 +02:00
Pierre Goiffon
264a8cd70a N°6494 - Some tests are run twice, some never
(cherry picked from commit a2a0b2cd0b)

(cherry picked from commit 4c9ea0c9d4)

# Conflicts:
#	tests/php-unit-tests/integration-tests/DictionariesConsistencyTest.php
2023-07-06 15:45:09 +02:00
Stephen Abello
aa1834170b N°6427 - Fix SwiftMailer not retrieving sendmail path 2023-07-06 14:31:54 +02:00
Stephen Abello
f94d67ab35 N°6340 - Fix permission refused when sending an email and renewing OAuth token in synchronous mode 2023-07-06 10:28:10 +02:00
Stephen Abello
3048c8c41f N°5560 - Display an error when trying to regenerate an expired OAuth token 2023-07-06 09:52:00 +02:00
Stephen Abello
246e4a9f50 N°6123 - Fix warnings when launching a backup on MariaDB > v10.6.1 with localhost dbhost 2023-07-06 09:28:01 +02:00
Molkobain
8907525b78 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-07-05 08:56:17 +02:00
Molkobain
6d58adb6dd N°6359 - Fix JS crash due to new version trying to detect MSIE browser through a dependency that we don't have.
Cherry-picked from f889c53d71
2023-07-05 08:41:00 +02:00
Stephen Abello
764a170cd0 N°6483 - Security hardening 2023-07-03 14:29:45 +02:00
Molkobain
5a33fb7a6a N°6474 - Fix regression introduced by 70e6f707 2023-06-27 18:16:55 +02:00
Benjamin Dalsass
2cca57c7fa N°6431 - CSV bulk export text delimiter option not initialized correctly 2023-06-16 15:50:28 +02:00
Pierre Goiffon
52820925b1 N°4725 DeprecatedCallsLog::NotifyDeprecatedFile remove throw ConfigException
Those exceptions are handled silently since 3.0.1
2023-06-14 19:01:50 +02:00
Pierre Goiffon
1824111de8 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-06-14 10:28:30 +02:00
Pierre Goiffon
5a0b5364d6 N°4698 setup/phpinfo.php : if no iTop installation then display a proper message instead of an exception (#265) 2023-06-14 10:18:38 +02:00
Pierre Goiffon
76eed2eba0 N°6098 updateLicenses script : check availability of the required JQ command (#458)
This packaging script requires both bash and the JQ command when running on Windows.
If the later isn't available, it will run without throwing an error...

With this change the script will now check directly at launch for the JQ command availability, and exit in error if it isn't.
2023-06-14 10:17:00 +02:00
Eric Espie
5d5589dd64 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-06-14 09:09:12 +02:00
Eric Espie
1ec671ef61 N°6351 - code hardening 2023-06-14 09:08:42 +02:00
Thomas Casteleyn
b8199a6e2c N°6418 - Fix dutch translations on impact relation view (#499)
* Fix author and copyrights
* Correct NL dict for impact relation view
2023-06-13 17:48:36 +02:00
Molkobain
9f38eec40a N°4106 - Reword PHPDoc to avoid confusion as the @internal was not accurate 2023-06-13 11:42:28 +02:00
Eric Espie
5f5537b8b9 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	js/breadcrumb.js
2023-06-12 11:39:13 +02:00
Eric Espie
72716b7ec8 N°6396 - Protect URL display 2023-06-12 11:36:51 +02:00
Eric Espie
e288af4ddb Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/setup_params/default-params.xml
2023-06-08 14:33:54 +02:00
Eric Espie
4f999de844 N°6359 - ⬆️ Update jQuery BBQ (from https://github.com/cee-chen/jquery-bbq) 2023-06-08 14:30:09 +02:00
Anne-Catherine
f47133bc28 N°6125 - Issue with GetAttributeFlags and GetInitialStateAttributeFlags within iTop 3.0.2 (#474) 2023-06-08 11:12:22 +02:00
odain
ea49c0a87c enable authent-cas in ci 2023-06-07 21:44:17 +02:00
odain
6cc971849b ci: enhance AddProfile 2023-06-07 21:44:00 +02:00
Eric Espie
0fbd41a884 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 -> fix syntax error 2023-06-07 17:30:39 +02:00
Eric Espie
70e6f707c4 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 -> composer autoloader 2023-06-07 17:23:47 +02:00
Eric Espie
e76ada641f Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/loginbasic.class.inc.php
#	application/loginexternal.class.inc.php
#	application/loginform.class.inc.php
#	application/loginurl.class.inc.php
#	application/loginwebpage.class.inc.php
#	composer.lock
#	datamodels/2.x/authent-cas/src/CASLoginExtension.php
#	lib/composer/autoload_real.php
#	lib/composer/installed.php
#	synchro/synchro_exec.php
#	synchro/synchro_import.php
#	tests/php-unit-tests/unitary-tests/application/utilsTest.php
2023-06-07 17:21:09 +02:00
Pierre Goiffon
2405810864 N°6238 Security hardening 2023-06-07 16:45:35 +02:00
Eric Espie
fff46d99fc N°6358 - Login REST API - renamed test 2023-06-07 15:31:51 +02:00
odain
3a891f707c ci: enhance AddProfile test method to work with any User (not only UserLocal) 2023-06-07 15:06:28 +02:00
odain
8b6ea43ebe N°6358 - Login REST API - fix cas + add tests 2023-06-07 15:05:32 +02:00
Eric Espie
90cf7502e8 N°6358 - Login REST API 2023-06-07 10:09:30 +02:00
Eric Espie
c596fa2967 N°6358 - Login API REST 2023-06-07 09:17:24 +02:00
Timothee
a45177410e N°6350 - Fixing phpunit test 2023-06-06 16:47:06 +02:00
Eric Espie
b8f61362f5 N°6348 - Hardening code 2023-06-01 16:44:40 +02:00
Eric Espie
e3ba826e5d N°6349 - Hardening code 2023-06-01 16:36:56 +02:00
Eric Espie
17d22219d2 N°6350 - Fix unit tests 2023-06-01 16:30:09 +02:00
Eric Espie
a49025f371 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/utils.inc.php
2023-06-01 16:04:52 +02:00
Eric Espie
9e96ea2873 N°6350 - code hardening 2023-06-01 15:35:56 +02:00
Eric Espie
1172159745 N°6351 - code hardening 2023-06-01 15:12:50 +02:00
Pierre Goiffon
cdcc069099 Fix typo in exception message
Regression introduced in fe179079 in support/3.0 branch and upwards
2023-05-09 14:02:02 +02:00
odain
8c639fc23a N°5753 - add config parameter allow_rest_services_via_tokens to bypass rest secure profile option 2023-05-05 15:53:32 +02:00
odain
da5a825c7e N°6171 - Password Expiration: can expire mode has no effect on user who have never changed their password 2023-05-05 11:37:44 +02:00
Pierre Goiffon
b9230ad402 N°6274 DeprecatedCallsLogTest : replace expectException deprecated calls
Message was : Support for using expectException() with PHPUnit\Framework\Error\Warning is deprecated and will be removed in PHPUnit 10. Use expectWarning() instead.
2023-05-05 10:16:56 +02:00
Pierre Goiffon
959ac7e3be N°6274 DeprecatedCallsLogTest : fix expected exception mismatch in PHP 8.0+
Undefined offset notice was changed to a warning in PHP 8.0... Also message was changed :(
2023-05-05 09:13:03 +02:00
Pierre Goiffon
1884596ecd N°6274 Fix log.class.inc.php crashing cause cannot load ItopTestCase class
Now the constant name is defined in approot
2023-05-04 17:34:14 +02:00
Pierre Goiffon
584cfa8cbf N°6274 Fix PHP Notices not caught in ItopDataTestCase PHPUnit
This was caused by the set_error_handler() done in DeprecatedCallsLog during startup

Now we are :
* not registering the handler if a PHPUnit test is running (based on a constant set in ItopTestCase::setUp)
* on registration only do it for the required notices
2023-05-04 17:08:47 +02:00
Stephen Abello
eebc61385d N°6009 - Fix restore backup button not working when JS dependencies are present 2023-05-02 09:24:54 +02:00
Pierre Goiffon
3c15186685 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-04-26 17:12:08 +02:00
Pierre Goiffon
fa038ded3d N°6254 ItopDataTestCase::CreateUserRequest : fix new argument default value
Was creating error Too few arguments passed
2023-04-26 16:42:27 +02:00
Pierre Goiffon
e7ea1b831c N°6254 ItopDataTestCase::CreateUserRequest : now pass fields values as array
More versatile way of doing things !
2023-04-26 16:22:26 +02:00
Molkobain
f15ac75f8f Merge remote-tracking branch 'origin/support/3.0.3' into support/3.0 2023-04-26 11:25:04 +02:00
Molkobain
c6edbf982d N°6124 - Performance: Draw datatable only once when elements added in linksets 2023-04-26 11:24:34 +02:00
Molkobain
5aea7ccbc9 N°6124 - Performance: Draw datatable only once when elements remove in linksets 2023-04-26 10:33:18 +02:00
Molkobain
e28dbebbd5 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/displayblock.class.inc.php
#	dictionaries/en.dictionary.itop.ui.php
#	dictionaries/fr.dictionary.itop.ui.php
2023-04-25 21:56:42 +02:00
Molkobain
4aff65f98b N°6217 - Add accessiblity meta data for title on "Power menu" 2023-04-25 21:51:32 +02:00
Molkobain
8aba578cfa Merge remote-tracking branch 'origin/support/3.0.3' into support/3.0 2023-04-25 21:05:42 +02:00
Molkobain
9d3e389011 N°6124 - Workaround performance problem on adding items to an object with an n:n relation having a large volume 2023-04-25 17:43:51 +02:00
acognet
7e7f8577e8 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/displayblock.class.inc.php
2023-04-25 15:14:22 +02:00
acognet
3c94974d9d N°541 - Dashlets: Improve readability when to much labels (pie chart) or too long labels (bar chart) 2023-04-25 12:09:11 +02:00
acognet
d6e5069dd5 N°541 - Dashlets: Improve readability when to much labels (pie chart) or too long labels (bar chart) 2023-04-24 14:26:33 +02:00
Stephen Abello
f839638e0b N°6188 - Creation cancellation in pop-up while in edition of parent object wrongfully returns to object list 2023-04-21 16:12:37 +02:00
Pierre Goiffon
740ff8c649 💡 DeprecatedCallsLog phpdoc 2023-04-21 14:58:00 +02:00
Molkobain
cfe227e0c7 N°6216 - Fix line-height being too big in the attachments table 2023-04-20 15:28:20 +02:00
Molkobain
ed79c8f099 Merge remote-tracking branch 'origin/support/3.0.3' into support/3.0 2023-04-20 12:53:34 +02:00
Molkobain
4560f751d1 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/displayblock.class.inc.php
#	application/itopwebpage.class.inc.php
#	dictionaries/en.dictionary.itop.ui.php
#	dictionaries/fr.dictionary.itop.ui.php
2023-04-20 12:53:12 +02:00
Molkobain
46e869d1f4 N°6124 - Workaround performance problem on the modification of an object with an n:n relation having a large volume 2023-04-20 12:22:12 +02:00
Molkobain
fbd72b2783 N°6217 - Add accessiblity meta data for title on "Power menu" 2023-04-20 11:03:43 +02:00
Molkobain
778118cfb4 N°6204 - REST API: Add unit test for callback parameter 2023-04-18 22:34:11 +02:00
Molkobain
096ed9a63a N°6204 - Improve REST API unit test readability 2023-04-18 22:14:39 +02:00
Molkobain
06eb79d4f4 N°6204 - Fix REST/JSON API crash when using JSON-P and iBackofficeDictXXX interfaces 2023-04-18 14:42:36 +02:00
Anne-Catherine
4e95ca3c7b N°541 - Dashlets: Improve readability when to much labels (pie chart) or too long labels (bar chart) (#452)
* N°541 - Dashlets: Improve readability when to much labels (pie chart) or too long labels (bar chart)
2023-04-13 11:23:20 +02:00
Pierre Goiffon
4c626d0782 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/log.class.inc.php
2023-04-12 10:22:34 +02:00
Pierre Goiffon
1114ed9562 N°6099 DeadLockLog : improve documentation and use existing constants (#441) 2023-04-12 10:21:34 +02:00
Pierre Goiffon
1ddfaf0b61 N°6100 ObjectFormManager::OnSubmit : better log for DBWrite exceptions (#353)
Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2023-04-11 18:09:45 +02:00
Pierre Goiffon
c6fb03547f Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-04-11 17:55:26 +02:00
Pierre Goiffon
34368fe795 N°6173 \HTMLSanitizer::Sanitize : Fix handling only svg_sanitizer (#450) 2023-04-11 17:52:41 +02:00
Pierre Goiffon
db46298cb8 Merge branch 'support/3.0.3' into support/3.0 2023-04-11 09:19:56 +02:00
Pierre Goiffon
064e8ee511 Fix AttributeDefinitionTest parse error in PHP 7.2
(cherry picked from commit 307edd3f7a)
2023-04-11 09:19:31 +02:00
Eric Espie
424e7b37d7 Merge branch 'support/3.0.3' into support/3.0 2023-04-07 09:44:38 +02:00
Eric Espie
ca7aa482ab N°6085 - UNION is not supported in UserRightsProfile::GetSelectFilter
(cherry picked from commit 8ffddeff01)
2023-04-07 09:43:50 +02:00
Eric Espie
368b3f4ef7 N°6085 - UNION is not supported in UserRightsProfile::GetSelectFilter
(cherry picked from commit 21d37fb237)
2023-04-07 09:43:40 +02:00
Molkobain
dc8e6f314a N°6085 - UNION is not supported in UserRightsProfile::GetSelectFilter
(cherry picked from commit fca4006811)
2023-04-07 09:43:25 +02:00
Eric Espie
8ffddeff01 N°6085 - UNION is not supported in UserRightsProfile::GetSelectFilter 2023-04-05 17:42:26 +02:00
Eric Espie
21d37fb237 N°6085 - UNION is not supported in UserRightsProfile::GetSelectFilter 2023-04-05 17:07:23 +02:00
Molkobain
fca4006811 N°6085 - UNION is not supported in UserRightsProfile::GetSelectFilter 2023-04-05 15:58:31 +02:00
Molkobain
c3b00939dd N°6140 - Add HTML metadata on custom fields to be aligned with regular fields 2023-03-31 17:58:09 +02:00
Molkobain
75df33f606 N°6139 - Add HTML metadata on activity panel to be aligned with regular fields 2023-03-30 18:39:09 +02:00
Molkobain
78d8829d65 N°6131 - Improve robustness of tooltips helper when no DOM element passed to CombodoTooltip::InitTooltipFromMarkup() 2023-03-27 18:04:01 +02:00
Pierre Goiffon
307edd3f7a Fix AttributeDefinitionTest parse error in PHP 7.2 2023-03-21 09:03:54 +01:00
Molkobain
6bf906a72f Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	js/dashboard.js
2023-03-17 15:44:23 +01:00
Molkobain
0f016d7511 N°6112 - Dashboard: Improve robustness by trimming dashlet ID returned by server 2023-03-17 15:37:57 +01:00
Pierre Goiffon
d782987f50 README : fix requirements link 2023-03-14 17:08:55 +01:00
Molkobain
b1fd7716f6 Fix community-licenses.xml 2023-03-14 12:08:54 +01:00
Molkobain
ac7abb3049 Prepare iTop 3.0.3 release
* Increase constants version to 3.0.3
* Increase modules version to 3.0.3
* Update licenses file
2023-03-14 09:55:18 +01:00
Pierre Goiffon
3689f3d026 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/php-unit-tests/unitary-tests/core/TriggerTest.php
2023-03-10 16:24:17 +01:00
Pierre Goiffon
5ee6223434 N°5893 Add test for \TriggerOnObject::LogException 2023-03-10 16:04:55 +01:00
Molkobain
4bfc1747b7 N°5784 - Fix AttributeOneWayPassword::HasAValue() implementation 2023-03-08 10:54:55 +01:00
Molkobain
15f32bf843 N°5784 - Fix ormPassword::IsEmpty() method 2023-03-08 10:04:59 +01:00
Molkobain
0ba386c0bc N°5784 - Rename unit test file to match convention 2023-03-08 09:47:42 +01:00
Molkobain
0c3cdb202b N°5784 - Fix ormPassword::IsEmpty() using the wrong class property 2023-03-08 09:36:52 +01:00
Molkobain
03ac3d4e7c N°5784 - Fix unit test for PHP 8.2 2023-03-08 09:34:35 +01:00
acognet
6510dc5c51 N°3805 - Collectors not working on iTop 3.0 (cherry picked from 4d7bac89f3 on origin/develop) 2023-03-07 22:58:38 +01:00
Molkobain
01faf39372 Tests: Force Synchro unit tests not to verify SSL certificate as most dev / test envs are self-signed 2023-03-07 22:50:29 +01:00
Molkobain
176e373d6c N°5530 - Fix list of impacted elements (Impact Analysis) not display correctly due to mixup in async JS files loading 2023-03-07 22:03:44 +01:00
Molkobain
a34274b883 N°5784 - PHP 8.0: Fix mandatory attribute not visible in transition form due to bad emptiness test (#379)
* N°5784 - PHP 8.0: Fix mandatory attribute not visible in transition form due to bad emptiness test

* N°5784 - Rework AttributeDefinition::HasAValue() implementation after code review

* N°5784 - Add unit test
2023-03-07 10:16:14 +01:00
Pierre Goiffon
03fb78c38c N°6068 Setup : fix no formatting on error messages 2023-03-06 14:23:21 +01:00
Stephen Abello
c9e656f7a0 N°4460 - Fix configuration editor selected line contrast in Darkmoon 2023-03-06 11:40:32 +01:00
Pierre Goiffon
976566ec71 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	setup/setuppage.class.inc.php
2023-03-06 11:26:33 +01:00
Pierre Goiffon
d908827787 N°6016 Setup Wizard : fix MissingDependencyException message logged as html in setup.log
Was the case since e831d66b (commit for parent bug N°5090)
Now we are getting the text version in the log (and still the html one on screen)

The unattended install isn't concerned : it just prints back CheckResult returned by \SetupUtils::CheckSelectedModules, with the exception text message ($e->getMessage())
2023-03-06 11:24:46 +01:00
Denis
93c0b98eb7 N°5922 - Fix plus button semantic on ext. key widget (#448)
* N°5922 - Enhance plus button on extkeywidget

* Properly reset the target class when closing the dialog

* Make icon buttons as actual clickable links for BeHat

* Apply suggestions from code review

Review by Guillaume. Thanks!

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2023-03-03 14:20:38 +01:00
Stephen Abello
98ab5aa1a4 N°4460 - Fix menu drawer color in Darkmoon 2023-03-03 10:59:49 +01:00
Stephen Abello
f117a2912b N°4460 - Fix minor contrast issue in Darkmoon 2023-03-03 10:50:02 +01:00
Stephen Abello
6594072617 N°4460 - Fix import contrast in Darkmoon 2023-03-03 10:43:39 +01:00
Stephen Abello
6bed56b34e Fix csv import SCSS file 2023-03-03 10:43:17 +01:00
Stephen Abello
94e8151519 N°4460 - Fix popover menu icons and separators style in Darkmoon 2023-03-03 10:24:52 +01:00
Stephen Abello
75b350f638 N°4460 - Fix ace editor style in Darkmoon 2023-03-03 10:06:47 +01:00
Stephen Abello
14cd60dd17 Fix hardcoded white color in markup 2023-03-02 16:36:07 +01:00
Stephen Abello
08f1e5a041 N°4460 - Fix configure this list contrast in Darkmoon 2023-03-02 16:36:07 +01:00
Stephen Abello
4c117d1a33 Fix hardcoded orange in backoffice style 2023-03-02 16:36:07 +01:00
Stephen Abello
f91dfbcf23 N°4460 - Fix datamodel viewer autocomplete contrast in Darkmoon 2023-03-02 16:36:07 +01:00
Stephen Abello
58497b380b Allow to overload datamodel viewer autocomplete style 2023-03-02 16:36:07 +01:00
Stephen Abello
03bff9f2c2 N°4460 - Fix export header contrast in Darkmoon 2023-03-02 16:36:07 +01:00
Stephen Abello
a34d3f91be Fix tabular fields selector SCSS variables 2023-03-02 16:36:06 +01:00
Stephen Abello
05753f174a N°4460 - Fix "load more entries" activity panel buttons contrast in Darkmoon 2023-03-02 16:36:06 +01:00
Stephen Abello
d0c89343b4 N°4460 - Fix skeletons placeholders contrast issue in Darkmoon 2023-03-02 16:36:06 +01:00
Stephen Abello
3021234895 N°4460 - Allow to customize skeleton placeholders colors using CSS3 variables 2023-03-02 16:36:06 +01:00
Stephen Abello
bccdb1bc3a N°4460 - Fix <code> contrast in Darkmoon 2023-03-02 16:36:06 +01:00
Molkobain
143410f4cd Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/dbobject.class.php
2023-02-28 15:20:07 +01:00
Pierre Goiffon
4cea418517 N°5893 - Log triggers exception in CRUD stack (#390)
* Log TriggerOnObjectCreate crash

* Log TriggerOnObjectUpdate crash

* Log TriggerOnObjectDelete crash

* Factorize TriggerOnObject log

* \TriggerOnObject::LogException : do not replace not persisted yet object keys
2023-02-28 15:13:28 +01:00
Molkobain
759b1825fe N°5918 - Fix activity panel disappearing when DoCheckToWrite fails 2023-02-28 13:33:47 +01:00
Anne-Catherine
370c1345d9 N°2916 - Import of IPv6 addresses fails when reconciliation is done on the IP (#382) 2023-02-28 12:08:32 +01:00
Anne-Catherine
af8f06c8c3 N°5603 - Autocomplete fails with error for an external key pointing to an abstract class with no friendlyname (#375) 2023-02-27 16:18:36 +01:00
Pierre Goiffon
bfe55183d0 N°6023 Fix error log
Thanks @Hipska !
2023-02-27 15:09:49 +01:00
odain
939771aa15 N°6022 - Make synchro scripts work by http via token authentication with SYNCHRO scopes 2023-02-27 11:07:52 +01:00
Molkobain
b174e4cab3 N°4517 - PHP 8.1: Fix deprecated notice for null value passed to string parameter of native PHP functions 2023-02-24 22:40:17 +01:00
Molkobain
61bd8b6bb4 N°4517 - PHP 8.1: Fix deprecated notice for null value passed to string parameter of native PHP functions 2023-02-24 21:40:10 +01:00
Pierre Goiffon
5c9eb7fa38 N°6020 PHPUnit for \utils::EscapeHtml and EscapedHtmlDecode methods
This will ensure conversion back and forth is working as expected (in other words, parameters to the php functions stays the same in both methods)
2023-02-23 18:56:28 +01:00
Pierre Goiffon
e960a4ad53 N°6023 Fix cannot load SVG files in AttributeImage since 3.0.0 (#449)
Caused by merge error in ddd6bf2

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2023-02-23 18:38:03 +01:00
Molkobain
7aad60ed1b Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.json
#	composer.lock
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_static.php
#	lib/composer/installed.php
#	lib/composer/platform_check.php
#	setup/setuputils.class.inc.php
2023-02-23 16:21:56 +01:00
Molkobain
97965277c7 N°6017 - Update OAuth dependencies 2023-02-23 15:57:32 +01:00
Pierre Goiffon
93aee5883b N°6020 New \utils::EscapedHtmlDecode method 2023-02-23 15:17:46 +01:00
Molkobain
18ed5ed526 N°6019 - Increase PHP min version to 7.1.3 to enable dependencies update 2023-02-23 14:53:48 +01:00
Pierre Goiffon
bbf6476570 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-02-23 12:05:38 +01:00
Pierre Goiffon
94c4f8c929 N°6016 MissingDependencyException : better log message (#355)
The error displayed on screen was already improved (see #280)
This commit improves the log message we can have for example by running unattended install.
2023-02-23 12:04:56 +01:00
Pierre Goiffon
d40cf7fe3b ReOrder LogChannels const 2023-02-23 11:52:19 +01:00
Pierre Goiffon
6997c0fd83 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/log.class.inc.php
2023-02-23 11:47:49 +01:00
Pierre Goiffon
822922df5c N°5588 - Improve PDF export robustness when AttributeImage dimensions cannot be determined (#350)
Can happen for example on SVG images
Now the export won't crash anymore, and we'll get a log (export channel, warning level) with  the object and attribute causing a problem as context

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2023-02-23 11:45:29 +01:00
Pierre Goiffon
cb2be0eccd N°5121 New AttributeURL validation use case
In comment as it isn't handled yet
2023-02-23 11:16:50 +01:00
Pierre Goiffon
f55fc8d264 N°6014 Validation pattern for URL : now handles commas in params (#356)
Seen on PRTG URLs

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2023-02-23 10:59:38 +01:00
Molkobain
ea2140258c N°5317 - Handle overlapping tables when table cells have fixed widths 2023-02-22 18:57:56 +01:00
Stephen Abello
31f2666941 Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	js/wizardhelper.js
2023-02-22 15:46:13 +01:00
Stephen Abello
cac7e94a67 N°5729 - Fix disabled button in bulk update/transition when picking a value in a drop-down list 2023-02-22 15:42:20 +01:00
Stephen Abello
da02a05fa3 Merge branch 'support/2.7' into support/3.0 2023-02-22 10:18:38 +01:00
Stephen Abello
6d019615d0 N°5865 - Restore DoCheckToWrite error messages in portal 2023-02-22 10:17:34 +01:00
Molkobain
ccdd315357 N°5919 - Add missing linkset descriptions in french and other languages 2023-02-21 22:14:57 +01:00
Eric Espie
9f81e4875a Merge branch 'hotfix/5944_GetClassesForInterface_filter' into support/3.0 2023-02-14 09:16:49 +01:00
Molkobain
4f102d764a Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-02-10 23:18:37 +01:00
Molkobain
dbd58cfeb6 Tests: Force RestAPI unit tests not to verify SSL certificate as most dev / test envs are self-signed 2023-02-10 23:07:27 +01:00
Eric Espie
99b7d66cf2 N°5944 - Wrong filter for utils::GetClassesForInterface() 2023-02-03 11:10:37 +01:00
Anne-Catherine
12ef74ec42 N°5849 - Fix wrong encoding of external keys in "Header with statstics" dashlet (#384)
N°5849 - Fix wrong encoding of external keys in "Header with statstics" dashlet #384
2023-01-30 16:06:10 +01:00
Molkobain
3ca4122673 N°5834 - Fix activity panel disappearing when creating a Ticket in 'resolved' state 2023-01-20 11:30:05 +01:00
Pierre Goiffon
efa20e77d0 N°3769 Add data-input-id HTML attribute to fields in a transition form
Was only present in object edit mode :(
2023-01-19 17:53:14 +01:00
Eric Espie
effc4141c7 N°5900 - DB integrity analysis crashes when too many errors - module version 2023-01-19 09:30:37 +01:00
Eric Espie
f75a51d59e N°5900 - DB integrity analysis crashes when too many errors - limit the results to 100 to avoid memory errors 2023-01-19 08:51:02 +01:00
Eric Espie
9dc54d6e4c N°5901 - Warnings in Details part of file system Tab 2023-01-18 16:39:40 +01:00
Eric Espie
640b1b9176 ✏️ Added missing use of class Toolbar 2023-01-18 16:38:16 +01:00
Molkobain
3459dc5997 N°5897 - Improve deprecated logs relevance for PHP "trigger_deprecation" 2023-01-17 16:29:25 +01:00
Pierre Goiffon
de7c9d965e 💡 PHPDoc in \DeprecatedCallsLog 2023-01-17 15:37:23 +01:00
Molkobain
4c127b6f61 Revert "N°4517 - PHP 8.1: Fix return type hint for iterable classes"
This reverts commit 61be903eb2.
2023-01-16 14:38:20 +01:00
Molkobain
61be903eb2 N°4517 - PHP 8.1: Fix return type hint for iterable classes 2023-01-16 14:21:00 +01:00
Pierre Goiffon
a50ed02057 N°4660 Fix OQLTest 2023-01-16 11:39:38 +01:00
Pierre Goiffon
0a7c8f9fd1 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/php-unit-tests/unitary-tests/core/OQLTest.php
#	tests/php-unit-tests/unitary-tests/core/iTopConfigParserTest.php
#	tests/php-unit-tests/unitary-tests/webservices/RestTest.php
2023-01-16 11:36:02 +01:00
Pierre Goiffon
f65e14397c N°4660 Fix permissions changes in tests 2023-01-16 11:22:23 +01:00
Pierre Goiffon
d7b94fb123 N°3769 Add data-input-type HTML attribute to fields in a transition form
Was only present in object edit mode :(
2023-01-12 16:40:31 +01:00
Pierre Goiffon
80a9ded404 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-01-12 10:43:09 +01:00
Pierre Goiffon
c696a81c3a N°5821 JenkinsFile : introduce buildDiscarder 2023-01-12 10:42:06 +01:00
Pierre Goiffon
b9ed00d53f N°4660 Fix iTopConfigParserTest setting permissions of iTop config file
Alternative method to restore config file
chmod cannot be used with +w
In \Config::WriteToFile we are using fopen with mode=w, so using the same
In consequence we are not modifying anymore the iTop config file permissions \o/
2023-01-11 16:04:21 +01:00
Molkobain
c4508ea80c N°4660 - Fix data synchro unit test failure due to another test not restoring correct user permissions on conf file 2023-01-11 14:26:23 +01:00
Molkobain
16390c9b00 N°5857 - PHPUnit: Replace usage of deprecated assetContains with assertStringContainsString 2023-01-11 13:26:54 +01:00
Molkobain
1271a895d1 N°5857 - PHPUnit: Replace usage of deprecated assetContains with assertStringContainsString 2023-01-11 11:59:01 +01:00
Eric Espie
030f1e2463 Fix Status test 2023-01-11 10:28:32 +01:00
Pierre Goiffon
5729d6a9cd 🎨 StatusIncTest : fix phpdoc, replace @expectedException 2023-01-11 10:02:59 +01:00
Molkobain
a5efef900c N°5608 - Harmonize namespaces and merge duplicated test files 2023-01-10 23:02:54 +01:00
Molkobain
c851a10982 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2023-01-10 22:49:13 +01:00
Molkobain
845adf43c6 N°5608 - Harmonize namespaces and merge duplicated test files 2023-01-10 22:36:35 +01:00
Molkobain
5916e4ea39 N°5608 - Ensure both old & new tests structure are ran for extensions for backward compatibility 2023-01-10 22:03:40 +01:00
Molkobain
7f37de777e N°5608 - Fix unit tests following restructuring Part III
* Missed a usage of "use_legacy_search" conf param on the last commit
* Fix log tests which didn't moved correctly from Git PoV 😕
2023-01-10 21:11:10 +01:00
Molkobain
bcf880f327 N°5608 - Fix unit tests following restructuring Part II
"use_legacy_search" conf param was removed some time ago
2023-01-10 19:23:54 +01:00
Thomas Casteleyn
b593beb8c7 N°5867 Display binary data size in SynchroReplica details (#286) 2023-01-10 18:53:00 +01:00
Molkobain
6aa9aa2831 N°5608 - Fix unit tests following restructuring Part I 2023-01-10 18:15:53 +01:00
Molkobain
d177ee4a7f Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	tests/manual-visual-tests/Backoffice/RenderAllUiBlocks.php
#	tests/php-unit-tests/ItopDataTestCase.php
#	tests/php-unit-tests/ItopTestCase.php
#	tests/php-unit-tests/integration-tests/dictionaries-test/fr.dictionary.itop.core.KO.wrong_php
#	tests/php-unit-tests/integration-tests/dictionaries-test/fr.dictionary.itop.core.OK.php
#	tests/php-unit-tests/integration-tests/iTopModulesPhpVersionChecklistTest.php
#	tests/php-unit-tests/integration-tests/iTopXmlVersionChecklistTest.php
#	tests/php-unit-tests/phpunit.xml.dist
#	tests/php-unit-tests/unitary-tests/application/SCSSCompilationTest.php
#	tests/php-unit-tests/unitary-tests/application/Session/SessionTest.php
#	tests/php-unit-tests/unitary-tests/application/ThemeHandlerTest.php
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/DO_NOT_CHANGE.css-variables.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/DO_NOT_CHANGE.light-grey.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/README.md
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/_included_file3.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/cross_reference1.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/cross_reference2.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/feature1/_feature1.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/included_file1.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/included_scss/included_file2.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/included_scss/included_file4.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/multi_imports.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/shortcut.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/shortcut2.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/simple_import.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/simple_import2.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/typography.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/css/ui-lightness/DO_NOT_CHANGE.jqueryui.scss
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-bg_diagonals-thick_18_b81900_40x40.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-bg_diagonals-thick_20_666666_40x40.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-icons_1c94c4_256x240.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-icons_222222_256x240.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-icons_E87C1E_256x240.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-icons_F26522_256x240.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-icons_ffd27a_256x240.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/css/ui-lightness/images/ui-icons_ffffff_256x240.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/ac-background.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/actions_right.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/bg.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/breadcrumb-separator.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/calendar.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/delete.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/desc.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/error.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/eye-closed-555.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/eye-closed-fff.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/eye-open-555.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/eye-open-fff.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/full-screen.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/green-header.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/green-square.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/indicator.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/info-mini.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/minus.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/ok.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/orange-header.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/plus.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/red-header.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/truncated.png
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/tv-collapsable-last.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/tv-collapsable.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/tv-expandable-last.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/tv-expandable.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/tv-item-last.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/testimages/images/tv-item.gif
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/themes/basque-red/main.css
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/themes/basque-red/main_imagemodified.css
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/themes/basque-red/main_importmodified.css
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/themes/basque-red/main_stylesheet.css
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/themes/basque-red/main_testcompilethemes.css
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/themes/basque-red/main_varchanged.css
#	tests/php-unit-tests/unitary-tests/application/theme-handler/expected/themes/basque-red/theme-parameters.json
#	tests/php-unit-tests/unitary-tests/application/theme-handler/getimages/expected-getimages.json
#	tests/php-unit-tests/unitary-tests/application/theme-handler/getimages/test-getimages.scss
#	tests/php-unit-tests/unitary-tests/core/ActionEmailTest.php
#	tests/php-unit-tests/unitary-tests/core/AttributeDefTest.inc.php
#	tests/php-unit-tests/unitary-tests/core/AttributeURLDefaultPattern.php
#	tests/php-unit-tests/unitary-tests/core/AttributeURLTest.php
#	tests/php-unit-tests/unitary-tests/core/BulkChangeTest.inc.php
#	tests/php-unit-tests/unitary-tests/core/CSVParserTest.php
#	tests/php-unit-tests/unitary-tests/core/DBObjectTest.php
#	tests/php-unit-tests/unitary-tests/core/DBSearchAddConditionPointingTo.php
#	tests/php-unit-tests/unitary-tests/core/ExpressionEvaluateTest.php
#	tests/php-unit-tests/unitary-tests/core/GetSelectFilterTest.php
#	tests/php-unit-tests/unitary-tests/core/InlineImageTest.php
#	tests/php-unit-tests/unitary-tests/core/Log/ExceptionLogTest.php
#	tests/php-unit-tests/unitary-tests/core/Log/ExceptionLogTest/Exceptions.php
#	tests/php-unit-tests/unitary-tests/core/Log/LogAPITest.php
#	tests/php-unit-tests/unitary-tests/core/Log/LogFileNameBuilderTest.php
#	tests/php-unit-tests/unitary-tests/core/LogAPITest.php
#	tests/php-unit-tests/unitary-tests/core/LogFileNameBuilderTest.php
#	tests/php-unit-tests/unitary-tests/core/MetaModelTest.php
#	tests/php-unit-tests/unitary-tests/core/OQLTest.php
#	tests/php-unit-tests/unitary-tests/core/UniquenessConstraintTest.php
#	tests/php-unit-tests/unitary-tests/core/XMLDataLoaderTest.php
#	tests/php-unit-tests/unitary-tests/core/dictApcuTest.php
#	tests/php-unit-tests/unitary-tests/core/dictTest.php
#	tests/php-unit-tests/unitary-tests/core/ormCaseLogTest.php
#	tests/php-unit-tests/unitary-tests/core/ormPasswordTest.php
#	tests/php-unit-tests/unitary-tests/core/ormStyleTest.php
#	tests/php-unit-tests/unitary-tests/setup/MFCompilerTest.php
#	tests/php-unit-tests/unitary-tests/setup/SubMFCompiler.php
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/1.7_to_1.6.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/1.7_to_1.6.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.6_to_1.7_2.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.6_to_1.7_2.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.7.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.7_to_1.6.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.7_to_1.6.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.7_to_1.6_2.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.7_to_1.6_2.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.7_to_3.0.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/1.7_to_3.0.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/3.0_to_1.7.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/3.0_to_1.7.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/Bug_4569.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/Convert-samples/Bug_4569.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_deleted_to_deleted.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_deleted_to_deleted.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_deleted_to_in-definition.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_deleted_to_in-definition.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_deleted_to_not-in-definition.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_deleted_to_not-in-definition.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_in-definition_to_deleted.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_in-definition_to_deleted.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_in-definition_to_in-definition.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_in-definition_to_in-definition.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_in-definition_to_not-in-definition.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_in-definition_to_not-in-definition.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_not-in-definition_to_deleted.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_not-in-definition_to_deleted.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_not-in-definition_to_in-definition.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_not-in-definition_to_in-definition.input.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_not-in-definition_to_not-in-definition.expected.xml
#	tests/php-unit-tests/unitary-tests/setup/iTopDesignFormat/MoveNode-samples/from_not-in-definition_to_not-in-definition.input.xml
#	tests/php-unit-tests/unitary-tests/setup/ressources/datamodels/datamodel-branding.xml
#	tests/php-unit-tests/unitary-tests/sources/application/Helper/WebResourcesHelperTest.php
#	tests/php-unit-tests/unitary-tests/sources/application/status/StatusIncTest.php
#	tests/php-unit-tests/unitary-tests/sources/application/status/status.php
#	tests/php-unit-tests/unitary-tests/synchro/DataSynchroTest.php
2023-01-10 15:27:44 +01:00
Molkobain
fbc0a898ae N°5608 - Move test files to corresponding directories after branch rebase 2023-01-10 12:11:12 +01:00
Molkobain
36f8e58e25 N°5608 - Use new ItopTestCase::RequireOnceXXX in unit tests 2023-01-10 12:11:12 +01:00
Molkobain
6a7dbb06b0 N°5608 - Add methods to require_once an iTop or a unit test file to avoid crashes when tests dir is moved 2023-01-10 12:11:12 +01:00
Molkobain
5721a324c1 Tests: Always display test status for better feedback 2023-01-06 22:30:09 +01:00
Molkobain
7de6c72154 Tests: Rename provider method name to match convention 2023-01-06 22:30:09 +01:00
Molkobain
c0cee02351 N°5608 - Factorize all core modules tests to a single test suite 2023-01-06 22:30:09 +01:00
Molkobain
bb674fb873 N°5608 - Move/rename "status" unit tests to match their counterpart location/name 2023-01-06 22:30:09 +01:00
Molkobain
6136eadd31 N°5608 - Fix some broken require paths since move/rename 2023-01-06 22:30:08 +01:00
Molkobain
87cb73c038 N°5608 - Rename "test" folder to "tests" to better match conventions 2023-01-06 22:30:08 +01:00
Molkobain
11d8547cef N°5608 - Move/rename unit tests to match their counterpart location/name 2023-01-06 22:30:08 +01:00
Molkobain
0998c73a1a N°5608 - Add README files 2023-01-06 22:30:07 +01:00
Molkobain
471f66649a N°5608 - Rename unitary test folders for better understanding 2023-01-06 22:30:07 +01:00
Molkobain
e8bf9cf688 N°5608 - Move "twig" PHP unit test to new folder
Notice: Test was not working, still not working
2023-01-06 22:30:07 +01:00
Molkobain
4f88a0e7d2 N°5608 - Move legacy PHP unit tests (not run by CI) to a dedicated folder 2023-01-06 22:30:07 +01:00
Molkobain
c6b0e273e6 N°5608 - Rename "VisualTests" folder to match new convention 2023-01-06 22:30:07 +01:00
Molkobain
d9539f9d01 N°5608 - Add comments to main autoloader 2023-01-06 22:30:06 +01:00
Molkobain
a3e309acb5 N°5608 - Revert "authent-local" test suite to its original rank as it is crashing the CI 🤔 2023-01-06 22:30:06 +01:00
Molkobain
c06cbfd4a9 N°5608 - Rename "coreExtensions" test suite to correct datamodel module (authent-local) 2023-01-06 22:30:06 +01:00
Molkobain
1d7e4e1a42 N°5608 - Move unit tests to a dedicated folder and start reorganizing to match iTop folder structure 2023-01-06 22:30:06 +01:00
Eric Espie
524e65a29b 📝 fix PHPDoc 2023-01-05 09:23:48 +01:00
Eric Espie
df7d7c877d N°5490 - PHP 8.0: Fix crash of bulk modify 2023-01-03 08:50:18 +01:00
Eric Espie
4bcad431aa 📝 Change packages for auto-documentation 2022-12-29 15:59:59 +01:00
Eric Espie
5fe32aac15 Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	application/applicationextension.inc.php
2022-12-29 12:40:37 +01:00
Eric Espie
88d9a29599 📝 Change packages for auto-documentation 2022-12-29 12:38:31 +01:00
Eric Espie
92a36dcfdd 📝 Change packages for auto-documentation 2022-12-29 12:24:56 +01:00
Eric Espie
23b4d4cb6b Merge branch 'support/2.7' into support/3.0 2022-12-28 09:52:52 +01:00
Eric Espie
b37e74b407 📝 Change packages for auto-documentation 2022-12-28 09:51:46 +01:00
Pierre Goiffon
cb6232cc05 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-12-15 15:36:43 +01:00
Pierre Goiffon
0d49c605e2 💡 Fix \DBSearch::FromOQL phpdoc + modifiers order 2022-12-15 15:36:14 +01:00
Molkobain
6d47b0f4f8 N°4517 - PHP 8.0: Fix undefined array key due to type cast being done before coalesce 2022-12-14 20:34:40 +01:00
Eric Espie
e1c28a5c22 Merge branch 'support/2.7' into support/3.0 2022-12-14 15:45:27 +01:00
Eric Espie
296ee019a0 Merge branch 'support/2.7' into support/3.0 - nothing to do 2022-12-14 15:44:05 +01:00
Molkobain
7c2f8f4d93 N°5765 - Setup: Never cache folder permissions test response (#374) 2022-12-14 09:33:54 +01:00
Pierre Goiffon
1f76ff940d N°5797 Replace wrong config load (#338) 2022-12-13 18:23:09 +01:00
Eric Espie
bb26e48d38 Update version to next release 2.7.9 2022-12-12 16:19:42 +01:00
Eric Espie
26042b990f Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-portal-base/portal/src/Twig/AppExtension.php
2022-12-08 08:34:16 +01:00
Eric Espie
cf433f2f80 N°5725 - Twig update 'filter', 'map' and 'reduce' filters 2022-12-08 08:25:11 +01:00
Eric Espie
ae94e58a43 N°5725 - Twig update 'filter', 'map' and 'reduce' filters 2022-12-07 13:53:15 +01:00
Eric Espie
f66692d5cf Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-portal-base/portal/src/Twig/AppExtension.php
2022-12-07 13:44:54 +01:00
Eric Espie
2b917f6647 Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-oauth-client/src/Service/PopupMenuExtension.php
2022-12-07 13:42:36 +01:00
Eric Espie
cda017fa4f N°5725 - Twig update 'filter', 'map' and 'reduce' filters 2022-12-07 13:37:52 +01:00
Pierre Goiffon
dad22f6f83 📄 Update Licenses 2022-12-07 11:04:33 +01:00
Eric Espie
9474f43d61 Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-oauth-client/src/Service/PopupMenuExtension.php
2022-12-02 11:20:31 +01:00
Eric Espie
9077f7ba37 N°5430 - OAuth authentication : customize redirect landing URL - remove unnecessary parameter to JS function OAuthConnect 2022-12-02 11:17:01 +01:00
Eric Espie
4d365c8a44 Merge branch 'support/2.7' into support/3.0 2022-12-02 09:26:40 +01:00
Eric Espie
957ff40f30 N°5155 - Email by SMTP with self-signed certificate (changed default values to the previous behaviour) 2022-12-02 09:25:53 +01:00
Eric Espie
7bb12c35ea Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	core/config.class.inc.php
2022-11-30 14:27:32 +01:00
Eric Espie
aff9c7748b N°5155 - Email by SMTP with self-signed certificate 2022-11-30 14:18:11 +01:00
Eric Espie
e518d34bc9 N°5553 - OAuth 2 : Hide Client Secret
* client_id is now 255 chars (AttributeString)
 * client_secret is now 64 chars (AttributePassword) and cannot be anymore in the uniqueness rules
 * The modification of redirect_url, client_id or client_secret change the status to inactive and generate a session message to ask for token regeneration
2022-11-30 14:15:37 +01:00
Eric Espie
51a305b445 N°5725 - Twig update 'filter', 'map' and 'reduce' filters (twig functions signature changed) 2022-11-30 13:40:44 +01:00
Eric Espie
5577f4a62e Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-11-30 13:36:18 +01:00
Eric Espie
f0141530b9 N°5725 - Twig update 'filter', 'map' and 'reduce' filters (+1 squashed commits)
Squashed commits:

[00148dec5] N°5725 - Twig update 'filter', 'map' and 'reduce' filters
2022-11-30 13:28:33 +01:00
Pierre Goiffon
92a802947d Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	setup/wizardsteps.class.inc.php
2022-11-29 19:02:51 +01:00
xtophe38
ce5096a896 N°5758 Change setup test for GDPR consent (#336)
We were using SetupUtils::IsProductVersion, but this was blocking for certain packages like TeemIP standalone.
After this change we are now relying on a new method : \SetupUtils::IsConnectableToITopHub. It will check the iTop Hub Connector module presence instead.
2022-11-29 19:00:17 +01:00
Pierre Goiffon
5efd45eafc Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	pages/ajax.render.php
2022-11-29 18:18:24 +01:00
Pierre Goiffon
23e0ed5e56 N°4449 Test for FPD detection in RuntimeDashboard 2022-11-29 18:10:17 +01:00
Pierre Goiffon
d412a52fcc N°4449 Fix FPD in dashboard export/import 2022-11-29 18:10:17 +01:00
Molkobain
cf5745b985 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/pdfbulkexport.class.inc.php
2022-11-26 00:09:10 +01:00
Molkobain
3e18ad590f Fix image attributes not being visible in PDF exports 2022-11-25 19:30:35 +01:00
Eric Espie
b174aa9aeb Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-oauth-client/vendor/composer/InstalledVersions.php
#	datamodels/2.x/itop-oauth-client/vendor/composer/installed.php
2022-11-25 17:37:01 +01:00
Pierre Goiffon
34f03715b6 LogChannel : add missing @since 2022-11-24 17:27:30 +01:00
Eric Espie
6a0cdb8705 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-oauth-client/vendor/composer/InstalledVersions.php
#	datamodels/2.x/itop-oauth-client/vendor/composer/installed.php
2022-11-24 14:35:51 +01:00
Eric Espie
22111bf667 N°5611 - Fix missing composer files in itop-oauth-client 2022-11-24 14:32:51 +01:00
Eric Espie
6d0c46595d N°5611 - Fix missing composer files in itop-oauth-client 2022-11-24 14:27:42 +01:00
Eric Espie
1e2205ecb0 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-11-24 13:58:12 +01:00
Eric Espie
d292a6b0c3 N°5333 - OAuth and iTop url change 2022-11-24 13:55:36 +01:00
Eric Espie
74702c8d06 N°5430 - OAuth authentication : customize redirect landing URL 2022-11-24 13:55:36 +01:00
Pierre Goiffon
df4a205ba0 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-11-24 09:00:56 +01:00
Pierre Goiffon
e9c91d986d 📝 CONTRIBUTING : fix typo (stash in stead of squash)
Thanks Molkobain ! (https://github.com/Combodo/iTop/pull/371#discussion_r1030759606)
2022-11-24 09:00:32 +01:00
Eric Espie
feafd5e2c9 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
N°5741 - remove use of get_config_parameter and get_module_setting in Twig

# Conflicts:
#	application/twigextension.class.inc.php
#	datamodels/2.x/itop-portal-base/portal/src/Twig/AppExtension.php
#	sources/application/TwigBase/Twig/Extension.php
2022-11-23 17:38:27 +01:00
Eric Espie
70a6b276ca Merge branch 'issue/5685-UpgradeApereoPHPCas' into support/2.7 2022-11-23 15:58:36 +01:00
Eric Espie
f77361ceb2 N°5685 - Upgrade apereo/phpcas 2022-11-23 15:53:43 +01:00
Eric Espie
75f4751b82 N°5741 - remove use of get_config_parameter in Twig 2022-11-23 15:09:20 +01:00
Eric Espie
65b6c0f4ea Fix CI 2022-11-23 11:04:58 +01:00
Eric Espie
c05684945f Fix CI 2022-11-23 10:34:24 +01:00
Eric Espie
6b1c033ec1 Fix CI 2022-11-23 09:54:30 +01:00
Eric Espie
4f14d1fb23 N°4974 - Session rework 2022-11-22 15:38:02 +01:00
Molkobain
8c95bd5a65 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-11-16 19:04:21 +01:00
Romain Quetiez
b56f2f56f1 N°5704 - Fix compatibility with PHP <7.3 (HEREDOC syntax) 2022-11-16 17:12:53 +01:00
Eric Espie
282d47aed4 N°5727 - REST API/get_related: Seemingly wrong results, when using [impacts, up] with [redundancy: true] 2022-11-16 13:51:38 +01:00
Eric Espie
2f8f0b658c N°5722 - code hardening 2022-11-16 09:40:19 +01:00
Eric Espie
e4884470ad Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-11-16 09:38:31 +01:00
Eric Espie
68d44fa981 N°5724 - code hardening 2022-11-16 09:32:47 +01:00
Eric Espie
7e5307bd96 N°4867 - "Twig content not allowed" error 2022-11-16 09:31:42 +01:00
Molkobain
5839d0e8e3 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	test/ItopTestCase.php
2022-11-08 21:14:50 +01:00
Romain Quetiez
cd010afb48 N°5704 - Unit tests on XML assembly (#329)
* Add a complete test suite for XML assembly

* Add a complete test suite for XML assembly

* Dispatched the test of GetDelta into real unit tests

* Add test for GetDelta on a rename operation

* Add comments on a weird case and a case on rename

* Update XML version after rebase from develop to support/2.7

* Fix phpdoc about coverage

* Remove ModelFactory::GetRootDirs and ItopTestCase::RecurseRmDir+CreateTmpDir+RecurseMkDir+RecurseCopy, that were meant to be introduced in iTop 3.0 and have been copied here by mistake, when rebasing the branch from develop to 2.7.0

* Update test/ItopTestCase.php

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>

* Update test/setup/ModelFactoryTest.php

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>

* Update test/ItopTestCase.php

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>

Co-authored-by: Pierre Goiffon <pierre.goiffon@combodo.com>
Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2022-11-08 19:43:07 +01:00
Pierre Goiffon
be5a252be7 iTopDesignTestFormat : improve code readability 2022-11-08 18:14:20 +01:00
Pierre Goiffon
073488a7bd Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-11-08 17:27:26 +01:00
Pierre Goiffon
0cf8d731bb Rename iTopDesignFormat test class 2022-11-08 15:59:14 +01:00
Pierre Goiffon
4e7df37931 📝 jqueryui.scss : add comment to inform it is deprecated 2022-10-25 11:54:02 +02:00
Pierre Goiffon
4b670cfa90 N°5625 Fix crash when opening DocumentFile in ES language
Regression introduced in 3.0.1 with a merge : 67fa156c
The % was removed in 530ec111 but we kept the call to Dict::Format, and the merge restored the % in ES dict

A larger fix will be done later with N°5491
2022-10-20 16:46:37 +02:00
acognet
87db88254b N°4517 - PHP 8.1 compatibility - Fix uppercase 2022-10-17 21:34:26 +02:00
acognet
5ddc006f51 N°4517 - PHP 8.1 compatibility 2022-10-17 16:27:42 +02:00
Pierre Goiffon
85a72d6a10 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-10-11 14:29:07 +02:00
Pierre Goiffon
189ca3c555 🚚 Move visual test file to the dedicated directory 2022-10-11 14:28:44 +02:00
Pierre Goiffon
c02b36a00c Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-10-03 15:56:02 +02:00
Pierre Goiffon
1e1f1f78bf 📝 Backup : more details on check-backup parameters 2022-10-03 14:41:44 +02:00
Pierre Goiffon
1494604740 📝 Backup : move info from wiki to distrib file 2022-10-03 14:35:14 +02:00
Molkobain
59b20ac1ee Fix typo 2022-09-27 20:14:53 +02:00
Molkobain
c753b57265 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-09-21 16:23:42 +02:00
Molkobain
583ab98210 Fix typo 2022-09-21 16:11:24 +02:00
Pierre Goiffon
a5b5518533 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/cmdbsource.class.inc.php
#	test/core/CMDBSource/TransactionsTest.php
2022-09-21 14:21:28 +02:00
Pierre Goiffon
88d743b1cc N°5538 Make PHPUnit test fail if transaction opened but not closed 2022-09-21 14:05:27 +02:00
Pierre Goiffon
7ac4bc95bb ItopDataTestCase : improve log message 2022-09-21 11:51:07 +02:00
Molkobain
7071712a0a N°5535 - Fix PHP max version to 8.1 in composer for iTop 3.0.2+ 2022-09-20 13:42:45 +02:00
Molkobain
e55ac6002a Increase ITOP_VERSION to 3.0.3-dev 2022-09-20 13:22:18 +02:00
Molkobain
e9c6549847 N°5535 - Fix PHP not validated version to 8.1 in iTop 3.0.2+ 2022-09-20 13:17:59 +02:00
Pierre Goiffon
091aaac55e Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-09-14 15:34:36 +02:00
Pierre Goiffon
d431811725 N°4947 Fix Email always picking "production" env config file (#331)
Note that the code was duplicated in both Email* impl, this is refactored : LoadConfig and m_oConfig are pulled up in Email, and SetRecipientFrom() calls are also refactored in Email
2022-09-14 15:33:48 +02:00
Pierre Goiffon
203cf17c67 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	setup/setuputils.class.inc.php
#	setup/wizardsteps.class.inc.php
2022-09-14 12:16:35 +02:00
xtophe38
7512f721e9 Setup wizard : use the ITOP_APPLICATION constant instead of hardcoded "iTop" string (#335)
* Update wizardsteps.class.inc.php

* Done as requested

* Fix typo for better readability/genericity

Co-authored-by: Molkobain <lajarige.guillaume@free.fr>
2022-09-13 20:11:38 +02:00
Pierre Goiffon
bdfe3a3b35 N°5235 Tmp dir setup check is now non blocking (woops previous commit was incomplete) (#301) 2022-09-13 18:22:29 +02:00
Pierre Goiffon
5cf391c3bb N°5235 - Add non blocking setup check : is tmp dir is writable (#301) 2022-09-13 18:20:35 +02:00
acognet
1ee5432b96 N°5508 - PHP 8 and PHP 8.1 : Add compatibility Alarm Console 2022-09-13 18:04:28 +02:00
Eric Espie
425362f515 N°5510 - Add unit test 2022-09-13 12:14:04 +02:00
Eric Espie
d50fe1573c Merge branch 'support/3.0.2' into support/3.0
# Conflicts:
#	application/loginbasic.class.inc.php
#	application/loginexternal.class.inc.php
#	application/loginform.class.inc.php
#	application/loginurl.class.inc.php
2022-09-12 11:00:07 +02:00
Eric Espie
2a064fd97d N°5394 - use session for the FSM 2022-09-12 10:56:25 +02:00
Eric Espie
e9a3974b98 N°5394 - revert 2.7 merge 2022-09-12 10:54:55 +02:00
Eric Espie
f02bc529fe Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/loginbasic.class.inc.php
#	application/loginexternal.class.inc.php
#	application/loginform.class.inc.php
#	application/loginurl.class.inc.php
2022-09-12 09:55:01 +02:00
Eric Espie
4c1df9927d N°5394 - use session for the FSM 2022-09-12 09:45:30 +02:00
Eric Espie
ca3c0cb163 N°5510 - Exception "$amount: Expected 5% to be within 0% and 1%" when compiling a theme 2022-09-09 09:20:52 +02:00
Pierre Goiffon
56e7992d4a Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	test/ItopTestCase.php
2022-09-08 18:25:15 +02:00
Pierre Goiffon
74003f12c1 N°5513 Remove test name debug info 2022-09-08 18:20:52 +02:00
Pierre Goiffon
3bc12b0434 N°5513 Improve PHPUnit output to stdout
Will allow to see progress when looking at the Jenkins output
2022-09-08 15:11:02 +02:00
Eric Espie
44c0e236b0 N°5509 - User Provisioning Issue 2022-09-08 09:58:29 +02:00
Eric Espie
cb2a597267 Fix notice on empty case log 2022-09-07 10:33:31 +02:00
Eric Espie
57bb0160c4 Merge branch 'support/3.0.2' into support/3.0 2022-09-05 12:08:53 +02:00
Eric Espie
6c4cd6c99c constants missing if no ticket in DM (vanilla) 2022-09-02 13:57:36 +02:00
Eric Espie
6190429f51 N°5394 - Rework session start 2022-09-01 16:08:16 +02:00
Molkobain
bdda29ef6a Merge remote-tracking branch 'origin/support/3.0.2' into support/3.0 2022-08-30 17:46:25 +02:00
Pierre Goiffon
9c57b0b1b7 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-08-29 12:33:06 +02:00
Pierre Goiffon
02a0969b53 N°5414 Fix undefined constant error in notification with wrong placeholder
Fix regression introduced in 33c2168 (#282)
2022-08-29 12:31:45 +02:00
Molkobain
6e3ff0e429 Update iTop version to 3.0.2 2022-08-29 09:40:47 +02:00
Stephen Abello
bc7749602d Merge branch 'support/3.0.2' into support/3.0
# Conflicts:
#	setup/setup.js
2022-08-24 16:46:16 +02:00
Stephen Abello
14facb4d6c N°5462 Add a setup check to verify if directory-level configuration files (.htaccess and web.config) are used by the server 2022-08-24 16:44:11 +02:00
Stephen Abello
7c6cc23aa8 Merge branch 'support/2.7' into support/3.0
# Conflicts:
#	setup/setup.js
2022-08-24 16:40:18 +02:00
Stephen Abello
d78a25ee4e N°5462 Add a setup check to verify if directory-level configuration files (.htaccess and web.config) are used by the server 2022-08-24 16:33:54 +02:00
Pierre Goiffon
06c3e295d6 Fix iTopXmlVersionIntegrationTest
* remove annotations for data tests : we are only comparing constants
* remove itop-community group : this test can be run whatever target was used to build
* remove wrong `@covers` annotation
2022-08-24 14:54:02 +02:00
Pierre Goiffon
6f438d52b2 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	test/integration/iTopModulesPhpVersionChecklistTest.php
2022-08-24 14:46:55 +02:00
Pierre Goiffon
7a6a3d1ac0 Integration tests : move and comment itop-community group 2022-08-24 14:41:32 +02:00
odain
f923ac879f ci: tag some tests with addition annotations to ease exclusion/inclusion mechanism 2022-08-24 12:07:04 +02:00
odain
0b46ab9e48 ci: add phpunit defaultProfiles annotation + tag some tests with addition annotations to ease exclusion/inclusion mechanism 2022-08-24 11:02:11 +02:00
Molkobain
bdf11e32a7 N°5318 - Security hardening 2022-08-24 10:47:40 +02:00
Molkobain
2caf3e2217 Merge remote-tracking branch 'origin/support/3.0.2' into support/3.0 2022-08-23 10:27:59 +02:00
Molkobain
1441b8a1d2 N°5318 - Fix bad merge of the coreexception.class.inc.php file 2022-08-23 10:01:51 +02:00
Stephen Abello
b1bc2cec1b N°5138 Fix tooltips flickering in bulk modify when it contains hyperlinks 2022-08-22 16:59:24 +02:00
Molkobain
e280f99996 N°5437 - PHP 8.0: Fix deprecated PHP notice in TWIG lib 2022-08-22 16:43:38 +02:00
acognet
d33bd88832 N°5428 - Request template: autocomplete field can not be a master field 2022-08-19 15:06:38 +02:00
Pierre Goiffon
a92b1971c0 N°5423 Fix "unexpected value" error on \CMDBChangeOpSetAttributeURL.newvalue for AttributeUrl with custom patterns 2022-08-18 14:48:55 +02:00
Molkobain
0efaf47325 N°4910 - Improve comment 2022-08-18 09:25:03 +02:00
Pierre Goiffon
a8f1b1d9d8 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/action.class.inc.php
2022-08-17 14:29:27 +02:00
Pierre Goiffon
6b32be0899 N°5216 Fix invalid message-id when sending notification using cron on system with a specific locale set (#297)
The timestamp used was indeed locale dependent.
This commit fixes this behavior by removing the locale dependency using a better printf format (see https://www.php.net/manual/fr/function.sprintf.php)
2022-08-17 14:11:32 +02:00
Pierre Goiffon
33c2168af2 🔊 Adds a debug log for invalid placeholders (#282)
This adds a debug log when a placeholder cannot be replaced.
Before the placeholder was just not replaced.
Now we can enable a debug log on the LogChannels::NOTIFICATION channel.
2022-08-17 14:09:59 +02:00
Molkobain
efd2fbb19a Fix module version after wrong merge 2022-08-16 17:49:23 +02:00
Molkobain
c8b82e6e48 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	approot.inc.php
#	css/css-variables.scss
#	datamodels/2.x/authent-cas/module.authent-cas.php
#	datamodels/2.x/authent-external/module.authent-external.php
#	datamodels/2.x/authent-ldap/module.authent-ldap.php
#	datamodels/2.x/authent-local/module.authent-local.php
#	datamodels/2.x/combodo-db-tools/module.combodo-db-tools.php
#	datamodels/2.x/itop-attachments/module.itop-attachments.php
#	datamodels/2.x/itop-backup/module.itop-backup.php
#	datamodels/2.x/itop-bridge-virtualization-storage/module.itop-bridge-virtualization-storage.php
#	datamodels/2.x/itop-change-mgmt-itil/module.itop-change-mgmt-itil.php
#	datamodels/2.x/itop-change-mgmt/module.itop-change-mgmt.php
#	datamodels/2.x/itop-config-mgmt/module.itop-config-mgmt.php
#	datamodels/2.x/itop-config/module.itop-config.php
#	datamodels/2.x/itop-core-update/module.itop-core-update.php
#	datamodels/2.x/itop-datacenter-mgmt/module.itop-datacenter-mgmt.php
#	datamodels/2.x/itop-endusers-devices/module.itop-endusers-devices.php
#	datamodels/2.x/itop-files-information/module.itop-files-information.php
#	datamodels/2.x/itop-full-itil/module.itop-full-itil.php
#	datamodels/2.x/itop-hub-connector/module.itop-hub-connector.php
#	datamodels/2.x/itop-incident-mgmt-itil/module.itop-incident-mgmt-itil.php
#	datamodels/2.x/itop-knownerror-mgmt/module.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-oauth-client/module.itop-oauth-client.php
#	datamodels/2.x/itop-portal-base/module.itop-portal-base.php
#	datamodels/2.x/itop-portal/module.itop-portal.php
#	datamodels/2.x/itop-problem-mgmt/module.itop-problem-mgmt.php
#	datamodels/2.x/itop-profiles-itil/module.itop-profiles-itil.php
#	datamodels/2.x/itop-request-mgmt-itil/module.itop-request-mgmt-itil.php
#	datamodels/2.x/itop-request-mgmt/module.itop-request-mgmt.php
#	datamodels/2.x/itop-service-mgmt-provider/module.itop-service-mgmt-provider.php
#	datamodels/2.x/itop-service-mgmt/module.itop-service-mgmt.php
#	datamodels/2.x/itop-sla-computation/module.itop-sla-computation.php
#	datamodels/2.x/itop-storage-mgmt/module.itop-storage-mgmt.php
#	datamodels/2.x/itop-tickets/module.itop-tickets.php
#	datamodels/2.x/itop-virtualization-mgmt/module.itop-virtualization-mgmt.php
#	datamodels/2.x/itop-welcome-itil/module.itop-welcome-itil.php
#	datamodels/2.x/version.xml
2022-08-16 17:35:00 +02:00
Lars Kaltefleiter
ae021064a4 🌐 Update German translations for oauth-client (#319) 2022-08-16 17:02:37 +02:00
Molkobain
c5d5379c49 N°5408 - Mentions: Fix empty results for class with no image attribute 2022-08-16 14:21:28 +02:00
Molkobain
83b2096d2d N°5407 - Mentions: Fix RegExp wildcard not usable as marker 2022-08-16 13:43:51 +02:00
Molkobain
c8cb64db24 N°4739 - Remove precompiled themes unit test as they are no longer used since the introduction of DM classes style SCSS 2022-08-16 11:48:38 +02:00
Benjamin Dalsass
0a61169326 Update version to next release 2.7.8 2022-08-16 09:47:46 +02:00
Molkobain
f70073cf3e N°3979 - Fix typo 2022-08-16 09:31:56 +02:00
Molkobain
fc9ac1b441 N°4739 - Add semantic on state for user classes
* Add new section in the backoffice SCSS structure for PHP classes of the DM that are in the core (not a module) and can't be styled via XML.
2022-08-14 21:35:56 +02:00
Anne-Catherine
47becb3be8 N°5024 - Missing result in search widget for external key (#327)
* N°5024 - Missing result in search widget for external key
2022-08-12 18:23:29 +02:00
acognet
7320005c08 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/cmdbabstract.class.inc.php
#	core/coreexception.class.inc.php
#	core/dbobject.class.php
2022-08-12 18:13:42 +02:00
Anne-Catherine
d7e5705520 N°5318 - Fix DBObject::CheckValue() messages being HTML encoded when not necessary (#326)
* Rollback N°4898 - Security fix

* N°5318 - security fix
2022-08-12 17:50:14 +02:00
Anne-Catherine
bacdd63dd4 N°3979 - Handle initial values on dependent fields (#325)
N°3979 - Handle initial values on dependent fields
2022-08-12 17:48:53 +02:00
Molkobain
b91ab8940e N°4918 - Fix "other tabs" menu displayed behind some elements 2022-08-12 14:59:06 +02:00
Stephen Abello
9bf65da420 Merge branch 'support/2.7' into support/3.0 2022-08-12 11:35:47 +02:00
Stephen Abello
35a8b501c9 N°5393 Security hardening 2022-08-12 11:33:55 +02:00
Molkobain
8e7aef17c6 N°4903 - Fix dynamic "app_root_url" conf. param. not used properly for the app. icon 2022-08-12 11:11:55 +02:00
Molkobain
24f2416427 Navigation menu: Fix duplicated conf. property code usage 2022-08-12 11:11:55 +02:00
Eric Espie
cc6cf79835 N°5389 - Email Notification templates with AttributeLinkedSetIndirect failed 2022-08-12 10:37:43 +02:00
Stephen Abello
f10e9c2d64 N°5393 Security hardening 2022-08-12 09:54:35 +02:00
Stephen Abello
bd97d9c7ca Replace OAuth object subtitle icon with a solid icon for more harmony 2022-08-12 09:53:24 +02:00
Stephen Abello
94b9fda354 Remove OAuth object subtitle tooltip as it's always empty 2022-08-12 09:53:24 +02:00
Eric Espie
7a7498537f N°5135 - Impersonate: history of changes versus log entries - Fix typo 2022-08-11 17:17:29 +02:00
acognet
b6e22e47ca N°4910 - Adding a regexp on an existing field with value not complient, block the object modification 2022-08-11 16:43:36 +02:00
jbostoen
d17e399a5f 🌐 N°5397 - Updated Dutch translations (#262)
Co-authored-by: Thomas Casteleyn <thomas.casteleyn@me.com>
2022-08-11 14:07:51 +02:00
Molkobain
48742f334f N°5198 - Add comment to clarify usage of array_replace 2022-08-11 11:38:53 +02:00
odain-cbd
ec01ab73aa N°5135 - Impersonate: history of changes versus log entries (#290)
* N°5135 - Impersonate: history of changes versus log entries

* N°5135 - enrich impersonated changelog userinfo with its previous value when overrided by an extension (ie approvalbase)

* N°5135 - indicate impersonation inside changelogs in both caselogs and activity

* N°5135 - Impersonate: history of changes versus log entries add specific username for caselogs

Co-authored-by: Eric Espie <eric.espie@combodo.com>
2022-08-11 11:12:07 +02:00
acognet
931bafe380 N°5198 - Inconsistent behavior in selection of combobox with more than 150 results 2022-08-10 17:49:40 +02:00
Stephen Abello
5164976b76 N°5050 * Revert changes made in 3b83d3f2 in english dictionary 🤦
* Move it to Spanish dictionary
2022-08-10 15:38:42 +02:00
Eric Espie
5854eefcce N°5395 - Errors from OAuth servers for email are not well handled (use 3.0 constants) 2022-08-10 15:27:25 +02:00
Molkobain
5845972941 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-08-10 15:14:27 +02:00
Eric Espie
7f7538ed58 N°5395 - Errors from OAuth servers for email are not well handled 2022-08-10 14:59:32 +02:00
Eric Espie
8fa616f440 N°5395 - Errors from OAuth servers for email are not well handled 2022-08-10 14:57:26 +02:00
Molkobain
62aaaabd7e Update visual test comment 2022-08-10 14:53:42 +02:00
Stephen Abello
b3750e46cf Stylize datatables before widget is loaded in order to avoid flickering 2022-08-10 14:07:39 +02:00
Stephen Abello
b43b2e9741 Remove padding between Dashlet/Preferences datatables and their parent panel 2022-08-10 14:07:38 +02:00
Stephen Abello
77e9eaba00 Add highlighted rows to RenderAllUiBlocks 2022-08-10 14:07:38 +02:00
Stephen Abello
3d593faad8 Fix datatables semantic colors not using sematinc variables 2022-08-10 14:07:38 +02:00
Stephen Abello
118622493f N°5050 Revert entry deleted in 3b83d3f2 2022-08-10 14:07:38 +02:00
Molkobain
e44523e623 N°5343 - Avoid crash when 1 level menu group is not actually a MenuGroup (#312) 2022-08-09 17:45:31 +02:00
Eric Espié
69749a5cbe N°5375 - XML custo on Semantic field with hierarchy, breaks at compilation (#323) 2022-08-09 17:37:01 +02:00
Molkobain
43b49034df Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-08-09 17:33:18 +02:00
Molkobain
5829e698da Fix typo 2022-08-09 17:19:21 +02:00
Eric Espié
d2041c0334 N°5009 - Invalid XML for class Attachment (icon node) (#324)
N°5009 - Invalid XML for class Attachment (icon node)
2022-08-09 16:55:50 +02:00
Stephen Abello
f9487e55d5 N°5088 Fix audit displaying only 10 rules per category 2022-08-09 15:34:46 +02:00
Stephen Abello
b8ecb68ad7 N°5192 Make highlighted row more visible by adding a border to the first cell 2022-08-09 14:27:09 +02:00
Stephen Abello
3b83d3f209 N°5050 Update Spanish translations (thanks to Miguel Turrubiates!) 2022-08-09 14:27:09 +02:00
Eric Espie
029e6114ad N°4715 - Remove deprecated legacy SQL build 2022-08-09 10:41:46 +02:00
Eric Espié
de5fee8876 N°4792 - memory limit is reached when an AttributeExternalKey is pointing to a class with an AttributeBlob (#322)
N°4792 - memory limit is reached when an AttributeExternalKey is poin…
2022-08-09 09:17:15 +02:00
Molkobain
80fa4ec71f Code format 2022-08-08 16:30:46 +02:00
Stephen Abello
b1432ef1c6 N°4927 Fix date picker widget initialized visible 2022-08-08 15:07:02 +02:00
Stephen Abello
0599341515 N°4975 Security hardening 2022-08-08 15:07:02 +02:00
Stephen Abello
8e840d4529 N°5138 N°4425 Fix not being able to click on hyperlinks in tooltips 2022-08-08 15:07:01 +02:00
Stephen Abello
b4880beb5b N°5192 Fix HILIGHT_CLASS_OK not displaying green rows since iTop 3.0 2022-08-08 15:07:01 +02:00
Molkobain
c6b88c4db0 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/dbobject.class.php
2022-08-08 11:57:12 +02:00
Molkobain
df347b90e5 N°5383 - Declare DBObject::EnumTransitions() as "overwritable hook" 2022-08-08 11:53:46 +02:00
Molkobain
47683f3bd4 N°5033 - Add model file to 'itop-bridge-virtualization-storage' module to avoid compilation crash when lnkVirtualDeviceToVolume class is removed 2022-08-08 08:58:34 +02:00
acognet
b704e0d131 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-08-04 16:38:47 +02:00
acognet
bb861aa262 N°3024 - Archiving Service Families (or any class with no child) with combodo-archive-manual 2022-08-04 16:26:21 +02:00
acognet
f9ac07830e Fix translation 2022-08-04 16:26:01 +02:00
Stephen Abello
1ab35c68c8 Fix typo in datetime input autocomplete attribute 2022-08-03 14:47:01 +02:00
Molkobain
f1acc956f4 N°4517 - PHP 8.1: Fix return type for class implementing IteratorAggregate 2022-08-03 10:33:24 +02:00
Molkobain
a2973f6f28 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	js/wizardhelper.js
2022-07-29 15:25:13 +02:00
Molkobain
614a586b4c N°3129 - PHP 8.0: Fix unit test for which the tested error message as changed 2022-07-29 11:08:32 +02:00
Pierre Goiffon
0f4c7ac90f N°5129 Prevent "fieldForm is null" JS error when updating dependant field
For example when changing Server.location, 3 JS errors are thrown in the console :/
2022-07-29 10:12:37 +02:00
Molkobain
77aa154388 Convert line endings to LF on misaligned text files 2022-07-28 10:02:18 +02:00
Molkobain
414e1542d0 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/authent-external/ja.dict.authent-external.php
#	datamodels/2.x/authent-local/da.dict.authent-local.php
#	datamodels/2.x/authent-local/ja.dict.authent-local.php
2022-07-28 10:00:32 +02:00
Molkobain
0687f9a0a9 Convert line endings to LF on misaligned text files 2022-07-28 09:58:04 +02:00
Molkobain
6e75ab2889 Add .gitattributes to enforce line endings
More info: https://docs.github.com/en/get-started/getting-started-with-git/configuring-git-to-handle-line-endings
2022-07-28 09:44:42 +02:00
Molkobain
a80cfb6b05 N°5302 - Code cleanup 2022-07-26 22:18:21 +02:00
Molkobain
6ee67a2a36 N°5108 - Fix variable name 2022-07-26 22:11:38 +02:00
Molkobain
a11bbd667a Fix typos 2022-07-26 20:09:37 +02:00
Pierre Goiffon
7268cf7311 👥 Add @nv35 to contributors list! 🙌
See #183
2022-07-26 17:21:19 +02:00
Molkobain
6cda9e001f Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-07-20 17:48:47 +02:00
Molkobain
b90d29d448 🔧 Add IntelliLang.xml file to provide PHP synthax highlighting in DM XML files 2022-07-20 17:48:01 +02:00
Molkobain
808092acdd N°5311 - Update deprecation comment to match PHP deprecations convention 2022-07-18 16:05:41 +02:00
Molkobain
b9c716a247 N°5102 - Convert line separators 2022-07-18 15:58:11 +02:00
Molkobain
bf7b2e1e7e Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-07-18 14:15:50 +02:00
Molkobain
1f78bf4119 N°5287 - Fix license in composer.json 2022-07-18 13:52:40 +02:00
Molkobain
28df2dad60 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	js/wizardhelper.js
2022-07-13 17:11:04 +02:00
Molkobain
5d25e77189 Code format 2022-07-13 17:03:01 +02:00
Molkobain
d9dabf25da PHPDoc 2022-07-13 17:03:01 +02:00
Molkobain
73af605892 Fix typo in dictionaries 2022-07-13 17:03:00 +02:00
Molkobain
a71d8a660f N°5311 - Deprecate old backoffice stylesheets 2022-07-12 11:20:48 +02:00
Eric Espie
03b56b2941 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 : wrong positioning of module_parameters for portal 2022-07-11 16:26:41 +02:00
Eric Espie
01ee91d003 N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
* migration to iTop 3.0
2022-07-11 15:20:47 +02:00
Benjamin Dalsass
f70f95c119 Update community licence 2.7.7 (script from git bash, not php execution) 2022-07-11 15:20:36 +02:00
Eric Espie
badc5ff3ec Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-07-11 15:20:29 +02:00
Eric Espie
8dbdcdcb25 autoloader updated 2022-07-11 14:18:44 +02:00
Eric Espie
13533a2fa9 ⬆️ libs upgrade 2022-07-11 14:18:20 +02:00
Eric Espie
e4343ded01 autoloader updated 2022-07-11 09:24:24 +02:00
Eric Espie
e105cc6d44 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.lock
#	core/log.class.inc.php
#	datamodels/2.x/itop-tickets/datamodel.itop-tickets.xml
#	lib/composer/autoload_real.php
#	setup/licenses/community-licenses.xml
#	setup/setuputils.class.inc.php
2022-07-11 09:23:18 +02:00
Benjamin Dalsass
53c50cf6fc Update community licence 2.7.7 2022-07-11 08:24:20 +02:00
Vincent Dumas
f19d1472c5 N°5102 - OAuth - replace double quote char EN
Use a special double quote characters so it is correctly handled in HTML
2022-07-08 13:44:00 +02:00
Vincent Dumas
eef00502cd N°5102 - OAuth - remove unsupported quote FR 2022-07-08 13:38:37 +02:00
Molkobain
0b1caac195 N°4867 - Restore datamodel node to avoid minor version migration crash
Will be properly removed in 3.1.0
2022-07-08 13:22:27 +02:00
Vincent Dumas
e900a44d47 N°5102 - OAuth client - FR tooltips 2022-07-08 12:22:52 +02:00
Vincent Dumas
a3de9fa898 N°5102 - OAuth client - Add EN tooltips 2022-07-08 12:06:47 +02:00
Eric Espie
aa8de912fd Merge branch 'support/3.0.1' into support/3.0 2022-07-08 11:01:02 +02:00
Eric Espie
f8648e2929 N°5267 - Error on class view when datamodel encoding is not UTF-8 - add logs to ease finding the model load errors 2022-07-08 10:59:21 +02:00
bdalsass
33054d306d N°5302 - Replace deprecated php strlen usages (#308) 2022-07-08 10:27:52 +02:00
bdalsass
8b0154cc62 N°5168 - Access to unauthorized contact information on Portal (#305)
GlobalRequestMgmt issue
2022-07-08 09:51:20 +02:00
Eric Espie
1a225bf55b N°5102 - Allow to send emails using GSuite SMTP and OAuth - Access rights 2022-07-07 17:57:24 +02:00
Eric Espie
24d19cd8d6 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Add a flag to select OAuth client for SMTP usage 2022-07-07 16:34:19 +02:00
Eric Espie
c25a4a7346 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Access rights 2022-07-07 14:17:09 +02:00
Stephen Abello
65c6e99a3f Fix typo/useless comment 2022-07-07 09:16:11 +02:00
Stephen Abello
8e85058495 Fix SCSS comment type 2022-07-07 09:15:20 +02:00
Eric Espie
20fb7b241f N°5102 - Allow to send emails using GSuite SMTP and OAuth - Highlight classes 2022-07-06 17:23:44 +02:00
Eric Espie
a0553e1195 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Highlight classes 2022-07-06 17:10:59 +02:00
Eric Espie
f40141072a N°5102 - Allow to send emails using GSuite SMTP and OAuth - Fix errors on vendor name 2022-07-06 14:10:01 +02:00
Eric Espie
c759856a61 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Highlight classes 2022-07-06 10:10:42 +02:00
Pierre Goiffon
237b181eec 💡 Fix \SetupUtils::GetTmpDir PHPDoc 2022-07-05 18:09:59 +02:00
Eric Espie
48957fd2f0 N°5102 - Allow to send emails using GSuite SMTP and OAuth - refactor scopes 2022-07-05 17:54:43 +02:00
Pierre Goiffon
8a99c37200 N°5287 Fix composer.json errors
See https://getcomposer.org/doc/03-cli.md#validate
2022-07-05 15:08:29 +02:00
Eric Espie
d388c3fd3d N°5102 - Allow to send emails using GSuite SMTP and OAuth - Limit error size 2022-07-04 16:48:56 +02:00
Stephen Abello
9fd2b7f4da N°5071 Fix objects popup shrinking when scrolling 2022-07-04 16:41:10 +02:00
Stephen Abello
b43e6d7af3 N°5071 Fix properties tab on objects popup hiding in "..." overflowing button 2022-07-04 16:39:02 +02:00
Eric Espie
1b8e48539d N°5102 - Allow to send emails using GSuite SMTP and OAuth - Add comment in configuration 2022-07-01 14:32:44 +02:00
Eric Espie
104beff158 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Fix log 2022-06-29 15:09:17 +02:00
Pierre Goiffon
4712569a36 📝 CONTRIBUTING : fix GitMoji link 2022-06-29 10:56:21 +02:00
Pierre Goiffon
779ac0e4d9 Dump autoloader 2022-06-28 15:19:08 +02:00
Pierre Goiffon
4a20a6e525 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.lock
#	lib/composer/autoload_files.php
#	lib/composer/autoload_real.php
#	lib/composer/autoload_static.php
#	lib/composer/installed.json
#	lib/composer/installed.php
2022-06-28 15:16:41 +02:00
Pierre Goiffon
2392f4a902 🔒 Update guzzlehttp/guzzle 2022-06-28 15:13:04 +02:00
Benjamin Dalsass
cb1203fde9 Merge 2.7 into Support 3.0 : Update oauth composer 2022-06-28 15:09:19 +02:00
Pierre Goiffon
1135896b3d Composer dump autoloader 2022-06-28 12:05:47 +02:00
acognet
39cd933ebb N°5108 - Update embedded libs for PHP 8.0 (3.0 branch) 2022-06-28 12:03:01 +02:00
Pierre Goiffon
2fcc386e1e Fix compilation error on OAuthClient.status
XML file version was update but structure wasn't aligned with the new XML version (AttributeEnum structure)
2022-06-28 11:55:03 +02:00
acognet
682f20bbba N°5108 - Update embedded libs for PHP 8.0 (3.0 branch) 2022-06-28 11:24:47 +02:00
Pierre Goiffon
74f7775332 Restore images/icons/*
Were removed by the merge in f0b94dd0
2022-06-28 11:02:56 +02:00
Eric Espie
a0f28a9098 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-28 10:47:20 +02:00
acognet
93a69cbc49 N°5108 - Update embedded libs for PHP 8.0 (3.0 branch) 2022-06-27 23:38:58 +02:00
Benjamin Dalsass
15b9ea45a0 Merge 2.7 into Support 3.0 : Upgrade oauth module version to 3.0.1 2022-06-27 09:31:49 +02:00
Benjamin Dalsass
1b76e96720 Merge 2.7 into Support 3.0 : Update autoload 2022-06-27 08:18:49 +02:00
Benjamin Dalsass
f0b94dd0f7 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/config.class.inc.php
#	datamodels/2.x/installation.xml
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-adjust.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-administrative-tools.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-application-window.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-apps-tab.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-archive-folder.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-audit.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-automatic.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-bandage.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-book-error.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-calendar.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-cassette.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-change-approved.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-change-emergency.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-change-normal.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-change-routine.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-change.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-checkmark.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-cloud-file.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-conflict.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-contract.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-customer.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-database-custom.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-database.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-delete.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-department.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-desktop.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-discussion-forum.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-documents.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-electrical.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-electricity.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-electronics.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-enclosure-for-servers.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-export-csv.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-faq.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-farm.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-file.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-globe-cable.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-globe-fiber.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-globe-wire.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-hdd.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-hierarchy.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-hypervisor.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-import-csv.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-important-book.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-in-transit.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-laptop.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-licence.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-map-as-drive.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-map-marker.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-mobile.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-music-robot.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-nas.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-network.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-new-item.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-note.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-office-phone.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-old-vmware-logo.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-organization.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-person-female.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-phone.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-plug-socket.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-power-plant.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-print.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-process-improvement.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-puzzle.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-rack.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-server-custom.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-server-storage.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-server.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-service.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-services.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-smartphone-tablet.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-software-instance.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-software-license.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-software-other.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-software.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-solve.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-stack.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-switch-san.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-switch.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-tape-library.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-tasklist.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-team.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-telephone.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-time-limit.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-virtual-machine.svg
#	datamodels/2.x/itop-oauth-client/assets/img/icons8-web.svg
#	datamodels/2.x/itop-welcome-itil/datamodel.itop-welcome-itil.xml
#	dictionaries/cs.dictionary.itop.ui.php
#	dictionaries/da.dictionary.itop.ui.php
#	dictionaries/de.dictionary.itop.ui.php
#	dictionaries/en.dictionary.itop.ui.php
#	dictionaries/es_cr.dictionary.itop.ui.php
#	dictionaries/fr.dictionary.itop.ui.php
#	dictionaries/hu.dictionary.itop.ui.php
#	dictionaries/it.dictionary.itop.ui.php
#	dictionaries/ja.dictionary.itop.ui.php
#	dictionaries/nl.dictionary.itop.ui.php
#	dictionaries/pt_br.dictionary.itop.ui.php
#	dictionaries/ru.dictionary.itop.ui.php
#	dictionaries/sk.dictionary.itop.ui.php
#	dictionaries/tr.dictionary.itop.ui.php
#	dictionaries/zh_cn.dictionary.itop.ui.php
#	js/wizardhelper.js
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_real.php
#	lib/composer/autoload_static.php
#	templates/pages/backoffice/oauth/Wizard.html.twig
2022-06-27 08:11:28 +02:00
Eric Espie
6df622e8ed N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-23 14:05:17 +02:00
Eric Espie
54eb9d081b N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-23 12:20:53 +02:00
Eric Espie
9f60f27636 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-22 16:41:45 +02:00
Eric Espie
ba59643f52 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-21 16:47:46 +02:00
Eric Espie
01c02a75a8 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-21 16:40:43 +02:00
Eric Espie
f5b3e5f341 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-21 16:10:34 +02:00
Eric Espie
9b825cb529 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-21 16:05:58 +02:00
Eric Espie
3f326f0913 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-21 16:05:58 +02:00
acognet
ec86bd246a N°5129 - Unwanted popup during a transition with an AttributeExternalField 2022-06-21 15:24:25 +02:00
Eric Espie
aa90d5b6ab N°5102 - Allow to send emails using GSuite SMTP and OAuth - Rework 2022-06-21 13:51:08 +02:00
Pierre Goiffon
d6798470e7 💡 N°5248 \cmdbAbstractObject::DisplayBareHeader phpdoc v3 2022-06-21 12:15:04 +02:00
Pierre Goiffon
073388436b 💡 N°5248 \cmdbAbstractObject::DisplayBareHeader phpdoc v2 2022-06-21 10:21:10 +02:00
Pierre Goiffon
84d1be07cd 💡 N°5248 Document method signature change in \cmdbAbstractObject::DisplayBareHeader 2022-06-20 15:38:51 +02:00
Pierre Goiffon
26747b8c7e Merge remote-tracking branch 'origin/support/3.0.1' into support/3.0 2022-06-17 10:50:18 +02:00
Benjamin Dalsass
d0b8c560f6 N°5037 - Setup: Add disclaimer about collected data
3.0 look and feel adaptation
2022-06-17 09:50:36 +02:00
Benjamin Dalsass
4d180eb303 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.lock
#	js/wizardhelper.js
#	lib/composer/autoload_real.php
#	lib/composer/installed.json
#	lib/composer/installed.php
#	lib/guzzlehttp/guzzle/CHANGELOG.md
#	setup/wizardsteps.class.inc.php
2022-06-17 09:25:57 +02:00
acognet
53d2129bd1 N°5129 - Unwanted popup during a transition with an AttributeExternalField 2022-06-16 17:58:19 +02:00
Eric Espie
d21b577dd7 N°5229 - Caselog inline image lost after migration to 3.0 - missing calls to InlineImage::FixUrls() 2022-06-14 17:40:21 +02:00
Benjamin Dalsass
00e8c11ec2 N°5037 - Setup: Add disclaimer about collected data
change ui organization
2022-06-14 17:18:34 +02:00
Benjamin Dalsass
617b6b991f N°5037 - Setup: Add disclaimer about collected data
flip modules array
2022-06-14 14:33:35 +02:00
Benjamin Dalsass
b3ea1050eb N°5037 - Setup: Add disclaimer about collected data 2022-06-14 12:40:36 +02:00
Benjamin Dalsass
ca98066d68 N°5037 - Setup: Add disclaimer about collected data 2022-06-14 10:54:25 +02:00
Pierre Goiffon
352f7c8675 Update guzzlehttp/guzzle 2022-06-14 09:47:13 +02:00
Eric Espie
df5d514c28 N°4642 - Core Update : limit the usage of this function to minor version - fix error message (revert) 2022-06-13 15:59:25 +02:00
Eric Espie
16663797b2 N°4642 - Core Update : limit the usage of this function to minor version - fix error message 2022-06-13 15:51:36 +02:00
Eric Espie
4099376472 N°5102 - Allow to send emails using GSuite SMTP and OAuth - Defer the deletion (expunge) to the end of connection 2022-06-09 11:40:13 +02:00
Pierre Goiffon
fb64fbab0b Fix syntax error in Darkmoon theme 2022-06-08 18:10:03 +02:00
Eric Espie
6e4fb5888c N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
* migration to iTop 3.0
2022-06-08 15:47:52 +02:00
Eric Espie
c94c727058 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * migration to iTop 3.0
2022-06-08 15:46:29 +02:00
Eric Espie
6d3118d9e9 N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth (fix config error message) 2022-06-08 13:24:29 +02:00
Benjamin Dalsass
a0c78a94c6 Merge remote-tracking branch 'origin/support/3.0' into support/3.0
# Conflicts:
#	core/log.class.inc.php
2022-06-08 13:05:50 +02:00
Benjamin Dalsass
f014ebfeb1 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/log.class.inc.php
#	setup/modelfactory.class.inc.php
2022-06-08 13:04:50 +02:00
Benjamin Dalsass
220b384479 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/log.class.inc.php
#	setup/modelfactory.class.inc.php
2022-06-08 12:38:41 +02:00
odain
4c585614cd ease testing: CreateTestOrganization returns org object 2022-06-08 11:07:31 +02:00
Eric Espie
9674378c56 N°5211 - Core update not working with auto-selected modules (comments) 2022-06-08 10:36:55 +02:00
Eric Espie
9e314ba77b N°5211 - Core update not working with auto-selected modules 2022-06-08 10:24:03 +02:00
Eric Espie
cdd7dcdc5c N°5211 - Core update not working with auto-selected modules 2022-06-08 10:12:19 +02:00
Benjamin Dalsass
34bed5ec4f N°5215 - Portal insufficient access control for ajax search form 2022-06-07 11:14:43 +02:00
Pierre Goiffon
3ea82e37d5 N°4635 Report \LogChannels::NOTIFICATIONS 2022-06-03 18:00:29 +02:00
Pierre Goiffon
596c62aec8 💡 N°4867 Add bug reference in phpdoc 2022-06-03 09:54:29 +02:00
Benjamin Dalsass
834084a3e2 Correct dictionary entry 2022-06-02 17:15:10 +02:00
Benjamin Dalsass
0819b9baba Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.json
#	composer.lock
#	core/config.class.inc.php
#	core/dbobject.class.php
#	core/email.class.inc.php
#	datamodels/2.x/itop-core-update/dictionaries/hu.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/it.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/ja.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/nl.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/ru.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/sk.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/tr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/zh_cn.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/pt_br.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/view/ConfirmUpdate.html.twig
#	datamodels/2.x/itop-portal-base/portal/src/Twig/AppExtension.php
#	datamodels/2.x/itop-tickets/datamodel.itop-tickets.xml
#	datamodels/2.x/itop-welcome-itil/datamodel.itop-welcome-itil.xml
#	dictionaries/cs.dictionary.itop.core.php
#	dictionaries/cs.dictionary.itop.ui.php
#	dictionaries/da.dictionary.itop.core.php
#	dictionaries/da.dictionary.itop.ui.php
#	dictionaries/de.dictionary.itop.core.php
#	dictionaries/de.dictionary.itop.ui.php
#	dictionaries/en.dictionary.itop.ui.php
#	dictionaries/es_cr.dictionary.itop.core.php
#	dictionaries/es_cr.dictionary.itop.ui.php
#	dictionaries/fr.dictionary.itop.core.php
#	dictionaries/fr.dictionary.itop.ui.php
#	dictionaries/hu.dictionary.itop.core.php
#	dictionaries/hu.dictionary.itop.ui.php
#	dictionaries/it.dictionary.itop.core.php
#	dictionaries/it.dictionary.itop.ui.php
#	dictionaries/ja.dictionary.itop.core.php
#	dictionaries/ja.dictionary.itop.ui.php
#	dictionaries/nl.dictionary.itop.core.php
#	dictionaries/nl.dictionary.itop.ui.php
#	dictionaries/pt_br.dictionary.itop.core.php
#	dictionaries/pt_br.dictionary.itop.ui.php
#	dictionaries/ru.dictionary.itop.core.php
#	dictionaries/ru.dictionary.itop.ui.php
#	dictionaries/sk.dictionary.itop.core.php
#	dictionaries/sk.dictionary.itop.ui.php
#	dictionaries/tr.dictionary.itop.core.php
#	dictionaries/tr.dictionary.itop.ui.php
#	dictionaries/zh_cn.dictionary.itop.core.php
#	dictionaries/zh_cn.dictionary.itop.ui.php
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_real.php
#	lib/composer/autoload_static.php
#	lib/composer/installed.json
#	lib/composer/installed.php
#	sources/application/TwigBase/Controller/Controller.php
#	sources/application/TwigBase/Twig/TwigHelper.php
2022-06-02 16:30:48 +02:00
acognet
265415030e N°4867 - "Twig content not allowed" error when use the extkey widget search icon in the user portal - Add comment 2022-06-02 12:35:42 +02:00
Eric Espie
3d26f28f9b N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
* Add icons to wizard
2022-06-01 11:44:02 +02:00
Eric Espie
0abec767e3 Dictionaries 2022-06-01 10:45:53 +02:00
Benjamin Dalsass
9fd10bd73e N°5168 - Security hardening 2022-05-31 16:28:02 +02:00
acognet
95dafc87c0 N°4867 - "Twig content not allowed" error when use the extkey widget search icon in the user portal - Add tests 2022-05-30 15:10:50 +02:00
acognet
fe1790793e N°4898 - security hardening 2022-05-30 15:10:49 +02:00
Eric Espie
ddb95dc64e Removed laminas service manager test folder 2022-05-27 09:32:16 +02:00
Eric Espie
f6f9ee26e1 Removed laminas service manager test folder 2022-05-27 09:29:00 +02:00
Eric Espie
21faa92904 Merge branch 'support/2.7' into feature/OAuthMail 2022-05-27 09:06:28 +02:00
Eric Espie
622f40c06c N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
 * Fix legacy mailboxes compatibility
2022-05-25 08:21:16 +02:00
acognet
964134cb60 N°4867 - "Twig content not allowed" error when use the extkey widget search icon in the user portal - Remove useless code 2022-05-24 18:20:18 +02:00
Pierre Goiffon
f0d1c3ac60 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/utils.inc.php
#	core/htmlsanitizer.class.inc.php
#	datamodels/2.x/itop-portal-base/portal/src/Twig/AppExtension.php
#	pages/UI.php
#	test/OQL/DataLocalizerTest.php
#	test/OQL/OQLToSQLAllClassesTest.php
#	test/OQL/OQLToSQLGroupByTest.php
#	test/OQL/OQLToSQLNestedSelectTest.php
#	test/OQL/OQLToSQLTest.php
#	test/application/UtilsTest.php
2022-05-24 11:13:28 +02:00
acognet
72f498a63b N°5168 - Fix error message "Call to a member function GetKey() on null" 2022-05-24 10:50:56 +02:00
Pierre Goiffon
f9a1f68295 N°4655 Remove OQL tests
Were only here to check legacy OQL engine, but since 2.7.0 we fixed couple of bugs in the current OQL engine : we can't keep same functionalities in both engines :/.

Plus now we are working on 2.7.7 and we're not aware of any use of this legacy engine...

Note that it will be deprecated (N°3141) and removed (N°4715) very soon.
2022-05-24 10:38:59 +02:00
Pierre Goiffon
9b67b0b9d5 Same options in phpunit config files 2022-05-23 14:53:13 +02:00
acognet
f798ef1d76 N°4538 - Dashlet Groupby on ExternalKey with special character, bad display - remove useless test 2022-05-23 14:21:03 +02:00
Eric Espie
754946bf62 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
 * Fix legacy mailboxes compatibility
2022-05-23 12:09:40 +02:00
Eric Espie
a6580e3cd8 Merge branch 'support/2.7' into feature/OAuthMail 2022-05-23 10:56:32 +02:00
Pierre Goiffon
da6621f2ff Fix include warning in unittestautoload.php on Windows 2022-05-23 09:53:30 +02:00
Molkobain
f2d42a7e56 N°5002 - Simplify code 2022-05-20 18:41:39 +02:00
Benjamin Dalsass
d01e4b4a85 N°5168 - Security hardening 2022-05-20 16:08:25 +02:00
Pierre Goiffon
f57d1f1de3 Fix PHPunit errors with InlineImageMock.php and UtilsTest
HTMLDOMSanitizerTest : fix "Fatal error: Cannot declare class InlineImage, because the name is already in use in /var/www/html/iTop/test/core/sanitizer/InlineImageMock.php"
We are now injecting the class to mock, instead of declaring another class with the same name (was working before but why ?!???)

\UtilsTest::testSanitizer : no more testing the "class" filter, because it is a simple indirection, and we need to load datamodel which is causing multiple problems (see the comment in the test method dataprovider)
2022-05-20 10:48:05 +02:00
Eric Espie
a3f122184c N°4642 - Core Update : limit the usage of this function - revert due to N°4666 fix 2022-05-20 10:20:47 +02:00
acognet
16fcddc249 N°4867 - "Twig content not allowed" error when use the extkey widget search icon in the user portal (regression of N°4384 ) 2022-05-20 09:52:25 +02:00
Eric Espie
2a9c9be36a N°4666 - Core Update : handle modules 2022-05-20 09:42:14 +02:00
Molkobain
227814e6c3 N°4517 - PHP 8.1: Fix missing use statement 2022-05-20 09:35:23 +02:00
Eric Espie
ca3aae23a1 N°4666 - Core Update : handle modules 2022-05-20 09:33:41 +02:00
bdalsass
4dd384e418 N°4872 - Create a ticket in resolved statut Inlineimage disappear (#294) 2022-05-20 09:26:06 +02:00
Molkobain
80e7313b24 PHPDoc 2022-05-19 17:40:14 +02:00
Eric Espie
183c3c1baf N°4666 - Core Update : handle modules 2022-05-19 16:30:06 +02:00
Eric Espie
160c52fe81 Merge branch 'support/2.7' into feature/OAuthMail 2022-05-19 14:49:48 +02:00
Benjamin Dalsass
5f0a820b4a N°4899 - add sanitizer url since annotation and tests for sanitizer function 2022-05-19 08:36:42 +02:00
Molkobain
60aaa01e2e N°4517 - PHP 8.1: Replace strlen() usages with utils::StrLen() for compatibility 2022-05-18 19:59:20 +02:00
Molkobain
d3fb08ba81 PHP 8.1: Replace strlen() usages with utils::StrLen() for compatibility 2022-05-18 18:32:48 +02:00
Benjamin Dalsass
03ef4246bf N°4899 - add sanitizer url since annotation and tests for sanitizer function 2022-05-18 12:03:07 +02:00
Benjamin Dalsass
5574eabfed N°4899 Adjust url sanitizer for 3.0 compliance 2022-05-18 10:49:23 +02:00
Benjamin Dalsass
87f606f768 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/dashlet.class.inc.php
#	pages/ajax.render.php
#	pages/csvimport.php
#	test/phpunit.xml.dist
2022-05-18 10:38:50 +02:00
Pierre Goiffon
534e7cf59d N°4655 New nightly PHPUnit file containing OQL tests
Those tests were removed in 72af2b7c as they took too much time to run.
We are re-enabling them but only for nightly builds !
2022-05-18 09:35:13 +02:00
Eric Espie
e1645f6903 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * Config messages
 * Fix unit tests
2022-05-18 08:41:58 +02:00
Benjamin Dalsass
61a2d200b4 N°4900 - Stored XSS in dashlets failed OQL query 2022-05-18 08:10:01 +02:00
Benjamin Dalsass
3d6bbe4029 Revert "N°4900 - Stored XSS in dashlets failed OQL query"
This reverts commit 562dd8fc21.
2022-05-18 08:05:19 +02:00
Thomas Casteleyn
3d04cf1cd6 🌐 Improve DBObject::CheckValue and CheckConsistency error messages (#288)
Now contains attribute code and value
2022-05-17 17:01:41 +02:00
Eric Espie
44eda676a3 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration
2022-05-17 16:56:43 +02:00
Molkobain
eac6f07823 N°4985 - PHP 8.0: Fix optional parameter before mandatory parameter
* Method is always (once) called with the value defined in iTop
  * No Combodo extension call the method
  * No customization in the ITSM Designer (snippets / extensions) call the method
  * Calling method with only the first parameter would crash anyway
2022-05-17 16:51:50 +02:00
Pierre Goiffon
424e2a5745 💡 Fix PHPDoc for \DBObject::CheckConsistency 2022-05-17 15:52:43 +02:00
Molkobain
46713236c4 PHPDoc - Add corresponding link thanks to @pirGoif 2022-05-17 15:34:58 +02:00
Molkobain
0ef4fee0b4 N°4985 - PHP 8.0: Fix usort callback return type 2022-05-17 15:28:04 +02:00
Eric Espie
1d45eff9b0 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration
2022-05-17 10:11:15 +02:00
Benjamin Dalsass
8e97279401 N°4899 - Reflected XSS on revert_dashboard operation 2022-05-17 09:27:06 +02:00
Eric Espie
932ef780fd N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration
2022-05-17 09:06:49 +02:00
Benjamin Dalsass
59424c3126 N°4976 - CSRF in import page 2022-05-17 09:02:06 +02:00
Benjamin Dalsass
562dd8fc21 N°4900 - Stored XSS in dashlets failed OQL query 2022-05-17 08:20:26 +02:00
Vladimir Kunin
f3e601e340 🐛 N°4834 - Fix mentions working only with latin alphabet (no dash, no cyrillic, no asian, ...) (#274)
* 🐛 Add the 'pattern' parameter with the unicode Cyrillic block regex to the CKEditor mentions config.

* Revert "🐛 Add the 'pattern' parameter with the unicode Cyrillic block regex to the CKEditor mentions config."

This reverts commit 1f5ac000b6.

* 🐛 Rewrite the CKEditor Mentions plugin regexp to make it suitable for all Unicode alphabets.
2022-05-16 20:06:30 +02:00
Molkobain
cf745554fb N°4985 - PHP 8.0: Fix strlen() test condition that needs to be more strict 2022-05-16 18:04:29 +02:00
Molkobain
e909eac98e N°4985 - PHP 8.0: Fix is_callable() first param syntax in ObjectFormManager 2022-05-16 17:44:34 +02:00
Molkobain
5e42efc3ec N°4985 - PHP 8.0: Fix usort callback return type in portal's lists initialization 2022-05-16 17:44:33 +02:00
Molkobain
ff58fb8617 N°5172 - Add internal helpers to keep usage of null value in native PHP methods: strlen() => utils::StrLen() 2022-05-16 16:15:18 +02:00
Pierre Goiffon
98b24dff36 Merge remote-tracking branch 'origin/support/3.0.1' into support/3.0 2022-05-16 15:28:10 +02:00
Pierre Goiffon
ed9197e6ef N°4224 Fix failed Jenkins build due to "Function ReflectionType::__toString() is deprecated"
E_DEPRECATED were previously hidden on the whole test infra.
But after PHPUnit update (N°3091) we restored them.

On legacy builds we are still using PHPUnit 6 and mocks which are generating such notices. So we are now hiding them only where necessary !
2022-05-16 15:16:03 +02:00
Eric Espie
eb1d56f439 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration
2022-05-16 14:51:12 +02:00
Eric Espie
644e1ac4f6 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration (wip)
2022-05-13 16:27:56 +02:00
Stephen Abello
4c88dbd9ac N°2504 N°3169 N°5102 Add libraries 2022-05-13 14:39:19 +02:00
Stephen Abello
11d2e62e67 N°2504 N°3169 N°5102 Correctly disable authentication button for 2.7 2022-05-13 14:38:55 +02:00
Stephen Abello
58b27a9daa N°2504 N°3169 N°5102 Handle result display 2022-05-13 14:28:38 +02:00
Stephen Abello
caf939bf58 N°2504 N°3169 N°5102 Add dictionaries 2022-05-13 14:06:11 +02:00
Eric Espie
8c217fdac9 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration (wip)
2022-05-13 12:07:27 +02:00
Eric Espie
6b80bbeaa2 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration (wip)
2022-05-13 11:45:42 +02:00
Eric Espie
134736dce5 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
 * 2.7 migration (wip)
2022-05-13 11:37:09 +02:00
Stephen Abello
4b870bcf1e N°2504 N°3169 N°5102 Add js template 2022-05-12 17:38:38 +02:00
acognet
2165bfe8c2 Fix "undefined offset" error during "Anonymize" action 2022-05-12 14:45:18 +02:00
Eric Espie
dd8a4a0082 N°3169 - Add feature to connect Gsuite mail box with OAuth
N°2504 - Add feature to connect Office mail box with OAuth2 for Microsoft Graph
N°5102 - Allow to send emails (eg. notifications) using GSuite SMTP and OAuth
2022-05-12 14:40:55 +02:00
Molkobain
c1f335fedb Merge remote-tracking branch 'origin/support/3.0.1' into support/3.0 2022-05-11 18:10:46 +02:00
Molkobain
22a4a2fc5e Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	setup/wizardsteps.class.inc.php
2022-05-11 17:50:00 +02:00
acognet
6946bb54ed Revert "Fix "undefined offset" error during "Anonymize" action"
This reverts commit b4e623d1
2022-05-11 12:38:23 +02:00
acognet
b4e623d175 Fix "undefined offset" error during "Anonymize" action 2022-05-11 10:18:58 +02:00
acognet
f4e04477db Fix "undefined offset" error during "Anonymize" action 2022-05-09 16:08:33 +02:00
Molkobain
c2607c4223 N°5035 - Setup: Remove tracking image at the end of the setup 2022-05-09 13:55:06 +02:00
Molkobain
66953be67d N°5060 - Activity panel: Increase "max_history_length" conf. parameter from 50 to 200 2022-05-09 13:14:09 +02:00
Molkobain
ce355e311c N°5060 - Activity panel: Show "load more entries" buttons no matter the filters 2022-05-09 13:14:08 +02:00
Pierre Goiffon
bab14e1489 N°4224 remove workarounds for DEPRECATED notices generated by mock
We shouldn't have the problem anymore with PHPUnit 8.5 !
2022-05-05 15:43:59 +02:00
Anne-Catherine
65a0aa7abb Update README.md 2022-05-04 10:48:33 +02:00
Anne-Catherine
261a44764d Update README.md
Change logo
2022-05-04 10:40:37 +02:00
Pierre Goiffon
b3ef9333af 💡 Added since annotation to \LogAPI::IsLogLevelEnabled 2022-05-03 17:18:07 +02:00
Pierre Goiffon
1fb0911710 🔧 N°3091 postbuild PHPunit XML : change html_errors PHP setting 2022-05-03 10:53:32 +02:00
Pierre Goiffon
867cc6ce7e Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-05-03 10:52:01 +02:00
Pierre Goiffon
b348e0ff27 🔧 N°3091 PHPunit XML : change html_errors PHP setting
We are outputting to console, and will get results in Jenkins or terminal, so no HTML please :o)
2022-05-03 10:51:48 +02:00
Pierre Goiffon
4646a05c7a N°4824 Update consumers after swiftmailer/swiftmailer
Multiple things to do as there were some changes in 6.0
Reference : https://github.com/swiftmailer/swiftmailer/blob/master/CHANGES#L107

* Fix "Call to undefined method Swift_Message::newInstance()" exception in notifications
* Fix removed Swift_MailTransport
2022-05-03 09:35:48 +02:00
Pierre Goiffon
84e35e27b8 N°5143 Fix FunctionExpression for DATE_FORMAT and formats %j, %k and %l 2022-05-02 18:59:10 +02:00
Pierre Goiffon
c5527c106c 🔧 N°3091 PHPunit XML : set columns 2022-05-02 15:33:39 +02:00
Pierre Goiffon
5eac1b8730 🔧 N°3091 PHPunit XML : fix correct PHP INI settings
see https://phpunit.readthedocs.io/en/8.5/configuration.html#the-php-element
2022-05-02 15:25:59 +02:00
Pierre Goiffon
603934bac1 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.lock
#	lib/composer/installed.php
2022-05-02 09:43:33 +02:00
Pierre Goiffon
0de15d040f ⬇️ N°4824 rollback scssphp/scssphp update (won't be done in this branch !) 2022-05-02 09:15:48 +02:00
Pierre Goiffon
41d032eee6 N°4284 Update BackOffice JQuery UI SCSS to remove SCSSPHP warnings 2022-05-02 08:48:28 +02:00
Pierre Goiffon
c4ae94fd4c Update denied test dirs 2022-04-29 17:15:50 +02:00
Pierre Goiffon
afaf72573b N°4284 remove unused dependencies 2022-04-29 17:13:58 +02:00
Pierre Goiffon
ddd41d2ba7 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.json
#	composer.lock
#	core/email.class.inc.php
#	css/ui-lightness/jqueryui.scss
#	lib/bin/php-parse
#	lib/bin/php-parse.bat
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_static.php
#	lib/composer/installed.json
#	lib/composer/installed.php
#	lib/composer/platform_check.php
#	lib/nikic/php-parser/grammar/php7.y
#	lib/nikic/php-parser/lib/PhpParser/Builder/FunctionLike.php
#	lib/nikic/php-parser/lib/PhpParser/Builder/Param.php
#	lib/nikic/php-parser/lib/PhpParser/Builder/Property.php
#	lib/nikic/php-parser/lib/PhpParser/BuilderFactory.php
#	lib/nikic/php-parser/lib/PhpParser/BuilderHelpers.php
#	lib/nikic/php-parser/lib/PhpParser/ConstExprEvaluator.php
#	lib/nikic/php-parser/lib/PhpParser/Lexer/Emulative.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Expr/ArrowFunction.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Expr/Closure.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Expr/FuncCall.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Expr/MethodCall.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Expr/New_.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Expr/NullsafeMethodCall.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Expr/StaticCall.php
#	lib/nikic/php-parser/lib/PhpParser/Node/FunctionLike.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Param.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Stmt/ClassLike.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Stmt/ClassMethod.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Stmt/Function_.php
#	lib/nikic/php-parser/lib/PhpParser/Node/Stmt/Property.php
#	lib/nikic/php-parser/lib/PhpParser/Node/UnionType.php
#	lib/nikic/php-parser/lib/PhpParser/NodeVisitor/NameResolver.php
#	lib/nikic/php-parser/lib/PhpParser/Parser/Php7.php
#	lib/nikic/php-parser/lib/PhpParser/PrettyPrinter/Standard.php
#	lib/nikic/php-parser/lib/PhpParser/PrettyPrinterAbstract.php
#	test/core/ConfigValidator/iTopConfigAstValidatorTest.php
2022-04-29 16:18:08 +02:00
Pierre Goiffon
1e8818984e 📄 N°4284 Update licenses 2022-04-29 15:53:03 +02:00
Pierre Goiffon
a023f73509 N°4284 Update jquery UI SCSS to remove SCSSPHP warnings
Replace "Alpha(..." with "alpha(..."

Example of warning at compilation with SCSSPHP :

DEPRECATION WARNING: Calling built-in functions with a non-standard name is deprecated since Scssphp 1.8.0 and will not work anymore in 2.0 (they will be treated as CSS function calls instead).
Use "alpha" instead of "Alpha".
         on line 55 of /var/www/html/iTop/css/../css/ui-lightness/jqueryui.scss
2022-04-29 15:39:26 +02:00
Pierre Goiffon
6f0e1a7f47 N°4824 Update consumers after swiftmailer/swiftmailer update
Also remove new Doctrine test dir (iTopComposerTest feedback)
2022-04-29 15:24:56 +02:00
Pierre Goiffon
0ef9bb1a47 ⬆️ N°4824 Composer libs : update swiftmailer/swiftmailer 2022-04-29 15:24:56 +02:00
Pierre Goiffon
71ceedc4bb 🔨 N°4284 Detect new test dirs on composer update 2022-04-29 15:24:56 +02:00
Pierre Goiffon
73c3c1249f ⬆️ N°4824 Composer libs : update scssphp/scssphp 2022-04-29 15:24:56 +02:00
Pierre Goiffon
88a10dba28 N°4824 Update consumers after pelago/emogrifier update 2022-04-29 15:24:56 +02:00
Pierre Goiffon
001e222f67 ⬆️ N°4824 Composer libs : update pelago/emogrifier 2022-04-29 15:24:56 +02:00
Pierre Goiffon
af8bcdc242 ⬆️ N°4824 Composer libs : update pear/archive_tar 2022-04-29 15:24:56 +02:00
Pierre Goiffon
f4c7afc148 N°4824 Update consumers & tests after nikic/php-parser update
Was done in 3.0.0 with N°3867
(cherry picked from commit cd1ba097cb)
(cherry picked from commit 5b42f67a99)
(cherry picked from commit 2d98ca2318)
(cherry picked from commit ddc5bbd1bb)
2022-04-29 15:24:56 +02:00
Pierre Goiffon
b19c73a36e ⬆️ N°4284 Composer libs : update nikic/php-parser
Was done in 3.0.0 with N°3867
2022-04-29 15:24:55 +02:00
Pierre Goiffon
5fe0d0b94f ⬆️ N°4284 Composer libs : update combodo/tcpdf 2022-04-29 15:18:41 +02:00
Pierre Goiffon
f8d435d5f3 N°4284 Composer libs : refresh symfony 2022-04-29 15:18:41 +02:00
Pierre Goiffon
f15ef36fd1 N°4284 Composer libs : remove symfony/polyfill-php70
Though it is still downloaded because asked by symfony framework, but as we don't need it in our code no need to specify it here !
2022-04-29 15:18:41 +02:00
Pierre Goiffon
64b25c4daa 📌 N°4284 Composer libs : fix twig/twig to ~1.42.5
Without specifying explicitly the Twig version, since the update of require php from 5.6 to 7.0 we are getting Twig 2.12.5 !
We don't want Twig 2 as this version changes the macro scope and causes massive changes in our code... This update will be done later in other branches.
2022-04-29 15:15:32 +02:00
Pierre Goiffon
e81587470d N°3091 Fix ExpressionEvaluateTest::testEveryTimeFormat
Might need a real fix sometime !!
2022-04-22 17:06:03 +02:00
Pierre Goiffon
fc6df1063c N°4660 restore old phpunit testsuites order
Was causing error in DataSynchroTest::testDataSynchroByHttp
2022-04-22 16:29:01 +02:00
Pierre Goiffon
5a37bc338a N°3091 Update PHPUnit to 8.5 : fix setUp and teardDown methods signatures on support/3.0 new tests 2022-04-22 16:04:54 +02:00
Pierre Goiffon
f4a027b474 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	composer.json
#	core/cmdbchangeop.class.inc.php
#	core/cmdbobject.class.inc.php
#	css/light-grey.scss
#	setup/setuputils.class.inc.php
#	test/ItopTestCase.php
#	test/core/ConfigTest.php
#	test/core/LogAPITest.php
#	test/core/UserRightsTest.php
#	test/core/dictApcuTest.php
#	test/core/dictTest.php
#	test/core/iTopConfigParserTest.php
#	test/core/ormLinkSetTest.php
#	test/phpunit.xml.dist
#	test/postbuild_integration.xml.dist
#	test/setup/SetupUtilsTest.php
#	test/status/StatusIncTest.php
#	webservices/cron.php
2022-04-22 15:26:18 +02:00
Pierre Goiffon
d0ba0d193b N°3091 iTopComposerTest : change deprecated PHPUnit method call 2022-04-22 14:42:12 +02:00
Pierre Goiffon
8e6e2432d3 Extensibility : iPortalUIExtension and AbstractPortalUIExtension aren't experimental anymore 2022-04-21 17:29:40 +02:00
Molkobain
83ec19dfca Remove duplicated lines in .gitignore 2022-04-21 14:26:56 +02:00
Pierre Goiffon
6e619f2c35 Fix \iTopConfigParserTest::testConfigWriteToFile_FromScratchInstallation throwing error 2022-04-21 12:02:35 +02:00
Pierre Goiffon
163ba41e8d N°3091 Update PHPUnit to 8.5 : remove doesNotPerformAssertions annotation
Modified tests :
- iTopConfigParsertest
- DBSearchIntersectTest::testIntersectOptimization

As expected this isn't working with PHPUnit 8.5
Why does it worked with previous PHPUnit 6 version ? Maybe this annotation wasn't handled yet ? The corresponding PHPUnit doc isn't available anymore...

Annotations doc for PHP 8.5 : https://phpunit.readthedocs.io/en/8.5/annotations.html#doesnotperformassertions
2022-04-21 12:02:35 +02:00
Pierre Goiffon
ec143c43db N°3091 Update PHPUnit to 8.5 : fix setUp and teardDown methods signatures
"Return type declaration must be compatible with parent"
See https://phpunit.de/announcements/phpunit-8.html "Return Type of Template Methods"
2022-04-21 12:02:35 +02:00
Pierre Goiffon
cacf0004a5 🙈 N°3091 Update PHPUnit to 8.5 : add PHPunit cache file to ignore
We don't want to disable the feature, nor we want this file to be versionned
https://phpunit.readthedocs.io/en/8.5/configuration.html#the-cacheresult-attribute
2022-04-21 12:02:35 +02:00
Pierre Goiffon
cb39541e2a N°3091 Update PHPUnit to 8.5 : composer and base files
Autoload wasn't working anymore, easy to see : just launch `php unittestautoload.php` (or see fatal errors when launching tests with your IDE)
2022-04-21 10:47:30 +02:00
Pierre Goiffon
b9ddadeb44 N°5109 update PHP requirements from 5.6 to 7.0
No embedded libs supports all versions from PHP 5.6 to 8.0 included :/
7.0.8 is required for our Symfony version (updated with N°4770)
2022-04-20 17:29:20 +02:00
Benjamin Dalsass
dabd2a3f4d N°5101 - Setup error when semantic field attribute code is not defined in current class 2022-04-20 14:32:03 +02:00
Pierre Goiffon
11e811cc4b N°3717 Improve iTop object history API (#192)
This fixes a major flaw in the history API that was causing "phantom" CMDBChange records (without any CMDBChangeOp attached). That was happening especially in iProcess impl.
For example this lead to the creation of the combodo-cmdbchange-cleaner module in the Mail To Ticket extension.

The modifications in detail : 
- We can now pass a non persisted CMDBChange instance to \CMDBObject::SetCurrentChange
- No persistence done in \CMDBObject::CreateChange anymore
- Persistence of the attached CMDChange will be done if necessary in CMDBChangeOp::OnInsert
- New CMDBObject::SetCurrentChangeFromParams helper method to ease resetting the current change
2022-04-19 17:13:18 +02:00
Pierre Goiffon
e422adb0d0 N°4998 Fix CSS for AttributeDuration in transition form (#281) 2022-04-19 12:25:15 +02:00
Molkobain
b03e28efb9 N°4966 - Code cleanup 2022-04-19 12:13:14 +02:00
Pierre Goiffon
7b3d859522 N°5027 AttributeUrl handle anchors starting with digits 2022-04-19 10:57:47 +02:00
Pierre Goiffon
e02d9f3f0e 💡 N°5090 Improve phpdoc using list array shape 2022-04-15 17:43:20 +02:00
Pierre Goiffon
e831d66b76 N°5090 Setup : improve missing dependencies message (#280)
The setup now relies on the new method MissingDependencyException::getHtmlDesc to get the message to display
MissingDependencyException is also now a CoreException child.

Note that previous behavior (MissingDependencyException instantiator setting message) is kept, as some consumer still do $e->getMessage() (like unattended install)
2022-04-15 17:30:05 +02:00
acognet
6fa2d47780 N°4538 - Dashlet Groupby on ExternalKey with special character, bad display 2022-04-15 10:03:04 +02:00
acognet
e691454339 N°5002 - memory leak after object creation in popup 2022-04-15 10:00:08 +02:00
acognet
079b406f18 N°4966 - No more custom dashboard switch 2022-04-15 09:54:41 +02:00
Timothee
dbe02a42c2 N°4888 New url() placeholder 2022-04-14 12:05:41 +02:00
Molkobain
94365ea40e Update contributors stickers image to 2022! 🚀 2022-04-13 16:05:00 +02:00
Molkobain
2716f9d24c Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/config.class.inc.php
2022-04-08 13:30:42 +02:00
Stephen Abello
bac2918ceb N°5028 Revert default logos by png ones 2022-04-08 09:46:26 +02:00
Pierre Goiffon
92997e3e57 💡 N°2498 add @since 2022-04-08 08:54:07 +02:00
Stephen Abello
604837c770 N°5028 Fix updated default logo in error webpages 2022-04-07 16:46:39 +02:00
Molkobain
f32c283c9c N°4759 - Navigation menu: Fix menu groups icons glitch when switching between collapsed / expanded mode 2022-04-07 16:02:06 +02:00
Stephen Abello
27d06a712b N°5028 Update setup favicon to default one 2022-04-07 15:01:07 +02:00
Stephen Abello
b15050487c N°5028 Fix updated default logo in unauthenticated webpages 2022-04-07 14:59:48 +02:00
Stephen Abello
46f232d561 N°4759 Harmonize top and bottom space around branding logo 2022-04-07 11:04:24 +02:00
Stephen Abello
63976df2e1 N°5028 Update iTop and Combodo logos to new ones 2022-04-07 11:03:32 +02:00
Molkobain
3514e21772 Revert precompiled themes update 2022-04-04 10:54:11 +02:00
Molkobain
3463b1715a N°4674 - CKEditor: Fix space indentation in code blocks 2022-04-04 10:21:52 +02:00
Pierre Goiffon
631b38a160 N°5003 Change cron_max_execution_time config param help text 2022-03-25 15:56:11 +01:00
Eric Espie
0287500feb N°4999 - Wrong object save order in activity panel 2022-03-25 09:31:16 +01:00
Molkobain
e4cbaf7096 Typo 2022-03-23 10:23:35 +01:00
Molkobain
73c6b4be20 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	test/core/DBObjectTest.php
2022-03-23 09:44:13 +01:00
Molkobain
fde2103659 👥 Add link to contributors' GitHub profile 2022-03-23 09:42:31 +01:00
Molkobain
24500216f6 👥 Add @ChristianBeer to contributors list! 🙌 2022-03-23 09:41:24 +01:00
acognet
2039b872d3 N°4977 - Wrong result in search on a Service subcategory for Service provider 2022-03-22 17:06:05 +01:00
Molkobain
b368c593e5 N°4462 - Improve message to explicitly say next "major" release 2022-03-22 12:25:52 +01:00
Stephen Abello
c9c731a2a5 N°3541 Split button and button-group js in 2 different files 2022-03-22 10:16:17 +01:00
acognet
8204723b5b N°4667 - Remove call to tooltip function - change type of preview (fix seen with Guillaume) 2022-03-21 15:14:30 +01:00
acognet
f93218a80f N°4479 - Impact analysis : Display and apply filter before display impact analysis graphical - fix var name 2022-03-21 11:11:47 +01:00
Molkobain
4f5a9c898c N°4462 - Set next min. PHP version for iTop 3.1
Note: This might change to PHP 7.2 this summer depending on RedHat 9.0 release date / plans
2022-03-21 09:51:23 +01:00
Eric Espie
7ce5712b71 N°4967 - 'Previous Values For Updated Attributes' not updated if DBUpdate is called without modifying the object 2022-03-21 08:43:03 +01:00
acognet
90b41e0b81 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/displayablegraph.class.inc.php
#	pages/UI.php
2022-03-18 15:51:45 +01:00
Pierre Goiffon
9d2c89f118 N°4959 Fix graph dashlet not refreshed
Previous fix in e4501389 was incomplete, cause passing empty as id isn't handled in called method.
2022-03-18 15:16:52 +01:00
acognet
61137a6f65 N°4479 - Impact analysis : Display and apply filter before display impact analysis graphical - Fix dictionnary 2022-03-18 11:02:04 +01:00
acognet
a26c8fbd48 N°4971 - "Please specify a value" does not disappear after selecting the value via the popup 2022-03-17 17:39:31 +01:00
Pierre Goiffon
0080a2e733 💡 N°3129 Fix phpdoc
Method was renamed in 45b5c39a but I forgot to update the PHPDoc
2022-03-17 15:36:39 +01:00
acognet
992ee3a74b N°4667 - Remove call to tooltip function - tooltip on attachment in portal 2022-03-17 12:53:03 +01:00
acognet
e45013891c N°4959 - Chart update fails in dashboard 2022-03-16 11:05:50 +01:00
acognet
ea043960ff Rename the map file. We are using the min version 2022-03-15 11:23:57 +01:00
acognet
d0f83046cd Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-files-information/dictionaries/pt_br.dict.itop-files-information.php
#	datamodels/2.x/itop-files-information/dictionaries/zh_cn.dict.itop-files-information.php
2022-03-15 10:56:01 +01:00
acognet
7f4fddb378 N°4644 - Core update : confusing warning message when integrity of iTop std files is modified - fix default translation 2022-03-15 10:52:19 +01:00
Stephen Abello
9cd076131f N°3541 Add event listener to enable/disable loading state for buttons group block 2022-03-14 15:32:42 +01:00
acognet
a71cb97db3 N°4644 - Core update : confusing warning message when integrity of iTop std files is modified - fix comment 2022-03-14 15:30:35 +01:00
acognet
0c80a4e430 N°4644 - Core update : confusing warning message when integrity of iTop std files is modified - merge from 2.7.0 2022-03-14 15:28:47 +01:00
acognet
779211e638 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-core-update/dictionaries/cs.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/da.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/de.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/en.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/es_cr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/fr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/hu.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/it.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/ja.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/nl.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/ru.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/sk.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/tr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/dictionaries/zh_cn.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/pt_br.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/view/SelectUpdateFile.html.twig
#	datamodels/2.x/itop-datacenter-mgmt/dictionaries/pl.dict.itop-datacenter-mgmt.php
#	datamodels/2.x/itop-endusers-devices/dictionaries/pl.dict.itop-endusers-devices.php
#	datamodels/2.x/itop-files-information/src/Service/FilesIntegrity.php
2022-03-14 15:17:28 +01:00
acognet
4c99f497cc N°4644 - Core update : confusing warning message when integrity of iTop std files is modified - List all modified files 2022-03-14 14:45:07 +01:00
Stephen Abello
d1e2be97d2 Typo in cron_task_max_execution_time description 2022-03-14 11:46:27 +01:00
Stephen Abello
93c6cfffda N°4931 Fix background tasks max duration being set to 3 times its periodicity 2022-03-14 09:35:46 +01:00
Molkobain
b50ba0ad49 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-03-13 20:36:49 +01:00
Molkobain
0205cdf713 N°4791 - Portal: Fix "Twig not allowed" error when transition form has no editable field (auto redirect)
Regression from b6fac4b4
2022-03-13 18:15:49 +01:00
Molkobain
39fc59a8b2 Code cleanup 2022-03-13 17:55:04 +01:00
Molkobain
107c9adf60 N°4791 - Expand usage of ObjectFormHandlerHelper::ENUM_MODE_XXX constants for better robustness / comprehension 2022-03-13 17:29:55 +01:00
Molkobain
143c30b099 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-core-update/cs.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/da.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/de.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/en.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/es_cr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/fr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/hu.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/it.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/ja.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/nl.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/pt_br.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/ru.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/sk.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/src/Service/CoreUpdater.php
#	datamodels/2.x/itop-core-update/tr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/view/ConfirmUpdate.html.twig
#	datamodels/2.x/itop-core-update/zh_cn.dict.itop-core-update.php
2022-03-11 18:03:21 +01:00
Molkobain
d29880b1b8 Update PHPDoc 2022-03-11 17:52:10 +01:00
acognet
3edfc2016d Fix typo 2022-03-11 15:41:12 +01:00
Molkobain
5f80be75ed N°4938 - Fix remaining broken AJAX endpoints in ajax.render.php 2022-03-11 10:47:05 +01:00
Molkobain
0d4796ae2b N°4938 - Fix background calls broken by lazy JS dictionaries loads 2022-03-11 09:34:27 +01:00
acognet
2d156bd77b N°4642 - Core Update : limit the usage of this function - disable if new modules found 2022-03-10 16:47:21 +01:00
Pierre Goiffon
5908ec5197 N°4515 AttributeURLTest : add SF forum url 2022-03-10 16:42:43 +01:00
acognet
d122dbfdd6 N°4642 - Core Update : limit the usage of this function - disable if new modules found 2022-03-10 16:06:37 +01:00
acognet
46d58e6512 N°4642 - Core Update : limit the usage of this function - disable if new modules found 2022-03-10 15:24:29 +01:00
Christian Beer
6cf781da33 🌐 Improve German translation (#277)
Many thanks @ChristianBeer for this great contribution, and @larhip for the validation !
2022-03-10 14:16:59 +01:00
Molkobain
0f2cbaf186 N°4849 - Enable notification emails grouping in threads in email clients (#275)
N°4849 - Enable notification emails grouping in threads in email clients (#275)
Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>
2022-03-10 09:31:29 +01:00
Molkobain
7ddb47dc83 N°4312 - Activity panel: Fix JS error on object without tabs (typically DBObject instead of cmdbAbstractObject)
Regression from b9c5f2c523
2022-03-09 20:06:19 +01:00
Molkobain
304e379c01 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	datamodels/2.x/itop-core-update/cs.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/da.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/de.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/en.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/es_cr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/fr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/hu.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/it.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/ja.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/nl.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/pt_br.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/ru.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/sk.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/tr.dict.itop-core-update.php
#	datamodels/2.x/itop-core-update/view/SelectUpdateFile.html.twig
#	datamodels/2.x/itop-core-update/view/SelectUpdateFile.ready.js.twig
#	datamodels/2.x/itop-core-update/zh_cn.dict.itop-core-update.php
2022-03-09 18:31:34 +01:00
Molkobain
93a138606f N°4664 - Core Update : block zip file upload until instance declared OK 2022-03-09 18:21:08 +01:00
Molkobain
70074ee1cb N°4644 - Core update: Update translations with missing entry 2022-03-09 17:31:22 +01:00
Molkobain
d28ccb264f N°4644 - Core update : confusing warning message when integrity of iTop std files is modified
(cherry picked from commit 69a0bd0c34)
2022-03-09 17:28:38 +01:00
Thomas Casteleyn
9f95d45f51 Fix check on when to load JS dicts 2022-03-08 18:42:55 +01:00
odain-cbd
8ab38854a8 N°4920 - Fix "undefined index" notice in user rights (#271) 2022-03-08 18:21:40 +01:00
acognet
bceb570d84 N°4874 - Auto Refresh of attribute Dasboard 2022-03-08 15:31:41 +01:00
acognet
138fa569f2 N°4642 - Core Update : limit the usage of this function to minor version 2022-03-08 14:56:15 +01:00
Molkobain
1f65ab5a92 N°4642 - Improve conventions
* Rename SCSS variables
  * Optimize SCSS rules
2022-03-07 17:05:29 +01:00
Molkobain
7cfac7300b N°4642 - Fix typo in SCSS variables 2022-03-07 16:31:43 +01:00
Molkobain
ede720c9b9 Merge remote-tracking branch 'origin/support/2.7' into support/3.0 2022-03-07 12:52:09 +01:00
Molkobain
684efee5d2 N°4664 - Code format 2022-03-07 12:49:27 +01:00
acognet
e347989dcb N°4664 - Core Update : block zip file upload until instance declared OK 2022-03-07 12:05:54 +01:00
acognet
e1051e7a47 N°4654 - Missing licence Information in About iTop for non admin users - add since 3.0.1 2022-03-07 11:35:18 +01:00
Molkobain
7e8eb26866 N°4654 - Change block ID to match conventions 2022-03-07 09:50:07 +01:00
Molkobain
6775a3e928 Code cleanup 2022-03-07 09:47:54 +01:00
Molkobain
faa38155e5 N°4911 - Mentions: Fix DBObject::Reload() for classes with an image attribute 2022-03-06 22:44:13 +01:00
Molkobain
558bbc3357 Revert "N°4911 - Mentions: Fix Person picture not displayed if marker configured on parent class (Contact)"
This reverts commit 106127e6b7.

As the image attribute can be different depending on the object finalclass, it cannot be added in the DBObjectSet::OptimizeColumnLoad(), which means that retrieving it within the loop might lead to a complete DBObject::Reload() of the object which can have a real impact on performances depending on the objects.
2022-03-06 22:44:13 +01:00
Molkobain
cd7f9e478f N°4913 - Avoid object initials to overflow in medallions 2022-03-06 22:44:12 +01:00
Molkobain
e3586cff65 Unit tests: Add unit cyrillic alphabet test case for utils::ToAcronym() 2022-03-06 16:31:48 +01:00
Molkobain
106127e6b7 N°4911 - Mentions: Fix Person picture not displayed if marker configured on parent class (Contact) 2022-03-06 12:49:11 +01:00
Molkobain
2299983db3 N°4741 - Factorize activation of on mention triggers 2022-03-06 11:54:39 +01:00
acognet
2fab7de34b N°4806 - UI:WelcomeMenu:Text contains empty string 2022-03-04 10:36:28 +01:00
acognet
c0ab79971c N°4654 - Missing licence Information in About iTop for non admin users - nicer loading icon 2022-03-04 10:36:27 +01:00
Molkobain
03ed9c9deb N°4905 - Fix usage of ITOP_APPLICATION constant in dictionaries 2022-03-04 10:31:01 +01:00
acognet
7152277760 N°4642 - Core Update : limit the usage of this function to minor version or disable the functionality ? 2022-03-03 22:02:35 +01:00
acognet
14d05da9f6 N°4664 - Core Update : block zip file upload until instance declared OK 2022-03-03 22:00:15 +01:00
acognet
69a0bd0c34 N°4644 - Core update : confusing warning message when integrity of iTop std files is modified 2022-03-03 21:59:04 +01:00
acognet
c09cee994a N°2884 - Core update : Database version not updated - remove definitively lines with $sDataModelVersion 2022-03-03 16:17:16 +01:00
acognet
50ee0b3eed N°4654 - Missing licence Information in About iTop for non admin users 2022-03-03 16:16:45 +01:00
Molkobain
84169a864c N°4856 - Update PHPDoc 2022-03-03 15:50:28 +01:00
acognet
9f27cf2b84 N°4525 - bad source for extensions in system information and about iTop with iTop Pr 2022-03-03 15:14:28 +01:00
Pierre Goiffon
f78986009f Improve messages of iTopModuleXmlInstallationChecklistTest::testAllModuleAreIncludedInInstallationXml 2022-03-03 10:46:06 +01:00
Eric Espie
4fdbec72d4 N°4569 - dictionaries 2022-03-03 10:00:25 +01:00
Eric Espie
94d31827e7 N°4569 - Fix tests 2022-03-02 17:54:27 +01:00
Eric Espie
45a8eb93e7 N°4569 - Add itop-themes-compat 2022-03-02 17:14:08 +01:00
Eric Espie
6ac3539373 N°4569 - Revert meta save of deleted nodes 2022-03-02 17:08:45 +01:00
Stephen Abello
a5d8425fe7 N°4741 Fix On mention trigger not working on object creation 2022-03-02 16:13:00 +01:00
Stephen Abello
3608c6b8ab N°4582 Prevent selectize behavior introduced by 2e08cff from displaying unescaped characters 2022-03-02 16:12:59 +01:00
Pierre Goiffon
2b1e583dc7 💡 N°4854 Document compiler behavior change for model.*.php files 2022-03-02 10:06:59 +01:00
Pierre Goiffon
3081aa473a Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	setup/runtimeenv.class.inc.php
2022-03-02 09:49:59 +01:00
Pierre Goiffon
809ea2eb49 💡 N°4854 Add phpdoc to utils::*Module* methods 2022-03-02 09:42:09 +01:00
acognet
2f98a3e7ac N°2884 - Core update : Database version not updated - prevent multi click on button "About iTop" 2022-03-01 17:04:37 +01:00
acognet
c737fc46ff N°2884 - Core update : Database version not updated 2022-02-28 15:21:44 +01:00
Stephen Abello
619c0d34e8 N°4764 Fix unit test 2022-02-28 14:59:56 +01:00
acognet
bdc7ed6f8e N°4057 - Custom Translation for Custom Tab is not inherited by instanciable Classes 2022-02-28 12:09:38 +01:00
Eric Espie
d9819d9c2a N°4784 - CAS authentication issue with iTop 3.0
* Fix regression when setting cas as first login mode
2022-02-28 11:55:45 +01:00
Eric Espie
f24f8a2f34 N°4569 - Fix restoring deleted nodes when parent is not present 2022-02-28 10:54:59 +01:00
Stephen Abello
3890b1a020 N°4764 Remove iTop version from webservices/status.php 2022-02-25 10:08:43 +01:00
Stephen Abello
2e08cff9ee N°4582 Align backspace behavior in selectize widgets with jQuery autocomplete one 2022-02-25 09:40:02 +01:00
Pierre Goiffon
968a0e5f3a Add check to prevent setup crash when creating config
Cherry-pick of 09b12bd0
This will prevent also a warning when running on PHP 8.0 (N°3129)
2022-02-24 15:39:20 +01:00
Molkobain
4694e8152e N°4809 - Remove iTopOwnershipToken class from CSV import list 2022-02-22 11:42:28 +01:00
Pierre Goiffon
4b731dd336 N°4836 Better fix by adding AjaxPage::SetOutputDataOnly() 2022-02-22 10:23:15 +01:00
Stephen Abello
5e0c7c211b N°4460 Fix run-query highlight color on error for Full Moon and Darkmoon 2022-02-22 10:13:36 +01:00
Pierre Goiffon
815870fe6b Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/cmdbabstract.class.inc.php
#	dictionaries/cs.dictionary.itop.model.php
#	dictionaries/da.dictionary.itop.model.php
#	dictionaries/de.dictionary.itop.model.php
#	dictionaries/es_cr.dictionary.itop.model.php
#	dictionaries/fr.dictionary.itop.model.php
#	dictionaries/hu.dictionary.itop.model.php
#	dictionaries/it.dictionary.itop.model.php
#	dictionaries/ja.dictionary.itop.model.php
#	dictionaries/pl.dictionary.itop.model.php
#	dictionaries/pt_br.dictionary.itop.model.php
#	dictionaries/tr.dictionary.itop.model.php
#	dictionaries/zh_cn.dictionary.itop.model.php
2022-02-22 09:36:06 +01:00
Pierre Goiffon
33ceab86fb N°4836 Fix dashlet editor when iBackofficeDictEntriesExtension impl exists 2022-02-21 16:52:31 +01:00
Molkobain
fe1bf3bfc1 PHPDoc 2022-02-19 17:18:42 +01:00
acognet
3727223db3 Fix comment 2022-02-18 18:05:36 +01:00
Stephen Abello
5b96d9f778 N°4769 Fix badly escaped run query suggestions containing multiple lines 2022-02-18 10:17:14 +01:00
Stephen Abello
162b15236d N°4783 Fix tabs headers hiding on Chrome with zoom-in/out 2022-02-18 09:17:55 +01:00
acognet
83e98ef2b8 N°4284 - Object modification: Attribute value lost if not allowed to be seen 2022-02-17 17:06:06 +01:00
Stephen Abello
d783954d13 N°4671 Fix dark moon extra tabs color 2022-02-17 14:48:35 +01:00
Molkobain
7207dc657c N°4662 - Add comment to all concerned templates 2022-02-17 14:13:41 +01:00
Stephen Abello
f1cce8e430 N°4582 Nicer focus indicator for extkey selectize inputs 2022-02-16 15:35:11 +01:00
Molkobain
3da49e6603 N°4814 - Improve image attribute placeholder when no default image 2022-02-16 11:45:18 +01:00
Pierre Goiffon
5048421bfa 🔥 N°4815 Remove .model files in /dictionaries
They were added with 3fb0c768 in 2.5.2, probably by mistake as they :
* exists only for certain languages and not for english
* only contain comments
2022-02-16 10:17:42 +01:00
Stephen Abello
b9c5f2c523 N°4312 Keep selected activity panel tab active when refreshing or modifying an object 2022-02-15 15:45:41 +01:00
acognet
ec75195a2f N°4662 - Portal: Fix broken display of the services catalogue when installing Service Provider + Sample Data
(cherry picked from commit f9e8bf88c8)
2022-02-15 14:08:44 +01:00
Stephen Abello
e971d628dd N°4565 Add a message indicator to caselog tabs toggler 2022-02-15 10:21:09 +01:00
acognet
bbd50ba73b N°4438 - Disable (temporarly) copy of precompiled stylesheets after setup 2022-02-15 09:59:47 +01:00
acognet
ba71c1bcd5 N°4747 - Broken XLSX Templates created 2022-02-15 09:59:47 +01:00
acognet
16be8fd3d3 N°4777 - UserRequest: selecting organisation through hierarchy tree 2022-02-15 09:59:47 +01:00
acognet
cacae0a2b3 N°4591 - Space trimed when filling html attribute or log attribute with object-copier 2022-02-15 09:59:47 +01:00
Pierre Goiffon
b1ed15f31c N°4787 Remove useless "+" dict entries
Emptied "+" entries when their value is the same as its counterpart
2022-02-14 16:33:10 +01:00
acognet
788caf9c50 N°4284 - Object modification: Attribute value lost if not allowed to be seen 2022-02-14 12:26:16 +01:00
Eric Espie
1728dcc40c N°4784 - CAS authentication issue with iTop 3.0
* Moved session closing after the login
2022-02-14 09:31:52 +01:00
acognet
35165568af N°4057 - Custom Translation for Custom Tab is not inherited by instanciable Classes 2022-02-14 09:10:18 +01:00
Pierre Goiffon
cb5554ddb1 N°4714 Fix setup crashing with "Call to undefined method utils::GetCoreVersionWikiSyntax()" 2022-02-14 08:49:46 +01:00
Pierre Goiffon
6a5840ed82 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	lib/composer/installed.php
#	setup/licenses/community-licenses.xml
#	setup/setuputils.class.inc.php
#	sources/application/TwigBase/Controller/Controller.php
2022-02-14 08:41:33 +01:00
Molkobain
4a67819f87 N°4714 - Revert rename of utils::GetItopVersionWikiSyntax as it is used in cached packages in the ITSM Designer 2022-02-11 20:00:39 +01:00
Pierre Goiffon
81c39c35cd N°4771 Fix lib test dir detection
Thanks to @Molkobain and @Hipska for their review in dfaa9733
2022-02-11 18:15:56 +01:00
Pierre Goiffon
4caf52f1ae 🔥 N°4781 Remove SetupUtils::Log 2022-02-11 16:48:24 +01:00
Pierre Goiffon
0c5b845c8a 📄 N°4770 Update license file 2022-02-11 16:23:54 +01:00
Pierre Goiffon
cdfdb1f2ca 🔧 N°4770 composer.json version constraint
Will help Dependabot !
2022-02-11 16:23:54 +01:00
Pierre Goiffon
f29a8792af ⬆️ N°4770 Update to latest Symfony 3.4 2022-02-11 16:23:03 +01:00
Pierre Goiffon
b494ff2ce6 N°4488 Remove cmdbAbstractObject methods used in export.php from API methods and add comment in export.php
`@deprecated` was added in 03e9bcd4 but as none of those will be removed in a near future, we are using `@internal`instead !
2022-02-11 16:15:35 +01:00
Molkobain
a65c55fc48 iTopWebPage: Add CSS classes in addition to HTML IDs in template
This ease mocking several pages in a single one when IDs are removed
2022-02-11 15:51:52 +01:00
Molkobain
01b94f42fe Fix object's actions menu cannot be open (regression from 0d26211d) 2022-02-11 15:00:44 +01:00
odain
df1e19dc43 enhance ItopDataTestCase->CreateUser to avoid be able to avoid hardcoded contact_id 2022-02-11 14:10:02 +01:00
Thomas Casteleyn
cbef9bb267 Allow binary data to be imported/synchronised with the synchro_import.php 2022-02-11 12:16:09 +01:00
Pierre Goiffon
9ad341f73a N°4771 Fix .make/composer/rmDeniedTestDir.php Throwing errors when dir in denied list not existing on disk 2022-02-10 15:12:31 +01:00
acognet
03e9bcd47a N°4488 - deprecate cmdbAbstractObject::GetSetAsHTMLSpreadsheet() used only by the old export.php 2022-02-10 15:04:59 +01:00
acognet
55effea0a3 N°4513 - User Portal can apply transition on on an objetc not in his scope 2022-02-10 14:01:21 +01:00
Pierre Goiffon
dfaa973359 N°4771 improve iTopComposerTest
- debug testListDeniedTestDir not working well on Windows
- update error message for testAllDirCovered
2022-02-10 12:54:09 +01:00
Pierre Goiffon
2e45b20fc4 N°4771 Fix .make/composer/rmDeniedTestDir.php doing nothing on Windows
Note that a .gitignore entry was added in dbc3da7b but it isn't necessary if rmDeniedTestDir work as expected !
2022-02-10 12:45:52 +01:00
Pierre Goiffon
e89090f0ec N°4771 Update lib test dirs list : reordered for readability / easier maintenance 2022-02-10 12:08:18 +01:00
Molkobain
c9d02826a0 Code cleanup (indentation and PHPDoc) 2022-02-09 19:28:21 +01:00
Pierre Goiffon
47db04bcb7 💡 N°4760 Add complement in phpdoc 2022-02-09 11:48:17 +01:00
Pierre Goiffon
a49c451ae4 💡 N°4760 Fix wrong phpdoc 2022-02-09 11:43:42 +01:00
Pierre Goiffon
25c3704990 N°4761 Fix license.xml content not displayed in setup with multi modules extensions (#261)
For example :
module "mymodule" is in extension "myextension"
On the file system the `license.xml` file will be in `/extensions/myextension/mymodule/license.mymodule.xml`
This form wasn't working in the setup but well displayed in the about box.

When \SetupUtils::GetLicenses was called in the setup it was searching with a GLOB pattern only in one level subfolders. Now we are searching 2 levels.
When called from the console, it is only searching in env-*, where everything is on one level.
2022-02-08 17:28:47 +01:00
Pierre Goiffon
3000659e86 🎨 Change disable breadcrumb method name to clarify usage
Thanks @eespie for the review !
2022-02-08 17:04:11 +01:00
Pierre Goiffon
ce36c00b83 Remove now useless default values
Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>
2022-02-08 17:04:11 +01:00
Pierre Goiffon
2a3e6384d9 ♻️ After dev team code review 2022-02-08 17:04:11 +01:00
Pierre Goiffon
dd7e73e413 🎨 Simpler code
Thanks Hipska !
2022-02-08 17:04:11 +01:00
Pierre Goiffon
1709082e39 Controller::CreatePage : default values for sUrl and sIcon 2022-02-08 17:04:11 +01:00
Pierre Goiffon
41f6e85673 Controller::CreatePage : use @list() intead of 3 lines with count() tests
Thanks Hipska !

Co-authored-by: Thomas Casteleyn <thomas.casteleyn@super-visions.com>
2022-02-08 17:04:11 +01:00
Pierre Goiffon
3ef3166bd5 Add new methods to override in order to control breadcrumb in Controller children classes 2022-02-08 17:04:11 +01:00
Pierre Goiffon
0d26211dbe Fix error in object details : "Too few arguments to function MenuBlock::GetRenderContent()" 2022-02-08 15:16:57 +01:00
Pierre Goiffon
3b99006159 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	test/integration/iTopModulesPhpVersionChecklistTest.php
2022-02-08 14:49:08 +01:00
Pierre Goiffon
299ad7e753 N°4714 Fix \utils::GetCoreVersionWikiSyntax throwing Exception when 2nd version digit is "0" (for example in 3.0.1) 2022-02-08 14:48:02 +01:00
Pierre Goiffon
94a2421186 N°4714 Fix iTopModulesPhpVersionIntegrationTest
Was still testing removed utils::GetItopMinorVersion()
And also wrong merge done in testITopModulesPhpVersion()
2022-02-08 14:30:06 +01:00
Pierre Goiffon
923c3a27a3 Prepare 3.0.1 version 2022-02-08 14:28:27 +01:00
Pierre Goiffon
c1a1186bf7 N°4714 Fix setup crashing with "Call to undefined method utils::GetItopVersionWikiSyntax()"
Regression caused by merge b3605146
2022-02-08 13:55:20 +01:00
Pierre Goiffon
b360514646 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	application/displayblock.class.inc.php
#	application/ui.extkeywidget.class.inc.php
#	application/utils.inc.php
#	approot.inc.php
#	core/config.class.inc.php
#	css/css-variables.scss
#	datamodels/2.x/authent-cas/module.authent-cas.php
#	datamodels/2.x/authent-external/module.authent-external.php
#	datamodels/2.x/authent-ldap/module.authent-ldap.php
#	datamodels/2.x/authent-local/module.authent-local.php
#	datamodels/2.x/combodo-db-tools/module.combodo-db-tools.php
#	datamodels/2.x/itop-attachments/module.itop-attachments.php
#	datamodels/2.x/itop-backup/module.itop-backup.php
#	datamodels/2.x/itop-bridge-virtualization-storage/module.itop-bridge-virtualization-storage.php
#	datamodels/2.x/itop-change-mgmt-itil/module.itop-change-mgmt-itil.php
#	datamodels/2.x/itop-change-mgmt/module.itop-change-mgmt.php
#	datamodels/2.x/itop-config-mgmt/module.itop-config-mgmt.php
#	datamodels/2.x/itop-config/module.itop-config.php
#	datamodels/2.x/itop-core-update/module.itop-core-update.php
#	datamodels/2.x/itop-datacenter-mgmt/module.itop-datacenter-mgmt.php
#	datamodels/2.x/itop-endusers-devices/module.itop-endusers-devices.php
#	datamodels/2.x/itop-files-information/module.itop-files-information.php
#	datamodels/2.x/itop-full-itil/module.itop-full-itil.php
#	datamodels/2.x/itop-hub-connector/module.itop-hub-connector.php
#	datamodels/2.x/itop-incident-mgmt-itil/module.itop-incident-mgmt-itil.php
#	datamodels/2.x/itop-knownerror-mgmt/module.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-portal-base/module.itop-portal-base.php
#	datamodels/2.x/itop-portal/module.itop-portal.php
#	datamodels/2.x/itop-problem-mgmt/module.itop-problem-mgmt.php
#	datamodels/2.x/itop-profiles-itil/module.itop-profiles-itil.php
#	datamodels/2.x/itop-request-mgmt-itil/module.itop-request-mgmt-itil.php
#	datamodels/2.x/itop-request-mgmt/module.itop-request-mgmt.php
#	datamodels/2.x/itop-service-mgmt-provider/module.itop-service-mgmt-provider.php
#	datamodels/2.x/itop-service-mgmt/module.itop-service-mgmt.php
#	datamodels/2.x/itop-sla-computation/module.itop-sla-computation.php
#	datamodels/2.x/itop-storage-mgmt/module.itop-storage-mgmt.php
#	datamodels/2.x/itop-tickets/module.itop-tickets.php
#	datamodels/2.x/itop-virtualization-mgmt/module.itop-virtualization-mgmt.php
#	datamodels/2.x/itop-welcome-itil/module.itop-welcome-itil.php
#	datamodels/2.x/version.xml
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_static.php
#	lib/composer/installed.php
#	setup/modelfactory.class.inc.php
#	setup/setuputils.class.inc.php
#	test/integration/iTopModulesPhpVersionChecklistTest.php
2022-02-08 13:18:50 +01:00
acognet
541794ca9c N°4482 - Polishing : Export page 2022-02-07 16:45:25 +01:00
acognet
5fbcae1f55 N°4576 - issue with search date widget 2022-02-07 16:44:13 +01:00
Eric Espie
0f6e0e5085 Allow file name to be set with parameters 2022-02-07 15:02:47 +01:00
Stephen Abello
3541a9e1db N°3541 Add event listener to enable/disable loading state for buttons block 2022-02-07 14:54:23 +01:00
Stephen Abello
1f95a4ee21 N°3541 Add loading state design to buttons block 2022-02-07 14:54:23 +01:00
Molkobain
af5a0d5006 N°4751 - Fix crash when disabling newsroom in configuration 2022-02-04 22:58:48 +01:00
acognet
84280a3b5f N°4530 - Bug with OQL and profiles. 2022-02-04 16:21:53 +01:00
Molkobain
e3bce622e5 Dashboard: Add "input" event to properties listeners for real-time updates 2022-02-02 21:29:35 +01:00
Molkobain
ef9392a8d5 Fix icon selection misalignment in edition 2022-02-02 21:10:34 +01:00
Molkobain
15087ab848 N°592 - Fix ModelFactory::GetField() always failing as $aLoadedClasses is never filled 2022-02-02 19:06:38 +01:00
Molkobain
7bb7445c91 N°4482 - Small refacto
- SCSS partial rule should target only the concerned elements
- Improve PHPDoc
2022-02-02 16:47:15 +01:00
Molkobain
6a4ce3c3b1 Fix regression from c3a2713bb 2022-02-02 10:54:01 +01:00
Stephen Abello
7df27de5c1 N°4674 Fix code highlighter calls 2022-02-02 10:35:50 +01:00
Pierre Goiffon
b4fc647845 N°4714 Rename \utils::GetItopVersionWikiSyntax to GetCoreVersionWikiSyntax
Will avoid confusion between core or product version !
2022-02-01 15:40:43 +01:00
Pierre Goiffon
de053eed72 N°4714 Update iTopXmlVersionIntegrationTest::testItopXmlVersion to use new constant 2022-02-01 15:27:57 +01:00
Pierre Goiffon
17612f88d3 N°4714 utils version method refactoring
- removes utils::GetItopPatchVersion and GetItopMinorVersion : unused and badly named :/
- GetItopVersionWikiSyntax now uses core version constant
- iTopModulesPhpVersionIntegrationTest::testiTopModulesPhpVersion now uses ITOP_CORE_VERSION constant
2022-02-01 15:24:56 +01:00
Pierre Goiffon
e14845728c Prepare 2.7.7 2022-02-01 15:19:10 +01:00
Pierre Goiffon
4e80fc0f76 N°4624 Remove processIsolation flag from postBuild tests
Was done in standard test suite (test/phpunit.xml.dist) with 6bf25f90
2022-02-01 14:50:33 +01:00
Pierre Goiffon
fcfcf85e0d N°4714 fix constant version usages in utils methods 2022-02-01 11:39:57 +01:00
Pierre Goiffon
f0715baf7d N°4714 move constant from core/config.class.inc.php to approot.inc.php
see N°4406
2022-02-01 11:39:35 +01:00
Molkobain
2733e7966f N°4731 - Restore "data-value-raw" HTML metadata on attributes in object details 2022-01-31 20:03:02 +01:00
Eric Espie
52327d1086 Migrate default theme test-red 2022-01-31 17:50:54 +01:00
Eric Espie
81cf3df5e2 Migrate default theme test-red 2022-01-31 17:35:26 +01:00
Pierre Goiffon
45b5c39af7 N°3129 PHP 8.0 compat : code review modifications
Many thanks @Molkobain & @Hipska !
2022-01-31 16:41:35 +01:00
Eric Espie
4463e91d85 N°4569 - Fix unit tests 2022-01-31 16:41:01 +01:00
Eric Espie
ce87bf9e23 N°4569 - Fix bad alteration on trashed nodes 2022-01-31 16:23:01 +01:00
Pierre Goiffon
dbc3da7bc3 N°3129 Remove twig-bundle Test dir
Thanks to iTopComposerTest::testNoDeniedDirIsPresentForNow :o)
2022-01-28 17:25:55 +01:00
Pierre Goiffon
ebc9fa684a N°3129 PHP 8.0 compat: Fix "Private methods cannot be final as they are never overridden by other classes"
Was breaking setup ajax compilation
Fixed in:
* \SetupUtils::Log
* \MetaModel::SetUniquenessRuleRootClass
2022-01-28 17:01:07 +01:00
Pierre Goiffon
606bdc1909 N°3129 PHP 8.0 compat: Fix "Access level to MFElement::ReplaceWith() must be public (as in class DOMElement)" 2022-01-28 17:01:07 +01:00
Pierre Goiffon
7495fb9af4 N°3129 PHP 8.0 compat: Fix "Deprecated: Required parameter ... follows optional parameter ..." in Twig
Update symfony/twig-bundle from 3.4.36 to 3.4.47
2022-01-28 17:01:07 +01:00
Pierre Goiffon
75dbad7406 N°3129 PHP 8.0 compat: Fix "Deprecated: Required parameter ... follows optional parameter ..."
* \SQLObjectQuery::PrepareSingleTable
* \HistoryBlock::GetRenderContent
* \MenuBlock::GetRenderContent
* \UILinksWidgetDirect::DisplayAsBlock
* \UILinksWidgetDirect::Display
* \UILinksWidgetDirect::DisplayEditInPlace
* \UIExtKeyWidget::AutoComplete
* \UIExtKeyWidget::DisplayFromAttCode
2022-01-28 17:01:07 +01:00
acognet
c95064b76d N°4433 - Fix "date_format" TWIG filter not working for date without time 2022-01-28 14:52:44 +01:00
acognet
f0933eaf1e N°4446 - Attachments: deleted file re-appear 2022-01-28 10:34:53 +01:00
Eric Espie
b9ea7d4913 N°4569 - Fix collision between existing nodes and saved ones 2022-01-27 17:42:52 +01:00
Stephen Abello
9c75a705f3 N°4570 Harmonize inputs font size/weight 2022-01-27 16:31:33 +01:00
Pierre Goiffon
3381c085f4 💡 N°4714 fix phpdoc 2022-01-27 16:15:57 +01:00
acognet
b89d181125 N°4634 - Missing class icone in predefined search 2022-01-27 14:47:24 +01:00
Pierre Goiffon
c3a2713bba N°4725 Fix \DeprecatedCallsLog::NotifyDeprecatedFile doesn't catch ConfigException 2022-01-27 09:25:28 +01:00
Pierre Goiffon
99b73fe1ee 🐛 N°4714 Restore ITOP_VERSION_NAME constant
Was removed by mistake on merge (627c0070)
2022-01-27 08:57:19 +01:00
Stephen Abello
151f42ceef N°4626 Fix backup error message not showing 2022-01-26 16:14:41 +01:00
Pierre Goiffon
627c0070c1 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/config.class.inc.php
#	setup/itopdesignformat.class.inc.php
2022-01-26 16:07:34 +01:00
Eric Espie
3a56824cde N°4569 - Fix unit tests names 2022-01-26 16:02:07 +01:00
Pierre Goiffon
9b6f7d94f4 N°4714 Handle ITOP_CORE_VERSION update in .make/release/update-versions.php 2022-01-26 15:45:10 +01:00
Eric Espie
9a6d40e9db N°4569 - Fix unit tests 2022-01-26 15:30:03 +01:00
Pierre Goiffon
64e8aa5fee N°4714 New ITOP_CORE_VERSION constant
See following constants PHPDoc for information :
* core/config.class.inc.php ITOP_VERSION
* core/config.class.inc.php ITOP_CORE_VERSION
* setup/itopdesignformat.class.inc.php ITOP_DESIGN_LATEST_VERSION
2022-01-26 15:19:29 +01:00
Eric Espie
a839b1c4ae N°4569 - Fix unit tests 2022-01-26 15:14:42 +01:00
Eric Espie
b58df7150f N°4634 - Fix typo 2022-01-26 14:43:30 +01:00
Eric Espie
1cd230a543 N°4569 - Fix module XML migration during setup (fix _delta and list ids) 2022-01-26 14:39:47 +01:00
Eric Espie
fc47e031b6 N°4569 - Fix module XML migration during setup 2022-01-26 14:03:44 +01:00
Pierre Goiffon
477128ad53 💡 N°4023 More phpdoc on \DBObjectSearch::AddCondition 2022-01-26 13:58:49 +01:00
acognet
3b4ba2aafd N°4634 - Missing class icone in predefined search 2022-01-26 12:51:39 +01:00
acognet
70f67068f4 N°4553 - Fix label size for "Greater/equals" in search for numeric attributes 2022-01-26 11:07:41 +01:00
acognet
4fec344799 N°4550 - Fix scroll bar in search for date attribute 2022-01-26 11:05:38 +01:00
Molkobain
cc5f7608e3 N°3861 - Dictionaries: Replace usages of hardcoded "iTop" string by ITOP_APPLICATION_SHORT constant 2022-01-26 10:28:47 +01:00
Eric Espie
468de06fe1 N°4569 - Fix deletion of light-grey theme for iTop 2.7 and older 2022-01-26 10:00:48 +01:00
acognet
aa20289dfe N°4576 - issue with search date widget 2022-01-25 17:14:33 +01:00
acognet
4449fdbbc5 N°4311 - Bubble caselog : differences between console and portal for Agent Name 2022-01-25 15:35:52 +01:00
Stephen Abello
04a690caff N°4696 Improve spacing between a fieldset and a field 2022-01-25 15:26:13 +01:00
Molkobain
0156eb0dda Activity panel: Fix missing space in HTML markup 2022-01-25 13:29:43 +01:00
acognet
e8448332f4 N°4529 - Object list: Count in header not updated when refreshing through the icon 2022-01-25 10:24:44 +01:00
acognet
e8e6ceb29e N°4529 - Object list: Count in header not updated when refreshing through the icon 2022-01-25 08:56:43 +01:00
Molkobain
1f42f897d8 N°4667 - Remove call to tooltip function 2022-01-25 08:55:49 +01:00
Pierre Goiffon
aa66bec783 💡 Add comment for the timezone config parameter 2022-01-24 15:54:42 +01:00
Pierre Goiffon
1da52a8517 Revert "dbtools report.php : compatibility with CLI + symlinks"
Woops pushed by mistake, sorry :/

This reverts commit cbd2181862.
2022-01-24 14:22:01 +01:00
Pierre Goiffon
cbd2181862 dbtools report.php : compatibility with CLI + symlinks 2022-01-24 14:16:41 +01:00
Molkobain
102528195b Fix typo, thanks to @jbostoen 2022-01-23 16:10:42 +01:00
Molkobain
7def094291 N°4705 - Fix newsroom messages not formatted correctly 2022-01-23 15:52:16 +01:00
acognet
ffb3edced5 N°4668 - Remove all deprecated function from iTopExtensions - ajax_page 2022-01-21 15:20:25 +01:00
acognet
17e8c53236 demove deprecated functions : replace ajax_page by AjaxPage 2022-01-21 11:52:02 +01:00
acognet
910638d93f N°4667 - Remove call to tooltip function 2022-01-21 11:51:59 +01:00
acognet
d005ff0099 Remove deprecated functions : replace ormLinkSet::AddObject by ormLinkSet::AddItem 2022-01-21 11:51:57 +01:00
acognet
4fdf8803a5 Remove deprecied function $oField->Render replaced by $oField->RenderExpression() 2022-01-21 11:51:56 +01:00
acognet
06af788480 N°4622 - Advanced search: Fix dictionaries being retrieved by XHR calls 2022-01-21 11:51:54 +01:00
Molkobain
7aa1719514 N°4701 - Fix meta-enums labels being double encoded when displayed 2022-01-21 11:12:53 +01:00
Pierre Goiffon
81c0951c2a N°4694 Fix ServiceSubcategory icon path in datamodel.itop-service-mgmt-provider.xml
Many thanks to hong on SourceForge (https://sourceforge.net/p/itop/tickets/2018/)
2022-01-19 09:27:14 +01:00
Molkobain
89ecdeb13b Code cleanup: Add missing quotes in selector 2022-01-17 19:03:05 +01:00
Pierre Goiffon
c6211cde09 Revert REST API init objects array (#231)
We didn't anticipated this was causing the REST API response to be changed for all consumers :
- before PR `"objects":null`
- after `"objects":[]`

We don't want that :/

We will instead fix collector-base (object of another PR, see #231)

This reverts commit 7243da3576.
This reverts commit 0940741568.
2022-01-17 18:38:33 +01:00
acognet
739001eca4 Fix PHP comments 2022-01-17 09:18:36 +01:00
Pierre Goiffon
7243da3576 💚 Fix RestTest
When no objects to return, since #231 we are now getting `[]` instead of `null`
2022-01-17 08:24:10 +01:00
acognet
c9d547030f Fix Get filter in DoAddObject 2022-01-14 15:34:24 +01:00
acognet
4923ac7015 N°4482 - Polishing : Export page 2022-01-14 11:52:55 +01:00
acognet
c1c264d6d8 Fix Get filter in DoAddObject 2022-01-14 11:03:19 +01:00
Thomas Casteleyn
0940741568 RestResultWithObjects : properly init objects array (#231) 2022-01-14 11:01:00 +01:00
annProg
041a938fc0 🐛 fix notice log when upload svg image 2022-01-14 10:24:37 +01:00
Stephen Abello
839048fab2 Merge branch 'support/2.7' into support/3.0 2022-01-14 10:22:48 +01:00
Stephen Abello
4180a41f27 N°4652 Better error message when XML node define fails from delta (#256)
N°4652 Add more details when trying to define an already existing XML node
Co-authored-by: Molkobain <guillaume.lajarige@combodo.com>
Co-authored-by: Pierre Goiffon <pierre.goiffon@combodo.com>
2022-01-14 10:20:46 +01:00
Stephen Abello
8ada56fc53 N°4652 Better error message when XML node define fails from delta (#256)
N°4652 Add more details when trying to define an already existing XML node
Co-authored-by: Molkobain <guillaume.lajarige@combodo.com>
Co-authored-by: Pierre Goiffon <pierre.goiffon@combodo.com>
2022-01-14 10:18:02 +01:00
Pierre Goiffon
6c5ca614e0 🔧 phpunit.xml restoring old style
Not enough time to work on this right now :(
Will be done with N°4660
2022-01-13 14:14:59 +01:00
Pierre Goiffon
4ddee0b624 🔧 phpunit.xml setup at the end
\Combodo\iTop\Test\UnitTest\Synchro\DataSynchroTest::RunDataSynchroTest was generating a ConfigException (file exists but cannot be read)
2022-01-13 13:50:39 +01:00
Pierre Goiffon
135ddbf37d Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	test/phpunit.xml.dist
2022-01-13 13:36:09 +01:00
Pierre Goiffon
a43adcd202 🔧 phpunit.xml comment OQL better
Was executing on Jenkins :(
2022-01-13 13:11:26 +01:00
Pierre Goiffon
e8e170fb06 🔧 phpunit.xml reorder testSuites again 2022-01-13 13:05:42 +01:00
Pierre Goiffon
5ac5d649aa 🔧 Try again : reorder test suites for better readability
Jenkins should now be fixed
2022-01-13 12:15:12 +01:00
acognet
ec0c98bb0f N°4482 - Polishing : Export page 2022-01-13 10:52:18 +01:00
Pierre Goiffon
decb802df4 Revert "🔧 Reorder test suites for better readability"
This reverts commit cacc3a3085.
2022-01-13 09:48:07 +01:00
Pierre Goiffon
cacc3a3085 🔧 Reorder test suites for better readability 2022-01-13 09:42:21 +01:00
Pierre Goiffon
0fd2ea6a47 🎨 phpunit.xml code formatting 2022-01-13 09:42:21 +01:00
Molkobain
ab7e73ef9b Unit tests: Fix typo in tests suite name 2022-01-12 15:56:42 +01:00
Molkobain
31e7a5383c Unit tests: Activate tests that were never ran... 🥶 2022-01-12 15:31:40 +01:00
Molkobain
64afa07ff5 Unit tests: Fix themes compilation test 2022-01-12 15:14:05 +01:00
Molkobain
656bbfe46d Update precompiled themes 2022-01-12 15:13:39 +01:00
Pierre Goiffon
426f275c03 💡 Add additional phpdoc to \DBBackup::GetMysqlCliTlsOptions 2022-01-12 11:21:21 +01:00
Pierre Goiffon
b55ba2ac7f Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/cmdbsource.class.inc.php
#	core/log.class.inc.php
#	test/setup/iTopDesignFormat/iTopDesignFormatTest.php
2022-01-12 09:56:16 +01:00
Pierre Goiffon
693a861e7d ♻️ Refactor DBBackuptest
Split each test in a dedicated method
2022-01-12 09:42:57 +01:00
Pierre Goiffon
0ee6c60e94 Fix DBBackupTest (again :/)
Was working on Windows but not on Linux...
2022-01-12 09:12:04 +01:00
Pierre Goiffon
a663e9fded Fix DBBackupTest
DB connection dependency was added in a222ead4 (N°2336) in \DBBackup::GetMysqlCliTlsOptions but test wasn't updated accordingly :/^

The test wasn't ran on Jenkins until b11bf308, so we saw the regression only yesterday :(

This is now fixed ! 🥳
2022-01-12 09:00:26 +01:00
Pierre Goiffon
b3bf516b20 💡 Fix PHPDoc for \DBBackup::GetMysqlCliTlsOptions 2022-01-12 08:24:28 +01:00
Molkobain
c2408b74cd Unit tests: Fix invalid/duplicate class name 2022-01-11 18:13:13 +01:00
Pierre Goiffon
6855c2f83a N°4624 restore backupGlobals to default 2022-01-11 17:29:32 +01:00
Molkobain
b11bf30881 Unit tests: Activate tests that were never ran... 🥶
Note that testGetMysqlCliTlsOptions will fail
2022-01-11 15:49:21 +01:00
Molkobain
64736f1463 Fix unit test provider 2022-01-11 15:48:45 +01:00
Pierre Goiffon
930b224ca2 💡 N°4624 phpdoc for ItopDataTestCase 2022-01-11 15:36:40 +01:00
acognet
c87de1024d N°4479 - Impact analysis : Display and apply filter before display impact analysis graphical 2022-01-11 08:32:58 +01:00
acognet
24e6840a8b N°4647 - Dictionaries for Polish not up to date 2022-01-10 18:07:30 +01:00
acognet
06ed048983 N°4448 - Enabled x icon on Organisation filter box even if there is no change on filter 2022-01-10 17:53:26 +01:00
acognet
937313495d Fix checkbox in datatable. 2022-01-10 17:53:25 +01:00
Pierre Goiffon
9493e31a5d 💡 N°4558 Add PHPDoc to document that\LogChannels::CMDB_SOURCE constant was added in 3.0.0 2022-01-10 17:11:13 +01:00
Pierre Goiffon
92b61c7491 N°4558 Rename \LogChannels::CMDBSOURCE to CMDB_SOURCE to match existing constant in support/3.0 branch 2022-01-10 17:09:43 +01:00
Pierre Goiffon
3a4c4cd33d N°4624 Fix SessionTest 2022-01-10 16:50:02 +01:00
Pierre Goiffon
9aa399894c N°4624 Add processIsolation PHPUnit option to all tests implementing ItopDataTestCase 2022-01-10 16:41:26 +01:00
Pierre Goiffon
bde5dc825d 💡 Fix iTopModulesPhpVersionIntegrationTest phpdoc 2022-01-10 16:35:48 +01:00
Pierre Goiffon
8578d18e7f Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	core/cmdbsource.class.inc.php
#	core/config.class.inc.php
#	core/displayablegraph.class.inc.php
#	core/log.class.inc.php
#	datamodels/2.x/itop-config-mgmt/dictionaries/tr.dict.itop-config-mgmt.php
#	datamodels/2.x/itop-knownerror-mgmt/dictionaries/tr.dict.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-service-mgmt/dictionaries/tr.dict.itop-service-mgmt.php
#	datamodels/2.x/itop-tickets/tr.dict.itop-tickets.php
#	datamodels/2.x/itop-welcome-itil/tr.dict.itop-welcome-itil.php
#	dictionaries/tr.dictionary.itop.core.php
#	dictionaries/tr.dictionary.itop.ui.php
#	pages/UI.php
#	setup/itopdesignformat.class.inc.php
#	test/core/LogAPITest.php
#	test/integration/iTopModulesPhpVersionChecklistTest.php
#	test/postbuild_integration/SetupCssIntegrityChecklistTest.php
#	test/postbuild_integration/iTopModuleXmlInstallationChecklistTest.php
#	test/status/StatusTest.php
2022-01-10 16:15:00 +01:00
acognet
9b0e55210d N°4349 - Drop-down mandatory template field documented still required in modification 2022-01-10 15:08:41 +01:00
Pierre Goiffon
e530cbb4f2 N°4624 Restore processIsolation on tests which actually need it
Warning, one symptom was having the CI returning an empty phpunit.results.xml !!
2022-01-07 17:25:18 +01:00
Pierre Goiffon
ddb8378fe6 N°4624 align phpunit annotations
Remove processIsolation when not needed
When needed, make sure to have also their counterpart (preserveGlobalState and backupGlobals)
2022-01-07 15:20:34 +01:00
Pierre Goiffon
47db23d91c 💚 N°4624 Fix other tests after global processIsolation was disabled in 6bf25f90 2022-01-07 12:44:08 +01:00
Pierre Goiffon
fc1f701bf6 💚 N°4624 TransactionsTest : add process isolation
Was global before 6bf25f90
2022-01-07 12:34:09 +01:00
Pierre Goiffon
ece31855af :bulb N°4619 table-selectable-lines.js fix missing doc comment 2022-01-07 12:08:35 +01:00
Pierre Goiffon
d57ef77758 N°4619 table-selectable-lines.js : handles better all click types
* Set one click handler instead of two
* Remove the now useless test on input:radio in updateLines()
* If clicking in a cell that have one input:radio or input:checkbox, and isn't located in the first column :
  - click on the cell input
  - don't select the line
2022-01-07 12:04:33 +01:00
Stephen Abello
365c7bb89e N°4397 Update Turkish translations 2022-01-07 11:09:51 +01:00
Pierre Goiffon
bf2c4dee1b 💡 N°4619 Document table-selectable-lines.js 2022-01-07 09:05:02 +01:00
acognet
11b812b5fc N°4564 - Tooltip for switching from standard dashboard to custo dashboard not refreshed 2022-01-06 15:09:48 +01:00
Pierre Goiffon
b073e4385c 💡 Document versions constants (#255)
Clarify ITOP_VERSION and ITOP_DESIGN_LATEST_VERSION uses
2022-01-06 14:49:34 +01:00
acognet
c37c46a4a8 N°4619 - Strange colors on selected lines on a list 2022-01-06 14:47:05 +01:00
Pierre Goiffon
f592d94af3 iTopModuleXmlInstallationChecklistTest : fix phpdoc, remove process isolation annotation, remove inspection warnings 2022-01-04 18:00:23 +01:00
Pierre Goiffon
f9359431fe 💡 N°4558 Add PHPDoc 2022-01-03 12:21:55 +01:00
Pierre Goiffon
25e560fdaa N°4558 Fix possible PHP notice in \CMDBSource::StartTransaction 2021-12-31 16:34:19 +01:00
Pierre Goiffon
0ce805b192 \MFCompilerTest::testCompileThemes : fix calling protected method 2021-12-31 15:09:18 +01:00
Pierre Goiffon
6bf25f90bc Tests : remove global process isolation
Is done in ItopDataTestCase using annotation
Other tests (like the one extending ItopTestCase) won't use isolation anymore
2021-12-29 15:31:25 +01:00
Pierre Goiffon
30d36fca81 N°4515 Fix function header for \Config::GetDefault 2021-12-29 14:30:19 +01:00
Pierre Goiffon
ffd0bbb1a4 N°4515 Fix default validation pattern for AttributeURL (#249)
URL containing ":" in their path were rejected. This caused problems with some URL from Alfresco or Sharepoint...
The default regexp used by AttributeURL was updated to avoid this.
Warning, check your config to see if you have any custom regexp configured (`url_validation_pattern` config parameter) !

Also a test was added to document the default regexp.
2021-12-29 11:43:07 +01:00
acognet
3db20e8028 N°4479 - Impact analysis : Display and apply filter before display impact analysis graphical 2021-12-23 16:53:15 +01:00
acognet
ed12f98075 Fix warning PHP seen in N°3702 - Migrate module to new UIBlock system : Follow-up forms without authentication 2021-12-23 13:19:18 +01:00
acognet
19eef5bd72 N°4578 - Dict::CloneString replace entry if already exists 2021-12-23 13:19:18 +01:00
Pierre Goiffon
7b2bcd1055 Merge remote-tracking branch 'origin/support/2.7' into support/3.0
# Conflicts:
#	css/css-variables.scss
#	datamodels/2.x/authent-cas/module.authent-cas.php
#	datamodels/2.x/authent-external/module.authent-external.php
#	datamodels/2.x/authent-ldap/module.authent-ldap.php
#	datamodels/2.x/authent-local/module.authent-local.php
#	datamodels/2.x/combodo-db-tools/module.combodo-db-tools.php
#	datamodels/2.x/itop-attachments/module.itop-attachments.php
#	datamodels/2.x/itop-backup/module.itop-backup.php
#	datamodels/2.x/itop-bridge-virtualization-storage/module.itop-bridge-virtualization-storage.php
#	datamodels/2.x/itop-change-mgmt-itil/module.itop-change-mgmt-itil.php
#	datamodels/2.x/itop-change-mgmt/module.itop-change-mgmt.php
#	datamodels/2.x/itop-config-mgmt/module.itop-config-mgmt.php
#	datamodels/2.x/itop-config/module.itop-config.php
#	datamodels/2.x/itop-core-update/module.itop-core-update.php
#	datamodels/2.x/itop-datacenter-mgmt/module.itop-datacenter-mgmt.php
#	datamodels/2.x/itop-endusers-devices/module.itop-endusers-devices.php
#	datamodels/2.x/itop-files-information/module.itop-files-information.php
#	datamodels/2.x/itop-full-itil/module.itop-full-itil.php
#	datamodels/2.x/itop-hub-connector/module.itop-hub-connector.php
#	datamodels/2.x/itop-incident-mgmt-itil/module.itop-incident-mgmt-itil.php
#	datamodels/2.x/itop-knownerror-mgmt/module.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-portal-base/module.itop-portal-base.php
#	datamodels/2.x/itop-portal/module.itop-portal.php
#	datamodels/2.x/itop-problem-mgmt/module.itop-problem-mgmt.php
#	datamodels/2.x/itop-profiles-itil/module.itop-profiles-itil.php
#	datamodels/2.x/itop-request-mgmt-itil/module.itop-request-mgmt-itil.php
#	datamodels/2.x/itop-request-mgmt/module.itop-request-mgmt.php
#	datamodels/2.x/itop-service-mgmt-provider/module.itop-service-mgmt-provider.php
#	datamodels/2.x/itop-service-mgmt/module.itop-service-mgmt.php
#	datamodels/2.x/itop-sla-computation/module.itop-sla-computation.php
#	datamodels/2.x/itop-storage-mgmt/module.itop-storage-mgmt.php
#	datamodels/2.x/itop-tickets/module.itop-tickets.php
#	datamodels/2.x/itop-virtualization-mgmt/module.itop-virtualization-mgmt.php
#	datamodels/2.x/itop-welcome-itil/module.itop-welcome-itil.php
#	datamodels/2.x/version.xml
2021-12-23 10:05:18 +01:00
Pierre Goiffon
108c1fcb2b iTopXmlVersionIntegrationTest : more details in test feedback 2021-12-23 09:56:12 +01:00
acognet
ced29dea8e Change iTop version to 3.0.1-dev 2021-12-22 16:03:58 +01:00
odain
20a07d61c6 N°4541 - no failure exit code captured when csv a import fails in CLI mode 2021-12-20 16:13:10 +01:00
Molkobain
682c821d0e Fix combodo-backoffice-darkmoon-theme version to 3.0.0 2021-12-20 16:12:14 +01:00
Molkobain
5f382ee053 Fix ThemeHandlerTest for file imports in a module 2021-12-20 15:56:58 +01:00
Stephen Abello
dc81630b16 Add Darkmoon to default datamodel 2021-12-20 14:00:21 +01:00
Pierre Goiffon
f84c095b22 💡 Some PHPDoc 2021-12-16 14:56:27 +01:00
Molkobain
9bfa60d272 N°4556 - Remove double icon on pop-up for 1-n links 2021-12-15 11:17:33 +01:00
Molkobain
3e51d010d2 N°4555 - Restore ability to kill concurrent lock 2021-12-15 11:15:40 +01:00
Pierre Goiffon
b190d0e385 Prepare 2.7.6 version 2021-12-14 16:54:42 +01:00
Stephen Abello
0bd64ef700 N°4481 Update filter with current class on datamodel viewer class details 2021-12-14 16:01:42 +01:00
Stephen Abello
9665c7c947 N°4481 Re-enable autocomplete filtering classes list in datamodel viewer 2021-12-14 15:49:11 +01:00
Pierre Goiffon
dcf872bcd5 N°4519 Reload ormLinkset during \DBObject::DBWriteLinks
This will fix a bug when doing a DBUpdate() inside \iApplicationObjectExtension::OnDBInsert : if nothing done (no Set() call for example) then \DBObject::ListChanges will return a change in all non empty ormLinkset.

With this fix, no change will be returned.
2021-12-14 14:54:56 +01:00
Stephen Abello
6254617814 Update opensearch favion & icon 2021-12-14 14:48:04 +01:00
Stephen Abello
fc4d19be5e N°4434 Prevent CIs' active ticket list from flickering 2021-12-14 14:01:05 +01:00
Stephen Abello
88d6b63e12 N°4434 Prevent FormTables from flickering 2021-12-14 14:01:05 +01:00
Molkobain
60b24bad64 Add Benjamin to the sample data, welcome! 👋 2021-12-14 13:32:14 +01:00
acognet
cde2f333b4 N°4543 - Restore API to add dictionary entries in the backoffice pages 2021-12-14 13:24:30 +01:00
acognet
427ec288ef N°4544 - Fix PopupMenuItem API not including item's JS / CSS files 2021-12-14 13:23:26 +01:00
Molkobain
18041527c5 N°4542 - Restore log default value being set through "default" URL param 2021-12-14 09:30:54 +01:00
Molkobain
f58e2ce6c0 ormCaseLog: Introduce class constants for formats 2021-12-13 23:23:43 +01:00
Molkobain
6312063cd3 Add Martin to the sample data, welcome! 🙌 2021-12-13 23:23:43 +01:00
acognet
d0c1f650d1 N°3816 - Migrate module to new UIBlock system : Bulk Event Management - add count of selected items 2021-12-13 18:59:27 +01:00
Stephen Abello
4511883baf N°4481 Fix created elements on 1-n disappearing when table is redrawn 2021-12-13 17:01:18 +01:00
Stephen Abello
1e6a4621ea N°4481 Fix badly escaped dialog tooltip 2021-12-13 17:01:18 +01:00
Molkobain
2a0fc227de Fix chinese dictionaries 2021-12-13 15:55:39 +01:00
annProg
05e98be6c7 🌐 Person Name for chinese user 2021-12-13 15:38:57 +01:00
Molkobain
fe7fa2035d Tab container: Fix flickering of hidden tabs on init 2021-12-13 15:37:47 +01:00
Purple Grape
a00f4156ea improved translation for ZH_CN 2021-12-13 15:36:15 +01:00
Molkobain
4d37e2267f N°4481 - Fix n:n link addition when there are more than 3+ ext. keys on the link class 2021-12-13 15:01:23 +01:00
Molkobain
5055397024 N°4481 - Restore HTML tables style identical between edition and visualization 2021-12-11 18:34:36 +01:00
Pierre Goiffon
2bb142e8ee Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	application/ui.extkeywidget.class.inc.php
#	pages/ajax.render.php
2021-12-10 18:18:17 +01:00
Pierre Goiffon
93f273a287 N°4384 Fix PHP warning when decoding formmanager_data when it is already in a PHP array form 2021-12-10 17:10:46 +01:00
Pierre Goiffon
04e7616c84 Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	sources/renderer/bootstrap/fieldrenderer/bslinkedsetfieldrenderer.class.inc.php
2021-12-10 15:57:49 +01:00
Pierre Goiffon
219b970703 N°4478 Fix linkedset widget in portal when adding new items with already selected ones
Was already committed to develop with e59d472c
2021-12-10 15:56:33 +01:00
Molkobain
408ca6d427 Code cleanup 2021-12-10 15:41:20 +01:00
Molkobain
ae323d393d Fix usage of ITOP_APPLICATION_SHORT constant in dictionaries 2021-12-10 15:35:04 +01:00
Pierre Goiffon
76c139253e 🎨 Fix language injection 2021-12-10 15:24:16 +01:00
Molkobain
2a50a543bf CSV Import: Fix order of confirmation dialog to match convention 2021-12-10 15:12:43 +01:00
Molkobain
ee54d6869b UIContentBlock: Fix PHPDoc 2021-12-10 15:08:57 +01:00
Molkobain
bd753d65a4 Hierarchical dialog: Put validation button on the right to match convention 2021-12-10 15:05:09 +01:00
Molkobain
2fe8f0e43b Add comment to prevent future misunderstanding 2021-12-10 15:05:09 +01:00
Stephen Abello
94cb5d3439 Correctly set selectize sub-input text color 2021-12-10 15:01:20 +01:00
Molkobain
0ed2388cf8 Rename "refresh action" param of datatables to match conventions 2021-12-10 14:55:51 +01:00
Stephen Abello
b91dee6c0c N°4495 Fix adv. search eternal key values as iTop 3.0 autocomplete endpoint returns html escaped content 2021-12-10 13:45:53 +01:00
Pierre Goiffon
02b09c2535 Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-12-10 13:38:42 +01:00
Pierre Goiffon
10cfb373f2 N°4481 Fix badly escaped dialog tooltip
Was commited to develop first (99a0e0c5 and 4f27f3ac)
2021-12-10 13:38:24 +01:00
Pierre Goiffon
69578d5d07 Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-12-10 12:30:57 +01:00
Pierre Goiffon
97d6d413bb N°4502 Fix dashboard page not refreshed after saving customm dashboard 2021-12-10 12:30:33 +01:00
Stephen Abello
4f27f3ac37 N°4481 Fix dialog title being escaped twice following 99a0e0c commit 2021-12-10 11:11:00 +01:00
Stephen Abello
4771908f42 Adv. Search hints: Remove markup from dict files and display hint message in a tooltip 2021-12-10 11:11:00 +01:00
Molkobain
d1751a042e N°4481 - Portal: Fix overflowing tables in logs 2021-12-10 10:48:14 +01:00
Stephen Abello
99a0e0c58e N°4481 Fix badly escaped dialog tooltip 2021-12-10 10:02:18 +01:00
Pierre Goiffon
7e0d5d64ce Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-12-10 09:21:43 +01:00
Pierre Goiffon
3f8f57fa9a N°4502 Fix cannot create new or edit existing custom dashboard
Regression brought by dbaf9241
2021-12-10 09:15:43 +01:00
Molkobain
434ce57b7e N°4481 - Fix lost code highlighting / formatting in attributes 2021-12-09 19:06:38 +01:00
Molkobain
c1eb928893 CombodoBackofficeToolbox.InitCodeHighlighting: Better protection as it was adding a log on every page with no attribute 💩 2021-12-09 18:05:27 +01:00
Molkobain
97cf0a2534 Object details: Fix code format in HTML fields when read-only and no log attribute 2021-12-09 18:01:13 +01:00
Molkobain
ec02657113 CombodoBackofficeToolbox.InitCodeHighlighting: Fix AttributeTemplateHTML not being formatted when read-only 2021-12-09 18:01:13 +01:00
Molkobain
600a629734 CombodoBackofficeToolbox.InitCodeHighlighting: Add protection against not loaded lib 2021-12-09 18:01:13 +01:00
Molkobain
9acdb45482 Object details: Fix JS selector for ownership lock workflow 2021-12-09 18:01:12 +01:00
odain
e51bd4c95f add ci annotation sampleDataNeeded 2021-12-09 17:13:21 +01:00
Pierre Goiffon
71b3eb0ec7 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	datamodels/2.x/itop-tickets/datamodel.itop-tickets.xml
2021-12-09 16:32:11 +01:00
Molkobain
c14c851e94 Breadcrumbs: Fix JS error on (auto submitting) search page when only 1 item in the breadcrumbs 2021-12-09 16:27:59 +01:00
acognet
011ac0222c change version number for 3.0.0 2021-12-09 14:18:44 +01:00
acognet
00580856ae update dictionnaries for 3.0 2021-12-09 14:18:11 +01:00
acognet
9b6dabf5fb update dictionnaries for 3.0 2021-12-09 14:00:49 +01:00
Pierre Goiffon
eb2a615bd2 N°4384 Security hardening
Module parameter flag for extensions
2021-12-09 12:08:23 +01:00
Molkobain
cfc3a82c44 N°4481 - Fix new lines not working in textarea on Firefox (better SCSS rule for fields) 2021-12-09 12:03:45 +01:00
acognet
b23dac591e Update license for 3.0 2021-12-09 11:57:33 +01:00
acognet
de004af288 update dictionnaries for 3.0 2021-12-09 11:57:22 +01:00
acognet
f48cdd51f4 update dictionnaries for 3.0 2021-12-09 11:29:39 +01:00
Molkobain
10d303f43f Advanced search: Fix border radius on criteria panel 2021-12-09 11:18:38 +01:00
Stephen Abello
6a7c953344 N°4481 Fix configure this list in external key creating alerts 2021-12-09 11:13:43 +01:00
Pierre Goiffon
0432727ace 🎨 Reformat itop-tickets XML 2021-12-09 11:07:57 +01:00
Stephen Abello
d0a4e541c3 N°4481 Move hierarchical key browser expand/collapse buttons to bottom button panel 2021-12-09 11:02:17 +01:00
Stephen Abello
d515816488 Fix hierarchical key browser dialog max height 2021-12-09 10:52:07 +01:00
Pierre Goiffon
25a5ec4bcf Update autoload 2021-12-08 18:43:32 +01:00
Pierre Goiffon
4fbe391243 Fix \Combodo\iTop\Test\UnitTest\Core\dictApcuTest that was broken with last merge 2021-12-08 18:41:57 +01:00
Pierre Goiffon
c9ef543e2e Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	core/log.class.inc.php
#	datamodels/2.x/itop-attachments/renderers.itop-attachments.php
#	js/search/search_form_criteria_enum.js
#	lib/composer/autoload_classmap.php
#	lib/composer/autoload_static.php
#	test/core/dictTest.php
2021-12-08 18:30:20 +01:00
Molkobain
cd5286d03b N°4522 - Remove DB views still present after migration from iTop 2.7 Pro to iTop 3.0 Pro 2021-12-08 18:07:14 +01:00
Pierre Goiffon
e6d61d1ebd Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-12-08 17:16:33 +01:00
Pierre Goiffon
f916f9cde8 N°4289 Allow to use privUITransactionFile when no user logged
Before we were throwing a SecurityException, which was blocking for combodo-unauthenticated-form for example
2021-12-08 17:16:12 +01:00
Molkobain
be06adc794 Export: Polish preview table headers 2021-12-08 16:40:07 +01:00
Molkobain
271c51f1f4 N°4481 - Export: Fix tooltip not unchecked when removing column 2021-12-08 16:21:54 +01:00
Molkobain
28e9f95f7c N°4481 - Export: Fix check/uncheck all buttons not working when several classes 2021-12-08 11:39:36 +01:00
Molkobain
d4da1b99d8 N°4518 - ActivityPanel: Fix inline images being shrinked in quick edit 2021-12-08 10:27:45 +01:00
vdumas
28ecb77bf1 N°4520 - Robustness of XML compilation with extensions 2021-12-08 10:22:30 +01:00
acognet
85effd0fb0 Merge branch 'develop' of https://github.com/Combodo/iTop into develop 2021-12-07 17:12:13 +01:00
Pierre Goiffon
c89c47d671 Fix mkdir race condition
See https://github.com/kalessil/phpinspectionsea/blob/master/docs/probable-bugs.md#mkdir-race-condition
2021-12-07 17:01:05 +01:00
acognet
6de4511601 Fix Language name 2021-12-07 16:16:00 +01:00
Stephen Abello
00acf271e2 N°4481 Fix wrong attribute name used in SLA methods 2021-12-07 16:13:06 +01:00
acognet
0e03e78490 Fix "0" for value or name of button 2021-12-07 15:55:12 +01:00
Stephen Abello
99cbb6c996 Set primary color on "run the import" button in import confirmation graph dialog 2021-12-07 15:30:35 +01:00
Stephen Abello
0e36070f0a Rework efcd065 method of determining whether UIContentBlock needs a div tag 2021-12-07 15:29:11 +01:00
Stephen Abello
bc349253cf N°4481 Fix hierarchical key browser bottom buttons position 2021-12-07 15:19:49 +01:00
Stephen Abello
f3ed286ee0 N°4481 Fix import confirmation graph not displaying anymore 2021-12-07 14:40:36 +01:00
Stephen Abello
efcd0654c7 Fix UIContentBlock not creating a div if it's only inheriting CSS classes 2021-12-07 14:40:36 +01:00
Stephen Abello
d413ebff2d N°4481 Fix icon selection label overflowing 2021-12-07 14:40:36 +01:00
Molkobain
33f94b7886 Fix webhook action tables not displaying in notifications page 2021-12-07 11:21:40 +01:00
acognet
817aded5aa N°3816 - Migrate module to new UIBlock system : Bulk Event Management 2021-12-07 10:10:02 +01:00
Stephen Abello
5e61388b65 N°4495 Security hardening 2021-12-07 09:56:20 +01:00
acognet
9e9cdd3d56 N°3816 - Migrate module to new UIBlock system : Bulk Event Management 2021-12-07 09:48:52 +01:00
acognet
d7d430e2a3 N°3695 - Migrate module to new UIBlock system : Alarm Console 2021-12-07 09:48:52 +01:00
Pierre Goiffon
09c4ba4044 N°4512 update-versions.php : update script for iTop 3.0.0
css-variables.scss doesn't contains iTop version anymore
2021-12-06 16:53:39 +01:00
Molkobain
3f795c7555 Allow wider tooltips on class attributes' label 2021-12-05 11:48:09 +01:00
Molkobain
c451e61972 CombodoTooltip: Add option to define max. width of the tooltip 2021-12-05 11:47:27 +01:00
Molkobain
afc0a02058 N°3508 - Rework notifications page to have distinct tabs depending on the action type 2021-12-04 20:49:30 +01:00
Molkobain
a5bf059e23 N°3508 - Add warning message on save if action has no trigger attached 2021-12-04 19:43:51 +01:00
Molkobain
9f0e2c0a3a Dashboard: Remove extra top margin when dashboard layout as no title or toolbar (eg. in dashboard pages) 2021-12-04 14:14:11 +01:00
Molkobain
827a108a38 N°4252 - Force form modals to have a max height of 90% of the window's height to avoid overflowing from the viewport 2021-12-03 13:27:57 +01:00
Stephen Abello
4b50f5e1db N°4481 Fix caselog edition in transition 2021-12-03 11:34:52 +01:00
Stephen Abello
910bbe1160 N°4501 Security hardening 2021-12-03 11:10:52 +01:00
Stephen Abello
5b742c97c9 N°4481 Fix activity panel in printable object pages 2021-12-03 10:29:04 +01:00
Stephen Abello
16a2137777 N°4481 Fix printable object pages when using vertical tabs 2021-12-03 10:29:04 +01:00
Stephen Abello
e8316782aa N°4481 Fix double encoding for delete pages 2021-12-03 10:29:04 +01:00
Molkobain
edcf9e6a1e N°4498 - Introduce new APIs due to iPageUIExtension deprecation (#245)
* Introduce new APIs due to iPageUIExtension deprecation

* Fix typo in interface name

* Rename interface to more consistent names
2021-12-02 13:38:05 +01:00
odain-cbd
9addc4a7ca Merge pull request #224 from Combodo/feature/dict-apcu-bug
Feature/dict apcu bug
2021-12-02 12:22:22 +01:00
odain
5ed71ecb96 N°4125 - fix file ending (hipska remark) 2021-12-02 12:21:54 +01:00
Stephen Abello
7db97c6804 N°3835 Upload file name security hardening 2021-12-02 10:40:18 +01:00
Stephen Abello
f039d54a51 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	webservices/export-v2.php
2021-12-02 10:36:16 +01:00
Stephen Abello
dab0e372d0 N°4499 Security hardening 2021-12-02 10:32:29 +01:00
Stephen Abello
dc8c6ed7a9 N°3835 Tagsets displayed in history security hardening 2021-12-02 10:21:55 +01:00
Stephen Abello
18e341b0b7 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	application/displayblock.class.inc.php
#	js/search/search_form_criteria_enum.js
#	test/core/ormLinkSetTest.php
2021-12-02 10:04:04 +01:00
Stephen Abello
2722f305e0 Fix C3 scss variable 2021-12-02 09:59:12 +01:00
Stephen Abello
469e2e6e0e N°3835 Tagset's tooltip security hardening 2021-12-02 09:57:26 +01:00
Stephen Abello
05301d4191 N°3835 Dashlets' Pill label security hardening 2021-12-02 09:57:26 +01:00
Stephen Abello
3df5febd3e N°3835 Autocomplete security hardening 2021-12-02 09:57:26 +01:00
Stephen Abello
dfd1d5fe35 N°4493 Security hardening 2021-12-02 09:54:31 +01:00
Stephen Abello
d289457c0c N°4495 Security hardening 2021-12-02 09:39:10 +01:00
Stephen Abello
f52b3bff0d N°4492 Security hardening 2021-12-01 15:53:52 +01:00
Stephen Abello
b6b17733bf N°4491 Security hardening 2021-12-01 10:29:29 +01:00
acognet
fc2b00699e Change the name of the css class to a valid name 2021-12-01 09:00:07 +01:00
acognet
b00b08d08b Remove role="row" in tr This selector is not used 2021-12-01 08:56:21 +01:00
Molkobain
c02ea05883 Fix AttributePassword rendering in the backoffice 2021-11-30 16:25:55 +01:00
Molkobain
61a0028d02 Change welcome message to remove "responsive" mention to be honest with ourselves 🤡 2021-11-30 15:45:47 +01:00
acognet
c1c2d027c3 N°4402 - DbObject::ListPreviousValuesForUpdatedAttributes() returns new values for _list-attributes (at least in DbObject::AfterUpdate()) Fix test 2021-11-30 12:11:04 +01:00
acognet
5269096ecd Merge branch 'support/2.7' of github.com:Combodo/iTop into support/2.7 2021-11-29 15:07:14 +01:00
Molkobain
e6511e049a N°4283 - Fix textarea padding in some pages, also fix "Run query" parameters header 2021-11-29 10:26:41 +01:00
odain
e4c68936a0 N°4125 - log error in an apc channel 2021-11-29 09:23:05 +01:00
Pierre Goiffon
74fbd12709 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	datamodels/2.x/itop-portal-base/portal/src/Helper/ObjectFormHandlerHelper.php
#	datamodels/2.x/itop-portal-base/portal/templates/layout.html.twig
2021-11-26 17:24:41 +01:00
Pierre Goiffon
4db5d4c08d N°4213 Allow all AttributeSet impl to be saved in portal 2021-11-26 17:14:01 +01:00
odain
3511867ba3 N°4125 - use Error log level + apc dedicated log channel 2021-11-26 17:07:20 +01:00
Molkobain
c40394638a N°4252 - Fix bad initialization of DesignerFormField::$aCssClasses 2021-11-26 16:01:22 +01:00
Stephen Abello
cc2862837a Fix activity panel header links color 2021-11-26 15:52:48 +01:00
Stephen Abello
e27c6b1cd7 Allow Selectize input color css rules to be overloaded through iTop 3.0 themes 2021-11-26 15:52:48 +01:00
Stephen Abello
ae00686e58 Allow C3 css rules to be overloaded through iTop 3.0 themes 2021-11-26 15:52:48 +01:00
Pierre Goiffon
7934f9b9dc N°4213 Fix EnumSet modifications cannot be saved in portal 2021-11-26 15:25:30 +01:00
Molkobain
7f2eef4a24 Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-11-26 13:59:29 +01:00
Molkobain
8a65a592f3 N°4360 - Rename class to match other classes convention 2021-11-26 13:47:05 +01:00
Pierre Goiffon
7d6b019cfa Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	sources/renderer/bootstrap/fieldrenderer/bslinkedsetfieldrenderer.class.inc.php
2021-11-26 11:45:11 +01:00
Pierre Goiffon
5e48400cb1 N°4478 Fix line selection (global and unique) not checking checkbox anymore 2021-11-26 11:44:32 +01:00
Pierre Goiffon
252562ace9 N°4478 Fix "Requested unknown parameter '' for row 0, column 0" when opening search on related object
Forgotten file :/
2021-11-26 11:08:25 +01:00
Pierre Goiffon
c9c32b0de1 Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-11-26 10:58:30 +01:00
Pierre Goiffon
770ac8ffe5 N°4478 Fix "Requested unknown parameter '' for row 0, column 0" when opening search on related object 2021-11-26 10:58:17 +01:00
Molkobain
db137d3816 N°4283 - Fix spacing for Pills when wrapping
Also repalce some spacing with variables
2021-11-26 10:34:57 +01:00
odain
dcfdb2d0a9 N°4125 - add integration test apart from ApcService mocking 2021-11-26 10:28:56 +01:00
odain
0cbf34ba5a N°4125 - fix tests under windows (again) 2021-11-26 09:47:01 +01:00
Molkobain
77768e8400 N°4252 - Fix DesignerFormField CSS classes for better integration within the Designer 2021-11-26 09:24:36 +01:00
Molkobain
5621eb2191 SCSS: Center on both axis DesignerField apply/cancel buttons 2021-11-26 09:24:35 +01:00
odain
f1037147a9 N°4125 - phpdoc only coming from pull request
Thanks to Hispka and  piRGoif
2021-11-26 09:17:19 +01:00
odain
bea52d5fb9 N°4125 - test did not run under windows 2021-11-26 09:12:58 +01:00
Stephen Abello
2bf970932e N°3515 Add missing icon for default welcome dashboard 2021-11-26 08:50:40 +01:00
Pierre Goiffon
b6fac4b411 N°4384 Security hardening 2021-11-25 16:07:40 +01:00
Pierre Goiffon
d8a77c22a3 Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	datamodels/2.x/itop-portal-base/portal/public/lib/datatables/js/dataTables.fixedHeader.min.js
#	datamodels/2.x/itop-portal-base/portal/public/lib/datatables/js/dataTables.responsive.min.js
#	datamodels/2.x/itop-portal-base/portal/public/lib/datatables/js/dataTables.scroller.min.js
#	datamodels/2.x/itop-portal-base/portal/public/lib/datatables/js/dataTables.select.min.js
#	datamodels/2.x/itop-portal-base/portal/public/lib/datatables/js/jquery.dataTables.min.js
2021-11-25 15:33:52 +01:00
Stephen Abello
b75a495336 N°4283 Add more blocks to RenderAllUiBlocks.php 2021-11-25 11:39:14 +01:00
Pierre Goiffon
ed3c387712 N°4478 Update Datatables lib 2021-11-25 10:55:48 +01:00
Stephen Abello
bbadc1f0be Replace hardcoded font size with SCSS variables 2021-11-25 10:34:38 +01:00
Stephen Abello
a141db4737 N°4283 Fix some spacing/sizing issue on specific pages 2021-11-25 10:09:49 +01:00
Stephen Abello
cb67dd1f1c Fix French dict typo 2021-11-25 09:42:09 +01:00
Stephen Abello
af653608ef N°4283 Replace hardcoded spacing values by SCSS spacing variables 2021-11-24 17:02:48 +01:00
Stephen Abello
9dac061b04 N°4283 Centralize blocks spacing between each other in block-integration 2021-11-24 17:02:48 +01:00
Stephen Abello
ccf1bba235 N°4283 Introduce SCSS variables for size and spacing 2021-11-24 17:02:48 +01:00
Pierre Goiffon
312a5b246b N°4399 Fix memory error on setup when lots of attachment in DB 2021-11-24 16:55:34 +01:00
Pierre Goiffon
ddd6bf22af Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	core/attributedef.class.inc.php
#	core/config.class.inc.php
#	core/htmlsanitizer.class.inc.php
#	sources/Renderer/RenderingOutput.php
#	test/core/sanitizer/HTMLDOMSanitizerTest.php
#	test/integration/DictionariesConsistencyTest.php
2021-11-24 15:01:38 +01:00
acognet
903de43589 N°4402 - DbObject::ListPreviousValuesForUpdatedAttributes() returns new values for _list-attributes (at least in DbObject::AfterUpdate()) Add tests 2021-11-24 12:10:30 +01:00
Pierre Goiffon
2d67594ccf N°4213 Fix EnumSet rendering on details form in portal 2021-11-24 12:07:10 +01:00
Pierre Goiffon
0c7eee7f9c 💡 Add doc for why phpinfo ext is mandatory 2021-11-24 12:01:44 +01:00
Pierre Goiffon
65f9f86bcc N°3635 DictionariesConsistencyTest : now we can have multiple possible localized language desc
The 'Español, Castellaño' to 'Español, Castellano' was causing problem on builds with other modules that we don't want to update !
2021-11-23 18:59:10 +01:00
Pierre Goiffon
efaf53e568 Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	core/htmlsanitizer.class.inc.php
2021-11-23 18:07:02 +01:00
Pierre Goiffon
81a2a9278c N°4360 Fix SvgDOMSanitizer expected data 2021-11-23 17:38:30 +01:00
Pierre Goiffon
e15d4bfab6 N°4360 Security hardening 2021-11-23 17:25:50 +01:00
acognet
e23c41232d N°4465 - Polishing iTop 3.0 beta6 - fix "configure this list" 2021-11-23 15:34:53 +01:00
Stephen Abello
e25d070a38 N°4465 Fix tagset and enumset dropdown overflowing out of the screen and not autoplacing themselves 2021-11-23 13:33:08 +01:00
Stephen Abello
499c97b914 N°4465 Fix transition button not grouping/ungrouping in some cases 2021-11-23 11:51:31 +01:00
Molkobain
c472b8ad3b N°4466 - Fix line breaks not displayed correctly 2021-11-23 11:40:52 +01:00
Molkobain
94ceb98b9e N°4466 - Fix line breaks not displayed correctly 2021-11-23 11:32:26 +01:00
Stephen Abello
b1de8683f0 N°3523 Adjust buttons and links colors to make application more accessible 2021-11-23 11:26:16 +01:00
Stephen Abello
cff2105908 Remove debug line 2021-11-23 11:06:23 +01:00
Stephen Abello
e11d5c142c N°3523 Adjust buttons and links colors to make application more accessible 2021-11-23 10:39:11 +01:00
Molkobain
f77b3bedaf N°2370 - Change PHPDoc to reflect reality, method will not be removed 2021-11-23 10:15:28 +01:00
Molkobain
3654df1cae N°4466 - SCSS: Improve readability 2021-11-23 09:57:53 +01:00
Molkobain
f3d2e89c68 N°4466 - Revert changes that broke contraints for fields to stay in their column (d0f9868 and c9aa6938) 2021-11-23 09:40:33 +01:00
Molkobain
dd46536f7c N°4477 - Update dataTables lib. to 1.11.3 in iTop 3.0 2021-11-22 17:31:48 +01:00
Molkobain
e249907a9c N°4475 N°4408 - Fix update on external key not refreshing dependents fields 2021-11-22 16:45:35 +01:00
Eric Espie
4ded943a43 N°2527 - Fix require approot 2021-11-22 16:00:45 +01:00
Molkobain
bd52f4fefb N°4468 - Add data-resource-id meta-data on all buttons 2021-11-22 15:44:27 +01:00
Pierre Goiffon
f57785e422 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	datamodels/2.x/authent-local/dictionaries/es_cr.dict.authent-local.php
#	datamodels/2.x/itop-config-mgmt/dictionaries/es_cr.dict.itop-config-mgmt.php
#	datamodels/2.x/itop-knownerror-mgmt/dictionaries/es_cr.dict.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-service-mgmt/dictionaries/es_cr.dict.itop-service-mgmt.php
#	datamodels/2.x/itop-tickets/dictionaries/es_cr.dict.itop-tickets.php
#	datamodels/2.x/itop-welcome-itil/es_cr.dict.itop-welcome-itil.php
#	dictionaries/es_cr.dictionary.itop.ui.php
#	test/integration/DictionariesConsistencyTest.php
2021-11-22 09:08:34 +01:00
Pierre Goiffon
77880c3675 🌐 N°3635 ES dict : change 'Español, Castellaño' to 'Español, Castellano' 2021-11-22 08:55:08 +01:00
Molkobain
bb369e68b5 N°4283 - Rename some SCSS partials to match conventions 2021-11-20 18:52:54 +01:00
Molkobain
2a2d68e204 N°4283 - Textarea: Make sure to use monospace font for code
- CSV import is now using monospace font
- Simplify SCSS code

Note: TextArea and all input UIBlocks need to be reworked as they are not properly organized, see comment in _input-text.scss
2021-11-20 18:42:41 +01:00
Molkobain
b49fbf1a97 N°4283 - Textarea: Make them take all available width 2021-11-20 18:12:41 +01:00
Molkobain
308bff7875 SCSS: Fix typo in variable name 2021-11-20 14:23:13 +01:00
Molkobain
9444e61856 N°4283 - Improve spacing of HTML inputs with their labels 2021-11-19 18:35:50 +01:00
Molkobain
2f114701a1 N°4283 - AttributeOneWayPassword: Fix spacing between the fields / button 2021-11-19 17:40:48 +01:00
Molkobain
5128db05cf N°4283 - AttributeBlob: Fix extra between the value and the links / input 2021-11-19 17:39:54 +01:00
Molkobain
9675202bb2 N°4283 - Force field labels to wrap even if it is a single giant word 2021-11-19 17:09:23 +01:00
Molkobain
cbe42cd727 N°4283 - Improve textarea and OQL inputs style
- All textarea app. wide avec the same padding
- OQL fields have the same padding as the other textareas
- OQL fields have the monospaced font
2021-11-19 16:34:01 +01:00
Pierre Goiffon
3559425fc1 N°°4463 Trigger : remove user rights check when controlling filter 2021-11-19 15:20:21 +01:00
Molkobain
a246528eec Update DoPostRequest() in itoprest.examples.php to fix optional headers like in utils::DoPostRequest 2021-11-19 14:47:51 +01:00
Stephen Abello
7fbbf1088a N°4460 Fix SCSS variable usage 2021-11-19 12:22:08 +01:00
Molkobain
fa4a5e2990 Merge spanish translations and remove duplicated files due to merge 2021-11-19 11:49:48 +01:00
Molkobain
b662a7e3c6 Remove (some) redundant description in spanish translations 2021-11-19 11:49:36 +01:00
Stephen Abello
cdc452282e Fix dictionnary entries 2021-11-19 11:38:08 +01:00
Molkobain
d8c4251c03 Remove (some) redundant description in spanish translations 2021-11-19 11:27:46 +01:00
Stephen Abello
72d1ab5cbc N°3523 Add accessibility to silo selection and user menu toggler 2021-11-19 11:16:19 +01:00
Stephen Abello
18b8e7093a N°3515 Update Enclosure icon (thanks to icons8 quick response ❤️) 2021-11-19 11:16:19 +01:00
Stephen Abello
aedb9ccbba N°3525 Make colors more accessible 2021-11-19 11:16:18 +01:00
Pierre Goiffon
67fa156c0e Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	application/dashboard.class.inc.php
#	core/action.class.inc.php
#	datamodels/2.x/combodo-db-tools/dictionaries/es_cr.dict.combodo-db-tools.php
#	datamodels/2.x/itop-attachments/dictionaries/es_cr.dict.itop-attachments.php
#	datamodels/2.x/itop-config-mgmt/dictionaries/es_cr.dict.itop-config-mgmt.php
#	datamodels/2.x/itop-core-update/dictionaries/es_cr.dict.itop-core-update.php
#	datamodels/2.x/itop-hub-connector/dictionaries/es_cr.dict.itop-hub-connector.php
#	datamodels/2.x/itop-knownerror-mgmt/dictionaries/es_cr.dict.itop-knownerror-mgmt.php
#	datamodels/2.x/itop-portal-base/dictionaries/es_cr.dict.itop-portal-base.php
#	datamodels/2.x/itop-request-mgmt-itil/dictionaries/es_cr.dict.itop-request-mgmt-itil.php
#	datamodels/2.x/itop-request-mgmt/dictionaries/es_cr.dict.itop-request-mgmt.php
#	datamodels/2.x/itop-sla-computation/dictionaries/es_cr.dict.itop-sla-computation.php
#	datamodels/2.x/itop-storage-mgmt/dictionaries/es_cr.dict.itop-storage-mgmt.php
#	datamodels/2.x/itop-tickets/dictionaries/es_cr.dict.itop-tickets.php
#	datamodels/2.x/itop-virtualization-mgmt/dictionaries/es_cr.dict.itop-virtualization-mgmt.php
#	datamodels/2.x/itop-welcome-itil/es_cr.dict.itop-welcome-itil.php
#	dictionaries/es_cr.dictionary.itop.core.php
#	dictionaries/es_cr.dictionary.itop.ui.php
#	pages/ajax.render.php
#	setup/wizardsteps.class.inc.php
#	synchro/synchro_import.php
2021-11-19 10:28:46 +01:00
Pierre Goiffon
9437e689fd N°3635 Update ES translations
Many thanks to Miguel Turrubiates !
2021-11-18 17:48:43 +01:00
Pierre Goiffon
a79459bc53 N°4162 Portal exception page : restore exception message
Was removed with Silex to Symfony migration
2021-11-18 14:56:17 +01:00
Pierre Goiffon
500bd15843 Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-11-18 08:54:32 +01:00
Pierre Goiffon
3e8dd2f4a5 N°4286 Setup : fix loop in first steps
Setup token wasn't removed at the right place :/
2021-11-18 08:54:10 +01:00
Pierre Goiffon
d0fade9ce1 Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	pages/ajax.render.php
#	setup/wizardsteps.class.inc.php
2021-11-17 17:39:36 +01:00
Pierre Goiffon
51a49dfce8 Remove warnings, use finally block, formatting 2021-11-17 16:10:50 +01:00
Molkobain
db8462ccc9 N°2788 - Constraint table to fit as much as possible in its column 2021-11-17 15:55:01 +01:00
Pierre Goiffon
066b71686d N°4286 Setup : restore backup download on WizStepDone
Setup token was put with N°2016 (6b5cc7c)
But later on we refactored the token handling in SetupUtils methods, and we had token removal in WizStepDone (43daa2ef) : so the backup download cannot be done :/
2021-11-17 14:39:44 +01:00
Pierre Goiffon
be633001a5 Revert "N°4360 Security hardening"
This reverts commit 8adf743cc7.

We will implement a different solution later (hopefully for 2.6.5 / 2.7.6 / 3.0.0 as well)
2021-11-17 11:13:29 +01:00
Molkobain
b0904cabfd N°4447 - Update german translations thanks to Martin Raeker from @itomig-de ! 2021-11-17 10:26:12 +01:00
Pierre Goiffon
84426c6634 N°4365 Security hardening 2021-11-17 10:15:12 +01:00
Molkobain
9d19c189e6 N°4420 N°4421 - Decrease transition duration a bit to match other transitions feeling 2021-11-16 22:41:42 +01:00
Molkobain
91d030933b Rename cmdbAbstractObject::EnumDisplayMode() to be consistent with the rest 2021-11-16 21:38:51 +01:00
Molkobain
d0f9868a19 N°2788 - Constraint table with <pre> to fit as much as possible in its column 2021-11-16 18:20:31 +01:00
Molkobain
2a913cd484 Restore prototypes of cmdbAbstractObject methods in which we added $sMode to preserve compatibility with existing extensions (#240)
* Restore prototypes of cmdbAbstractObject methods in which we added $sMode to preserve compatibility with existing extensions

* Rename cmdbAbstractObject::ENUM_OBJECT_MODE_XXX

* Add cmdbAbstractObject::ENUM_OBJECT_MODE_BULK_EDIT

* Refactor usage of $sDisplayMode in cmdbAbstractObject::DisplayModifyForm()
2021-11-16 17:47:09 +01:00
Pierre Goiffon
dbaf924171 N°4363 Security hardening 2021-11-16 17:19:19 +01:00
Pierre Goiffon
1b2d75efd6 N°4420 N°4421 Table selectable lines : restore style, restore script inclusion in object edition (#242) 2021-11-16 16:05:07 +01:00
Stephen Abello
d66a1e8c10 N°3515 Update some classes/dashboard icons to match 3.0 UI 2021-11-16 15:21:53 +01:00
Molkobain
a5ad981d70 N°4408 - Fix visual glitches on transition buttons in object details 2021-11-16 14:42:32 +01:00
Pierre Goiffon
8adf743cc7 N°4360 Security hardening 2021-11-16 12:01:16 +01:00
Molkobain
4e544a8eab Object details: Fix header buttons being too close to the right border when editing with a sticky header 2021-11-15 18:42:11 +01:00
Pierre Goiffon
75450ded1d N°4359 Security hardening 2021-11-15 16:38:11 +01:00
Molkobain
2b97fed5db Fix unclosed TWIG tag in toolbar spacer 2021-11-15 16:24:41 +01:00
Molkobain
62d8a2ba1f Fix crash in activity panel when entry user is unknown 2021-11-15 16:24:41 +01:00
acognet
fe9a442500 N°4370 - Field content overlapping on rest of the UI (Backoffice) - 2 2021-11-15 15:48:51 +01:00
acognet
11d2991286 N°4417 - Fix portal user not seeing support agent avatar on caselog in portal 2021-11-15 15:36:03 +01:00
Pierre Goiffon
bcca6ac720 Merge remote-tracking branch 'origin/support/2.6' into support/2.7 2021-11-15 15:07:19 +01:00
Molkobain
abb63182e3 N°4346 - Fix operator 2021-11-15 12:08:28 +01:00
Molkobain
4409162eb7 N°2875 - Fix mentions not working with some non url encoded "markers" (eg. '#') 2021-11-14 22:53:10 +01:00
Molkobain
0dc3d249da N°3526 - Clean up pass on UIBlocks
- Add ancestors CSS classes on UIBlocks when missing (programmatically)
- Fix SCSS due to some blocks inheriting their ancestors rules
2021-11-14 22:33:48 +01:00
Molkobain
3598da8808 N°3526 - Clean up pass on UIBlocks
- Move UIBlock::ENUM_BLOCK_FILES_TYPE_XXX to iUIBlock
- Add PHPDoc
- Remove Object return type hint on overloadable methods
- Add scalar return type hint
- Add type hint on parameters
2021-11-14 22:33:48 +01:00
Molkobain
a9b30e160f N°3526 - Clean up pass on UIBlockFactories
- Add PHPDoc
- Remove (Object) return type hint on overloadable methods
2021-11-14 22:33:48 +01:00
Stephen Abello
249fa6ca93 N°3515 Update some classes icon to match 3.0 UI 2021-11-13 11:57:00 +01:00
acognet
50d73e7fca N°4346 - Restore HTML metadata (data-xxx) on lists in the backoffice 2021-11-12 11:20:48 +01:00
Molkobain
1b9e67dc6e SCSS: Fix Quick Create / Global Search drawers being slightly visible when closed and with a full history 2021-11-11 11:09:40 +01:00
Molkobain
ca2124130f N°3517 - Clean-up pass on all block factories 2021-11-10 19:51:59 +01:00
Molkobain
fffd4cf962 N°4346 - Remove duplicated loop and factorize code 2021-11-10 19:12:14 +01:00
Molkobain
4a6b351c37 N°4440 - Fix hierarchy tooltip on ext. key widget 2021-11-10 18:49:25 +01:00
Molkobain
206143824b N°4408 - Improve transition buttons UX in object details
Transition buttons are now grouped in the "Apply" button when there is not enough space to display them all
2021-11-10 18:44:25 +01:00
Molkobain
90c866f696 N°4427 - Fix bouncing results in search page 2021-11-09 19:22:50 +01:00
vdumas
0bbdbdb1cd N°3735 revert typo fix on Known Error module as it would remove the module on all iTop having it installed today 2021-11-09 18:03:11 +01:00
odain
865f9f4f67 add @since annotation + @see from Hispka 2021-11-09 17:14:13 +01:00
odain
a7e54d4bad N°4125 - fix infinite loop 2021-11-09 17:08:08 +01:00
Stephen Abello
395c9c288b N°4355/1745 Prevent malformed caselog entries from breaking activity panel DOM 2021-11-09 16:19:16 +01:00
acognet
60a17c9a65 N°4406 - Warning: Missing constant ITOP_DESIGN_LATEST_VERSION 2021-11-09 15:20:42 +01:00
acognet
2de6ba2827 N°3928 - Polishing: Impact analysis 2021-11-09 15:18:08 +01:00
Pierre Goiffon
2beb795f9a N°4304 Security hardening 2021-11-09 11:32:53 +01:00
Pierre Goiffon
6847d8a5c7 N°4414 Startup error handler : fix message logged twice (#243) 2021-11-09 10:25:29 +01:00
Stephen Abello
f6885567eb N°4408 Add correct CSS class to console renderer richtext field 2021-11-09 09:49:37 +01:00
Stephen Abello
4b888a3805 N°4378 Restore keyboard shortcuts behavior for object details 2021-11-09 09:49:37 +01:00
odain
07f470024a N°4367 : renamed the phpunit annotation for ci purpose 2021-11-09 08:55:54 +01:00
Molkobain
4c69865480 N°2875 - Fix error when trigger has an OQL on a root class which is not abstract 2021-11-08 19:21:43 +01:00
Pierre Goiffon
06985d3cf2 N°4387 synchro_import restore previous set_time_limit call
Was changed in b1761e04 (iTop 2.7.0) by mistake

Added noinspection as the IDE warning (https://github.com/kalessil/phpinspectionsea/blob/master/docs/control-flow.md#statement-could-be-decoupled-from-foreach) seems to be a false positive ?
2021-11-08 16:14:19 +01:00
acognet
ab40c67678 N°4346 - Restore HTML metadata (data-xxx) on lists in the backoffice - after configure this list 2021-11-08 15:02:45 +01:00
odain
a286564345 N°4367 : add phpunit annotation for ci 2021-11-08 06:42:45 +01:00
Stephen Abello
c9e592c07d N°3904 Avoid restore buttons from asking for confirmation multiple times 2021-11-05 15:51:04 +01:00
denis.flaven@combodo.com
5bcdcb52b2 N°4534 - creation of a new category 'filter' to hide admins to
non-admins without breaking legacy code.
2021-11-05 11:29:41 +01:00
Pierre Goiffon
456283866c ✏️ Fix typo in code comment 2021-11-05 11:24:18 +01:00
Stephen Abello
821c14ee86 N°3904 Fix scheduled backups not being restorable from user interface 2021-11-05 10:28:09 +01:00
Stephen Abello
30f1ad8da8 N°4412 Activity panel's notification entries weren't expandable since c0fc62b 2021-11-05 10:07:30 +01:00
vdumas
6d0b979bcd N°3735 revert one part of the previous commit done by mistake 2021-11-04 17:58:49 +01:00
Pierre Goiffon
e16425ab8a Revert behavior change in \UserRights::FindUser v2
Was made in 2ab0fab0 by mistake, committed incorrectly in 2e426d37 (wooops)
2021-11-04 17:28:06 +01:00
Pierre Goiffon
2e426d373d Revert behavior change in \UserRights::FindUser
Was made in 2ab0fab0 by mistake
2021-11-04 17:26:09 +01:00
vdumas
a1a38ca224 N°3735 Add missing translation for older methods 2021-11-04 17:10:17 +01:00
vdumas
05830de4e7 N°3735 Add Method Parameters translation for ITSM Designer 2021-11-04 16:42:10 +01:00
Pierre Goiffon
2e8920f3d1 N°4367 Fix \privUITransactionFileTest::testIsTransactionValid
Was crashing because of limitations on loading User objects
2021-11-04 16:15:01 +01:00
Stephen Abello
4450c28295 N°4408 Prevent dependent field from being triggered twice 2021-11-04 16:02:51 +01:00
Stephen Abello
aa43201cbe N°4408 Do not display non-interpreted HTML when richtext fields are loading 2021-11-04 16:02:51 +01:00
Eric Espie
3d7df7600f N°4346 - Restore HTML metadata (data-xxx) on lists in the backoffice 2021-11-04 14:56:06 +01:00
Stephen Abello
aba0d4144c N°4408 Fix inputs flickering when widgets are loading 2021-11-04 10:49:17 +01:00
Stephen Abello
fe82f54066 N°4396 Fix graphs not displaying anymore in Dashboard Attribute 2021-11-03 15:26:33 +01:00
Pierre Goiffon
2d44d9d1c6 N°4367 disable test for now
On develop we have an error on Jenkins :
> Login with user2 throw an error
2021-11-03 15:19:42 +01:00
Molkobain
8c03525fbb N°2875 - Fix missing argument ":this" when submitting an entry in the activity panel 2021-11-03 12:01:20 +01:00
Eric Espie
79c17970f8 Fix tests on packages missing composer.json file 2021-11-03 11:31:43 +01:00
Pierre Goiffon
04f7660267 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	js/utils.js
2021-11-03 11:19:23 +01:00
Pierre Goiffon
8c7f7abaab Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	test/application/privUITransactionFileTest.php
2021-11-03 11:10:43 +01:00
Eric Espie
e963a6741f N°3985 - avoid sql request for notifications in case of object creation and avoid reloads on requesting triggers 2021-11-03 11:00:41 +01:00
Pierre Goiffon
e8d314e1f6 N°4367 Fix \privUITransactionFileTest::testIsTransactionValid
* change user name for when password policy is active
* admin user doesn't exist on Jenkins : create a second user
* test UserRights::Login return value
* document that we depend on the sample data
2021-11-03 10:50:25 +01:00
Molkobain
ebe493f7f7 Set attribute: Add tooltip on items when attribute is in edition 2021-11-02 18:48:03 +01:00
Pierre Goiffon
e29f1825be N°4367 Fix "redeclaration of const CombodoSanitizer"
The utils.js can be included more than once in old iTop branches :( This is fixed in 3.0.0 (develop branch)

Also add missing ";"
2021-11-02 17:14:16 +01:00
vdumas
2df8bb1707 N°3735 - Add SetComputedDate on DBObject 2021-11-02 16:55:25 +01:00
Eric Espie
27995c14bf N°3985 - avoid sql request for history in case of object creation 2021-11-02 15:35:51 +01:00
Molkobain
890d0f64ce Add @ilya-stukalov to the constributors, thanks! 2021-11-01 18:18:17 +01:00
Vladimir Kunin
a29bb83a20 Fix typos 2021-10-29 18:27:04 +02:00
Vladimir Kunin
413820a22b Update general UI translations: many typos & errors, "iTop" replaced by constant ITOP_APPLICATION_SHORT, add new & improve existing strings. 2021-10-29 18:27:04 +02:00
Vladimir Kunin
860472beea Update CMDBChangeOp UI translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
dd4283199e Update NavigationMenu translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
e147aa31aa Add KeyboardShortcuts translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
b8aa3dfb0c Update Activity panel translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
83e2dbc30a Update Newsroom translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
f63dad7a3a Update tab container translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
c75bb6b892 Update Navigation Menu translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
15ffb82257 Update preferences translations 2021-10-29 18:27:04 +02:00
Vladimir Kunin
5e2ae18570 Typo 2021-10-29 18:27:04 +02:00
ilya.stukalov
070a23e61b Add UI translations for iTop 3.0. 2021-10-29 18:27:04 +02:00
acognet
0ab6655ae7 N°4385 - MetaModel::GetRelatedObjectsUp does yield correct results, while DBObject->GetRelatedObjectsUp does not 2021-10-29 13:36:32 +02:00
acognet
322371dd9f N°4349 - Drop-down mandatory template field documented still required in modification 2021-10-29 13:33:44 +02:00
Molkobain
b8e974cfd1 N°4398 - Add object name in the tab name when browsing datamodel viewer 2021-10-28 15:58:32 +02:00
odain
e03eb1e279 N°3556: fix broken ci temporarly for test using ItopDataTestCase 2021-10-28 11:48:14 +02:00
bruno-ds
6d2b75df9e N°4261 - test correctness: log deactivation is performed using bool false and not Error level
thanks @BenGrenoble
2021-10-26 15:54:44 +02:00
Stephen Abello
ab1b6837a2 N°3800 Fix line spacing in rich text editor and in its displayed content 2021-10-26 15:26:29 +02:00
Stephen Abello
5c02b5c38c N°4396 Fix graphs not displaying anymore in Dashboard Attribute 2021-10-26 10:50:32 +02:00
Stephen Abello
dd486dd015 N°3911 Fix datamodel viewer table overflowing in some case 2021-10-26 10:11:12 +02:00
Molkobain
b7e8c0de8a N°4400 - Restore PHP debug output being displayed in a modal 2021-10-25 21:34:03 +02:00
Molkobain
32dae59b9b N°4400 - Move inline JS functions to corresponding JS file 2021-10-25 19:51:07 +02:00
acognet
5540988001 N°4349 - Drop-down mandatory template field documented still required in modification 2021-10-25 15:50:43 +02:00
Stephen Abello
f8c59e6171 N°3911 Allow datamodel viewer graph to be horizontally scrolled when overflowing out of page 2021-10-25 15:35:33 +02:00
acognet
ab23ea1da0 N°3928 - Polishing: Impact analysis 2021-10-25 14:12:11 +02:00
Molkobain
3d49cd199a Fix Panel not being collapsible anymore (regression from 1c11cef2f, thanks @accognet !) 2021-10-25 12:15:02 +02:00
denis.flaven@combodo.com
ee848129b7 New methods for creating/import test data from XML files. 2021-10-25 11:49:56 +02:00
Molkobain
63448276cc Tooltips: Add possibility to define theme through meta-data 2021-10-24 11:12:07 +02:00
Stephen Abello
d5af6e9061 N°4319 Backup page datatable no longer grow off limits, even on Chrome, also fix restore button 2021-10-22 14:39:30 +02:00
Molkobain
2fc3e7ad38 N°2875 - Fix empty mention results when host object is being created 2021-10-22 13:23:24 +02:00
Stephen Abello
465ed58471 N°4319 Backup page datatable no longer grow off limits 2021-10-22 10:35:43 +02:00
Eric Espie
fac454595a removing meaningless information 2021-10-22 10:10:14 +02:00
acognet
89ea4adbce N°4366 - RCSS in /pages/ajax.searchform.php on develop 2021-10-21 17:15:27 +02:00
bruno-ds
427f107ddf N°4261 - Fix CI and add a test case 2021-10-21 17:04:08 +02:00
Pierre Goiffon
59d674d744 Fix broken export
Argument 1 passed to Combodo\iTop\Controller\AjaxRenderController::ExportBuild() must be an instance of Combodo\iTop\Controller\ajax_page, instance of AjaxPage given,

Caused by merge of support/2.7 with 2 conflicts on the same line (347cbca5)
2021-10-21 17:03:36 +02:00
Molkobain
54db7243bf N°2875 - Restore correct app. version check in the module installer 🥶 2021-10-21 16:36:41 +02:00
Eric Espie
e6d2b0bc18 N°4346 - Restore HTML metadata (data-xxx) on lists in the backoffice 2021-10-21 16:18:57 +02:00
bruno-ds
9e1f5a1b63 N°4261 - ExceptionLog restore Portal log level to Error as for iTop 2.7 (no more BC break)
- default level is now Error,
 - for "write in DB": each level (including error) are ignored by default
2021-10-21 16:18:27 +02:00
Stephen Abello
5b42b8983a N°3515 Update some classes icon to match 3.0 UI 2021-10-21 16:00:18 +02:00
Molkobain
5bae964064 Setup: Fix spacing between module's label and module's more info link 2021-10-21 15:58:19 +02:00
Molkobain
ef9c18e393 Fix setup crash on upgrade when env-production / data/cache-production have been deleted (missing dict files) 2021-10-21 15:16:15 +02:00
Pierre Goiffon
ed43d00afe Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	application/transaction.class.inc.php
#	core/userrights.class.inc.php
2021-10-21 15:12:23 +02:00
Pierre Goiffon
908a48e0a1 Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	application/transaction.class.inc.php
#	test/application/privUITransactionFileTest.php
2021-10-21 15:09:50 +02:00
Pierre Goiffon
9b854dbcc7 N°4289 skip test (not working on Jenkins) 2021-10-21 14:52:59 +02:00
Pierre Goiffon
7757f1f2d2 N°4289 Security hardening 2021-10-21 12:43:03 +02:00
bruno-ds
5e2f8a4ea6 N°4261 - ExceptionLog: improve readability 2021-10-21 11:07:44 +02:00
bruno-ds
62f7eca0a8 N°4261 - Log in db: change default level.
In order to preserve the existing behavior: not EventIssue creation (unless configured otherwise).
2021-10-21 11:07:44 +02:00
Stephen Abello
820f2cbed6 N°4015 Set a minimum height for last tab in scrollable mode and allow customizing tabs minimum height in themes 2021-10-21 10:37:38 +02:00
bruno-ds
d03718681f N°4261 - Log in db: change default configuration.
As since the latest changes by Pir, the default value is handled directly in the class.
2021-10-21 10:11:26 +02:00
Pierre Goiffon
a353317746 N°4289 Fix privUITransactionFile generating error if MetaModel not loaded 2021-10-20 17:26:32 +02:00
Pierre Goiffon
723eb90160 N°4289 privUITransactionSession phpDoc 2021-10-20 17:25:58 +02:00
Pierre Goiffon
0e14be8b15 N°4261 Refactor ExceptionLog (#239)
Doing a code review with Bruno, we agreed to do some little refactoring :

* Level per exception class
  - Before the whole ExceptionLog::Log method was a total rewrite of its parent, with some code duplicates... not a good idea : we should better improve LogAPI to make other similar uses possible in the future !
  - The logic to get level from config must be in a GetMinLogLevel override
* Write to DB
  - Pull up this functionnality in LogAPI
  - Add a sCode parameter in GetLevelDefault

Doing this refactoring, I also improved :

* Test the attributes set when creating the EventIssue object : during my dev I had crashes because I didn't filled all the mandatory fields... Having a PHPUnit test checking this will prevent future bugs to happen if attributes are modified in the class or in the object creation method
* Use Throwable instead of Exception : this was added in PHP 7.0 and will allow to catch both Exception and Error
* Because we need to have 2 statements on the same line in \Combodo\iTop\Test\UnitTest\Core\Log\ExceptionLogTest::testLogInFile, I modified the editorConfig file to allow disabling the formatter using comments.
2021-10-20 16:01:08 +02:00
Pierre Goiffon
ef6d7925fc Log : always log the same structure, and add a delimiter at the end
This will allow to parse the logs more easily !
2021-10-20 15:16:57 +02:00
acognet
ec8c2ca122 N°4374 - Add sanitizer helper for front end (JS) - Rollback 2021-10-20 10:31:41 +02:00
acognet
ebe50b319a N°4357 - Autocomplete issue with accent in a list 2021-10-20 10:31:40 +02:00
Eric Espie
48b1a15bf7 N°4369 - updated autoloader 2021-10-20 09:52:32 +02:00
Eric Espie
5102400be4 N°4369 - Return product and version in status rest ws 2021-10-20 08:52:25 +02:00
Molkobain
4bde828dbb 🌐 N°2875 - Fix missing word in TriggerOnObjectMention:mentioned_filter(+) thanks to @jbostoen 2021-10-19 21:36:23 +02:00
Eric Espie
e0929f4d0d N°4375 - Change CKEditor plugins init 2021-10-19 17:16:17 +02:00
Eric Espie
ef1903dabe N°4369 - Return product and version in status rest ws 2021-10-19 16:20:06 +02:00
Molkobain
e53a45ec5d N°2875 - Update config. param. 2021-10-19 15:40:42 +02:00
Molkobain
0811fd4aa7 N°2875 - Default triggers/action are created during first install/upgrade of 3.0.0 for DM classes with a log attribute in order to allow Person mention out of the box 2021-10-19 15:16:43 +02:00
Molkobain
cdf5789d62 N°2875 - Add $bRootFirst param. to MetaModel::EnumChildClasses() to be iso with MetaModel::EnumParentClasses() 2021-10-19 15:16:43 +02:00
Molkobain
8f2b5ad8e2 N°2875 - Invert TriggerOnObjectMention approach
- Trigger is now positioned on a specific "host" class (eg. Ticket)
- Trigger now has a "mentioned objects" filter which determines the scope of mentioned objects which will activate the trigger
2021-10-19 15:16:42 +02:00
Molkobain
df49e9c3b5 N°2875 - Add class icon to Trigger and Action 2021-10-19 15:16:42 +02:00
Molkobain
6915b0b824 N°2875 - RichText: Fix config property being an array instead of a string (also add a setter) 2021-10-19 15:16:42 +02:00
Molkobain
0b0c99c935 🌐 N°2875 - Add TriggerOnObjectMention:mentioned_filter(+) translations 2021-10-19 15:16:42 +02:00
Molkobain
b9a68f4aeb 🌐 N°2875 - Add TriggerOnObject:filter description
Note: The new translations are based on the russian one as it seemed pretty good, hence the russian translation is not "reset".
2021-10-19 15:16:41 +02:00
Eric Espie
c611b11981 N°4369 - About box with reduced information for non-administrators 2021-10-19 14:52:57 +02:00
Stephen Abello
25763c2d2e N°4351 Fix case log own entries overflowing when unnecessary 2021-10-19 14:49:44 +02:00
acognet
c8f3d23d30 N°4361 - XSS in csvimport on develop 2021-10-19 11:32:05 +02:00
acognet
88fda1466e N°4374 - Add sanitizer helper for front end (JS) 2021-10-19 11:26:29 +02:00
Eric Espie
8a7f0d346d N°4375 - Change CKEditor plugins init 2021-10-19 11:04:33 +02:00
acognet
3e5440aa3b N°3928 - Polishing: Impact analysis - remove icons in pdf list 2021-10-19 10:19:41 +02:00
acognet
6f08038f34 N°4347 - Fix JS errors in custom dashboards for list dahslets 2021-10-19 09:50:53 +02:00
Pierre Goiffon
216e62c448 N°4367 Replace uses of utils.js EncodeHtml() 2021-10-19 08:48:58 +02:00
Eric Espie
f4856150ed N°4375 - Upgrade to CKEditor 4.16.2 2021-10-19 08:46:58 +02:00
Pierre Goiffon
d73d39e71a utils.js : deprecate EncodeHtml and copy it to CombodoSanitizer.EscapeHtml 2021-10-19 08:43:27 +02:00
Pierre Goiffon
6abdabd197 Removing config file writing in OQL PHPUnit tests (#238) 2021-10-18 16:37:24 +02:00
Pierre Goiffon
020460d048 N°4367 update test to use new utils constants 2021-10-18 15:24:10 +02:00
Pierre Goiffon
347cbca5cf Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	application/transaction.class.inc.php
#	application/ui.extkeywidget.class.inc.php
#	composer.json
#	composer.lock
#	js/utils.js
#	lib/composer/InstalledVersions.php
#	lib/composer/installed.json
#	lib/composer/installed.php
#	lib/pear/archive_tar/Archive/Tar.php
#	lib/pear/archive_tar/package.xml
#	setup/wizardsteps.class.inc.php
#	sources/Controller/AjaxRenderController.php
2021-10-18 14:57:19 +02:00
Pierre Goiffon
8ea5be4ead Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	application/transaction.class.inc.php
2021-10-18 14:32:27 +02:00
Pierre Goiffon
b3f827ed5e N°4367 Security hardening 2021-10-18 14:27:58 +02:00
Pierre Goiffon
eaf8a187aa N°3332 report function rename
The method was renamed in 18d52319 but only on support/2.7 and above
2021-10-18 11:36:17 +02:00
Pierre Goiffon
34f64c61f6 privUITransaction fix inspections errors + formatting 2021-10-18 11:32:38 +02:00
acognet
1d28bbe3f4 N°3928 - Polishing: Impact analysis 2021-10-18 11:15:22 +02:00
Molkobain
54c89dcbb5 PHPDoc 2021-10-14 18:03:27 +02:00
acognet
06dac2417a Rollback N°4361 - XSS in csvimport on develop 2021-10-14 16:25:16 +02:00
acognet
83125d9ae1 N°4362 - XSS in ajax.render.php?operation=wizard_helper on develop 2021-10-14 15:46:46 +02:00
odain
20f4419062 ci: add phpunit annotation to exclude/include test 2021-10-14 14:26:07 +02:00
acognet
0f4ca4237d N°4362 - XSS in ajax.render.php?operation=wizard_helper on develop 2021-10-14 10:14:01 +02:00
acognet
bc2c12a8c3 N°3928 - Polishing: Impact analysis 2021-10-14 09:31:21 +02:00
Pierre Goiffon
8154e718a1 N°4356 modifications after code review
Thanks @Molkobain !
2021-10-13 17:23:29 +02:00
Eric Espie
9ec6c2098b N°3928 - Fix iTop logo 2021-10-13 17:21:44 +02:00
Eric Espie
4305e40ae5 Fix warning 2021-10-13 17:15:58 +02:00
Pierre Goiffon
0f149ed852 N°4381 remove old deprecations.md file
Content wasn't up to date
Check the wiki instead (https://www.itophub.io/wiki/page?id=3_0_0%3Ainstall%3A270_to_300_migration_notes)
2021-10-13 16:50:27 +02:00
Pierre Goiffon
d5f9ca9c4b N°4381 CONTRIBUTING : move badge image 2021-10-13 16:48:11 +02:00
Pierre Goiffon
198c63dd79 N°4381 Replace documentation/itop-tickets.htm by a wiki link
Page wasn't maintained anymore
A link was displayed at the end of the setup
2021-10-13 16:40:06 +02:00
acognet
96ae91494b N°3928 - Polishing: Impact analysis 2021-10-13 14:25:55 +02:00
acognet
ceaa98f4ef N°4349 - Drop-down mandatory template field documented still required in modification 2021-10-13 14:25:38 +02:00
acognet
af4b9aaa52 N°4370 - Field content overlapping on rest of the UI (Backoffice) - 2 2021-10-13 14:25:23 +02:00
acognet
d2662b608b N°4349 - Drop-down mandatory template field documented still required in modification 2021-10-13 14:12:23 +02:00
Molkobain
591d189a33 N°3935 - Increase size a bit 2021-10-13 13:36:08 +02:00
Molkobain
36bea54bac N°3935 - Improve transition form UI with different style for cancel button and wider inputs 2021-10-13 13:11:11 +02:00
Pierre Goiffon
b5369a0c03 N°4356 Fix portal attachment download
Was opening the attachment directly in the browser (HTTP header Content-Disposition set to 'inline' instead of 'download')
2021-10-13 12:10:22 +02:00
Molkobain
1c11cef2f8 N°3939 - Keep current tab when editing an object (regression from 1e99ad436) 2021-10-12 21:51:51 +02:00
Molkobain
d8bd5528d3 Merge remote-tracking branch 'origin/support/3.0.0-beta5' into develop 2021-10-12 20:11:36 +02:00
Molkobain
9ed8cf7970 Setup: Ease usage of the UI when zoomed up to 150% (licenses fieldset being too height) 2021-10-12 18:44:47 +02:00
Molkobain
be24d409ed Config: Move security.hide_administrators parameter with other security.xxx parameters 2021-10-12 18:01:56 +02:00
Molkobain
64d91b194f PHPDoc 2021-10-12 18:01:45 +02:00
Eric
2bc61caab1 N°4207 N°4298 Fix data/.maintenance flag not removed by setup anymore
Was already fixed in the develop branch
(cherry picked from commit d0986c048a)
(cherry picked from commit 9126635cf2)
2021-10-12 12:23:49 +02:00
Pierre Goiffon
8f0a5fcaf9 N°4231 Security hardening 2021-10-12 11:11:11 +02:00
Eric Espie
b6df73bdcc N°2527 - Fix dependencies 2021-10-12 09:04:52 +02:00
Eric Espie
836a35d0dd N°4352 - Fix unlock message 2021-10-12 08:55:59 +02:00
acognet
c7a7bfcd68 N°3928 - Polishing: Impact analysis 2021-10-12 08:17:50 +02:00
Molkobain
e7e09b5023 N°4372 - Fix AttributeText limited dimensions in fullscreen when height/width is defined in the DM 2021-10-11 18:08:52 +02:00
Molkobain
3f24b80043 Code cleanup 2021-10-11 18:00:33 +02:00
Pierre Goiffon
fe3512cb5f N°4335 Fix export with PHP < 7.0+ 2021-10-11 17:05:30 +02:00
acognet
2a32c5691b N°4370 - Field content overlapping on rest of the UI (Backoffice) - 2 2021-10-11 16:17:19 +02:00
acognet
dce244f5aa N°4370 - Field content overlapping on rest of the UI (Backoffice) - 2 2021-10-11 15:28:37 +02:00
acognet
63bd1643ce N°4370 - Field content overlapping on rest of the UI (Backoffice) - 2 2021-10-11 09:11:38 +02:00
acognet
3c84a74ea4 N°4357 - Autocomplete issue with accent in a list 2021-10-11 09:09:59 +02:00
acognet
d9870c2513 N°4361 - XSS in csvimport on develop 2021-10-11 09:09:13 +02:00
acognet
7f0493c91d N°3928 - Polishing: Impact analysis 2021-10-07 18:11:04 +02:00
acognet
26e32b1759 Remove console.log 2021-10-07 14:04:22 +02:00
acognet
1b1a6321d7 N°4349 - Drop-down mandatory template field documented still required in modification 2021-10-07 14:04:22 +02:00
acognet
0eba00259a N°3928 - Polishing: Impact analysis 2021-10-07 11:45:53 +02:00
denis.flaven@combodo.com
a7a9e5f0eb N°4354 - Fixed the test which was using a (now fixed) edge case! 2021-10-06 18:45:41 +02:00
denis.flaven@combodo.com
bf4835eec0 N°4354 - Hide Administrator profile to non-admins 2021-10-06 15:34:23 +02:00
acognet
9fbc631b07 N°4349 - Drop-down mandatory template field documented still required in modification 2021-10-05 14:18:28 +02:00
acognet
c6cb7c41cd N°4349 - Drop-down mandatory template field documented still required in modification 2021-10-05 11:47:45 +02:00
acognet
0cb1583688 N°1731 - Allow Transitions without unnecessary confirmation - add force_transition_confirmation param 2021-10-05 11:36:08 +02:00
acognet
370b42d1fd N°3835 - Make global pass on all inputs (objects, dashlets, ...) to ensure XSS and double encoding have been dealt with 2021-10-04 17:28:05 +02:00
Eric Espie
0da8c761c7 N°2527 - Manage hierarchical keys in database maintenance tools 2021-10-04 16:26:16 +02:00
Eric Espie
8c39374abb N°2527 - Manage hierarchical keys in database maintenance tools 2021-10-04 16:23:35 +02:00
acognet
eb239843aa N°4347 - Fix JS errors in custom dashboards for list dahslets 2021-10-04 15:57:17 +02:00
acognet
e38ca54691 N°3835 - Make global pass on all inputs (objects, dashlets, ...) to ensure XSS and double encoding have been dealt with 2021-10-04 15:57:17 +02:00
Eric Espie
f9fc85e763 N°4326 - Fix error in dashboard when no tooltip exist on Pill
(cherry picked from commit 6caf78fdcd)
2021-10-04 11:27:14 +02:00
Eric Espie
94d99a4109 N°2527 - Manage hierarchical keys in database maintenance tools 2021-10-04 11:25:20 +02:00
Eric Espie
f39e801719 N°2527 - Manage hierarchical keys in database maintenance tools 2021-10-04 11:24:30 +02:00
acognet
645f20742c N°3934 - Polishing: User Preferences 2021-10-04 11:00:23 +02:00
acognet
d86065b4a6 N°3934 - Polishing: User Preferences 2021-10-04 10:01:10 +02:00
Molkobain
8af54efd44 N°4068 - Object details: Avoid image attributes to overlap other attributes when they are very large
- Keep its width contained in the column
- Maintain aspect ratio of the container div to hint the user on which size the image should be
- Keep image real size as long as it fits in the container
2021-10-02 10:25:19 +02:00
Molkobain
c96ee4fafc Fix typo 2021-10-01 18:30:03 +02:00
Molkobain
ced4d1c5f1 Fix dictionary entry verbal form 2021-10-01 18:28:24 +02:00
acognet
6d3e8df3e4 N°3934 - Polishing: User Preferences 2021-10-01 18:22:17 +02:00
acognet
963fae243c N°3835 - Make global pass on all inputs (objects, dashlets, ...) to ensure XSS and double encoding have been dealt with 2021-10-01 18:22:17 +02:00
Molkobain
5a09365221 N°3925 - External key: Use more vertical space when possible (30% of the window tops) and fit within the window if not enough space (below or above the input) 2021-10-01 17:38:55 +02:00
Eric Espie
49c5f75c6c N°3520 - Fix static datatables rows 2021-10-01 15:18:29 +02:00
Molkobain
bd67bc8838 N°3882 - Handle use of transparent colors in dynamic header dashlet 2021-10-01 11:48:05 +02:00
Molkobain
c9aa693872 AttributeSet: Avoid items' label to wrap on display in the backoffice (regression from 42be0c20) 2021-10-01 09:37:51 +02:00
acognet
776c03ef6a fix loading of ckeditor 2021-10-01 09:15:34 +02:00
Molkobain
ae6f8fba5c N°3520 - Add missing data-role on UIBlocks 2021-09-30 22:07:39 +02:00
Molkobain
a139dc7e6e N°3520 - HTML metadata: Add data-role to backoffice logos 2021-09-30 21:31:27 +02:00
Molkobain
7d46626d9c N°3520 - HTML metadata: Add object state in object details if present 2021-09-30 21:30:56 +02:00
Molkobain
9ea25188ba N°3925 - Fix state flags not taken into account correctly by a child class (regression from f2ff5a4e) 2021-09-30 19:41:56 +02:00
Molkobain
fadafa8267 N°3925 - Fix stimulus not applied after submission of multiple logs in an object (read-only) 2021-09-30 19:13:33 +02:00
Molkobain
e0d6bc18be N°3925 - Improve display of long external keys in autocomplete / dropdowns
- Show ellipsis if label is overflowing
- Show tooltip on hover (useful for overflowing labels)
2021-09-30 19:13:33 +02:00
Molkobain
2ae01c19e1 Advanced search: Fix checkbox / label alignment on multi choices criteria 2021-09-30 17:49:33 +02:00
Stephen Abello
a5e2831e31 N°3931 Allow HTML in DataTables' Panel title 2021-09-30 15:53:40 +02:00
acognet
e86454ff74 N°3912 - Polishing: Export 2021-09-30 15:06:21 +02:00
acognet
62be3f9f58 fix loading of ckeditor 2021-09-30 15:06:21 +02:00
acognet
cddbe27182 N°4315 - Polish bulk modify screens 2021-09-30 15:06:21 +02:00
Stephen Abello
1f56e39577 N°3931 Make object deletion errors more visible 2021-09-30 15:01:30 +02:00
Stephen Abello
a35c80de57 Align FormTable row metadata forwarding with Datatables/StaticTables ones 2021-09-30 15:01:29 +02:00
Eric Espie
4b8ef4f919 N°3572 - Fix Data Integrity tab results display
- fix synchrodatasource SQL definitions
- fix Hierarchical keys warnings due to bad parameters
2021-09-30 14:53:00 +02:00
Pierre Goiffon
c3d23981fb 💡 Document limitation in \LogAPI::GetConfig 2021-09-30 14:45:06 +02:00
Pierre Goiffon
9c6d8253f4 Fix \Combodo\iTop\Test\UnitTest\Core\CMDBSourceTest::testIsOpenedDbConnectionUsingTls 2021-09-30 10:49:11 +02:00
acognet
4d6a8a76aa N°3904 - Polishing: Backup 2021-09-30 10:20:11 +02:00
Pierre Goiffon
8fa6ae6703 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	core/cmdbsource.class.inc.php
2021-09-30 09:51:13 +02:00
Pierre Goiffon
fdc987f367 Merge remote-tracking branch 'origin/support/2.7.5' into support/2.7 2021-09-29 17:51:17 +02:00
Eric Espie
be9bb10606 N°4339 - Fix page title for object creation 2021-09-29 17:03:53 +02:00
Eric Espie
11d3d5af49 N°3908 - Fix button location (moved to the right of the screen) 2021-09-29 15:56:52 +02:00
Eric Espie
b630492d7a N°4337 - Fix "Missing TWIG template" error 2021-09-29 15:16:13 +02:00
Eric Espie
1a1439946b N°4338 - Fix indirect links removal 2021-09-29 14:32:01 +02:00
Molkobain
1db32c6dee N°4315 - Cleanup in SCSS 2021-09-29 14:21:24 +02:00
Eric Espie
dade45308c N°4332 - Fix table name 2021-09-29 11:30:07 +02:00
acognet
b1597f7d90 recompile styles 2021-09-29 11:24:09 +02:00
acognet
e2904fb0ee N°4230 - Printable version issues 2021-09-29 11:21:00 +02:00
acognet
8dbbc9a124 N°4315 - Polish bulk modify screens 2021-09-29 11:21:00 +02:00
bruno-ds
4297b854e1 N°4034 - Add the get_module_setting function to TwigBase.
This is temporary, as in the 3.1, this file will be deprecated in favor of `sources/application/TwigBase/Twig/Extension.php`.
More info in the N°4034.
2021-09-29 10:58:23 +02:00
Eric Espie
c53c1d5b9c N°4332 - Fix table name 2021-09-29 10:33:46 +02:00
Molkobain
a3db7f0e83 Merge remote-tracking branch 'origin/support/3.0.0-beta5' into develop 2021-09-29 10:18:53 +02:00
Stephen Abello
157c031236 N°4296 Correctly unescape dashboard title tooltip when switching dashboard 2021-09-29 10:15:57 +02:00
denis.flaven@combodo.com
78b1ee04e8 N°4336 - Improve tooltip pertinence, by hiding useless entries 2021-09-28 18:17:16 +02:00
Molkobain
30da7d2ea4 Add deprecated annotations on duplicated TwigExtension files to ease choose for developers 2021-09-28 17:38:59 +02:00
denis.flaven@combodo.com
d467cb5c79 N°4078 - Use the icon AND tooltip when the hyperlink is put as 'shortcut' 2021-09-28 17:25:35 +02:00
Eric Espie
142699c3b1 N°4332 - Fix table prefix 2021-09-28 17:14:05 +02:00
Eric Espie
9dcb789cfd N°3908 - Polishing: Application Upgrade - move the buttons at the bottom 2021-09-28 17:04:08 +02:00
Stephen Abello
aac504ec0b N°3917 Fix object details icon cover method when using class highlight icon as object icon 2021-09-28 16:25:47 +02:00
denis.flaven@combodo.com
a7a7ce77fb N°4096 - Automatic email sending retry in case of error. 2021-09-28 15:42:28 +02:00
Eric Espie
6caf78fdcd N°4326 - Fix error in dashboard when no tooltip exist on Pill 2021-09-28 15:07:27 +02:00
Stephen Abello
5680d9579c N°3917 Refactor algorithm to get object details semantic image icon in object's GetIcon method in order to propagate this feature anywhere where GetIcon is called 2021-09-28 15:01:06 +02:00
Molkobain
ec47645ef7 Merge branch 'support/3.0.0-beta5' into develop 2021-09-28 12:58:08 +02:00
Molkobain
4c6a7ca30b N°3791 - Fix crash when displaying object with a null state value 2021-09-28 12:51:21 +02:00
Molkobain
a70acf29ae Simplify double if condition 2021-09-28 12:35:02 +02:00
Eric Espie
57b08b5b24 N°4328 - Fix XML version 2021-09-28 10:10:10 +02:00
Molkobain
90906912cc N°3556 - Fix CaptureWebPage not retrieve parts from UIBlocks 2021-09-28 10:09:43 +02:00
Eric Espie
3064d868b7 N°4328 - Fix Overview tab displayed before object creation 2021-09-28 10:01:03 +02:00
Eric Espie
548d08b1ec N°4332 - Merge multi-LDAP module into iTop 2021-09-28 09:10:26 +02:00
denis.flaven@combodo.com
f226916bb8 N°4078 - Use the icon when the hyperlink is put as 'shortcut' 2021-09-27 19:06:46 +02:00
Eric Espie
47fcddc9a6 N°4326 - Fix external keys in dynamic header dashlet 2021-09-27 17:35:52 +02:00
Molkobain
86b03b9e92 Set back @covers annotation 2021-09-27 17:34:48 +02:00
acognet
9811d6f8ea N°3912 - Polishing: Export 2021-09-27 15:08:04 +02:00
Eric Espie
f67f3eaf74 N°4326 - Fix unknown attribute when no state attcode is given 2021-09-27 14:43:12 +02:00
odain
0b4d4764bd ci testing: use proper annotation to include/exlude test linked to composer.json 2021-09-27 11:57:25 +02:00
acognet
580deb655d Remove unused tablesorter 2021-09-27 09:25:20 +02:00
acognet
5e2bfdf660 N°3912 - Polishing: Export 2021-09-27 09:23:52 +02:00
Molkobain
0d51dc61f9 N°4001 - Fix double title & extra space on object creation failure page 2021-09-26 22:37:41 +02:00
Molkobain
9949b1b11a N°4318 - Improve large field limits visualization with scrollbar's track color 2021-09-26 22:27:18 +02:00
Molkobain
8be141f692 N°3791 - Replace all hard-coded style colors in the DM with corresponding semantic / palette colors 2021-09-26 17:45:18 +02:00
Molkobain
a11bc9ad33 N°3791 - Enable use of SCSS variables in the DM classes / (meta)enum attributes style 2021-09-26 16:53:42 +02:00
Molkobain
3214ae91c7 N°3791 - Panel: Use style defined in the DM for classes
Note that for now, semantic colors cannot be used directly in a <main_color> or <complementary_color> tag. Only valid CSS color (hexa, hsla, ...)
2021-09-26 15:15:34 +02:00
Molkobain
21545da062 Rename Panel / Alert / Button color constants for something more accurate
Done now before their as used too widely. We are most likely to allow dev. to use custom colors soon, so we want to avoid confusing / renaming then. (iTop extensions have been verified, none had to be migrated)
2021-09-26 01:26:42 +02:00
Molkobain
7476b6d059 Button group: Fix button groups always being on a new line instead of staying in the flow 2021-09-26 01:22:53 +02:00
Molkobain
b15c8e30bc N°3791 - Panel: Use style defined in the DM for classes
Note that for now, semantic colors cannot be used directly in a <main_color> or <complementary_color> tag. Only valid CSS color (hexa, hsla, ...)
2021-09-26 01:17:28 +02:00
Molkobain
39d71c9c43 N°3882 - Pill: Fix default color scheme when in a panel 2021-09-26 00:51:04 +02:00
Molkobain
75d913a003 Compiler: Factorize DM classes style and add them to the DM CSS rules 2021-09-25 23:51:52 +02:00
Molkobain
2b38c98183 Compiler: Update unit tests for DM classes / (meta)enum attributes style 2021-09-25 23:27:29 +02:00
Molkobain
ca7f6362bf ormStyle: Fix icon URL including the app. root in the MetaModel to ease usage with load balancers 2021-09-25 17:00:50 +02:00
Molkobain
4d8ac5fee5 PHPDoc 2021-09-25 17:00:50 +02:00
acognet
938de4c71c N°3787 - Use data loader for auto refresh 2021-09-24 17:28:52 +02:00
Pierre Goiffon
3ff117596d 💡 N°4325 add phpdoc 2021-09-24 17:16:59 +02:00
Molkobain
194459e0de Breadcrumbs: Harmonize spacing with other top bar elements 2021-09-24 17:04:55 +02:00
Molkobain
95179b0c18 Dashboard: Fix multi-select field padding on selected values 2021-09-24 17:02:53 +02:00
Molkobain
d76c9cee6f N°3900 - Breadcrumbs: Better fix than 7ae4fe06e 2021-09-24 17:02:53 +02:00
odain
6e45b74665 Composer: Fix required versions => rename cover annotation 2021-09-24 15:01:08 +02:00
acognet
3d8259a083 N°3923 - Polishing: External key 2021-09-24 15:00:32 +02:00
Molkobain
6d8a36e061 N°3882 - Fix null status color when class has no style defined 2021-09-24 14:54:29 +02:00
acognet
814038f5fd recompile styles 2021-09-24 12:12:14 +02:00
acognet
f237b4dd30 N°3705 - Migrate module to new UIBlock system : Kanban board - fix z-index of selectize dropdown list 2021-09-24 12:05:09 +02:00
Pierre Goiffon
4cf4c0e4c3 ♻️ N°4325 refactor CMDBSource mysqli attributes to a separate wrapper class (#237)
In 2.7.5 with N°3513 we added a second mysqli attribute in CMDBSource, so that we can test transactions (see TransactionsTest).

But this wasn't documented, and was really causing confusion !

This refactor wraps both attributes in a dedicated object so that the logic is clearer.
2021-09-24 11:45:39 +02:00
Stephen Abello
86538cf88e Add metadata to legacy search elements 2021-09-24 10:53:02 +02:00
acognet
722cae240e align style of spinner 2021-09-24 10:09:02 +02:00
acognet
f0d3149a1c N°3787 - Use data loader for auto refresh 2021-09-24 10:09:02 +02:00
Stephen Abello
92e315e2c7 Re-dump autoloader since 7c7386a broke it -- with platform check enabled 2021-09-24 10:04:37 +02:00
Stephen Abello
6150881154 Re-dump autoloader since 7c7386a broke it 2021-09-24 09:31:34 +02:00
Molkobain
cf223b583e N°3882 - Protection against ormStyle being null for an object 2021-09-24 09:04:24 +02:00
Molkobain
eb5e5591d7 N°4326 - Improve robustness of DesignerComboField::SetAllowedValues() 2021-09-23 22:25:57 +02:00
Molkobain
dcf4053c30 Setup: Improve components' licenses display 2021-09-23 21:46:36 +02:00
Molkobain
fedc3d4d76 N°3556 - Fix JS dict. entries not available in SetupPage anymore 2021-09-23 21:46:36 +02:00
Molkobain
e93c0123aa PHPDoc 2021-09-23 18:12:52 +02:00
Molkobain
0004586779 N°4327 - Fix JS "ReferenceError" in Application Upgrade 2021-09-23 17:40:48 +02:00
Molkobain
7ae4fe06ed N°3900 - Breadcrumbs: Fix all items being hidden even when they should not (when browser's window is zoomed in/out) 2021-09-23 16:41:12 +02:00
Pierre Goiffon
ec1dcc8df6 💡 N°3513 PHPDoc 2021-09-23 14:42:16 +02:00
Pierre Goiffon
47ed863da9 N°4215 N°3513 Fix DB errors fetch from the wrong object n°2 2021-09-23 14:32:43 +02:00
Molkobain
7404599721 N°3882 - Fix unit tests 2021-09-23 14:16:22 +02:00
Pierre Goiffon
88290f9e91 N°4215 N°3513 Fix DB errors fetch from the wrong object 2021-09-23 13:55:23 +02:00
Molkobain
eb8aed19c2 Code cleanup 2021-09-23 13:10:23 +02:00
Molkobain
3a05e9159d PHPDoc 2021-09-23 12:29:34 +02:00
Pierre Goiffon
cfdbc8ae62 N°4215 When checking for TLS cnx, don't set anymore CMDBSource mysql attributes ! 2021-09-23 11:59:44 +02:00
Molkobain
99026cec1f N°3882 - Compiler: Prepare unit test for DM CSS rules (needs to be completed with the team) 2021-09-23 11:44:12 +02:00
Molkobain
029d2ad526 N°3882 - Compiler: Factorize AttributeEnum/AttributeMetaEnum style compilation 2021-09-23 11:44:12 +02:00
Molkobain
1cb100b010 N°3882 - Header dynamic: Pills now shows the real color from the DM 2021-09-23 11:44:12 +02:00
Molkobain
197864ff83 N°3882 - Object details: Status indicator (dot) now shows the real state color 2021-09-23 11:44:11 +02:00
Molkobain
1e73ee8ccd N°3882 - Refactor display of field badges (meta enums / enums) in lists to match original mockups 2021-09-23 11:44:11 +02:00
Molkobain
e2b73995e1 N°3882 - Move DataModel classes fields' style to theme instead of (duplicated) inline CSS 2021-09-23 11:44:11 +02:00
Molkobain
24cedbdebd PHPDoc 2021-09-23 11:44:11 +02:00
Molkobain
0dc95f93a9 Code conventions 2021-09-23 11:44:10 +02:00
Molkobain
b6bd7fe400 Portal: Remove deprecated message for ItopExtensionsExtraRoutes as there is no alternative yet.
YAML routes can only be declared by the core, not modules.
2021-09-23 11:44:10 +02:00
acognet
03a19ab3f4 N°2573 - Remove MetaModel::GetNextKey 2021-09-23 11:36:10 +02:00
Stephen Abello
50849ae4ea N°4315 Harmonize bulk modify screen with other bulk actions 2021-09-23 11:34:54 +02:00
Stephen Abello
70d7f576f3 N°4001 Remove empty lines from tag set tooltips 2021-09-23 10:31:06 +02:00
acognet
bf491b7298 recompile styles 2021-09-23 09:30:30 +02:00
acognet
40ec7e35fd N°4245 - Using customfield in notifications triggered by TriggerOnObjectUpdate via ApplyStimulus 2021-09-23 09:20:33 +02:00
acognet
ffe5541361 N°2259 - iTop Compilation of branding images ignore real format of source image 2021-09-23 09:19:55 +02:00
acognet
73c55748d7 N°3904 - Polishing: Backup 2021-09-23 09:19:54 +02:00
acognet
0754dda1d9 N°3905 - Polishing: CSV Import 2021-09-23 09:19:54 +02:00
acognet
057bea196e Fix setTitleBlock 2021-09-23 09:19:54 +02:00
acognet
e97a266c44 N°3946 - LogAPI : log config parameters aren't used when logging in the setup wizard context 2021-09-23 09:19:54 +02:00
Eric Espie
b4278a6987 Supportability: Add UserId in EventIssue if 'userinfo' field is empty 2021-09-23 08:25:32 +02:00
Pierre Goiffon
aaa8f6d311 N°4215 Fix call to a function on null error when setting TLS connection in the setup
Regression introduced by b1ca1f2630 / N°3513
2021-09-22 15:59:39 +02:00
Stephen Abello
50f860a0e8 N°3974 When editing an object, align fields synchro icons 2021-09-22 15:05:17 +02:00
Stephen Abello
198c9ed479 N°4296 When switching dashboard, update dashboard title tooltip with new value 2021-09-22 14:03:57 +02:00
Stephen Abello
6e076ae1fa N°3911 Fix HTML content in external key tooltip not showing 2021-09-22 13:49:48 +02:00
Stephen Abello
9d44f0982c N°3911 Fix spacing between attribute label and attribute code 2021-09-22 13:49:44 +02:00
Molkobain
fd933ce49a N°4245 - Temporary partial rollback 2021-09-22 13:34:13 +02:00
odain
ae0c43a099 N°4227 - enhance cli restore feedback when backup file not accessible 2021-09-22 11:42:27 +02:00
Stephen Abello
7c7386afc7 N°3851 Update Emogrifier to a version supporting iTop PHP versions range 2021-09-21 16:45:12 +02:00
bruno-ds
c306c6e30d N°4261 - code review with @PirGoif 2021-09-21 16:38:10 +02:00
Molkobain
d9ccac3aea Composer: Fix required versions of PHP in order to keep our package constraints up-to-date 2021-09-21 16:12:22 +02:00
Eric Espie
d8316734e2 N°4305 - n-n links to same class - Be more robust on original search given to ormLinkSet 2021-09-21 15:46:20 +02:00
Molkobain
7ac5c1bbbb Composer: Fix target PHP version in platform to the min. supported version.
Having this set to the minimum supported version ensure that when packages versions are retrieved/updated, only versions compatible with this PHP version are selected.
2021-09-21 15:22:56 +02:00
Molkobain
37585614ba Branding: Cleanup of old references since refactoring of logos compilation 2021-09-21 15:12:05 +02:00
Molkobain
03b728b394 PHPDoc 2021-09-21 14:38:43 +02:00
Pierre Goiffon
ae2072f4d5 N°3002 Get developer_mode.enabled config param first normally, and if not set from disk 2021-09-21 13:56:15 +02:00
Molkobain
2f6ed8f8af Code conventions 2021-09-21 13:37:35 +02:00
Molkobain
1f5dabf8f6 Code conventions 2021-09-21 13:36:11 +02:00
Stephen Abello
eb5cdb053e Fix unsanitized table id 2021-09-21 12:10:53 +02:00
Pierre Goiffon
25ee577eba 💡 phpdoc 2021-09-21 12:07:37 +02:00
Pierre Goiffon
f0aaf21a79 💚 N°3002 Fix php-mock-objects notices
The error handler now checks if logger is enabled before doing anything
2021-09-21 12:01:42 +02:00
acognet
a906086751 recompile styles 2021-09-21 11:18:40 +02:00
acognet
ab17eaad27 N°4260 - Fix display of log attributes in list 2021-09-21 10:57:47 +02:00
Molkobain
469c1553bf Fix typo in icon filename 2021-09-21 10:45:04 +02:00
Pierre Goiffon
4f72f8be0c N°4158 developer_mode.enabled config param is now always read from disk
If no config file on disk then will return default value
Was failing in the compilation process as during a moment we have in MetaModel a Config instance only containing data from params, and without previous params that were on disk :/
2021-09-21 10:37:17 +02:00
Pierre Goiffon
5f2323f10b N°4092 Symlinks flag : now always update the flag
Before this commit we were only creating/removing the flag is the functionnality was available : but this was causing confusions !
2021-09-21 10:36:07 +02:00
Eric Espie
98013a68a4 N°4305 - n-n links to same class - Fix fatal error when original set is already provided with the target class 2021-09-21 10:23:30 +02:00
Stephen Abello
f55193604c N°3929 Fix carets on dashboard editor's select fields 2021-09-21 10:00:24 +02:00
Stephen Abello
586b8c5c71 N°3929 Fix apply/undo button on specific dashboard editor fields 2021-09-21 09:58:34 +02:00
Molkobain
a771d35197 N°3685 - Fix missing C3 lib in a dashboard menu node 2021-09-21 09:51:25 +02:00
Molkobain
96e4ef68df Code conventions 2021-09-21 09:38:01 +02:00
Molkobain
df40b53b6b Code format 2021-09-21 09:24:26 +02:00
acognet
6d4f919519 Refactor -> create utils::AddParamToUrl - renaming of function + encode parameters 2021-09-20 17:29:50 +02:00
Molkobain
8af116275c Change use of "sizeof()" by "count()" to avoid confusion 2021-09-20 17:02:06 +02:00
Eric Espie
e930d34963 N°4305 - n-n links to same class - Fix aliases in request 2021-09-20 16:09:32 +02:00
Molkobain
4de79afe56 Fix non updated image for contributing guide 2021-09-20 13:19:05 +02:00
bruno-ds
daf24d8cb3 N°4261 - implement feedbacks from the team
plus:
 - the entrypoint is now `LogException()` instead of `FromException()` which sounded more like a factory and less like an active method.
 - merge conflicting commit with @molkobain (CC fix)
 - remove the writing of the exception object in the error.log context (adding it was an error, it's way too verbose!!).
   - Technical note: The context is still used to propagate the exception across several call stack, so it now uses a less generic naming in order to avoid conflicts (see `ExceptionLog::CONTEXT_EXCEPTION`). another solution would have been to add a new parameter to `ExceptionLog::Log()`, but I didn't want to add constraint over the hypothetical evolution of the base class method.
2021-09-20 12:27:39 +02:00
bruno-ds
6e0d570d41 N°4261 - Portal exception logging: Add exception's file and line to the context.
plus:
 - the exception object is no more automatically added to the error.log context (it's way too verbose)
 - code cleanup (use constant instead of repeated strings)
 - ExceptionLog main method is now named `LogException` instead of `FromException`
2021-09-20 12:27:39 +02:00
Molkobain
ce4379920d Update contributing guide with new stickers 👀 2021-09-20 12:17:13 +02:00
acognet
291bbdf3da recompile styles 2021-09-18 23:13:43 +02:00
acognet
61f6c1fe33 N°2259 - iTop Compilation of branding images ignore real format of source image 2021-09-17 16:36:40 +02:00
acognet
a1d6a705ca N°4260 - Fix display of log attributes in list 2021-09-17 16:29:33 +02:00
acognet
b861d45b08 Refactor -> create utils::AddParamToUrl 2021-09-17 16:29:06 +02:00
Molkobain
fc7d2551cd N°4302 - Fix hard-coded image att. code in UserRights::GetUserPictureAbsUrl() 2021-09-17 12:04:13 +02:00
Stephen Abello
b15267d8db N°4239 Update bulk transition/modify mono/multi values indicator style 2021-09-17 11:35:01 +02:00
Stephen Abello
94ce62e424 Remove unintentional function overload committed in e3687b3 2021-09-16 15:16:19 +02:00
Molkobain
6271a33fdb Code review: Fix code conventions 2021-09-16 14:53:40 +02:00
Molkobain
4b6db53e84 Update current version 2021-09-16 13:38:41 +02:00
Eric Espie
540b9f8164 N°3908 - Polishing: Application Upgrade - display the installation progress bar 2021-09-16 11:24:22 +02:00
Eric Espie
5839bab042 N°3908 - Polishing: Application Upgrade - clickable checkbox label, remove history menu, filter history with most recent first, remove unnecessary columns in history 2021-09-16 11:14:50 +02:00
Pierre Goiffon
adc7666dd0 💚 Change setup.css test
Was checking comment presence, but we removed the comments (N°3865)
2021-09-16 10:21:21 +02:00
Stephen Abello
e3687b3cbb N°3685 Use minified versions of jQuery UI timepicker library 2021-09-16 10:09:33 +02:00
Stephen Abello
e81c02b25a N°3685 Fix combodo webfont preloading file name 2021-09-16 10:09:33 +02:00
Pierre Goiffon
28a8a4457e 📦 Update setup.css 2021-09-16 09:38:52 +02:00
Molkobain
eee0f453da N°3685 - Use minified versions of dataTables libs. 2021-09-16 09:20:54 +02:00
Molkobain
164a5501c0 Add missing condition for compiled JS dictionaries 2021-09-15 22:58:09 +02:00
Molkobain
ab3c1ad4af Add TWIG comment 2021-09-15 20:22:30 +02:00
Molkobain
83a3530880 Activity panel: Improve accessibility 2021-09-15 20:16:09 +02:00
Molkobain
0ad23e272b Update precompiled themes 2021-09-15 16:16:20 +02:00
Stephen Abello
b28ef803a3 N°3685 Display text while font is loading 2021-09-15 16:16:20 +02:00
Stephen Abello
b2155c042e N°3685 Fix twig variable name 2021-09-15 16:16:20 +02:00
Stephen Abello
b1b1d25186 N°3685 Preload necessary fonts to speed up display 2021-09-15 16:16:20 +02:00
Stephen Abello
61ee4d6807 N°3685 Replace Raleway truetype font files with woff ones 2021-09-15 16:16:20 +02:00
Molkobain
443292e1f6 PHPDoc 2021-09-15 16:16:20 +02:00
Molkobain
c025a7aa3b N°3685 - Add unit test for WebResourcesHelper 2021-09-15 16:16:20 +02:00
Stephen Abello
86ebb93149 N°3685 Compile SCSS files as a compressed CSS file and fix SCSS copyright comment so that they don't end up in compiled CSS 2021-09-15 16:16:20 +02:00
Molkobain
120670240c PHPDoc 2021-09-15 16:16:20 +02:00
Molkobain
5bd8a25440 N°3685 - Use WebResourcesHelper for D3/C3.js usages 2021-09-15 16:16:20 +02:00
Molkobain
754f755141 N°3685 - Use WebResourcesHelper for D3/C3.js usages 2021-09-15 16:16:20 +02:00
Molkobain
74b7223d44 N°3685 - Introduce WebResourcesHelper and use it for SimpleGraph usages 2021-09-15 16:16:20 +02:00
Stephen Abello
1fb2ff355d N°3685 Optimize CSS size: .ibo-button is extended at multiple places, reducing its use in loops when possible greatly improves compiled selectors 2021-09-15 16:16:20 +02:00
Molkobain
61f3d3aeda N°3685 - Front-end performances: Use only necessary parts of Bulma SCSS 2021-09-15 16:16:20 +02:00
Molkobain
99860e9e20 N°3685 - Front-end performances: Split compatibility files for easier maintenance / inclusion 2021-09-15 16:16:20 +02:00
Molkobain
eb164b47e2 N°3685 - Front-end performances: Update comments 2021-09-15 16:16:20 +02:00
Molkobain
dbd197d9bc N°3685 - Front-end performances: Include advanced search resources only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
e638c65685 N°3685 - Front-end performances: Remove clipboard lib. as it is not used in the backoffice yet 2021-09-15 16:16:20 +02:00
Molkobain
42b779d301 N°3685 - Front-end performances: Include dataTables lib. only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
da3bab9647 N°3685 - Front-end performances: Include jQuery.popup_menu lib. only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
94d53575ae N°3685 - Front-end performances: Include dataTables lib. only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
c26cfad062 Fix JS widget name in comment (decrease false positives in grep) 2021-09-15 16:16:20 +02:00
Molkobain
9cd9087cc7 N°3685 - Front-end performances: Move deprecated JS files to optional compatibility scripts 2021-09-15 16:16:20 +02:00
Molkobain
df7991adeb N°3685 - Front-end performances: Remove JS lib. already included in parent class 2021-09-15 16:16:20 +02:00
Molkobain
2dcfe0e281 N°3685 - Front-end performances: Include ScrollMagic lib. only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
bac584a6b4 N°3685 - Front-end performances: Include graph libs. (Raphael, simple_graph, ...) only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
e4d7bf7dbb N°3685 - Front-end performances: Identify used libs. 2021-09-15 16:16:20 +02:00
Molkobain
2d907f31dd N°3685 - Front-end performances: Use minified versions of libs. 2021-09-15 16:16:20 +02:00
Molkobain
e2001f4585 N°3685 - Front-end performances: Move deprecated JS files to optional compatibility scripts 2021-09-15 16:16:20 +02:00
Molkobain
9810f666fd N°3685 - Front-end performances: Use minified versions of libs. 2021-09-15 16:16:20 +02:00
Molkobain
de5f47d43e N°3685 - UIBlock resources: Add CKEditor resources to RichText 2021-09-15 16:16:20 +02:00
Molkobain
d2662e27e1 N°3685 - Front-end performances: Include BBQ lib. only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
9ac0100d3a N°3685 - Front-end performances: Remove JS lib. already included in parent class 2021-09-15 16:16:20 +02:00
Molkobain
1ea5983464 N°3685 - Front-end performances: Move deprecated JS files to optional compatibility scripts 2021-09-15 16:16:20 +02:00
Molkobain
15081ba82c N°3685 - Front-end performances: Include graph lib. (D3/C3.js) only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
df189bd1f2 N°3685 - Front-end performances: Include advanced search resources only when necessary 2021-09-15 16:16:20 +02:00
Molkobain
06f469faf2 N°3685 - Front-end performances: Add conf. param. to include deprecated JS/CSS files back if necessary 2021-09-15 16:16:20 +02:00
Molkobain
b27aa70a1e N°4247 - Button group: Make sure buttons of a same group always stay on the same line 2021-09-15 15:40:29 +02:00
Molkobain
0e35b8e4fa N°4247 - Activity panel: Make sure that cancel / send buttons always stay on the same line 2021-09-15 15:39:25 +02:00
Molkobain
c0fc62bcb8 N°4247 - Activity panel: All entries are now expanded / collapsed by the corresponding icons 2021-09-15 14:48:17 +02:00
bruno-ds
d1721b0834 N°4261 -Fix CI
Try to repair an odd error in the CI:
> Fatal error: Uncaught Exception: Serialization of 'ReflectionClass' is not allowed

avoid instantiation in the provider, delay them to the actual test
2021-09-15 14:39:00 +02:00
bruno-ds
66e4f369f7 N°4261 -Fix CI
Try to repair an odd error in the CI:
> Fatal error: Uncaught Exception: Serialization of 'ReflectionClass' is not allowed

Maybe it's triggered by the mocks being a property of the test class, so I inlined them.
+ misc. minor modification in order to try to figure out what is causing this behavior.
2021-09-15 13:34:04 +02:00
Pierre Goiffon
c5e1dbce88 💡 PHPDoc for \cmdbAbstractObject::UpdateObjectFromArg 2021-09-14 17:54:28 +02:00
bruno-ds
5d23a250ae N°4261 - New log handler dedicated to Exceptions & use of it in the portal's Exception listener
Such Exceptions are triggered with a Warning level and default the minimum default level in order to write in DB is above, so the behavior is not modified:
 - logs are written in errors.log (with a warning elvel instead of an error)
 - logs are not written in DB unless `log_level_min.write_in_db` is changed
2021-09-14 17:40:11 +02:00
Molkobain
b46357a1bd N°4254 - Fix autocomplete results being hidden below the modal after first opening 2021-09-14 17:31:59 +02:00
Eric Espie
4433cdb21b N°4047 - Fix undefined offset in core\dbobject.class.php - rewrite duplicate check 2021-09-14 16:13:43 +02:00
Eric Espie
45dc79f5af N°4211 - Remove DBObject::Reload calls added in 3.0.0 - Fix Highlight code (computed only for lifecycle and stopwatch) 2021-09-14 15:01:42 +02:00
Eric Espie
2ab0fab051 N°4211 - Remove DBObject::Reload calls added in 3.0.0 - Fix User cache when user not in DB 2021-09-14 15:01:42 +02:00
acognet
be81d1f6c0 N°3901 - Polishing: Menu - count 2021-09-14 12:21:10 +02:00
acognet
ddedce1589 Fix shortcut 2021-09-14 12:01:06 +02:00
Eric Espie
b557f16cfa N°4211 - Remove DBObject::Reload calls added in 3.0.0 - Try Person for User's Contact 2021-09-14 11:06:36 +02:00
Pierre Goiffon
30bf2015cb GitHook install : update create symlink message to add target path 2021-09-14 09:42:23 +02:00
acognet
14b6e903cb N°4245 - Using customfield in notifications triggered by TriggerOnObjectUpdate via ApplyStimulus 2021-09-14 09:41:40 +02:00
acognet
4f6e040346 N°3907 - Polishing: Run query - update of precompiled css 2021-09-14 09:15:22 +02:00
acognet
3e12799d1d N°3907 - Polishing: Run query 2021-09-14 09:10:54 +02:00
acognet
7d0550879f N°3910 - Polishing: data synchro 2021-09-14 09:09:36 +02:00
acognet
6a765fad50 N°3685 - Performance checks on the front end - Avoid reload 2021-09-13 09:19:08 +02:00
Stephen Abello
cbb70c94e5 Update precompiled stylesheets 2021-09-10 10:29:11 +02:00
Stephen Abello
b120488085 N°3922 Restyle one way password inputs, reset buttons and displayed hints 2021-09-10 10:28:38 +02:00
Pierre Goiffon
191891ac35 💬 Pre-commit hook : change message to avoid confusions
"push" is a git verb, so changed it to "add" instead
2021-09-10 08:38:53 +02:00
Molkobain
f171380396 Modals: Fix close "x" not being aligned 2021-09-09 18:01:03 +02:00
Molkobain
f9e54e1dde JSDoc 2021-09-09 18:01:03 +02:00
Eric Espie
15e99a898e N°3985 - Performance checks on the back end - Enhance KPIs 2021-09-09 17:21:57 +02:00
odain
27c397cc1a N°4225/4227: recommit lost restore.php + refactor duplicated code for cli restore/backup in common-cli.execution.php 2021-09-09 16:57:42 +02:00
acognet
616229140e N°3901 - Polishing: Menu 2021-09-09 14:27:36 +02:00
acognet
04e016c919 N°3919 - Polishing: IP Attribute 2021-09-09 14:27:36 +02:00
Eric Espie
a4e43d3f17 N°4225 - Remove Read-only mode for backup 2021-09-09 14:25:19 +02:00
Eric Espie
ed6969be2c N°4227 - Manual iTop restore - maintenance mode 2021-09-09 13:56:07 +02:00
Stephen Abello
8105c4d6cd N°3913 Fix last step double scrollbar on smaller screen 2021-09-09 11:02:18 +02:00
Stephen Abello
3b7073ad4e Remove commented lines 2021-09-09 10:01:52 +02:00
Stephen Abello
dbb84fa4e6 N°4239 Use blocks for bulk modify/transition/delete, harmonize and polish display 2021-09-09 09:52:09 +02:00
Pierre Goiffon
91c7ed9f4d pre-commit hook to disallow commit with SCSS file but without CSS file 2021-09-09 09:28:45 +02:00
Molkobain
e4c818cacb N°4288 - Portal: Update TWIG extensions to match those available in the backoffice 2021-09-08 21:47:05 +02:00
Molkobain
5b6b07af48 N°2007 - Portal: Don't show tooltip if empty on BrowseBrick items 2021-09-08 20:12:03 +02:00
Molkobain
1331bc2139 Add PHPDoc 2021-09-08 15:38:42 +02:00
Molkobain
08946066fb Session management: Add PHPDoc 2021-09-08 14:54:20 +02:00
Molkobain
0de4e62fcd Session management: Revert modification in third-party lib 2021-09-08 14:49:29 +02:00
Molkobain
8edd155351 N°4254 - Fix jQuery dialogs not being stacked correctly 2021-09-08 13:31:58 +02:00
Molkobain
3980ba81e7 Fix typo 2021-09-08 12:33:19 +02:00
acognet
0193868581 N°3901 - Polishing: Menu 2021-09-08 11:48:45 +02:00
Stephen Abello
d2b3de9734 Update precompiled stylesheets 2021-09-08 11:16:58 +02:00
Stephen Abello
d1c39c5e10 N°3929 Fix dashboard properties buttons and change semantics colors/icons 2021-09-08 11:16:06 +02:00
Stephen Abello
e29ae488a1 N°3929 Align dashboard switch button with specifications 2021-09-08 11:16:06 +02:00
Molkobain
ad3e3195a8 Compiler: Add log message in case a profile (user rights) relies on a missing group 2021-09-08 10:58:00 +02:00
Eric Espie
738411005b Fix CI 2021-09-08 10:20:16 +02:00
Pierre Goiffon
40b095e407 📦 Update compiled CSS 2021-09-08 08:04:46 +02:00
Pierre Goiffon
3b7cb9a554 💄 Setup : fix (v2) missing space on backup checkbox
Replaces &nbsp; added in 7890cbd7 with CSS
As the other setup checkboxes seems to be OK (space might already be added, or we might have a line feed in the code between checkbox and label), we are only modifying the backup checkbox
2021-09-07 17:57:25 +02:00
Eric Espie
f474b3de06 Fix CI 2021-09-07 16:58:36 +02:00
Pierre Goiffon
7890cbd701 💄 Setup : fix missing space on backup checkbox 2021-09-07 16:56:47 +02:00
Eric Espie
eef3e9b7ae Merge branch 'develop' into SessionManagement 2021-09-07 16:33:10 +02:00
odain
3c081461b0 fix ci: use env-production instead 2021-09-07 15:22:46 +02:00
Eric Espie
a916df64c9 Merge branch 'develop' into feature/cli-backup-restore 2021-09-07 14:48:06 +02:00
Eric Espie
1d0b96e10f Merge branch 'develop' into feature/cli-backup-restore 2021-09-07 14:45:35 +02:00
Stephen Abello
28070f8682 Update precompiled stylesheets 2021-09-07 14:41:39 +02:00
Stephen Abello
3e428000bd N°3914 Fix "Configure this list" buttons being narrowed when reconstructing modal 2021-09-07 14:40:43 +02:00
Stephen Abello
165b11f948 N°3914 Avoid table header sorting icons from overlapping with header label 2021-09-07 14:40:36 +02:00
acognet
c6495e7212 N°3907 - Polishing: Run query - update of precompiled css 2021-09-07 14:06:28 +02:00
acognet
0fb0b9deab N°3907 - Polishing: Run query 2021-09-07 10:59:14 +02:00
Molkobain
ecb1acf5af Update precompiled stylesheets 2021-09-07 10:54:34 +02:00
Eric Espie
b239e822ef N°4227 / N°4225 - Check cron context in WaitCronTermination 2021-09-07 10:54:27 +02:00
Eric Espie
615aa594f0 N°4227 / N°4225 - Fix cron backup 2021-09-07 10:47:26 +02:00
acognet
2e346a7e80 N°4184 - Alert UI block is collapsible only if there is a title 2021-09-07 10:45:37 +02:00
acognet
f5b557b0bc N°4191 - Fix not selectable caller in NormalChange when only 1 organization 2021-09-07 10:45:37 +02:00
Molkobain
2703075d39 SCSS: Rename variables to match conventions 2021-09-07 10:42:55 +02:00
Molkobain
f6fbd5a7a5 N°3900 - Breadcrumbs: Improve behavior when items are too many for the screen width
When the screen isn't large enough we now put the oldest entries in a dropdown menu like on a browser to access the previous pages.
2021-09-07 10:22:38 +02:00
Molkobain
d1a05f41e5 Button: Fix position to relative to allow absolute positioning of child elements 2021-09-07 10:22:38 +02:00
Stephen Abello
6b67ad93b9 Update precompiled stylesheets 2021-09-07 09:35:53 +02:00
Stephen Abello
884d3c9477 N°3920 On a fullscreen text field and clicking on an image, make popup display on top of current text field 2021-09-07 09:35:53 +02:00
Stephen Abello
26426123b8 N°3920 Move fullscreen button for text field next to field label 2021-09-07 09:35:53 +02:00
Pierre Goiffon
6725a9f1ef N°3807 Fix HTML licenses not displayed correctly 2021-09-07 08:58:00 +02:00
Eric Espie
8e0ae67803 N°4227 / N°4225 - Enhance SetupUtils interface 2021-09-06 17:53:46 +02:00
acognet
979a43edc9 N°3551 - Migrate module to new UIBlock system : Customer Survey - Fix problems of id in checkbox after action like "configure this list" 2021-09-06 15:57:34 +02:00
Eric Espie
2aaac00015 N°3985 - Performance checks on the back end - Fix KPI logs 2021-09-06 14:16:42 +02:00
Stephen Abello
c46cd1c514 Add hover and active style to add caselog entry button 2021-09-03 11:27:37 +02:00
Stephen Abello
74d2a6e46c Activity form can now have extra inputs 2021-09-02 17:27:48 +02:00
Stephen Abello
1d57b4330b Correctly trigger iTop API when adding a caselog entry through quick edit 2021-09-02 17:27:48 +02:00
acognet
034516d0ef Fix on ready script 2021-09-02 15:29:53 +02:00
acognet
72d7758259 N°3905 - Polishing: CSV Import - typo + fix loading js for Panel 2021-09-02 15:26:07 +02:00
acognet
3e9a19b0ea Fix empty page size 2021-09-02 10:11:45 +02:00
Molkobain
6118ee6876 Update precompiled themes 2021-09-01 15:10:15 +02:00
Molkobain
fea3c719af Top bar: Force page title to stay on 1 line 2021-09-01 14:56:21 +02:00
Molkobain
78eda6a2fc N°3800 - Fix text color in code blocks for the activity entries (also update comment to explain both cases) 2021-09-01 14:29:07 +02:00
Molkobain
65db576654 PHPDoc 2021-09-01 09:55:28 +02:00
Pierre Goiffon
69bca189fd N°3800 Update compiled CSS 2021-08-31 16:53:21 +02:00
Pierre Goiffon
5b78820b32 N°3800 Fix color for highlighted code blocks
We want content in a simple code tag to be black
But the color set by Highligh.js must be kept
2021-08-31 16:44:59 +02:00
acognet
79954d3cee N°4259 - Migrate object-copier to itop 3.0 style 2021-08-31 12:07:32 +02:00
Molkobain
8a5c144e3b Fix typo 2021-08-31 09:30:15 +02:00
Stephen Abello
af28a2e01d Update precompiled stylesheets 2021-08-31 09:28:44 +02:00
Stephen Abello
55513b2f4b Move horizontal scroll from tabcontainer to tabs element 2021-08-31 09:26:00 +02:00
Molkobain
e4bf15feb3 Tab container: Hide ellipsis at first to only show if necessary (better UX) 2021-08-30 18:00:03 +02:00
Molkobain
0080caf55f N°2788 - Revert hand-made adjustments for some HTML as it is now handled by .ibo-is-html-content 2021-08-30 17:32:30 +02:00
Molkobain
aed8135d56 N°2788 - Improve how small/large fields value wrap without overlapping the content next to them 2021-08-30 17:32:29 +02:00
Pierre Goiffon
d0ba84068d N°3002 Better log deprecated call location
Now logs file location when called by a function
2021-08-30 16:43:30 +02:00
Pierre Goiffon
d6d1a5cc23 N°3002 Fix undefined index notice in \DeprecatedCallsLog::DeprecatedNoticesErrorHandler 2021-08-30 15:58:55 +02:00
Molkobain
6700de097a N°3712 - Activity panel: Fix origin icon for log entries 2021-08-27 17:28:01 +02:00
Molkobain
cf556de76e Add method to get number of entries of an ormCaseLog 2021-08-27 17:28:01 +02:00
Stephen Abello
72cddf30fb Update demo objects with fresher data 2021-08-27 10:55:36 +02:00
Stephen Abello
5ec6a1cc0c Fix sso buttons alignment with login inputs 2021-08-27 10:55:36 +02:00
Eric
fe0db8f357 N°3985 - Performance checks on the back end - Fix Session helper 2021-08-27 09:08:14 +02:00
Eric
1ab2b9c5d4 N°3985 - Performance checks on the back end - better KPI logs 2021-08-26 17:14:46 +02:00
Eric
67cd5e321e N°3985 - Performance checks on the back end - Fix Session helper 2021-08-26 16:14:14 +02:00
Eric
81d9ea389d N°3985 - Performance checks on the back end - Fix Session helper 2021-08-26 15:33:07 +02:00
Eric
3ee9757a85 🔊 Log when no Twig template is found in controller 2021-08-26 12:06:21 +02:00
Eric
97e0150974 N°3224 - migration audit tool - allow php functions in XPath 2021-08-26 11:54:45 +02:00
acognet
7f37c5912a N°3914 - Polishing: Lists - fix display of datatable and rename attribute for init data 2021-08-26 11:37:17 +02:00
Stephen Abello
2f5a1c99a5 Add variables to class icon size CSS classes 2021-08-26 11:22:31 +02:00
Eric
5ce9b6ca99 Merge branch 'develop' into SessionManagement 2021-08-26 10:28:43 +02:00
Eric
bd9286f903 N°3985 - Performance checks on the back end - Use Session helper 2021-08-26 10:27:26 +02:00
Molkobain
4ae7090a51 N°4062 - Advanced search: Fix visual glitch when submitting the search while the results are sticking 2021-08-25 20:55:58 +02:00
Stephen Abello
335074701f Update precompiled stylesheets 2021-08-25 16:57:26 +02:00
Stephen Abello
76f70d45dd N°4182 Large own caselog entries were not scrolling in activity panel 2021-08-25 16:34:29 +02:00
Stephen Abello
6f147acd76 Update precompiled stylesheets 2021-08-25 16:20:12 +02:00
Stephen Abello
a84d2ce6bb N°3928 Avoid double carret on multiselect 2021-08-25 16:18:56 +02:00
Stephen Abello
ea9c1ab0b3 Add helpers to set size to class icons 2021-08-25 16:18:56 +02:00
Molkobain
e1dc269171 SCSS: Rename variable to something more semantic lik in other blocks 2021-08-25 15:46:08 +02:00
Molkobain
16dc7de8e2 Rename method for consistency across the widget 2021-08-25 15:13:03 +02:00
Stephen Abello
88e210d84d N°3928 Use a more precise selector for tooltips singleton 2021-08-25 14:55:26 +02:00
Stephen Abello
4f6bd5444b N°3928 Create tooltip singleton for impact analysis matching elements (icon/text) 2021-08-25 14:34:40 +02:00
Stephen Abello
0f204f94eb Add helper to create tooltip singleton 2021-08-25 14:34:40 +02:00
Vincent Dumas
f5ae76360e Simple typo in declaration of an entry
No associated bug
2021-08-25 14:18:14 +02:00
vdumas
8d59024d8e N°463 use CDATA on oql tags 2021-08-25 14:13:14 +02:00
Molkobain
32e0031242 N°4254 - Fix items list not visible for external key in modals 2021-08-25 11:25:28 +02:00
Stephen Abello
3fdebdc217 Update precompiled stylesheets 2021-08-25 11:07:14 +02:00
Stephen Abello
7083807319 N°3928 Migrate impact analysis page to 3.0 style 2021-08-25 11:06:26 +02:00
Stephen Abello
0f01dbc3e5 Allow to add an icon to lists display block 2021-08-25 11:06:26 +02:00
Stephen Abello
8289b028cf N°3928 Limit impact analysis size 2021-08-25 11:06:25 +02:00
Stephen Abello
f72a6ee963 Hints that disabled tabs are not clickable 2021-08-25 11:06:25 +02:00
Stephen Abello
08359cdd05 N°3928 Replace legacy loading gif 2021-08-25 11:06:25 +02:00
Stephen Abello
de17439f55 N°3928 Remove function messing up tabs height while giving no real benefit 2021-08-25 11:06:25 +02:00
Stephen Abello
6e555e29d1 N°3928 Fix impact analysis not showing when displaying list first 2021-08-25 11:06:25 +02:00
Stephen Abello
9dae34461b Use tab widget prefix for our slightly modified tabs widgets 2021-08-25 11:06:25 +02:00
Stephen Abello
06b1e581fe N°3928 Use right tab widget in impact analysis and make sure widget is initialized before using it 2021-08-25 11:06:24 +02:00
acognet
d4b515c7b7 Fix id in checkbox 2021-08-25 10:31:33 +02:00
Molkobain
20759eca23 Fix "Configure this list" due to regression in 280afb35 2021-08-25 09:30:53 +02:00
Molkobain
4e420cbcd6 N°4062 - Advanced search: Fix sticky header glitches with pagination 2021-08-24 17:55:41 +02:00
vdumas
0e60c67910 N°463 Add 3 predefined OQL queries 2021-08-24 10:29:33 +02:00
Molkobain
808c1fa571 N°3712 - Activity panel: Fix origin indicator being displayed on all type of entries 2021-08-24 10:17:56 +02:00
Molkobain
dbf8475883 N°4256 - Fix CMDBChange origin to 'csv-interactive' on the CSV Import page 2021-08-24 10:01:44 +02:00
Eric
2c2155a8e0 N°3985 - Performance checks on the back end 2021-08-23 13:57:03 +02:00
Stephen Abello
ffbd94d671 Cleanup 2021-08-20 16:53:38 +02:00
Molkobain
3abcdc9c58 Rename CSS prefixes of autocomplete to match conventions 2021-08-20 16:50:16 +02:00
Molkobain
242f499101 Remove require as the class is handled by the autoloader 2021-08-20 16:50:16 +02:00
Molkobain
6b0106ff73 PHPDoc 2021-08-20 16:50:16 +02:00
acognet
bf991ffb8a N°3685 - Performance checks on the front end - Minimize size of generated javascript 2021-08-20 16:03:22 +02:00
acognet
280afb35a9 Datatable : on init load data for the first page 2021-08-20 15:54:34 +02:00
acognet
e095749c90 Fix typo 2021-08-20 15:54:34 +02:00
Stephen Abello
ced0e7cc8f N°4093 When clicking on a tab before tab widget is loaded, prevent AjaxTabs from redirecting our page to their target 2021-08-20 11:18:13 +02:00
Molkobain
6df98c3d41 N°4248 - Change demo samples icons for services / service families 2021-08-20 09:41:19 +02:00
Stephen Abello
21e16fd2e8 Make extension source clearer in setup and about box 2021-08-19 18:01:40 +02:00
Molkobain
bc2e25be99 N°3918 - Change missing object tooltip text to "Object not found" 2021-08-19 15:02:04 +02:00
Molkobain
0c5ebc3a84 N°1616 - Fix large HTML table overflowing in HTML fields or logs 2021-08-19 15:02:04 +02:00
Stephen Abello
43412b78e3 N°1632 Remove unused autoloader in UnauthenticatedWebPage 2021-08-19 14:08:21 +02:00
Eric
9126635cf2 Allow setup ends correctly when problem occurs 2021-08-19 13:50:16 +02:00
Eric
d0986c048a Allow setup again when problem occurs 2021-08-19 12:14:14 +02:00
Eric
fe0c52bedd themes 2021-08-19 11:48:26 +02:00
Eric
8926c6783a 🐛 scss reference was in bulma not in iTop scss 2021-08-19 11:48:25 +02:00
Stephen Abello
95b6dd0cc3 N°1632 Add a common webpage to be used for unauthenticated/token based actions, guarantees harmony between extensions style and a common API 2021-08-19 11:41:01 +02:00
Eric
121e39b738 fix themes 2021-08-19 11:26:31 +02:00
Eric
48dee9c136 🐛 remove undefined scss reference 2021-08-19 10:55:58 +02:00
Eric
befde44215 🐛 fix non-existing variable 2021-08-19 10:41:36 +02:00
acognet
a827eed59d Restore unwanted changes 2021-08-19 10:41:18 +02:00
Molkobain
1613c1bbdc Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	application/itopwebpage.class.inc.php
#	core/config.class.inc.php
#	setup/setuputils.class.inc.php
2021-08-18 18:55:56 +02:00
Molkobain
909af7f59c JSDoc 2021-08-18 18:53:42 +02:00
vdumas
495b39a7ab N°4246 - Add missing class parameter 2021-08-18 17:05:16 +02:00
vdumas
f9ff66941d N°4079 - FR Dictionnary typo 2021-08-18 17:03:14 +02:00
acognet
29871bc6da Fix precompiled css 2021-08-18 16:49:52 +02:00
Molkobain
1c983e8093 Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	core/config.class.inc.php
#	datamodels/2.x/itop-portal-base/portal/src/controllers/objectcontroller.class.inc.php
#	pages/ajax.render.php
2021-08-18 16:12:22 +02:00
Molkobain
92a9a8c65f N°4129 - Security hardening 2021-08-18 15:57:18 +02:00
Federico Lazcano
a3e1b95c8e Update install.txt
Change old URL for new, linking to iTop Hub.
2021-08-18 14:35:35 +02:00
acognet
bf2d98a1bf N°580 - Jean Dupont - Jean Dupont, auto-complete avec homonyme 2021-08-18 10:41:38 +02:00
acognet
abe103eade N°580 - Jean Dupont - Jean Dupont, auto-complete avec homonyme 2021-08-18 09:32:26 +02:00
acognet
034052cf4b avoid 404 error when loading image in autocomplete 2021-08-18 09:32:26 +02:00
Molkobain
4458f26379 N°3750 - Behat: Add metadata about logs label 2021-08-17 17:49:22 +02:00
Molkobain
007e1ded0d N°3786 - Fix unload XHR call being always sent, even when no draft entries 2021-08-17 16:11:21 +02:00
Molkobain
5651512f68 N°4244 - Add protection against unfortunate massive delete of inline images / attachments when a null temp ID is passed 2021-08-17 15:58:52 +02:00
Molkobain
8c043f137c N°3750 - Behat: Add missing metadata to DesignerFormField 2021-08-17 10:01:22 +02:00
acognet
b3cce54ee9 Fix precompiled css 2021-08-17 10:00:19 +02:00
acognet
e4e4e3b0bf Fix precompiled css 2021-08-17 09:18:58 +02:00
acognet
1cb3b4bd96 Remove lines in double 2021-08-16 21:56:39 +02:00
acognet
97ee6570d2 N°3572 - Migrate backoffice pages to new UIBlock system : Toolkit 2021-08-16 15:17:05 +02:00
acognet
8c8f711fe8 N°3551 - Migrate module to new UIBlock system : Customer Survey 2021-08-16 15:16:08 +02:00
acognet
f140efd95c N°4007 - When a search is on auto submit, auto submit it also on first display - new fix in order to avoid reload in case of OQLMenuNode - rollback some deleted lines 2021-08-16 12:53:27 +02:00
acognet
6b19758654 Add deprecated 2021-08-16 11:24:58 +02:00
acognet
2899c82ef2 Fix Typo 2021-08-16 09:55:40 +02:00
acognet
12c2929f1d Context menu remains in place while scrolling 2021-08-16 09:54:51 +02:00
acognet
9d28e43804 N°4232 - Order By error on query with two classes 2021-08-16 09:53:19 +02:00
Molkobain
27217815d1 N°2510 - Fix expand/collapse buttons of log entries in a list 2021-08-16 09:37:36 +02:00
Molkobain
8e3cc471df N°1836 - Cancel of an object creation form now redirects to the search page of the same class (instead of just showing "operation cancelled") 2021-08-14 23:33:21 +02:00
Molkobain
58e35ea33b N°1047 - Replace hard coded 'iTop' occurrences with ITOP_APPLICATION_SHORT 2021-08-14 22:43:29 +02:00
Stephen Abello
0b81601699 N°3913 Allow iTop Hub iframe to fully display after setup 2021-08-13 17:46:24 +02:00
Stephen Abello
4d3ba6edd0 N°3913 Make setup's collapsable sections' arrow clickable 2021-08-13 17:08:26 +02:00
Stephen Abello
9de014c9cb Add favicon to setup pages 2021-08-13 15:54:43 +02:00
Stephen Abello
75dbaada72 Update favicon style 2021-08-13 15:52:34 +02:00
Stephen Abello
0d4dd0c67b Harmonize iTop's logo and fluent icons 2021-08-13 15:28:17 +02:00
Stephen Abello
fabdef37d2 N°3913 UI improvements for setup, also remove A LOT of <table> 😬 2021-08-13 12:23:52 +02:00
Molkobain
e666631f63 N°3918 - Restore style on broken wiki links (also add a tooltip to explain what it means) 2021-08-13 11:56:40 +02:00
odain
280feca863 Revert "N°4225 - Protect manual backups from cron (and vice versa) - minimal work ie protect manual backup from cron only"
This reverts commit e3dc1b77cc.
2021-08-13 11:16:48 +02:00
DudekArtur
7690e43b39 Update pl.dictionary.itop.core.php 2021-08-13 10:11:16 +02:00
Molkobain
0c66882990 N°3918 - Fix regression on mentions display introduced by 7af10e51 2021-08-12 21:04:50 +02:00
Molkobain
7613ac7a9b Graphviz: Remove generated SVG image after usage as it won't be cached 2021-08-12 19:56:02 +02:00
Molkobain
7af10e5197 N°3918 - Fix wiki syntax "[[CLASS:ID]]" not working in logs 2021-08-12 17:28:50 +02:00
odain
095c975ec6 N°4227 / N°4225 - require cleanup + fix manual restore 2021-08-12 16:25:50 +02:00
odain
9e1e5a8a47 N°4227 - Manual iTop restore - protect any restore from cron or db updates and release readonly mode afterward only if restore set it itself 2021-08-12 16:25:50 +02:00
odain
2c026fa891 N°4225 - Protect manual backups from cron (and vice versa) - protect any backup from cron/db updates and release readonly mode only when backup set it itself 2021-08-12 16:25:50 +02:00
odain
00d65aeb45 N°4227 - Manual iTop restore - create manual CLI restore 2021-08-12 16:25:50 +02:00
odain
5702f603ac N°4227 - Manual iTop restore - move restore mutex management inside in DBRestore->RestoreFromCompressedBackup primitive 2021-08-12 16:25:50 +02:00
odain
e3dc1b77cc N°4225 - Protect manual backups from cron (and vice versa) - minimal work ie protect manual backup from cron only 2021-08-12 16:25:50 +02:00
Stephen Abello
c304f70ff4 Harmonize external key's autocomplete items display with dropdown ones 2021-08-12 14:40:36 +02:00
Stephen Abello
53fd41e748 N°4127 Fix XSS vulnerability in autocomplete lists 2021-08-12 14:21:05 +02:00
Molkobain
7577fbb8bf N°4236 - Fix user with no admin right can't connect in iTop when log_usage set to true 2021-08-12 11:13:59 +02:00
Molkobain
0fc912b357 Rename MetaModel::IsObjectExistsInDb() to MetaModel::IsObjectInDB() 2021-08-12 09:37:24 +02:00
Molkobain
c475e66176 Add documentation 2021-08-12 09:35:14 +02:00
Pierre Goiffon
cd1ba097cb N°3867 Fix error "LEVEL_WARNING of type Identifier is forbidden" error when saving valid config in configuration editor 2021-08-11 18:07:38 +02:00
Molkobain
fdca4d4cc3 N°3786 - Fix object locked hint (on activity panel) not displayed until message removed 2021-08-11 17:41:31 +02:00
Pierre Goiffon
4379b4d908 N°3800 Fix HTML content display for table borders v2 2021-08-11 17:31:08 +02:00
Pierre Goiffon
5b42f67a99 N°3867 Code review: remove condition that is quite too strict (danger !!)
Thanks @odain !
2021-08-11 17:22:21 +02:00
Pierre Goiffon
0b9ccc8e67 N°3800 Fix HTML content display for table borders and code color 2021-08-11 17:08:00 +02:00
Pierre Goiffon
2d98ca2318 N°3867 Fix "Invalid configuration: Stmt_Expression is forbidden in line 10" error when saving valid config in configuration editor
Now this is tested in \ConfigValidator\iTopConfigAstValidatorTest
2021-08-11 16:38:56 +02:00
odain
92add2bbfe add annotation to datasynchro test 2021-08-11 10:17:35 +02:00
Pierre Goiffon
f15bdb75ca N°4173 Fix memory_limit error on target object hyperlink generation 2021-08-10 19:08:00 +02:00
Pierre Goiffon
a66830de17 N°4173 Fix memory_limit error when saving an object pointing to a big AttributeBlob
Check of pointed object was loading the whole object instead of just doing a count
2021-08-10 19:08:00 +02:00
Pierre Goiffon
714294e1b4 N°4173 Fix memory_limit exhausted when having ExtKey widget pointing on class with AttributeBlob
Was failing when opening an object form, and when the list contained target objects with total file size above memory_limit
2021-08-10 18:46:10 +02:00
Molkobain
e3d2c1d761 Advanced search: Restore "more criteria" inputs color 2021-08-10 16:27:08 +02:00
Molkobain
59d95cc14b Field: Change how field's value wrap to fix unwanted "new line" between some elements (lists, ...) 2021-08-10 16:27:08 +02:00
Pierre Goiffon
ddc5bbd1bb N°3867 Fix write config now removes PHP vars
Now the PhpParser tree has a different structure, beginning with a PhpParser\Node\Stmt\Expression
2021-08-10 15:47:01 +02:00
Pierre Goiffon
9bbee0d603 ⬆️ N°3867 Upgrade php-parser from 3.1.5 to latest version 4.12.0
The 3.1.5 version wasn't maintained anymore and was compatible with PHP 7.2 maximum
2021-08-10 15:45:02 +02:00
acognet
be1ef5b452 N°3634 - Feedback alpha 3.0 : finish list - display printable object 2021-08-10 12:10:54 +02:00
Pierre Goiffon
cbdc48b7e1 iTopConfigParserTest now works on Windows 2021-08-10 11:48:13 +02:00
denis.flaven@combodo.com
bb5679959e Fixed unit tests for password_renewed_date, broken by the correction of
n°4095.
2021-08-10 10:40:54 +02:00
Molkobain
cdbb4470fc N°4039 - Add margin below an object details
- Easier read of the fields at the bottom of it
- Better display of a dropdown at the bottom of it
2021-08-09 17:20:56 +02:00
Molkobain
252d752bf5 Navigation menu: Improve french translations for the current user tooltip 2021-08-09 17:20:56 +02:00
denis.flaven@combodo.com
99d0c05c1c N°4095 - Provisions for future implementation of users password
expiration.
2021-08-09 17:13:08 +02:00
Molkobain
5926e9d110 Navigation menu: Add current user's login to the tooltip 2021-08-09 16:28:53 +02:00
Molkobain
c8dd8c3806 Code cleanup: Remove forgotten commented line 2021-08-09 13:54:02 +02:00
Molkobain
70b07721e6 N°2875 - Fix typo in config example 2021-08-09 10:46:42 +02:00
Molkobain
bd050dfe69 N°2875 - Add possibility to configure the marker scope by either a class or an OQL 2021-08-09 10:38:27 +02:00
Molkobain
9eb477ce83 N°2875 - Fix visual glitches on long results
- Medallion could be horizontally compressed
- Title wrapped instead of overflowing, making reading across entries difficult
2021-08-09 10:38:27 +02:00
Pierre Goiffon
a742b6c610 🔊 N°3002 DeprecatedCallsLog error handler : add trigger_error message 2021-08-09 09:06:17 +02:00
Pierre Goiffon
fcf769666e N°3913 setup : in "done" step, add back styling on HTML content 2021-08-06 17:59:42 +02:00
Pierre Goiffon
72e628c5d5 💡 Reference in PHPDoc for \LogAPI::GetMinLogLevel 2021-08-06 17:39:34 +02:00
Pierre Goiffon
bf28602ae6 💡 Improve PHPDoc for \LogAPI::GetMinLogLevel 2021-08-06 17:37:56 +02:00
Pierre Goiffon
b8a0d899f4 Fix \coreExtensions\UserLocalTest::testValidatePassword failing because of DEPRECATED notices 2021-08-06 17:13:24 +02:00
Pierre Goiffon
d335736cfc 🔊 N°3002 Add trigger_error to catch deprecated notices inside DeprecatedCallsLog
They are logged as WARNING level in \DeprecatedCallsLog::ENUM_CHANNEL_PHP_LIBMETHOD channel

Such deprecated notices are generated inside Symfony for example using @trigger_error(..., E_DEPRECATED).
Having such a log will help us migrate to the next lib version !
2021-08-06 17:13:24 +02:00
Molkobain
80f7d07378 N°3592 - Fix alignment of custom fields in the backoffice 2021-08-06 17:04:26 +02:00
Molkobain
0be6a8aef4 N°3592 - Remove part of 146a95bae as it was unnecessary 2021-08-06 17:04:26 +02:00
Stephen Abello
0fe857071d Fix login css glitches with iTop 3.0 2021-08-06 15:41:43 +02:00
acognet
05981c8af8 N°4156 - GUI broken when a external key contains "\" 2021-08-06 11:56:25 +02:00
Molkobain
0abea749fa N°3786 - Fix lock removal when leaving an object details page in read-only with lock on the activity panel 2021-08-06 11:12:56 +02:00
Molkobain
78af6fdc84 N°3944 - Add comment to explain the 2 similar IFs 2021-08-06 11:11:57 +02:00
acognet
1e97b5a8c0 Revert N°3423 - Allow AttributeImage / AttributeDocument content to be cached by the browser + N°4029 - Caching images in chrome does not work 2021-08-06 09:51:59 +02:00
acognet
0214243b63 N°3914 - Polishing: Lists - remove pagination when it is unnecessary 2021-08-06 09:19:31 +02:00
Pierre Goiffon
d30871ac59 Revert "N°3002 Add trigger_error to catch deprecated notices inside DeprecatedCallsLog"
This reverts commit d247ea915d.
Will solve CI build errors... I will work in my own branch to tweak this !
2021-08-05 17:35:17 +02:00
Pierre Goiffon
d247ea915d N°3002 Add trigger_error to catch deprecated notices inside DeprecatedCallsLog
Such notices are generated inside Symfony for example using @trigger_error(..., E_DEPRECATED).
Having such a log will help us migrate to the next version !
2021-08-05 17:18:19 +02:00
acognet
0e0aed1ba4 N°3423 - Allow AttributeImage / AttributeDocument content to be cached by the browser + N°4029 - Caching images in chrome does not work 2021-08-05 16:34:24 +02:00
acognet
bc770ef3d5 N°4007 - When a search is on auto submit, auto submit it also on first display - new fix in order to avoid reload in case of OQLMenuNode -add param in searchFormHandler 2021-08-05 16:20:56 +02:00
Pierre Goiffon
56a4fb0b42 Allow to run all tests from within the IDE
Just :
* configure the config file (test\phpunit.xml.dist)
* add runner parameters : --fail-on-risky --exclude-group beforeSetup
* specify iTop root as custom working directory
2021-08-05 15:21:41 +02:00
acognet
3139628dd8 N°4007 - When a search is on auto submit, auto submit it also on first display - new fix in order to avoid reload in case of OQLMenuNode 2021-08-05 15:08:48 +02:00
acognet
7d9b19cd9e N°4119 - Loose application context in advanced search ajax call 2021-08-05 12:15:47 +02:00
Stephen Abello
b3cb95d2f1 Removed inline background color 2021-08-05 11:56:17 +02:00
Stephen Abello
a6765cdc3a Update precompiled stylesheets 2021-08-05 10:38:40 +02:00
Stephen Abello
97d52fb539 N°3685 Revert most of e4f58b5b changes, replace @extend .ibo-button calls with classes in markup for most cases, except jquery-ui buttons 2021-08-05 10:20:30 +02:00
Pierre Goiffon
ad936d7a2f 🔇 N°3731 Remove DeprecatedCallLog in \MetaModel::BulkUpdate
Method is still called in \ObsolescenceDateUpdater !
2021-08-04 17:37:10 +02:00
Pierre Goiffon
090eb9a560 🔇 N°3731 Remove DeprecatedCallLog in \MetaModel::GetFilterCodeOrigin
Method is still called !
2021-08-04 17:34:13 +02:00
Stephen Abello
e4f58b5b98 N°3685 Greatly optimize SCSS rules to reduce compiled CSS file size (4.7Mo -> 620ko) 2021-08-04 16:38:40 +02:00
acognet
c99a22c9f7 N°4025 - Universal search : cannot select class anymore 2021-08-04 14:41:25 +02:00
Pierre Goiffon
29cf20beaf N°3909 Fix notification configuration help layout 2021-08-04 12:00:48 +02:00
denis.flaven@combodo.com
e325d535ae N°4096 - Add automatic email reprocessing in case of error 2021-08-04 11:24:59 +02:00
Pierre Goiffon
11cfdb2a17 N°3807 Fix container added for all Html components
This was causing issues for example in the setup, as any raw content is sent using \WebPage::add, which create an HTML component.
I reverted the layout update, and created a new factory method to be used when needed : \Combodo\iTop\Application\UI\Base\Component\Html\HtmlFactory::MakeHtmlContent
2021-08-04 11:19:35 +02:00
Pierre Goiffon
66720b9731 N°3807 Update theme CSS 2021-08-04 11:19:35 +02:00
acognet
234f46cafa N°1731 - Allow Transitions without unnecessary confirmation 2021-08-04 10:51:04 +02:00
acognet
27c3ce0389 N°3907 - Polishing: Run query - Add dictionary entry 2021-08-04 10:44:26 +02:00
Pierre Goiffon
9d0e2fa64a N°3807 Bring back styling to raw HTML content
Bulma minireset (https://github.com/jgthms/bulma/blob/master/sass/base/minireset.sass) was applied everywhere in iTop. This was causing HTML content without any Bulma or iTop 3.0.* CSS classes to render with no styles anymore, not even the default browser's ones. Especially rendering for content styled in CK Editor was problematic...

This commit creates a new `ibo-is-html-content` CSS class (in css/backoffice/utils/helpers/_misc.scss) that just extends the `content` Bulma class (indirection to reduce framework coupling).
This new iTop CSS class is added in :
* AttributeText and its children when format is HTML
* HTML components
* activity entries in HTML format

The class can also be used elsewhere when needed, for example in modules having custom pages that aren't using yet the iTop 3.0.* UI components or CSS classes.
2021-08-04 10:37:54 +02:00
acognet
e211633fed N°4039 - List contain stays in place when scrolling on a screen 2021-08-04 10:37:02 +02:00
denis.flaven@combodo.com
29967aa41a N°3944 - LogAPI : fix default log level in config when logging using a channel 2021-08-04 10:07:58 +02:00
Pierre Goiffon
3ebb1cfc66 💡 phpDoc 2021-08-03 17:15:38 +02:00
Molkobain
6c2221b8b6 Datatables: Remove extra white space in template 2021-08-03 16:16:21 +02:00
Molkobain
c0b3aed12c N°3712 - Code cleanup thanks to @piR 2021-08-03 16:15:09 +02:00
Stephen Abello
53efc9f75e Update precompiled stylesheets 2021-08-03 15:55:06 +02:00
Stephen Abello
0d566f2e47 Fix panel collapsible toggler display 2021-08-03 15:49:27 +02:00
Stephen Abello
b294e3c734 N°3928 Correctly align impact analysis's filter refresh button 2021-08-03 15:49:27 +02:00
Stephen Abello
6704f9eccf N°3928 Allow user to collapse impact analysis' filter 2021-08-03 15:49:27 +02:00
Molkobain
90cb6e1d49 N°4124 - Extract computations into variables for easier comprehension 2021-08-03 11:37:01 +02:00
Molkobain
c0aa4f2d69 Initialize array properly 2021-08-03 11:11:02 +02:00
Molkobain
01984c24c0 Fix wrong usage of spaceless filter 2021-08-02 20:15:16 +02:00
Molkobain
1da1e0b1bd N°3712 - Activity panel: Improve history entries to have a different icon depending the origin (interactive, webservices, csv, ...) 2021-08-02 19:42:32 +02:00
Molkobain
39bcd3e4cd 🌐 N°3712 - Add dict. entries for CMDBChange->origin values 2021-08-02 19:42:32 +02:00
Molkobain
156cce6098 N°3712 - Extract CMDBChange origin values in a dedicated class 2021-08-02 19:42:32 +02:00
acognet
3130e95f4f N°3907 - Polishing: Run query 2021-08-02 18:56:07 +02:00
Molkobain
e28f704f3e N°4076 - Revert regression in global search from 344cce9fd
Current query was not visible when reaching the results page
2021-08-02 15:20:05 +02:00
Stephen Abello
5c6c59941a N°3901 Correctly hide menu search placeholder 2021-08-02 15:18:06 +02:00
Stephen Abello
bc9d47933e Update precompiled stylesheets 2021-08-02 11:43:28 +02:00
Stephen Abello
07a10e4146 N°3930 Fix dashlet blocker position 2021-08-02 11:42:57 +02:00
Stephen Abello
e8a21870ad Update precompiled stylesheets 2021-08-02 11:28:37 +02:00
Stephen Abello
2e132d5c53 N°3930 Restore dashlet blocker on dashboard editor 2021-08-02 11:28:37 +02:00
Eric
3359609349 Allow mode selection for queries 2021-07-31 15:23:19 +02:00
Molkobain
2966759466 Code cleanup 2021-07-30 17:09:51 +02:00
Molkobain
25395405e5 N°3905 - Remove remaining spaces 2021-07-30 17:09:50 +02:00
Stephen Abello
b589e2d001 Update precompiled stylesheets 2021-07-30 16:48:48 +02:00
Stephen Abello
27f3619cf5 Fix undefined variable used in scss 2021-07-30 16:48:23 +02:00
Stephen Abello
616fc436d0 CSS improvements 2021-07-30 16:40:33 +02:00
acognet
4f2f765207 N°3912 - Polishing: Export - fix page webservices/export.php - revert delete of utils.js 2021-07-30 15:16:51 +02:00
Pierre Goiffon
9931fa1a6b 🎨 N°4092 rename method
Thanks @Molkobain !
2021-07-30 12:09:30 +02:00
Pierre Goiffon
a13f2750ea 🎨 Replace call_user_func call to \cmdbAbstractObject::GetShortcutActions for better IDE recognition
And also :
* removed an obsolete use statement
* fix method phpdoc
2021-07-30 11:41:41 +02:00
Stephen Abello
243d105f59 Fix return value from new method added in 49fd482 2021-07-30 10:54:16 +02:00
Stephen Abello
7783ba570e PHPDoc 2021-07-30 10:37:52 +02:00
acognet
5a9fa2ac32 N°3912 - Polishing: Export - fix page webservices/export.php 2021-07-29 17:59:51 +02:00
Pierre Goiffon
619e3de5a8 N°4092 Setup : add symlinks option in install
Was only available during update
2021-07-29 17:34:24 +02:00
Pierre Goiffon
83064d68c7 N°4092 Setup : symlink option now always displayed if functionality enabled
Previously we were also testing for flag presence.
In consequence the confirmation dialog when unchecking the option is also removed (we can enable back the option using the setup)
2021-07-29 17:24:20 +02:00
Stephen Abello
f3c11e72cf N°3552 Add method to retrieve User object from Person object 2021-07-29 16:37:03 +02:00
Stephen Abello
c9e887a264 N°3552 Allow AddLogEntry to set entry's user_id from another user using a new parameter 2021-07-29 16:37:02 +02:00
Stephen Abello
49fd482389 N°3552 Correctly display case log entry with no iTop user linked (such as mail to ticket entries) 2021-07-29 16:37:02 +02:00
acognet
96de4e1796 N°4117 - Text field display, too many empty lines 2021-07-29 11:52:39 +02:00
acognet
44f413583c N°4124 - Unable to scroll down on some object 2021-07-29 11:38:20 +02:00
acognet
91104002ea N°4037 - Missing close button on list export on portal - rollback commit for N°3746 2021-07-28 16:02:35 +02:00
acognet
f98ba1594c N°3705 - Migrate module to new UIBlock system : Kanban board - css and dictionnary in ajax page 2021-07-28 16:02:35 +02:00
Molkobain
431dc5532b Change comment / test for clarification 2021-07-28 15:59:43 +02:00
Molkobain
df473ae313 PHPDoc 2021-07-28 15:31:22 +02:00
Molkobain
40ce74cffa N°4203 - Activity panel: Add button to load all entries at once 2021-07-28 14:58:15 +02:00
Molkobain
7598c18ad6 N°4203 - Activity panel: Hide "load more entries" button when only "logs" filter is active 2021-07-28 14:55:17 +02:00
Molkobain
d38b655f5f Activity panel: Limit visual glitches on entries on first display by hiding them all before displaying only the relevant.
Otherwise, entries from the other logs / activity tabs are visible for a second before filtering on the entry of the current tab only.
2021-07-28 14:55:17 +02:00
Eric
f4345ef312 N°4199 - Add <code> to EnumSet values to fix XML conversion 2021-07-28 14:40:19 +02:00
Eric
13b548e95d N°4199 - Add <code> to EnumSet values to fix XML conversion 2021-07-28 14:39:52 +02:00
Eric
3a988ab499 N°4175 - Adding a lifecycle to an existing class fails on setup (using xml version < 3.0) 2021-07-28 13:30:39 +02:00
Eric
14a5f87d62 N°4036 - User edition controls : a user cannot remove contact 2021-07-28 13:09:18 +02:00
Eric
8dae459b12 N°4036 - User edition controls : the profiles selection should allow the User modification (when editing your own User) 2021-07-28 11:45:02 +02:00
odain
2fe4265223 N°4125 - Make translations loading more robust toward APCu cache corruption or invalid dictionnary - adaptations to get current correction accepted 2021-07-28 11:14:49 +02:00
Eric
8dc10424e8 🎨 cleanup code 2021-07-28 09:59:10 +02:00
Eric
54a6573948 N°4036 - User edition controls : the profiles selection should allow the User modification (when editing your own User) 2021-07-28 09:13:47 +02:00
Eric
1d5e0b6fe9 Temporary ignored test for CI 2021-07-27 18:01:39 +02:00
Eric
acb8a377dd N°4036 - User edition controls : a user cannot change his own status (fix) 2021-07-27 17:40:00 +02:00
odain
d86f489c89 fix provided themes to avoid scss setup compilation 2021-07-27 17:22:24 +02:00
Eric
2c154b601d N°4036 - User edition controls : allowed orgs must contain user org 2021-07-27 15:57:03 +02:00
Eric
7dad079688 N°4036 - User edition controls : a user cannot remove contact 2021-07-27 15:57:03 +02:00
Eric
ace2eb6dab N°4036 - User edition controls : a user cannot change his own status 2021-07-27 15:57:03 +02:00
Eric
25f3c1cbc4 N°4036 - User edition controls : a user cannot add to himself a profile denying the backoffice 2021-07-27 15:57:03 +02:00
Eric
8f7e7c136d Fix links when object edition fails 2021-07-27 15:57:03 +02:00
Eric
71a7e060e4 N°4036 - User edition controls : a user cannot delete himself 2021-07-27 15:57:03 +02:00
Pierre Goiffon
c450f1d02f 💡 aModifierProperties documentation 2021-07-27 15:54:47 +02:00
acognet
4431762c10 N°3592 - Migrate module to new UIBlock system : Customized request forms - precompiled css v2 2021-07-27 15:33:47 +02:00
acognet
97170892e6 N°3905 - Polishing: CSV Import - remove spaces 2021-07-27 15:08:38 +02:00
acognet
5137d634e3 N°3592 - Migrate module to new UIBlock system : Customized request forms - precompiled css 2021-07-27 15:03:04 +02:00
acognet
146a95baec N°3592 - Migrate module to new UIBlock system : Customized request forms - remove space in edit screen 2021-07-27 14:38:44 +02:00
Pierre Goiffon
2b71ea108a Setup memory_limit check : clearer message
Now the current value is displayed as entered in the PHP conf
And the recommended value is displayed in a friendly format (32M instead of raw bytes value)
2021-07-27 11:37:05 +02:00
Molkobain
a7ac9126a2 PHPDoc 2021-07-26 18:07:12 +02:00
Eric
ee544b646d N°4076 - PHPDoc 2021-07-26 17:48:36 +02:00
Eric
344cce9fdd N°4076 - Allow block parameters to change the behaviour of blocks on the page 2021-07-26 17:20:45 +02:00
Stephen Abello
bfcfcdd4cc N°3930 Fix dashlet group by preview not displaying 2021-07-26 14:26:44 +02:00
Molkobain
4410bf7e1f N°4144 - Portal: Fix caselog fullscreen icon too small to be clickable 2021-07-26 12:07:49 +02:00
Eric
d1fda1dbc6 composer classmap changed 2021-07-23 16:47:15 +02:00
Stephen Abello
5c702be641 Update precompiled themes 2021-07-23 11:29:33 +02:00
Stephen Abello
8a9ad78e9c N°3930 Bring back error icons on dashlet property 2021-07-23 11:29:33 +02:00
Molkobain
778be8abce N°4195 - Avoid dictionary entries to be added to the setup page as it breaks the fresh install
In fresh install there is no env-xxx yet, so when the setup tries to load the english dictionary from there it crashes.
In setup pages, all string are hard coded, no dictionary entries are available (yet)
2021-07-23 09:00:19 +02:00
Molkobain
0760adcef6 Object details: Fix status code being set to the color instead of the code 2021-07-22 18:12:11 +02:00
Pierre Goiffon
29ca291860 N°4192 Fix error on Contract classes object details
Was crashing on all classes without state attribute, or with state attribute nullable
2021-07-22 11:07:07 +02:00
Stephen Abello
93d0e4ae7c Update jQuery datepicker z-index 2021-07-22 10:43:22 +02:00
Molkobain
61bc07b598 Add PHPDoc to explain behavior change (as in the migration notes) 2021-07-21 17:46:39 +02:00
Pierre Goiffon
00ee36f938 Merge remote-tracking branch 'origin/support/2.7' into develop
# Conflicts:
#	README.md
2021-07-21 12:22:20 +02:00
Pierre Goiffon
1aa5185c93 Merge remote-tracking branch 'origin/support/2.6' into support/2.7
# Conflicts:
#	README.md
2021-07-21 12:19:52 +02:00
Pierre Goiffon
834ac00d37 📝 README : update latest releases
Was made in #143 but on develop only, but we are still maintaining older branches !
2021-07-21 12:15:22 +02:00
Molkobain
957cb87b8d N°3786 - Fix lock removal when leaving an object details page in edition
The main problem was WebPage::$a_scripts are now printed after the DOM when the mechanism actually prints some JS to redirect to another page immediately.
As there are a LOT of calls to WebPage::add_script(), we kept it to ensure the compatibility; and we add a new WebPage::add_early_script() for JS snippets that explicitly need to be execute before the DOM interpretation.
2021-07-20 20:13:44 +02:00
Eric
d0813f6607 N°4169 - Fix forms properties for designer 2021-07-20 17:49:30 +02:00
Stephen Abello
cf4673d284 Update precompiled stylesheets 2021-07-20 10:21:06 +02:00
Stephen Abello
e3422f5fd9 CSS improvements 2021-07-20 10:20:31 +02:00
Stephen Abello
d7a0878a39 Fix broken variables import in 3.0 themes 2021-07-20 10:04:12 +02:00
Molkobain
076f0e00a7 N°4178 - Stay on the same page when logging again from the "Login again" prompt 2021-07-18 22:58:33 +02:00
Molkobain
eb04ecb5b4 Fix new URL parameter being append after the '#' in CombodoGlobalToolbox.AddParameterToUrl 2021-07-18 22:37:01 +02:00
Molkobain
3323d5532b JSDoc 2021-07-18 22:04:39 +02:00
Molkobain
d68d8204f2 N°4176 - Portal: Deprecate "AddParameterToUrl" function 2021-07-18 22:02:47 +02:00
Molkobain
4a50b95069 N°3924 - Fix misleading orphan activity entries when creating an object 2021-07-17 00:11:16 +02:00
Molkobain
fd9e4f413c N°3924 - Fix missing activity panel on object details when cancelling transition form 2021-07-16 22:53:28 +02:00
Molkobain
dca3fc996c N°3924 - Fix double encoding of the object name in transition page title 2021-07-16 22:39:15 +02:00
Molkobain
c58c1bbf1d N°3924 - Fix notification link in activity panel not opening notifications tab 2021-07-16 22:29:54 +02:00
Molkobain
524919b946 N°4171 - Remove lock message from the log entry form when object is in edition 2021-07-16 20:13:49 +02:00
Molkobain
e15953524a N°3786 - Add pause at the end of the page unload async request to follow the guideline used in N°2763 2021-07-16 20:08:25 +02:00
Molkobain
68f3c53faa N°4171 - Concurrent lock: Fix expiration modal being duplicated sometimes 2021-07-16 16:44:35 +02:00
Molkobain
82e3ddaacd N°4142 - Improve backoffice rendering by showing system avatar no matter what 2021-07-15 21:34:58 +02:00
Molkobain
dfbbee2a1c N°4142 - Add config. param. to hide user avatars in the GUIs -mostly in logs- (backoffice, end-users portal, ...) 2021-07-15 21:23:20 +02:00
Molkobain
4843545171 N°4142 - Fix UserRights::GetUserPictureAbsUrl() returning user's placeholder picture for users with an unknown login 2021-07-15 17:33:38 +02:00
Molkobain
4e58b8616a N°3203 - PHPDoc and small variable refactor 2021-07-15 17:31:30 +02:00
Molkobain
1a79dcd773 N°3203 - Portal: Fix image attribute of an object not authorized if object out of scope 2021-07-15 11:41:07 +02:00
Molkobain
a4104d4315 N°3539 - Remove viewport meta tag as we won't be able to make the backoffice responsive in 3.0 2021-07-15 09:09:47 +02:00
Molkobain
4e1db7d7e2 Merge remote-tracking branch 'origin/support/2.7' into develop 2021-07-13 11:44:42 +02:00
Molkobain
8e6379a112 Merge branch 'support/2.7.5' into support/2.7 2021-07-13 11:42:30 +02:00
Molkobain
da217a1cb3 N°4161 - Fix ManageBrick crash when no item listed 2021-07-12 18:10:22 +02:00
Pierre Goiffon
a683634a05 N°4126 Fix HTML escaped in \SetupUtils::CheckDbServer messages
As content is sent to JS returned to the AJAX request, we need to escape JS string delimiter (single quote)
We had previously a \utils::HtmlEntities call, but this isn't necessary as all content is generated internally, without calling any dict or extensibility interface.
2021-07-12 14:41:26 +02:00
Molkobain
2f1b5d2736 Fix typo in method parameter 2021-07-12 12:47:43 +02:00
Molkobain
c9bf784fce Revert space introduced by 418312bca 2021-07-12 11:37:17 +02:00
Molkobain
4ef10ae7c9 PHPDoc 2021-07-12 10:58:38 +02:00
Molkobain
5174250ff1 N°3836 - Dashlet: Refactor part of the code to match conventions 2021-07-12 10:51:45 +02:00
Pierre Goiffon
7b6ac202c6 N°4518 Add config parameter to set platform as dev env (#220)
developer_mode.enabled, default value null
If true or false then will be used by \utils::IsDevelopmentEnvironment as return value, in all other cases will follow previous behavior
2021-07-12 09:27:36 +02:00
Molkobain
d960183403 Merge remote-tracking branch 'origin/support/3.0.0-beta2' into develop 2021-07-09 16:28:00 +02:00
Eric
ece3e0490d N°3573 - Allow retrieving operation
(cherry picked from commit e6a38a8055)
2021-07-09 15:24:20 +02:00
Eric
1562cb1f38 🎨 Allow tab stickiness for twig based extensions
(cherry picked from commit 1a7755365c)
2021-07-09 15:23:35 +02:00
Molkobain
11a22abfd5 SCSS: Fix horizontal scrollbars being ticker than vertical ones on webkit browsers 2021-07-09 12:52:32 +02:00
Stephen Abello
5254c9a633 N°3930 Fix dashlets select property with a set size 2021-07-08 10:32:41 +02:00
Stephen Abello
f7a35072f5 N°4075 Fix autocompletes in modals 2021-07-07 16:59:50 +02:00
Molkobain
b5f5780f35 Merge remote-tracking branch 'origin/support/3.0.0-beta2' into develop
# Conflicts:
#	datamodels/2.x/itop-structure/precompiled-themes/fullmoon/main.css
#	datamodels/2.x/itop-structure/precompiled-themes/test-red/main.css
2021-07-07 15:08:38 +02:00
Molkobain
f9064084f9 N°4130 - Activity panel: Remove edits and transitions from default filters on logs 2021-07-07 14:11:03 +02:00
Molkobain
67afbd1d8d N°4146 - Fix crash on object deletion 2021-07-07 13:18:10 +02:00
Molkobain
d6b9172e26 N°4131 - Fix multiple "User disconnected" dialogs in the backoffice
(cherry picked from commit d8f36a8aa9)
2021-07-07 09:32:01 +02:00
Molkobain
8e1e71c740 N°4109 - Fix JS message "Gateway timeout" / "Unauthorized" / "" being displayed on object details page
(cherry picked from commit e279799bf8)
2021-07-07 09:31:53 +02:00
Molkobain
ebbf6e56be N°4127 - Security: Fix XSS vulnerability in object attribute's tooltip 2021-07-07 09:28:41 +02:00
Pierre Goiffon
bd67b71f3d Merge remote-tracking branch 'origin/support/2.7' into develop 2021-07-06 11:36:34 +02:00
Pierre Goiffon
69ad10785b 🔧 .editorConfig : disable PHP variables alignement
Still enabled for key/value pairs though ! Example in \UtilsTest::ConvertToBytesProvider
2021-07-05 12:34:20 +02:00
Pierre Goiffon
9aead898e2 Fix Wiki URL to use iTop Hub instead of wiki.openitop
Thanks @Molkobain and @Hipska !
2021-07-05 12:29:07 +02:00
Pierre Goiffon
a48ebfefba N°4126 Change max_allowed_packet error message
Thanks @Molkobain !
2021-07-05 09:54:47 +02:00
Pierre Goiffon
e2a6e6b846 💚 Fix compiled CSS 2021-07-05 09:53:11 +02:00
Molkobain
7ca689e190 Setup: Fix sizes being displayed as bits instead of bytes 2021-07-04 22:49:54 +02:00
Molkobain
d8f36a8aa9 N°4131 - Fix multiple "User disconnected" dialogs in the backoffice 2021-07-04 21:54:56 +02:00
Molkobain
e279799bf8 N°4109 - Fix JS message "Gateway timeout" / "Unauthorized" / "" being displayed on object details page 2021-07-04 16:46:49 +02:00
Eric
a117906ff6 🎨 Add constant for cmdbsource log channel 2021-07-02 17:01:46 +02:00
Pierre Goiffon
c76d4f12fd Fix constant remove in iTopHub:DBBackupSentence ZN dict key
Thanks Hipska for your feedback in the original commit 67e92120 !
2021-07-02 16:30:31 +02:00
Molkobain
b16529e337 Update version.xml to 3.0.0-beta2 2021-07-02 12:28:58 +02:00
Molkobain
67e9212008 Massively update dictionaries 2021-07-02 12:26:51 +02:00
acognet
35b70bfc00 N°3929 - Polishing: Dashboards 2021-07-02 11:29:10 +02:00
acognet
418312bca5 N°3930 - Polishing: Dashlets 2021-07-02 11:22:57 +02:00
Pierre Goiffon
4748717e50 N°4126 Improve max_allowed_packet checks messages 2021-07-02 10:10:35 +02:00
Pierre Goiffon
d90b1a3d82 🐛 N°4020 Fix syntax error for PHP < 7.1
`syntax error, unexpected 'const' (T_CONST), expecting variable (T_VARIABLE) in /var/www/itop274/setup/compiler.class.inc.php on line 61`
Was added in 1059befa
2021-07-02 09:26:03 +02:00
odain
ed719e13c7 N°4125 - Add a warning log when corrupted data returned by APCu 2021-07-02 08:53:58 +02:00
odain
2d705c6697 add autoload 2021-07-01 17:38:59 +02:00
odain
c98ad106c4 N°4125 - Make translations loading more robust toward APCu cache corruption or invalid dictionnary 2021-07-01 17:34:23 +02:00
acognet
76a237aad4 N°3930 - Polishing: Dashlets 2021-07-01 17:28:35 +02:00
Pierre Goiffon
3694108f42 N°3870 updateLicenses : fix generating wrong product names on Windows
Was including paths fragments.

Example :
<product scope="datamodels">C:\Dev\wamp64\www\itop-dev\.make\license/../..//datamodels/2.x/authent-cas/vendor/apereo/phpcas</product>

Instead of :
<product scope="datamodels">apereo/phpcas</product>
2021-07-01 17:20:55 +02:00
Eric
1a7755365c 🎨 Allow tab stickiness for twig based extensions 2021-07-01 16:08:03 +02:00
Pierre Goiffon
8cf75f826f 🔨 updateLicenses : add logs and replace rm -f by unlink() 2021-07-01 15:30:33 +02:00
Molkobain
a1da086a64 Revert "Fix and simplify dynamic dictionaries load in ajax pages"
This reverts commit e46743af
2021-07-01 13:38:16 +02:00
Molkobain
5d1d6d07a6 Fix regression introduced in 9048d09bf 2021-07-01 10:55:50 +02:00
Eric
e6a38a8055 N°3573 - Allow retrieving operation 2021-07-01 10:40:04 +02:00
Molkobain
3b3f1806ce Fix resources URL not being printed correctly
If there was any parameters in the URL it would not work as the `&` would have been printed as `&amp;`, see similar issue in the previous commit
2021-07-01 09:55:01 +02:00
Molkobain
e46743af2a Fix and simplify dynamic dictionaries load in ajax pages 2021-07-01 09:55:00 +02:00
Molkobain
9048d09bf6 Fix JS dictionaries not being load in \WebPage 2021-07-01 09:55:00 +02:00
Molkobain
3cd03729b9 Setup: Fix "Reload" button style when config file is read-only 2021-07-01 09:55:00 +02:00
Eric
ff760dacbe N°3573 - Allow disabling buttons 2021-06-30 17:05:03 +02:00
Thomas Casteleyn
94f662c71a Show real next backup date (#196)
* Get the next backup date from what is scheduled in the background task.
* Show different message if cron is not running.
2021-06-30 14:59:36 +02:00
Eric
c7d87ad5b0 🎨 Display human readable sizes in bytes as int instead of float 2021-06-30 11:18:08 +02:00
Pierre Goiffon
ad9726b64c 🔧 .editorConfig : restore old ij_visual_guides value
Was overwritten by mistake in 19505649
2021-06-30 10:24:19 +02:00
Pierre Goiffon
e32e275f40 🎨 Align dataprovider elements 2021-06-29 16:45:34 +02:00
Pierre Goiffon
195056492e 🔧 .editorConfig : enable var alignement 2021-06-29 16:45:18 +02:00
Eric
5691ca0327 Fix CI 2021-05-28 08:48:47 +02:00
odain
0001e8ffc4 💚 use new ci validation 2020-10-09 10:13:51 +02:00
4318 changed files with 253063 additions and 127998 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.4 MiB

View File

@@ -11,7 +11,7 @@ tab_width = 4
ij_continuation_indent_size = 8
ij_formatter_off_tag = @formatter:off
ij_formatter_on_tag = @formatter:on
ij_formatter_tags_enabled = false
ij_formatter_tags_enabled = true
ij_smart_tabs = false
ij_visual_guides = 300
ij_wrap_on_typing = true
@@ -78,7 +78,7 @@ ij_editorconfig_space_before_colon = false
ij_editorconfig_space_before_comma = false
ij_editorconfig_spaces_around_assignment_operators = true
[{*.ant, *.fxml, *.jhm, *.jnlp, *.jrxml, *.rng, *.tld, *.wsdl, *.xml, *.xsd, *.xsl, *.xslt, *.xul, phpunit.xml.dist}]
[{*.ant,*.fxml,*.jhm,*.jnlp,*.jrxml,*.rng,*.tld,*.wsdl,*.xml,*.xsd,*.xsl,*.xslt,*.xul,phpunit.xml.dist}]
indent_size = 2
tab_width = 2
ij_smart_tabs = true
@@ -286,11 +286,12 @@ ij_continuation_indent_size = 4
ij_smart_tabs = true
ij_wrap_on_typing = false
ij_php_align_assignments = false
ij_php_align_class_constants = false
ij_php_align_class_constants = true
ij_php_align_group_field_declarations = false
ij_php_align_inline_comments = false
ij_php_align_key_value_pairs = false
ij_php_align_multiline_array_initializer_expression = false
ij_php_align_key_value_pairs = true
ij_php_align_match_arm_bodies = false
ij_php_align_multiline_array_initializer_expression = true
ij_php_align_multiline_binary_operation = false
ij_php_align_multiline_chained_methods = false
ij_php_align_multiline_extends_list = false
@@ -298,6 +299,7 @@ ij_php_align_multiline_for = true
ij_php_align_multiline_parameters = false
ij_php_align_multiline_parameters_in_calls = false
ij_php_align_multiline_ternary_operation = false
ij_php_align_named_arguments = false
ij_php_align_phpdoc_comments = false
ij_php_align_phpdoc_param_names = false
ij_php_anonymous_brace_style = end_of_line
@@ -417,6 +419,7 @@ ij_php_see_weight = 3
ij_php_since_weight = 28
ij_php_sort_phpdoc_elements = true
ij_php_space_after_colon = true
ij_php_space_after_colon_in_enum_backed_type = true
ij_php_space_after_colon_in_named_argument = true
ij_php_space_after_colon_in_return_type = true
ij_php_space_after_comma = true
@@ -431,6 +434,7 @@ ij_php_space_before_catch_parentheses = true
ij_php_space_before_class_left_brace = true
ij_php_space_before_closure_left_parenthesis = true
ij_php_space_before_colon = true
ij_php_space_before_colon_in_enum_backed_type = false
ij_php_space_before_colon_in_named_argument = false
ij_php_space_before_colon_in_return_type = false
ij_php_space_before_comma = false
@@ -466,6 +470,7 @@ ij_php_spaces_around_equality_operators = true
ij_php_spaces_around_logical_operators = true
ij_php_spaces_around_multiplicative_operators = true
ij_php_spaces_around_null_coalesce_operator = true
ij_php_spaces_around_pipe_in_union_type = false
ij_php_spaces_around_relational_operators = true
ij_php_spaces_around_shift_operators = true
ij_php_spaces_around_unary_operator = false
@@ -540,7 +545,6 @@ ij_html_space_after_tag_name = false
ij_html_space_around_equality_in_attribute = false
ij_html_space_inside_empty_tag = false
ij_html_text_wrap = normal
ij_html_uniform_ident = false
[{*.markdown,*.md}]
ij_visual_guides = none

48
.gitattributes vendored Normal file
View File

@@ -0,0 +1,48 @@
# Set the default behavior, in case people don't have core.autocrlf set.
* text=auto
# Explicitly declare text files you want to always be normalized and converted
# to native line endings on checkout.
*.bash text eol=lf
*.bat text eol=lf
*.cmd text eol=lf
*.css text eol=lf
*.scss text eol=lf
*.dist text eol=lf
.editorconfig text eol=lf
.env* text eol=lf
.gitignore text eol=lf
.htaccess text eol=lf
*.htm text eol=lf
*.html text eol=lf
*.ini text eol=lf
*.js text eol=lf
*.json text eol=lf
*.lock text eol=lf
*.md text eol=lf
*.php text eol=lf
*.php_cs text eol=lf
*.php8 text eol=lf
*.plex text eol=lf
*.sh text eol=lf
*.svg text eol=lf
*.ts text eol=lf
*.twig text eol=lf
*.txt text eol=lf
*.xml text eol=lf
*.xsd text eol=lf
*.yaml text eol=lf
*.yml text eol=lf
# Denote all files that are truly binary and should not be modified.
*.png binary
*.jpeg binary
*.jpg binary
*.gif binary
*.ico binary
*.pdf binary
*.swf binary
*.zip binary
*.ttf binary
*.woff binary
*.woff2 binary

83
.github/pull_request_template.md vendored Normal file
View File

@@ -0,0 +1,83 @@
<!--
IMPORTANT: Please follow the guidelines within this PR template before submitting it, it will greatly help us process your PR. 🙏
Any PRs not following the guidelines or with missing information will not be considered.
-->
## Base information
| Question | Answer
|---------------------------------------------------------------|--------
| Related to a SourceForge thead / Another PR / Combodo ticket? | <!-- Put the URL -->
| Type of change? | Bug fix / Enhancement / Translations
## Symptom (bug) / Objective (enhancement)
<!--
If it's a bug
- Explain the symptom in details
- If possible put error messages, logs or screenshots (you can paste image directly in this editor).
If it's an enhancement
- Describe what is blocking you, what is the objective with as much details as possible.
- Add screenshots if it's related to UI.
-->
## Reproduction procedure (bug)
<!--
Remove this section only if it's NOT a bug.
Otherwise, explain step by step how to reproduce the issue on a standard iTop Community.
If it requires a custom datamodel, provide the minimal XML delta to reproduce it on a standard iTop Community.
-->
1. On iTop x.y.z <!-- Put complete iTop version (eg. 3.1.0-2) -->
2. With PHP x.y.z <!-- Put complete PHP version (eg. 8.1.24) -->
2. First go there
2. Then do that
3. ...
4. Finally, see that...
## Cause (bug)
<!--
Remove this section only if it's NOT a bug.
Otherwise, explain what is the cause of the issue (where in the code and why)
-->
## Proposed solution (bug and enhancement)
<!--
Explain in details how you are proposing to solve this:
- What did you do in the code and why
- If you changed something in the UI, put before / after screenshots (you can paste image directly in this editor)
-->
## Checklist before requesting a review
<!--
Don't remove these lines, check them once done.
-->
- [ ] I have performed a self-review of my code
- [ ] I have tested all changes I made on an iTop instance
- [ ] I have added a unit test, otherwise I have explained why I couldn't
- [ ] Is the PR clear and detailed enough so anyone can understand digging in the code?
## Checklist of things to do before PR is ready to merge
<!--
Things that needs to be done in the PR before it can be considered as ready to be merged
Examples:
- Changes requested in the review
- Unit test to add
- Dictionary entries to translate
- ...
-->
- [ ] ...
- [ ] ...
- [ ] ...

16
.github/workflows/action.yml vendored Normal file
View File

@@ -0,0 +1,16 @@
name: Add PRs to Combodo PRs Dashboard
on:
pull_request_target:
types:
- opened
jobs:
add-to-project:
name: Add PR to Combodo Project
runs-on: ubuntu-latest
steps:
- uses: actions/add-to-project@v1.0.2
with:
project-url: https://github.com/orgs/Combodo/projects/5
github-token: ${{ secrets.PR_AUTOMATICALLY_ADD_TO_PROJECT }}

10
.gitignore vendored
View File

@@ -19,7 +19,7 @@
# composer reserver directory, from sources, populate/update using "composer install"
vendor/*
test/vendor/*
tests/*/vendor/*
# all conf but listing prevention
/conf/**
@@ -37,7 +37,9 @@ test/vendor/*
# iTop extensions
/extensions/**
!/extensions/.htaccess
!/extensions/readme.txt
!/extensions/web.config
# all logs but listing prevention
/log/**
@@ -45,9 +47,15 @@ test/vendor/*
!/log/index.php
!/log/web.config
# PHPUnit: Cache file, local XML working copies
/tests/php-unit-tests/.phpunit.result.cache
/tests/php-unit-tests/phpunit.xml
/tests/php-unit-tests/postbuild_integration.xml
# Jetbrains
/.idea/**
!/.idea/IntelliLang.xml
# doc. generation
/.doc/vendor

15
.idea/IntelliLang.xml generated Normal file
View File

@@ -0,0 +1,15 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="LanguageInjectionConfiguration">
<injection language="InjectablePHP" injector-id="xml">
<display-name>iTop - Class method code</display-name>
<place><![CDATA[xmlTag().withLocalName(string().equalTo("code"))]]></place>
<xpath-condition>name(..) = 'method' and count(/itop_design) = 1</xpath-condition>
</injection>
<injection language="InjectablePHP" injector-id="xml">
<display-name>iTop - Snippet code</display-name>
<place><![CDATA[xmlTag().withLocalName(string().equalTo("snippet"))]]></place>
<xpath-condition>name(..) = 'snippets' and count(/itop_design) = 1</xpath-condition>
</injection>
</component>
</project>

View File

@@ -27,7 +27,7 @@ $iTopFolder = __DIR__."/../../../";
require_once("$iTopFolder/approot.inc.php");
require_once(APPROOT."/application/utils.inc.php");
if (php_sapi_name() !== 'cli')
if (PHP_SAPI !== 'cli')
{
throw new \Exception('This script can only run from CLI');
}
@@ -48,4 +48,4 @@ if (!file_exists($sCssFile))
{
fwrite(STDERR, "Failed to compile $sCssFile, exiting.");
exit(1);
}
}

View File

@@ -26,7 +26,7 @@ $iTopFolder = __DIR__ . "/../../" ;
require_once ("$iTopFolder/approot.inc.php");
require_once (APPROOT."/setup/setuputils.class.inc.php");
if (php_sapi_name() !== 'cli')
if (PHP_SAPI !== 'cli')
{
throw new \Exception('This script can only run from CLI');
}
@@ -36,22 +36,38 @@ clearstatcache();
$oiTopComposer = new iTopComposer();
$aDeniedButStillPresent = $oiTopComposer->ListDeniedButStillPresent();
echo "\n";
foreach ($aDeniedButStillPresent as $sDir)
{
if (! preg_match('#[tT]ests?/?$#', $sDir))
if (false === iTopComposer::IsTestDir($sDir))
{
echo "\nfound INVALID denied test dir: '$sDir'\n";
echo "ERROR found INVALID denied test dir: '$sDir'\n";
throw new \Exception("$sDir must end with /Test/ or /test/");
}
try
{
SetupUtils::rrmdir($sDir);
echo "Remove denied test dir: '$sDir'\n";
}
catch (\Exception $e)
{
echo "\nFAILED to remove denied test dir: '$sDir'\n";
if (false === file_exists($sDir)) {
echo "INFO $sDir is in denied list, but not existing on disk => skipping !\n";
continue;
}
}
try {
SetupUtils::rrmdir($sDir);
echo "OK Remove denied test dir: '$sDir'\n";
}
catch (\Exception $e) {
echo "\nFAILED to remove denied test dir: '$sDir'\n";
}
}
$aAllowedAndDeniedDirs = array_merge(
$oiTopComposer->ListAllowedTestDir(),
$oiTopComposer->ListDeniedTestDir()
);
$aExistingDirs = $oiTopComposer->ListAllTestDir();
$aMissing = array_diff($aExistingDirs, $aAllowedAndDeniedDirs);
if (false === empty($aMissing)) {
echo "Some new tests dirs exists !\n"
.' They must be declared either in the allowed or denied list in '.iTopComposer::class." (see N°2651).\n"
.' List of dirs:'."\n".var_export($aMissing, true);
}

13
.make/git-hooks/README.md Normal file
View File

@@ -0,0 +1,13 @@
# Git hooks for iTop
## ❓ Goal
Those [git hooks](https://git-scm.com/docs/githooks) aims to ease developing on [iTop](https://github.com/Combodo/iTop).
## ☑ Available hooks
* pre-commit : rejects commit if you have at least one SCSS file staged, and no CSS file
## ⚙ Install
Just run install.php !

View File

@@ -0,0 +1,26 @@
<?php
$aHooks = [
'pre-commit.php',
];
$sAppRoot = dirname(__DIR__, 2);
foreach ($aHooks as $sSourceHookFileName) {
echo "Processing for `{$sSourceHookFileName}`...\n";
$sSourceHookPath = __DIR__.DIRECTORY_SEPARATOR.$sSourceHookFileName;
$aPathParts = pathinfo($sSourceHookFileName);
$sTargetHookPath = $sAppRoot.DIRECTORY_SEPARATOR.'.git'.DIRECTORY_SEPARATOR.'hooks'.DIRECTORY_SEPARATOR.$aPathParts['filename'];
if (file_exists($sTargetHookPath) || is_link($sTargetHookPath)) {
echo "Existing $sTargetHookPath ! Removing...";
unlink($sTargetHookPath);
echo "OK !\n";
}
echo "Creating symlink for hook in $sTargetHookPath...";
symlink($sSourceHookPath, $sTargetHookPath);
echo "OK !\n";
}

View File

@@ -0,0 +1,49 @@
#!/usr/bin/php
<?php
/**
* Reject any commit containing .scss files, but no .css file !
*/
echo "Checking files staged...\n";
$sFilesToCommit = shell_exec('git diff --cached --name-only --diff-filter=ACMRT');
$aFilesToCommit = explode("\n", $sFilesToCommit);
$aScssFiles = GetFilesWithExtension('scss', $aFilesToCommit);
if (count($aScssFiles) === 0) {
echo "No scss file : OK to go !\n";
exit(0);
}
$aCssFiles = GetFilesWithExtension('css', $aFilesToCommit);
if (count($aCssFiles) === 0) {
echo "There are SCSS files staged but no CSS file : REJECTING commit.\n";
echo "You must add the compiled SCSS files by running the setup !\n";
exit(1);
}
echo "We have SCSS but also CSS => OK to commit !\n";
exit(0);
function GetFilesWithExtension($sExtension, $aFiles) {
return array_filter(
$aFiles,
function($item) use ($sExtension) {
return (endsWith($item, '.'.$sExtension));
}
);
}
function endsWith( $haystack, $needle ) {
$length = strlen( $needle );
if( !$length ) {
return true;
}
return substr( $haystack, -$length ) === $needle;
}
function exitWithMessage($sMessage, $iCode) {
echo $sMessage;
exit($iCode);
}

View File

@@ -10,10 +10,6 @@
* `curl -L -o /usr/bin/jq.exe https://github.com/stedolan/jq/releases/latest/download/jq-win64.exe`
* this is a Windows port : https://stedolan.github.io/jq/
*
* Known bug on Windows :
* Licenses added from Composer contains a path in the product node (N°3870)
* `<product scope="lib">C:\Dev\wamp64\www\itop-dev\.make\license/../..//lib/symfony/console</product>`
*
* Licenses sources :
* * `composer licenses --format json` (see https://getcomposer.org/doc/03-cli.md#licenses)
* * keep every existing nodes with `/licenses/license[11]/product/@scope` not in ['lib', 'datamodels']
@@ -23,17 +19,24 @@
* The target license file path is in `$xmlFilePath`
*/
$iTopFolder = __DIR__ . "/../../" ;
$xmlFilePath = $iTopFolder . "setup/licenses/community-licenses.xml";
$iTopFolder = __DIR__."/../../";
$xmlFilePath = $iTopFolder."setup/licenses/community-licenses.xml";
function get_scope($product_node)
{
$jqExec = shell_exec("jq -V"); // a param is mandatory otherwise the script will freeze
if ((null === $jqExec) || (false === $jqExec)) {
echo "/!\ JQ is required but cannot be launched :( \n";
echo "Check this script PHPDoc block for instructions\n";
die(-1);
}
function get_scope($product_node) {
$scope = $product_node->getAttribute("scope");
if ($scope === "")
{ //put iTop first
if ($scope === "") { //put iTop first
return "aaaaaaaaa";
}
return $scope;
}
@@ -70,39 +73,83 @@ function get_license_nodes($file_path)
$xp = new DOMXPath($dom);
$licenseList = $xp->query('/licenses/license');
$licenses = iterator_to_array($licenseList);
$licenses = iterator_to_array($licenseList);
usort($licenses, 'sort_by_product');
return $licenses;
}
/** @noinspection SuspiciousAssignmentsInspection */
function fix_product_name(DOMNode &$oProductNode)
{
$sProductNameOrig = $oProductNode->nodeValue;
// sample : `C:\Dev\wamp64\www\itop-27\.make\license/../..//lib/symfony/polyfill-ctype`
$sProductNameFixed = remove_dir_from_string($sProductNameOrig, 'lib/');
// sample : `C:\Dev\wamp64\www\itop-27\.make\license/../..//datamodels/2.x/authent-cas/vendor/apereo/phpcas`
$sProductNameFixed = remove_dir_from_string($sProductNameFixed, 'vendor/');
$oProductNode->nodeValue = $sProductNameFixed;
}
function remove_dir_from_string($sString, $sNeedle)
{
if (strpos($sString, $sNeedle) === false) {
return $sString;
}
$sStringTmp = strstr($sString, $sNeedle);
$sStringFixed = str_replace($sNeedle, '', $sStringTmp);
// DEBUG trace O:)
// echo "$sNeedle = $sString => $sStringFixed\n";
return $sStringFixed;
}
$old_licenses = get_license_nodes($xmlFilePath);
//generate file with updated licenses
$generated_license_file_path = __DIR__."/provfile.xml";
exec("bash " . __DIR__ . "/gen-community-license.sh $iTopFolder > ". $generated_license_file_path);
echo "- Generating licences...";
exec("bash ".__DIR__."/gen-community-license.sh $iTopFolder > ".$generated_license_file_path);
echo "OK!\n";
echo "- Get licenses nodes...";
$new_licenses = get_license_nodes($generated_license_file_path);
exec("rm -f ". $generated_license_file_path);
unlink($generated_license_file_path);
foreach ($old_licenses as $b) {
$aProductNode = get_product_node($b);
if (get_scope($aProductNode) !== "lib" && get_scope($aProductNode) !== "datamodels" )
{
if (get_scope($aProductNode) !== "lib" && get_scope($aProductNode) !== "datamodels") {
$new_licenses[] = $b;
}
}
usort($new_licenses, 'sort_by_product');
echo "OK!\n";
echo "- Overwritting Combodo license file...";
$new_dom = new DOMDocument("1.0");
$new_dom->formatOutput = true;
$root = $new_dom->createElement("licenses");
$new_dom->appendChild($root);
foreach ($new_licenses as $b) {
$node = $new_dom->importNode($b,true);
$root->appendChild($new_dom->importNode($b,true));
$node = $new_dom->importNode($b, true);
// N°3870 fix when running script in Windows
// fix should be in gen-community-license.sh but it is easier to do it here !
if (strncasecmp(PHP_OS, 'WIN', 3) === 0) {
$oProductNodeOrig = get_product_node($node);
fix_product_name($oProductNodeOrig);
}
$root->appendChild($node);
}
$new_dom->save($xmlFilePath);
$new_dom->save($xmlFilePath);
echo "OK!\n";

View File

@@ -25,8 +25,8 @@ require_once (__DIR__.DIRECTORY_SEPARATOR.'update.classes.inc.php');
/** @var \FileVersionUpdater[] $aFilesUpdaters */
$aFilesUpdaters = array(
new iTopVersionFileUpdater(),
new CssVariablesFileUpdater(),
new DatamodelsModulesFiles(),
new ConstantFileUpdater('ITOP_CORE_VERSION', 'approot.inc.php'),
);
if (count($argv) === 1)

View File

@@ -69,6 +69,40 @@ abstract class AbstractSingleFileVersionUpdater extends FileVersionUpdater
}
}
/**
* @since 2.7.7 3.0.1 3.1.0 N°4714
*/
class ConstantFileUpdater extends AbstractSingleFileVersionUpdater {
/** @var string */
private $sConstantName;
/**
* @param $sConstantName constant to search, for example `ITOP_CORE_VERSION`
* @param $sFileToUpdate file containing constant definition
*/
public function __construct($sConstantName, $sFileToUpdate)
{
$this->sConstantName = $sConstantName;
parent::__construct($sFileToUpdate);
}
/**
* @inheritDoc
*/
public function UpdateFileContent($sVersionLabel, $sFileContent, $sFileFullPath)
{
$sConstantSearchPattern = <<<REGEXP
/define\('{$this->sConstantName}', ?'[^']+'\);/
REGEXP;
return preg_replace(
$sConstantSearchPattern,
"define('{$this->sConstantName}', '{$sVersionLabel}');",
$sFileContent
);
}
}
class iTopVersionFileUpdater extends AbstractSingleFileVersionUpdater
{
public function __construct()
@@ -89,26 +123,6 @@ class iTopVersionFileUpdater extends AbstractSingleFileVersionUpdater
}
}
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;

View File

@@ -111,9 +111,9 @@ Our tests are located in the `test/` directory, containing a PHPUnit config file
* Use the present tense ("Add feature" not "Added feature")
* Use the imperative mood ("Move cursor to..." not "Moves cursor to...")
* Limit the first line to 72 characters or less
* Please start the commit message with an applicable emoji code (following the [Gitmoji guide](https://gitmoji.carloscuesta.me/)).
Beware to use the code (for example `:bug:`) and not the character (🐛) as Unicode support in git clients is very poor for now...
Emoji examples :
* Please start the commit message with an applicable emoji code (following the [Gitmoji guide](https://gitmoji.dev/)).
Beware to use the code (for example `:bug:`) and not the character (🐛) as Unicode support in git clients is very poor for now...
Emoji examples :
* 🌐 `:globe_with_meridians:` for translations
* 🎨 `:art:` when improving the format/structure of the code
* ⚡️ `:zap:` when improving performance
@@ -131,7 +131,7 @@ Our tests are located in the `test/` directory, containing a PHPUnit config file
When your code is working, please:
* stash as much as possible your commits,
* squash as much as possible your commits,
* rebase your branch on our repo last commit,
* create a pull request.
@@ -152,5 +152,9 @@ Stickers' design might change from one year to another. For the first year we wa
* White hat: Find and/or fix a vulnerability
* Contributor: Contribute by finding a bug, making an extension or any other way
* Partner: For Combodo's official partners
* Graduated: Follow a Combodo's iTop training
* Ambassador: Outstanding community contributors
* Beta tester: Test and give feedback on beta releases
* Extension developer: Develop and publish an extension
![](documentation/contributing-guide/contributing-stickers-side-by-side.png)
![](.doc/contributing-guide/contributing-stickers-side-by-side.png)

8
Jenkinsfile vendored
View File

@@ -1,6 +1,14 @@
def infra
node(){
properties([
buildDiscarder(
logRotator(
daysToKeepStr: "28",
numToKeepStr: "500")
)
])
checkout scm
infra = load '/var/lib/jenkins/workspace/itop-test-infra_master/src/Infra.groovy'

View File

@@ -1,13 +1,11 @@
<p align="center"><a href="https://www.combodo.com/itop-193" target="_blank">
<img src="https://www.combodo.com/logos/logo-itop.svg">
<img src="https://www.combodo.com/logos/logo-itop-baseline.svg" width=350>
</a></p>
# iTop - ITSM & CMDB
iTop stands for *IT Operations Portal*.
It is a complete open source, ITIL, web based service management tool including a fully customizable CMDB, a helpdesk system and a document management tool.
iTop also offers mass import tools and web services to integrate with your IT
iTop stands for IT Operations Portal. It is a complete open source and web based IT service management platform including a fully customizable CMDB, a helpdesk system and a document management tool. It is ITIL compliant and easily customizable and extensible thanks to a high number of adds-on and web services to integrate with your IT.
iTop also offers mass import tools to help you being even more efficient.
## Features
- Fully configurable [Configuration Management (CMDB)][10]
@@ -39,7 +37,7 @@ iTop also offers mass import tools and web services to integrate with your IT
- [iTop Forums][1]: community support
- [iTop Tickets][2]: for feature requests and bug reports
- [Releases download][3]
- [Software requirements][4]
- [iTop requirements][4]
- [Documentation][5] covering both iTop and its official extensions
- [iTop Hub][6] : discover and install extensions !
@@ -47,7 +45,7 @@ iTop also offers mass import tools and web services to integrate with your IT
[1]: https://sourceforge.net/p/itop/discussion/
[2]: https://sourceforge.net/p/itop/tickets/
[3]: https://sourceforge.net/projects/itop/files/itop/
[4]: https://www.itophub.io/wiki/page?id=latest:install:upgrading_itop
[4]: https://www.itophub.io/wiki/page?id=latest:install:requirements
[5]: https://www.itophub.io/wiki
[6]: https://store.itophub.io/en_US/
@@ -78,18 +76,19 @@ We would like to give a special thank you 🤗 to the people from the community
- Alves, David
- Beck, Pedro
- Beer, Christian (a.k.a [@ChristianBeer](https://www.github.com/ChristianBeer))
- Bilger, Jean-François
- Bostoen, Jeffrey (a.k.a @jbostoen)
- Bostoen, Jeffrey (a.k.a [@jbostoen](https://www.github.com/jbostoen))
- Cardoso, Anderson
- Cassaro, Bruno
- Casteleyn, Thomas (a.k.a @Hipska)
- Casteleyn, Thomas (a.k.a [@Hipska](https://www.github.com/Hipska))
- Castro, Randall Badilla
- Colantoni, Maria Laura
- Couronné, Guy
- Dvořák, Lukáš
- Goethals, Stefan
- Gumble, David
- Kaltefleiter, Lars (a.k.a @larhip)
- Kaltefleiter, Lars (a.k.a [@larhip](https://www.github.com/larhip))
- Khamit, Shamil
- Kincel, Martin
- Konečný, Kamil
@@ -98,10 +97,13 @@ We would like to give a special thank you 🤗 to the people from the community
- Lazcano, Federico
- Lucas, Jonathan
- Malik, Remie
- Mindêllo de Andrade, Lucas (a.k.a @rokam)
- Mindêllo de Andrade, Lucas (a.k.a [@rokam](https://www.github.com/rokam))
- Raenker, Martin
- Rosenke, Stephan
- Seki, Shoji
- Shilov, Vladimir
- Stukalov, Ilya (a.k.a [@ilya](https://www.github.com/ilya-stukalov))
- Tarjányi, Csaba (a.k.a [@tacsaby](https://github.com/tacsaby))
- Tulio, Marco
- Turrubiates, Miguel
@@ -112,6 +114,7 @@ We would like to give a special thank you 🤗 to the people from the community
- DudekArtur
- Karkoff1212
- Laura
- nv35
- Purple Grape
- Schlobinux
- theBigOne

View File

@@ -10,7 +10,7 @@ define('PORTAL_PROFILE_NAME', 'Portal user');
class UserRightsBaseClassGUI extends cmdbAbstractObject
{
// Whenever something changes, reload the privileges
protected function AfterInsert()
{
UserRights::FlushPrivileges();
@@ -34,7 +34,7 @@ class URP_Profiles extends UserRightsBaseClassGUI
{
$aParams = array
(
"category" => "addon/userrights,grant_by_profile",
"category" => "addon/userrights,grant_by_profile,filter",
"key_type" => "autoincrement",
"name_attcode" => "name",
"state_attcode" => "",
@@ -59,7 +59,7 @@ class URP_Profiles extends UserRightsBaseClassGUI
}
protected static $m_aCacheProfiles = null;
public static function DoCreateProfile($sName, $sDescription)
{
if (is_null(self::$m_aCacheProfiles))
@@ -71,7 +71,7 @@ class URP_Profiles extends UserRightsBaseClassGUI
{
self::$m_aCacheProfiles[$oProfile->Get('name')] = $oProfile->GetKey();
}
}
}
$sCacheKey = $sName;
if (isset(self::$m_aCacheProfiles[$sCacheKey]))
@@ -82,10 +82,10 @@ class URP_Profiles extends UserRightsBaseClassGUI
$oNewObj->Set('name', $sName);
$oNewObj->Set('description', $sDescription);
$iId = $oNewObj->DBInsertNoReload();
self::$m_aCacheProfiles[$sCacheKey] = $iId;
self::$m_aCacheProfiles[$sCacheKey] = $iId;
return $iId;
}
function GetGrantAsHtml($oUserRights, $sClass, $sAction)
{
$bGrant = $oUserRights->GetProfileActionGrant($this->GetKey(), $sClass, $sAction);
@@ -102,7 +102,7 @@ class URP_Profiles extends UserRightsBaseClassGUI
return '<span style="background-color: #ffdddd;">'.Dict::S('UI:UserManagement:ActionAllowed:No').'</span>';
}
}
function DoShowGrantSumary($oPage)
{
if ($this->GetRawName() == "Administrator")
@@ -114,7 +114,7 @@ class URP_Profiles extends UserRightsBaseClassGUI
// Note: for sure, we assume that the instance is derived from UserRightsProfile
$oUserRights = UserRights::GetModuleInstance();
$aDisplayData = array();
foreach (MetaModel::GetClasses('bizmodel,grant_by_profile') as $sClass)
{
@@ -123,12 +123,12 @@ class URP_Profiles extends UserRightsBaseClassGUI
{
$bGrant = $oUserRights->GetClassStimulusGrant($this->GetKey(), $sClass, $sStimulusCode);
if ($bGrant === true)
{
{
$aStimuli[] = '<span title="'.$sStimulusCode.': '.htmlentities($oStimulus->GetDescription(), ENT_QUOTES, 'UTF-8').'">'.htmlentities($oStimulus->GetLabel(), ENT_QUOTES, 'UTF-8').'</span>';
}
}
$sStimuli = implode(', ', $aStimuli);
$aDisplayData[] = array(
'class' => MetaModel::GetName($sClass),
'read' => $this->GetGrantAsHtml($oUserRights, $sClass, 'r'),
@@ -140,7 +140,7 @@ class URP_Profiles extends UserRightsBaseClassGUI
'stimuli' => $sStimuli,
);
}
$aDisplayConfig = array();
$aDisplayConfig['class'] = array('label' => Dict::S('UI:UserManagement:Class'), 'description' => Dict::S('UI:UserManagement:Class+'));
$aDisplayConfig['read'] = array('label' => Dict::S('UI:UserManagement:Action:Read'), 'description' => Dict::S('UI:UserManagement:Action:Read+'));
@@ -198,7 +198,7 @@ class URP_Profiles extends UserRightsBaseClassGUI
* @param $aReasons array To store the reasons why the attribute is read-only (info about the synchro replicas)
* @param $sTargetState string The target state in which to evalutate the flags, if empty the current state will be used
* @return integer Flags: the binary combination of the flags applicable to this attribute
*/
*/
public function GetAttributeFlags($sAttCode, &$aReasons = array(), $sTargetState = '')
{
$iFlags = parent::GetAttributeFlags($sAttCode, $aReasons, $sTargetState);
@@ -219,7 +219,7 @@ class URP_UserProfile extends UserRightsBaseClassGUI
{
$aParams = array
(
"category" => "addon/userrights,grant_by_profile",
"category" => "addon/userrights,grant_by_profile,filter",
"key_type" => "autoincrement",
"name_attcode" => array("userlogin", "profile"),
"state_attcode" => "",
@@ -404,7 +404,7 @@ class URP_UserOrg extends UserRightsBaseClassGUI
{
if (!UserRights::IsLoggedIn() || UserRights::IsAdministrator()) { return; }
$oUser = UserRights::GetUserObject();
$oUser = UserRights::GetUserObject();
$oAddon = UserRights::GetModuleInstance();
$aOrgs = $oAddon->GetUserOrgs($oUser, '');
if (count($aOrgs) > 0)
@@ -432,6 +432,12 @@ class UserRightsProfile extends UserRightsAddOnAPI
UR_ACTION_BULK_DELETE => 'bd',
);
/**
* @var array $aUsersProfilesList Cache of users' profiles. Hash array of user ID => [profile ID => profile friendlyname, profile ID => profile friendlyname, ...]
* @since 2.7.10 3.0.4 3.1.1 3.2.0 N°6887
*/
private $aUsersProfilesList = [];
// Installation: create the very first user
public function CreateAdministrator($sAdminUser, $sAdminPwd, $sLanguage = 'EN US')
{
@@ -490,6 +496,7 @@ class UserRightsProfile extends UserRightsAddOnAPI
}
protected $m_aUserOrgs = array(); // userid -> array of orgid
protected $m_aAdministrators = null; // [user id]
// Built on demand, could be optimized if necessary (doing a query for each attribute that needs to be read)
protected $m_aObjectActionGrants = array();
@@ -528,7 +535,7 @@ class UserRightsProfile extends UserRightsAddOnAPI
$oSearch->AllowAllData();
$oCondition = new BinaryExpression(new FieldExpression('userid'), '=', new VariableExpression('userid'));
$oSearch->AddConditionExpression($oCondition);
$oUserOrgSet = new DBObjectSet($oSearch, array(), array('userid' => $iUser));
while ($oUserOrg = $oUserOrgSet->Fetch())
{
@@ -546,6 +553,7 @@ class UserRightsProfile extends UserRightsAddOnAPI
// Cache
$this->m_aObjectActionGrants = array();
$this->m_aAdministrators = null;
}
public function LoadCache()
@@ -610,30 +618,113 @@ class UserRightsProfile extends UserRightsAddOnAPI
{
$this->LoadCache();
$aObjectPermissions = $this->GetUserActionGrant($oUser, $sClass, UR_ACTION_READ);
if ($aObjectPermissions['permission'] == UR_ALLOWED_NO)
// Let us pass an administrator for bypassing the grant matrix check in order to test this method without the need to set up a complex profile
// In the nominal case Administrators never end up here (since they completely bypass GetSelectFilter)
if (!static::IsAdministrator($oUser) && (MetaModel::HasCategory($sClass, 'silo') || MetaModel::HasCategory($sClass, 'bizmodel')))
{
return false;
// N°4354 - Categories 'silo' and 'bizmodel' do check the grant matrix. Whereas 'filter' always allows to read (but the result can be filtered)
$aObjectPermissions = $this->GetUserActionGrant($oUser, $sClass, UR_ACTION_READ);
if ($aObjectPermissions['permission'] == UR_ALLOWED_NO)
{
return false;
}
}
// Determine how to position the objects of this class
//
$oFilter = true;
$aConditions = array();
// Determine if this class is part of a silo and build the filter for it
$sAttCode = self::GetOwnerOrganizationAttCode($sClass);
if (is_null($sAttCode))
if (!is_null($sAttCode))
{
// No filtering for this object
return true;
$aUserOrgs = $this->GetUserOrgs($oUser, $sClass);
if (count($aUserOrgs) > 0)
{
$oFilter = $this->MakeSelectFilter($sClass, $aUserOrgs, $aSettings, $sAttCode);
}
// else: No org means 'any org'
}
// Position the user
//
$aUserOrgs = $this->GetUserOrgs($oUser, $sClass);
if (count($aUserOrgs) == 0)
// else: No silo for this class
// Specific conditions to hide, for non-administrators, the Administrator Users, the Administrator Profile and related links
// Note: when logged as an administrator, GetSelectFilter is completely bypassed.
if ($this->AdministratorsAreHidden())
{
// No org means 'any org'
return true;
if ($sClass == 'URP_Profiles')
{
$oExpression = new FieldExpression('id', $sClass);
$oScalarExpr = new ScalarExpression(1);
$aConditions[] = new BinaryExpression($oExpression, '!=', $oScalarExpr);
}
else if (($sClass == 'URP_UserProfile') || ($sClass == 'User') || (is_subclass_of($sClass, 'User')))
{
$aAdministrators = $this->GetAdministrators();
if (count($aAdministrators) > 0)
{
$sAttCode = ($sClass == 'URP_UserProfile') ? 'userid' : 'id';
$oExpression = new FieldExpression($sAttCode, $sClass);
$oListExpr = ListExpression::FromScalars($aAdministrators);
$aConditions[] = new BinaryExpression($oExpression, 'NOT IN', $oListExpr);
}
}
}
return $this->MakeSelectFilter($sClass, $aUserOrgs, $aSettings, $sAttCode);
// Handling of the added conditions
if (count($aConditions) > 0)
{
if($oFilter === true)
{
// No 'silo' filter, let's build a clean one
$oFilter = new DBObjectSearch($sClass);
}
// Add the conditions to the filter
foreach($aConditions as $oCondition)
{
$oFilter->AddConditionExpression($oCondition);
}
}
return $oFilter;
}
/**
* Retrieve (and memoize) the list of administrator accounts.
* Note that there should always be at least one administrator account
* @return number[]
*/
private function GetAdministrators()
{
if ($this->m_aAdministrators === null)
{
// Find all administrators
$this->m_aAdministrators = array();
$oAdministratorsFilter = new DBObjectSearch('User');
$oLnkFilter = new DBObjectSearch('URP_UserProfile');
$oExpression = new FieldExpression('profileid', 'URP_UserProfile');
$oScalarExpr = new ScalarExpression(1);
$oCondition = new BinaryExpression($oExpression, '=', $oScalarExpr);
$oLnkFilter->AddConditionExpression($oCondition);
$oAdministratorsFilter->AddCondition_ReferencedBy($oLnkFilter, 'userid');
$oAdministratorsFilter->AllowAllData(true); // Mandatory to prevent infinite recursion !!
$oSet = new DBObjectSet($oAdministratorsFilter);
$oSet->OptimizeColumnLoad(array('User' => array('login')));
while($oUser = $oSet->Fetch())
{
$this->m_aAdministrators[] = $oUser->GetKey();
}
}
return $this->m_aAdministrators;
}
/**
* Whether or not to hide the 'Administrator' profile and the administrator accounts
* @return boolean
*/
private function AdministratorsAreHidden()
{
return ((bool)MetaModel::GetConfig()->Get('security.hide_administrators'));
}
@@ -653,14 +744,20 @@ class UserRightsProfile extends UserRightsAddOnAPI
// load and cache permissions for the current user on the given class
//
$iUser = $oUser->GetKey();
$aTest = @$this->m_aObjectActionGrants[$iUser][$sClass][$iActionCode];
if (is_array($aTest)) return $aTest;
if (isset($this->m_aObjectActionGrants[$iUser][$sClass][$iActionCode])){
$aTest = $this->m_aObjectActionGrants[$iUser][$sClass][$iActionCode];
if (is_array($aTest)) return $aTest;
}
$sAction = self::$m_aActionCodes[$iActionCode];
$bStatus = null;
// Cache user's profiles
if(false === array_key_exists($iUser, $this->aUsersProfilesList)){
$this->aUsersProfilesList[$iUser] = UserRights::ListProfiles($oUser);
}
// Call the API of UserRights because it caches the list for us
foreach(UserRights::ListProfiles($oUser) as $iProfile => $oProfile)
foreach($this->aUsersProfilesList[$iUser] as $iProfile => $oProfile)
{
$bGrant = $this->GetProfileActionGrant($iProfile, $sClass, $sAction);
if (!is_null($bGrant))
@@ -786,11 +883,16 @@ class UserRightsProfile extends UserRightsAddOnAPI
// Note: this code is VERY close to the code of IsActionAllowed()
$iUser = $oUser->GetKey();
// Cache user's profiles
if(false === array_key_exists($iUser, $this->aUsersProfilesList)){
$this->aUsersProfilesList[$iUser] = UserRights::ListProfiles($oUser);
}
// Note: The object set is ignored because it was interesting to optimize for huge data sets
// and acceptable to consider only the root class of the object set
$bStatus = null;
// Call the API of UserRights because it caches the list for us
foreach(UserRights::ListProfiles($oUser) as $iProfile => $oProfile)
foreach($this->aUsersProfilesList[$iUser] as $iProfile => $oProfile)
{
$bGrant = $this->GetClassStimulusGrant($iProfile, $sClass, $sStimulusCode);
if (!is_null($bGrant))
@@ -819,9 +921,10 @@ class UserRightsProfile extends UserRightsAddOnAPI
}
/**
* Find out which attribute is corresponding the the dimension 'owner org'
* returns null if no such attribute has been found (no filtering should occur)
*/
* @param string $sClass
* @return string|null Find out which attribute is corresponding the dimension 'owner org'
* returns null if no such attribute has been found (no filtering should occur)
*/
public static function GetOwnerOrganizationAttCode($sClass)
{
$sAttCode = null;

View File

@@ -586,10 +586,10 @@ class UserRightsProfile extends UserRightsAddOnAPI
/**
* Read and cache organizations allowed to the given user
*
* @param $oUser
* @param $sClass (not used here but can be used in overloads)
* @param User $oUser
* @param string $sClass (not used here but can be used in overloads)
*
* @return array
* @return array keys of the User allowed org
* @throws \CoreException
* @throws \Exception
*/

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/AjaxPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/AjaxPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -24,6 +24,7 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Application\Helper\Session;
use Combodo\iTop\Application\UI\Base\Component\Input\InputUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Layout\UIContentBlock;
use Combodo\iTop\Application\UI\Base\UIBlock;
@@ -227,6 +228,20 @@ class ApplicationContext
}
return $sContext;
}
/**
* Returns the context an array of input blocks
*
* @return array The context as a sequence of <input type="hidden" /> tags
* @since 3.0.0
*/
public function GetForUIForm()
{
$aContextInputBlocks = [];
foreach ($this->aValues as $sName => $sValue) {
$aContextInputBlocks[] = InputUIBlockFactory::MakeForHidden("c[$sName]", htmlentities($sValue, ENT_QUOTES, 'UTF-8'));
}
return $aContextInputBlocks;
}
/**
* Returns the context as sequence of input tags to be inserted inside a <form> tag
@@ -321,7 +336,7 @@ class ApplicationContext
$sPrevious = self::GetUrlMakerClass();
self::$m_sUrlMakerClass = $sClass;
$_SESSION['UrlMakerClass'] = $sClass;
Session::Set('UrlMakerClass', $sClass);
return $sPrevious;
}
@@ -334,9 +349,9 @@ class ApplicationContext
{
if (is_null(self::$m_sUrlMakerClass))
{
if (isset($_SESSION['UrlMakerClass']))
if (Session::IsSet('UrlMakerClass'))
{
self::$m_sUrlMakerClass = $_SESSION['UrlMakerClass'];
self::$m_sUrlMakerClass = Session::Get('UrlMakerClass');
}
else
{
@@ -361,26 +376,19 @@ class ApplicationContext
{
$oAppContext = new ApplicationContext();
if (is_null($sUrlMakerClass))
{
$sUrlMakerClass = self::GetUrlMakerClass();
}
if (is_null($sUrlMakerClass)) {
$sUrlMakerClass = self::GetUrlMakerClass();
}
$sUrl = call_user_func(array($sUrlMakerClass, 'MakeObjectUrl'), $sObjClass, $sObjKey);
if (strlen($sUrl) > 0)
{
if ($bWithNavigationContext)
{
return $sUrl."&".$oAppContext->GetForLink();
}
else
{
return $sUrl;
}
}
else
{
return '';
}
if (utils::StrLen($sUrl) > 0) {
if ($bWithNavigationContext) {
return $sUrl."&".$oAppContext->GetForLink();
} else {
return $sUrl;
}
} else {
return '';
}
}
/**
@@ -389,9 +397,9 @@ class ApplicationContext
*/
protected static function LoadPluginProperties()
{
if (isset($_SESSION['PluginProperties']))
if (Session::IsSet('PluginProperties'))
{
self::$m_aPluginProperties = $_SESSION['PluginProperties'];
self::$m_aPluginProperties = Session::Get('PluginProperties');
}
else
{
@@ -411,7 +419,7 @@ class ApplicationContext
if (is_null(self::$m_aPluginProperties)) self::LoadPluginProperties();
self::$m_aPluginProperties[$sPluginClass][$sProperty] = $value;
$_SESSION['PluginProperties'][$sPluginClass][$sProperty] = $value;
Session::Set(['PluginProperties', $sPluginClass, $sProperty], $value);
}
/**

View File

@@ -30,9 +30,9 @@ require_once(APPROOT.'application/newsroomprovider.class.inc.php');
* You may implement such interfaces in a module file (e.g. main.mymodule.php)
*
* @api
* @package LoginExtensibilityAPI
* @copyright Copyright (C) 2010-2021 Combodo SARL
* @license http://opensource.org/licenses/AGPL-3.0
* @package Extensibility
* @since 2.7.0
*/
interface iLoginExtension
@@ -40,12 +40,16 @@ interface iLoginExtension
/**
* Return the list of supported login modes for this plugin
*
* @api
*
* @return array of supported login modes
*/
public function ListSupportedLoginModes();
}
/**
* @api
* @package LoginExtensibilityAPI
* @since 2.7.0
*/
interface iLoginFSMExtension extends iLoginExtension
@@ -57,6 +61,7 @@ interface iLoginFSMExtension extends iLoginExtension
* if LoginWebPage::LOGIN_FSM_RETURN_OK is returned then the login is OK and terminated
* if LoginWebPage::LOGIN_FSM_RETURN_IGNORE is returned then the FSM will proceed to next plugin or state
*
* @api
* @param string $sLoginState (see LoginWebPage::LOGIN_STATE_...)
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
@@ -66,6 +71,8 @@ interface iLoginFSMExtension extends iLoginExtension
}
/**
* @api
* @package LoginExtensibilityAPI
* @since 2.7.0
*/
abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
@@ -112,6 +119,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
/**
* Initialization
*
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -125,6 +133,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
* Detect login mode explicitly without respecting configured order (legacy mode)
* In most case do nothing here
*
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -141,6 +150,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
* 1 - display login form
* 2 - read the values posted by the user
*
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -154,6 +164,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
* Control the validity of the data provided by the user
* Automatic user provisioning can be done here
*
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -164,6 +175,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
}
/**
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -174,6 +186,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
}
/**
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -184,6 +197,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
}
/**
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -194,6 +208,7 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
}
/**
* @api
* @param int $iErrorCode (see LoginWebPage::EXIT_CODE_...)
*
* @return int LoginWebPage::LOGIN_FSM_RETURN_ERROR, LoginWebPage::LOGIN_FSM_RETURN_OK or LoginWebPage::LOGIN_FSM_RETURN_IGNORE
@@ -205,22 +220,28 @@ abstract class AbstractLoginFSMExtension implements iLoginFSMExtension
}
/**
* @api
* @package LoginExtensibilityAPI
* @since 2.7.0
*/
interface iLogoutExtension extends iLoginExtension
{
/**
* Execute all actions to log out properly
* @api
*/
public function LogoutAction();
}
/**
* @api
* @package UIExtensibilityAPI
* @since 2.7.0
*/
interface iLoginUIExtension extends iLoginExtension
{
/**
* @api
* @return LoginTwigContext
*/
public function GetTwigContext();
@@ -228,18 +249,20 @@ interface iLoginUIExtension extends iLoginExtension
/**
* @api
* @package Extensibility
* @package PreferencesExtensibilityAPI
* @since 2.7.0
*/
interface iPreferencesExtension
{
/**
* @api
* @param \WebPage $oPage
*
*/
public function DisplayPreferences(WebPage $oPage);
/**
* @api
* @param \WebPage $oPage
* @param string $sOperation
*
@@ -252,7 +275,7 @@ interface iPreferencesExtension
* Extend this class instead of implementing iPreferencesExtension if you don't need to overload all methods
*
* @api
* @package Extensibility
* @package PreferencesExtensibilityAPI
* @since 2.7.0
*/
abstract class AbstractPreferencesExtension implements iPreferencesExtension
@@ -298,7 +321,7 @@ abstract class AbstractPreferencesExtension implements iPreferencesExtension
* A recommended pattern is to cache data by the mean of static members.
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
*/
interface iApplicationUIExtension
{
@@ -320,6 +343,7 @@ interface iApplicationUIExtension
* }
* </code>
*
* @api
* @param DBObject $oObject The object being displayed
* @param WebPage $oPage The output context
* @param boolean $bEditMode True if the edition form is being displayed
@@ -333,6 +357,7 @@ interface iApplicationUIExtension
*
* The method is called rigth after all the tabs have been displayed
*
* @api
* @param DBObject $oObject The object being displayed
* @param WebPage $oPage The output context
* @param boolean $bEditMode True if the edition form is being displayed
@@ -347,6 +372,7 @@ interface iApplicationUIExtension
* The method is called after the changes from the standard form have been
* taken into account, and before saving the changes into the database.
*
* @api
* @param DBObject $oObject The object being edited
* @param string $sFormPrefix Prefix given to the HTML form inputs
*
@@ -361,6 +387,7 @@ interface iApplicationUIExtension
* javascript into the edition form, and if that code requires to store temporary data
* (this is the case when a file must be uploaded).
*
* @api
* @param string $sTempId Unique temporary identifier made of session_id and transaction_id. It identifies the object in a unique way.
*
* @return void
@@ -372,6 +399,7 @@ interface iApplicationUIExtension
*
* Sorry, the verb has been reserved. You must implement it, but it is not called as of now.
*
* @api
* @param DBObject $oObject The object being displayed
*
* @return string[] desc
@@ -383,6 +411,7 @@ interface iApplicationUIExtension
*
* Sorry, the verb has been reserved. You must implement it, but it is not called as of now.
*
* @api
* @param DBObject $oObject The object being displayed
*
* @return string Path of the icon, relative to the modules directory.
@@ -402,6 +431,7 @@ interface iApplicationUIExtension
* * HILIGHT_CLASS_OK
* * HILIGHT_CLASS_NONE
*
* @api
* @param DBObject $oObject The object being displayed
*
* @return integer The value representing the mood of the object
@@ -428,6 +458,7 @@ interface iApplicationUIExtension
*
* See also iPopupMenuExtension for greater flexibility
*
* @api
* @param DBObjectSet $oSet A set of persistent objects (DBObject)
*
* @return array
@@ -439,7 +470,7 @@ interface iApplicationUIExtension
* Extend this class instead of implementing iApplicationUIExtension if you don't need to overload
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.7.0
*/
abstract class AbstractApplicationUIExtension implements iApplicationUIExtension
@@ -513,7 +544,7 @@ abstract class AbstractApplicationUIExtension implements iApplicationUIExtension
* or through the GUI.
*
* @api
* @package Extensibility
* @package ORMExtensibilityAPI
*/
interface iApplicationObjectExtension
{
@@ -526,6 +557,7 @@ interface iApplicationObjectExtension
* If the extension returns false, then the framework will perform the usual evaluation.
* Otherwise, the answer is definitively "yes, the object has changed".
*
* @api
* @param \cmdbAbstractObject $oObject The target object
*
* @return boolean True if something has changed for the target object
@@ -538,6 +570,7 @@ interface iApplicationObjectExtension
* The GUI calls this verb and reports any issue.
* Anyhow, this API can be called in other contexts such as the CSV import tool.
*
* @api
* @param \cmdbAbstractObject $oObject The target object
*
* @return string[] A list of errors message. An error message is made of one line and it can be displayed to the end-user.
@@ -551,6 +584,7 @@ interface iApplicationObjectExtension
*
* Please not that it is not possible to cascade deletion by this mean: only stopper issues can be handled.
*
* @api
* @param \cmdbAbstractObject $oObject The target object
*
* @return string[] A list of errors message. An error message is made of one line and it can be displayed to the end-user.
@@ -566,6 +600,7 @@ interface iApplicationObjectExtension
* * {@see DBObject::ListPreviousValuesForUpdatedAttributes()} : list of changed attributes and their values before the change
* * {@see DBObject::Get()} : for a given attribute the new value that was persisted
*
* @api
* @param \cmdbAbstractObject $oObject The target object
* @param CMDBChange|null $oChange A change context. Since 2.0 it is fine to ignore it, as the framework does maintain this information
* once for all the changes made within the current page
@@ -581,6 +616,7 @@ interface iApplicationObjectExtension
*
* The method is called right <b>after</b> the object has been written to the database.
*
* @api
* @param \cmdbAbstractObject $oObject The target object
* @param CMDBChange|null $oChange A change context. Since 2.0 it is fine to ignore it, as the framework does maintain this information
* once for all the changes made within the current page
@@ -594,6 +630,7 @@ interface iApplicationObjectExtension
*
* The method is called right <b>before</b> the object will be deleted from the database.
*
* @api
* @param \cmdbAbstractObject $oObject The target object
* @param CMDBChange|null $oChange A change context. Since 2.0 it is fine to ignore it, as the framework does maintain this information
* once for all the changes made within the current page
@@ -607,7 +644,7 @@ interface iApplicationObjectExtension
* Extend this class instead of iApplicationObjectExtension if you don't need to overload all methods
*
* @api
* @package Extensibility
* @package ORMExtensibilityAPI
* @since 2.7.0
*/
abstract class AbstractApplicationObjectExtension implements iApplicationObjectExtension
@@ -667,7 +704,7 @@ abstract class AbstractApplicationObjectExtension implements iApplicationObjectE
* by the application, as long as the class definition is included somewhere in the code
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
*/
interface iPopupMenuExtension
@@ -676,18 +713,21 @@ interface iPopupMenuExtension
* Insert an item into the Actions menu of a list
*
* $param is a DBObjectSet containing the list of objects
* @api
*/
const MENU_OBJLIST_ACTIONS = 1;
/**
* Insert an item into the Toolkit menu of a list
*
* $param is a DBObjectSet containing the list of objects
* @api
*/
const MENU_OBJLIST_TOOLKIT = 2;
/**
* Insert an item into the Actions menu on an object details page
*
* $param is a DBObject instance: the object currently displayed
* @api
*/
const MENU_OBJDETAILS_ACTIONS = 3;
/**
@@ -697,12 +737,14 @@ interface iPopupMenuExtension
* is being displayed.
*
* $param is a Dashboard instance: the dashboard currently displayed
* @api
*/
const MENU_DASHBOARD_ACTIONS = 4;
/**
* Insert an item into the User menu (upper right corner)
*
* $param is null
* @api
*/
const MENU_USER_ACTIONS = 5;
/**
@@ -710,6 +752,7 @@ interface iPopupMenuExtension
*
* $param is an array('portal_id' => $sPortalId, 'object' => $oObject) containing the portal id and a DBObject instance (the object on
* the current line)
* @api
*/
const PORTAL_OBJLISTITEM_ACTIONS = 7;
/**
@@ -717,6 +760,7 @@ interface iPopupMenuExtension
*
* $param is an array('portal_id' => $sPortalId, 'object' => $oObject) containing the portal id and a DBObject instance (the object
* currently displayed)
* @api
*/
const PORTAL_OBJDETAILS_ACTIONS = 8;
@@ -754,6 +798,7 @@ interface iPopupMenuExtension
* This method is called by the framework for each menu.
* The items will be inserted in the menu in the order of the returned array.
*
* @api
* @param int $iMenuId The identifier of the type of menu, as listed by the constants MENU_xxx
* @param mixed $param Depends on $iMenuId, see the constants defined above
*
@@ -766,7 +811,7 @@ interface iPopupMenuExtension
* Base class for the various types of custom menus
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
*/
abstract class ApplicationPopupMenuItem
@@ -776,7 +821,7 @@ abstract class ApplicationPopupMenuItem
/** @ignore */
protected $sLabel;
/** @ignore */
protected $sTooltip;
protected $sTooltip;
/** @ignore */
protected $sIconClass;
/** @ignore */
@@ -833,6 +878,7 @@ abstract class ApplicationPopupMenuItem
}
/**
* @api
* @param $aCssClasses
*/
public function SetCssClasses($aCssClasses)
@@ -843,6 +889,7 @@ abstract class ApplicationPopupMenuItem
/**
* Adds a CSS class to the CSS classes that will be put on the menu item
*
* @api
* @param $sCssClass
*/
public function AddCssClass($sCssClass)
@@ -853,7 +900,7 @@ abstract class ApplicationPopupMenuItem
/**
* @param $sTooltip
*
*
* @since 3.0.0
*/
public function SetTooltip($sTooltip)
@@ -863,24 +910,24 @@ abstract class ApplicationPopupMenuItem
/**
* @return string
*
*
* @since 3.0.0
*/
public function GetTooltip()
{
return $this->sTooltip;
}
/**
* @param $sIconClass
*
*
* @since 3.0.0
*/
public function SetIconClass($sIconClass)
{
$this->sIconClass = $sIconClass;
}
}
/**
* @return string
*
@@ -890,7 +937,7 @@ abstract class ApplicationPopupMenuItem
{
return $this->sIconClass;
}
/**
* Returns the components to create a popup menu item in HTML
*
@@ -909,8 +956,10 @@ abstract class ApplicationPopupMenuItem
/**
* Class for adding an item into a popup menu that browses to the given URL
*
* Note: This works only in the backoffice, {@see \URLButtonItem} for the end-user portal
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
*/
class URLPopupMenuItem extends ApplicationPopupMenuItem
@@ -923,6 +972,7 @@ class URLPopupMenuItem extends ApplicationPopupMenuItem
/**
* Constructor
*
* @api
* @param string $sUID The unique identifier of this menu in iTop... make sure you pass something unique enough
* @param string $sLabel The display label of the menu (must be localized)
* @param string $sUrl If the menu is an hyperlink, provide the absolute hyperlink here
@@ -946,7 +996,7 @@ class URLPopupMenuItem extends ApplicationPopupMenuItem
'tooltip' => $this->sTooltip
);
}
/** @ignore */
public function GetUrl()
{
@@ -963,8 +1013,10 @@ class URLPopupMenuItem extends ApplicationPopupMenuItem
/**
* Class for adding an item into a popup menu that triggers some Javascript code
*
* Note: This works only in the backoffice, {@see \JSButtonItem} for the end-user portal
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
*/
class JSPopupMenuItem extends ApplicationPopupMenuItem
@@ -1014,13 +1066,13 @@ class JSPopupMenuItem extends ApplicationPopupMenuItem
{
return $this->aIncludeJSFiles;
}
/** @ignore */
public function GetJsCode()
{
return $this->sJsCode;
}
/** @ignore */
public function GetUrl()
{
@@ -1033,7 +1085,7 @@ class JSPopupMenuItem extends ApplicationPopupMenuItem
* will automatically reduce several consecutive separators to just one
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
*/
class SeparatorPopupMenuItem extends ApplicationPopupMenuItem
@@ -1042,6 +1094,7 @@ class SeparatorPopupMenuItem extends ApplicationPopupMenuItem
/**
* Constructor
* @api
*/
public function __construct()
{
@@ -1059,7 +1112,7 @@ class SeparatorPopupMenuItem extends ApplicationPopupMenuItem
* Class for adding an item as a button that browses to the given URL
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
*/
class URLButtonItem extends URLPopupMenuItem
@@ -1071,7 +1124,7 @@ class URLButtonItem extends URLPopupMenuItem
* Class for adding an item as a button that runs some JS code
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
*/
class JSButtonItem extends JSPopupMenuItem
@@ -1095,15 +1148,18 @@ class JSButtonItem extends JSPopupMenuItem
* the specified place and can use the passed iTopWebPage object to add javascript or CSS definitions
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.0
* @deprecated since 3.0.0 use iPageUIBlockExtension instead
* @deprecated 3.0.0 If you need to include:
* * JS/CSS files/snippets, use {@see \iBackofficeLinkedScriptsExtension}, {@see \iBackofficeLinkedStylesheetsExtension}, etc instead
* * HTML (and optionally JS/CSS), use {@see \iPageUIBlockExtension} to manipulate {@see \Combodo\iTop\Application\UI\Base\UIBlock} instead
*/
interface iPageUIExtension
{
/**
* Add content to the header of the page
*
* @api
* @param iTopWebPage $oPage The page to insert stuff into.
*
* @return string The HTML content to add into the page
@@ -1113,6 +1169,7 @@ interface iPageUIExtension
/**
* Add content to the footer of the page
*
* @api
* @param iTopWebPage $oPage The page to insert stuff into.
*
* @return string The HTML content to add into the page
@@ -1122,6 +1179,7 @@ interface iPageUIExtension
/**
* Add content to the "admin banner"
*
* @api
* @param iTopWebPage $oPage The page to insert stuff into.
*
* @return string The HTML content to add into the page
@@ -1145,7 +1203,7 @@ interface iPageUIExtension
* the specified place and can use the passed iTopWebPage object to add javascript or CSS definitions
*
* @api
* @package Extensibility
* @package UIBlockExtensibilityAPI
* @since 3.0.0
*/
interface iPageUIBlockExtension
@@ -1176,7 +1234,7 @@ interface iPageUIBlockExtension
* Extend this class instead of iPageUIExtension if you don't need to overload all methods
*
* @api
* @package Extensibility
* @package UIExtensibilityAPI
* @since 2.7.0
* @deprecated since 3.0.0 use AbstractPageUIBlockExtension instead
*/
@@ -1218,7 +1276,7 @@ abstract class AbstractPageUIExtension implements iPageUIExtension
* Extend this class instead of iPageUIExtension if you don't need to overload all methods
*
* @api
* @package Extensibility
* @package UIBlockExtensibilityAPI
* @since 3.0.0
*/
abstract class AbstractPageUIBlockExtension implements iPageUIBlockExtension
@@ -1248,14 +1306,168 @@ abstract class AbstractPageUIBlockExtension implements iPageUIBlockExtension
}
}
/**
* Implement this interface to add script (JS) files to the backoffice pages
*
* @see \iTopWebPage::$a_linked_scripts
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeLinkedScriptsExtension
{
/**
* @see \iTopWebPage::$a_linked_scripts Each script will be included using this property
* @return array An array of absolute URLs to the files to include
*/
public function GetLinkedScriptsAbsUrls(): array;
}
/**
* Implement this interface to add inline script (JS) to the backoffice pages' head.
* Will be executed first, BEFORE the DOM interpretation.
*
* @see \iTopWebPage::$a_early_scripts
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeEarlyScriptExtension
{
/**
* @see \iTopWebPage::$a_early_scripts
* @return string
*/
public function GetEarlyScript(): string;
}
/**
* Implement this interface to add inline script (JS) to the backoffice pages that will be executed immediately, without waiting for the DOM to be ready.
*
* @see \iTopWebPage::$a_scripts
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeScriptExtension
{
/**
* @see \iTopWebPage::$a_scripts
* @return string
*/
public function GetScript(): string;
}
/**
* Implement this interface to add inline script (JS) to the backoffice pages that will be executed right when the DOM is ready.
*
* @see \iTopWebPage::$a_init_scripts
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeInitScriptExtension
{
/**
* @see \iTopWebPage::$a_init_scripts
* @return string
*/
public function GetInitScript(): string;
}
/**
* Implement this interface to add inline script (JS) to the backoffice pages that will be executed slightly AFTER the DOM is ready (just after the init. scripts).
*
* @see \iTopWebPage::$a_ready_scripts
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeReadyScriptExtension
{
/**
* @see \iTopWebPage::$a_ready_scripts
* @return string
*/
public function GetReadyScript(): string;
}
/**
* Implement this interface to add stylesheets (CSS) to the backoffice pages
*
* @see \iTopWebPage::$a_linked_stylesheets
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeLinkedStylesheetsExtension
{
/**
* @see \iTopWebPage::$a_linked_stylesheets
* @return array An array of absolute URLs to the files to include
*/
public function GetLinkedStylesheetsAbsUrls(): array;
}
/**
* Implement this interface to add inline style (CSS) to the backoffice pages' head.
*
* @see \iTopWebPage::$a_styles
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeStyleExtension
{
/**
* @see \iTopWebPage::$a_styles
* @return string
*/
public function GetStyle(): string;
}
/**
* Implement this interface to add Dict entries
*
* @see \iTopWebPage::$a_dict_entries
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeDictEntriesExtension
{
/**
* @see \iTopWebPage::a_dict_entries
* @return array
*/
public function GetDictEntries(): array;
}
/**
* Implement this interface to add Dict entries prefixes
*
* @see \iTopWebPage::$a_dict_entries_prefixes
* @api
* @package BackofficeUIExtensibilityAPI
* @since 3.0.0
*/
interface iBackofficeDictEntriesPrefixesExtension
{
/**
* @see \iTopWebPage::a_dict_entries_prefixes
* @return array
*/
public function GetDictEntriesPrefixes(): array;
}
/**
* Implement this interface to add content to any enhanced portal page
*
* IMPORTANT! Experimental API, may be removed at anytime, we don't recommend to use it just now!
*
* @api
* @package Extensibility
* @since 2.4.0
* @package PortalExtensibilityAPI
*
* @since 2.4.0 interface creation
* @since 2.7.0 change method signatures due to Silex to Symfony migration
*/
interface iPortalUIExtension
{
@@ -1266,6 +1478,7 @@ interface iPortalUIExtension
/**
* Returns an array of CSS file urls
*
* @api
* @param \Symfony\Component\DependencyInjection\Container $oContainer
*
* @return array
@@ -1275,6 +1488,7 @@ interface iPortalUIExtension
/**
* Returns inline (raw) CSS
*
* @api
* @param \Symfony\Component\DependencyInjection\Container $oContainer
*
* @return string
@@ -1284,6 +1498,7 @@ interface iPortalUIExtension
/**
* Returns an array of JS file urls
*
* @api
* @param \Symfony\Component\DependencyInjection\Container $oContainer
*
* @return array
@@ -1293,6 +1508,7 @@ interface iPortalUIExtension
/**
* Returns raw JS code
*
* @api
* @param \Symfony\Component\DependencyInjection\Container $oContainer
*
* @return string
@@ -1302,6 +1518,7 @@ interface iPortalUIExtension
/**
* Returns raw HTML code to put at the end of the <body> tag
*
* @api
* @param \Symfony\Component\DependencyInjection\Container $oContainer
*
* @return string
@@ -1311,6 +1528,7 @@ interface iPortalUIExtension
/**
* Returns raw HTML code to put at the end of the #main-wrapper element
*
* @api
* @param \Symfony\Component\DependencyInjection\Container $oContainer
*
* @return string
@@ -1320,6 +1538,7 @@ interface iPortalUIExtension
/**
* Returns raw HTML code to put at the end of the #topbar and #sidebar elements
*
* @api
* @param \Symfony\Component\DependencyInjection\Container $oContainer
*
* @return string
@@ -1328,7 +1547,11 @@ interface iPortalUIExtension
}
/**
* IMPORTANT! Experimental API, may be removed at anytime, we don't recommend to use it just now!
* Extend this class instead of iPortalUIExtension if you don't need to overload all methods
*
* @api
* @package PortalExtensibilityAPI
* @since 2.4.0
*/
abstract class AbstractPortalUIExtension implements iPortalUIExtension
{
@@ -1393,7 +1616,7 @@ abstract class AbstractPortalUIExtension implements iPortalUIExtension
* Implement this interface to add new operations to the REST/JSON web service
*
* @api
* @package Extensibility
* @package RESTExtensibilityAPI
* @since 2.0.1
*/
interface iRestServiceProvider
@@ -1401,6 +1624,7 @@ interface iRestServiceProvider
/**
* Enumerate services delivered by this class
*
* @api
* @param string $sVersion The version (e.g. 1.0) supported by the services
*
* @return array An array of hash 'verb' => verb, 'description' => description
@@ -1410,6 +1634,7 @@ interface iRestServiceProvider
/**
* Enumerate services delivered by this class
*
* @api
* @param string $sVersion The version (e.g. 1.0) supported by the services
* @param string $sVerb
* @param array $aParams
@@ -1423,69 +1648,90 @@ interface iRestServiceProvider
* Minimal REST response structure. Derive this structure to add response data and error codes.
*
* @api
* @package Extensibility
* @package RESTExtensibilityAPI
* @since 2.0.1
*/
class RestResult
{
/**
* Result: no issue has been encountered
* @api
*/
const OK = 0;
/**
* Result: missing/wrong credentials or the user does not have enough rights to perform the requested operation
* @api
*/
const UNAUTHORIZED = 1;
/**
* Result: the parameter 'version' is missing
* @api
*/
const MISSING_VERSION = 2;
/**
* Result: the parameter 'json_data' is missing
* @api
*/
const MISSING_JSON = 3;
/**
* Result: the input structure is not a valid JSON string
* @api
*/
const INVALID_JSON = 4;
/**
* Result: the parameter 'auth_user' is missing, authentication aborted
* @api
*/
const MISSING_AUTH_USER = 5;
/**
* Result: the parameter 'auth_pwd' is missing, authentication aborted
* @api
*/
const MISSING_AUTH_PWD = 6;
/**
* Result: no operation is available for the specified version
* @api
*/
const UNSUPPORTED_VERSION = 10;
/**
* Result: the requested operation is not valid for the specified version
* @api
*/
const UNKNOWN_OPERATION = 11;
/**
* Result: the requested operation cannot be performed because it can cause data (integrity) loss
* @api
*/
const UNSAFE = 12;
/**
* Result: the request page number is not valid. It must be an integer greater than 0
* @api
*/
const INVALID_PAGE = 13;
/**
* Result: the operation could not be performed, see the message for troubleshooting
* @api
*/
const INTERNAL_ERROR = 100;
/**
* Default constructor - ok!
* @api
*/
public function __construct()
{
$this->code = RestResult::OK;
}
/**
* @var int
* @api
*/
public $code;
/**
* @var string
* @api
*/
public $message;
}
@@ -1493,7 +1739,7 @@ class RestResult
* Helpers for implementing REST services
*
* @api
* @package Extensibility
* @package RESTExtensibilityAPI
*/
class RestUtils
{
@@ -1642,6 +1888,7 @@ class RestUtils
/**
* Read and interpret object search criteria from a Rest/Json structure
*
* @api
* @param string $sClass Name of the class
* @param StdClass $oCriteria Hash of attribute code => value (can be a substructure or a scalar, depending on the nature of the
* attriute)
@@ -1702,6 +1949,8 @@ class RestUtils
*
* @return DBObject The object found
* @throws Exception If the input structure is not valid or it could not find exactly one object
*
* @see DBObject::CheckChangedExtKeysValues() generic method to check that we can access the linked object isn't used in that use case because values can be literal, OQL, friendlyname
*/
public static function FindObjectFromKey($sClass, $key, $bAllowNullValue = false)
{
@@ -1751,6 +2000,7 @@ class RestUtils
/**
* Search objects from a polymorph search specification (Rest/Json)
*
* @api
* @param string $sClass Name of the class
* @param mixed $key Either search criteria (substructure), or an object or an OQL string.
* @param int $iLimit The limit of results to return
@@ -1787,8 +2037,16 @@ class RestUtils
elseif (is_string($key))
{
// OQL
$oSearch = DBObjectSearch::FromOQL($key);
}
try {
$oSearch = DBObjectSearch::FromOQL($key);
} catch (Exception $e) {
throw new CoreOqlException('Query failed to execute', [
'query' => $key,
'exception_class' => get_class($e),
'exception_message' => $e->getMessage(),
]);
}
}
else
{
throw new Exception("Wrong format for key");
@@ -1937,4 +2195,28 @@ class RestUtils
interface iModuleExtension
{
public function __construct();
}
/**
* KPI logging extensibility point
*
* KPI Logger extension
*/
interface iKPILoggerExtension
{
/**
* Init the statistics collected
*
* @return void
*/
public function InitStats();
/**
* Add a new KPI to the stats
*
* @param \Combodo\iTop\Core\Kpi\KpiLogData $oKpiLogData
*
* @return mixed
*/
public function LogOperation($oKpiLogData);
}

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/CaptureWebPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/CaptureWebPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/CLIPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/CLIPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/CSVPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/CSVPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -543,7 +543,7 @@ EOF
if ($bFromDasboardPage) {
$sTitleForHTML = utils::HtmlEntities(Dict::S($this->sTitle));
$sHtml = "<div class=\"ibo-top-bar--toolbar-dashboard-title\">{$sTitleForHTML}</div>";
$sHtml = "<div class=\"ibo-top-bar--toolbar-dashboard-title\" title=\"{$sTitleForHTML}\">{$sTitleForHTML}</div>";
if ($oPage instanceof iTopWebPage) {
$oTopBar = $oPage->GetTopBarLayout();
$oToolbar = ToolbarUIBlockFactory::MakeStandard();
@@ -552,7 +552,7 @@ EOF
$oToolbar->AddHtml($sHtml);
} else {
$oPage->add_script(<<<JS
$(".ibo-top-bar--toolbar-dashboard-title").html("$sTitleForHTML");
$(".ibo-top-bar--toolbar-dashboard-title").html("$sTitleForHTML").attr("title", $('<div>').html("$sTitleForHTML").text());
JS
);
}
@@ -583,7 +583,7 @@ JS
$oPage->add('<div id="select_dashlet" class="ibo-dashboard--available-dashlets--list" data-role="ibo-dashboard--available-dashlets--list">');
$aAvailableDashlets = $this->GetAvailableDashlets();
foreach ($aAvailableDashlets as $sDashletClass => $aInfo) {
$oPage->add('<span dashlet_class="'.$sDashletClass.'" class="ibo-dashboard-editor--available-dashlet-icon dashlet_icon ui-widget-content ui-corner-all" data-role="ibo-dashboard-editor--available-dashlet-icon" id="dashlet_'.$sDashletClass.'" title="'.$aInfo['label'].'"><img src="'.$sUrl.$aInfo['icon'].'" /></span>');
$oPage->add('<span dashlet_class="'.$sDashletClass.'" class="ibo-dashboard-editor--available-dashlet-icon dashlet_icon ui-widget-content ui-corner-all" data-role="ibo-dashboard-editor--available-dashlet-icon" id="dashlet_'.$sDashletClass.'" data-tooltip-content="'.$aInfo['label'].'" title="'.$aInfo['label'].'"><img src="'.$sUrl.$aInfo['icon'].'" /></span>');
}
$oPage->add('</div>');
@@ -789,6 +789,7 @@ class RuntimeDashboard extends Dashboard
/**
* @inheritDoc
* @return bool $bIsNew
* @throws \Exception
*/
public function Save()
@@ -798,6 +799,7 @@ class RuntimeDashboard extends Dashboard
$oUDSearch->AddCondition('user_id', UserRights::GetUserId(), '=');
$oUDSearch->AddCondition('menu_code', $this->sId, '=');
$oUDSet = new DBObjectSet($oUDSearch);
$bIsNew = false;
if ($oUDSet->Count() > 0)
{
// Assuming there is at most one couple {user, menu}!
@@ -811,10 +813,12 @@ class RuntimeDashboard extends Dashboard
$oUserDashboard->Set('user_id', UserRights::GetUserId());
$oUserDashboard->Set('menu_code', $this->sId);
$oUserDashboard->Set('contents', $sXml);
$bIsNew = true;
}
utils::PushArchiveMode(false);
$oUserDashboard->DBWrite();
utils::PopArchiveMode();
return $bIsNew;
}
/**
@@ -860,28 +864,29 @@ class RuntimeDashboard extends Dashboard
{
$bCustomized = false;
if (!appUserPreferences::GetPref('display_original_dashboard_'.$sDashBoardId, false))
{
$sDashboardFileSanitized = utils::RealPath($sDashboardFile, APPROOT);
if (false === $sDashboardFileSanitized) {
throw new SecurityException('Invalid dashboard file !');
}
if (!appUserPreferences::GetPref('display_original_dashboard_'.$sDashBoardId, false)) {
// Search for an eventual user defined dashboard
$oUDSearch = new DBObjectSearch('UserDashboard');
$oUDSearch->AddCondition('user_id', UserRights::GetUserId(), '=');
$oUDSearch->AddCondition('menu_code', $sDashBoardId, '=');
$oUDSet = new DBObjectSet($oUDSearch);
if ($oUDSet->Count() > 0)
{
if ($oUDSet->Count() > 0) {
// Assuming there is at most one couple {user, menu}!
$oUserDashboard = $oUDSet->Fetch();
$sDashboardDefinition = $oUserDashboard->Get('contents');
$bCustomized = true;
}
else
{
$sDashboardDefinition = @file_get_contents($sDashboardFile);
} else {
$sDashboardDefinition = @file_get_contents($sDashboardFileSanitized);
}
}
else
{
$sDashboardDefinition = @file_get_contents($sDashboardFile);
$sDashboardDefinition = @file_get_contents($sDashboardFileSanitized);
}
if ($sDashboardDefinition !== false)
@@ -889,7 +894,7 @@ class RuntimeDashboard extends Dashboard
$oDashboard = new RuntimeDashboard($sDashBoardId);
$oDashboard->FromXml($sDashboardDefinition);
$oDashboard->SetCustomFlag($bCustomized);
$oDashboard->SetDefinitionFile($sDashboardFile);
$oDashboard->SetDefinitionFile($sDashboardFileSanitized);
} else {
$oDashboard = null;
}
@@ -913,6 +918,11 @@ class RuntimeDashboard extends Dashboard
{
$bCustomized = false;
$sDashboardFileSanitized = utils::RealPath(APPROOT.$sDashboardFile, APPROOT);
if (false === $sDashboardFileSanitized) {
throw new SecurityException('Invalid dashboard file !');
}
// Search for an eventual user defined dashboard
$oUDSearch = new DBObjectSearch('UserDashboard');
$oUDSearch->AddCondition('user_id', UserRights::GetUserId(), '=');
@@ -924,7 +934,7 @@ class RuntimeDashboard extends Dashboard
$sDashboardDefinition = $oUserDashboard->Get('contents');
$bCustomized = true;
} else {
$sDashboardDefinition = @file_get_contents($sDashboardFile);
$sDashboardDefinition = @file_get_contents($sDashboardFileSanitized);
}
@@ -932,7 +942,7 @@ class RuntimeDashboard extends Dashboard
$oDashboard = new RuntimeDashboard($sDashBoardId);
$oDashboard->FromXml($sDashboardDefinition);
$oDashboard->SetCustomFlag($bCustomized);
$oDashboard->SetDefinitionFile($sDashboardFile);
$oDashboard->SetDefinitionFile($sDashboardFileSanitized);
} else {
$oDashboard = null;
}
@@ -1065,11 +1075,11 @@ EOF
dashboard.html(data);
dashboard.unblock();
if ($('#ibo-dashboard-selector$sDivId input').prop("checked")) {
$('#ibo-dashboard-selector$sDivId').data('tooltip-content', '$sSwitchToStandard');
$('#ibo-dashboard-selector$sDivId').attr('data-tooltip-content', '$sSwitchToStandard');
} else {
$('#ibo-dashboard-selector$sDivId').data('tooltip-content', '$sSwitchToCustom');
$('#ibo-dashboard-selector$sDivId').attr('data-tooltip-content', '$sSwitchToCustom');
}
CombodoTooltip.InitAllNonInstantiatedTooltips($('#ibo-dashboard-selector$sDivId').parent());
CombodoTooltip.InitAllNonInstantiatedTooltips($('#ibo-dashboard-selector$sDivId').parent(), true);
}
);
}
@@ -1131,7 +1141,7 @@ JS
$oToolbar->AddSubBlock($oActionButton);
$aActions = array();
$sFile = addslashes($this->sDefinitionFile);
$sFile = addslashes(utils::LocalPath($this->sDefinitionFile));
$sJSExtraParams = json_encode($aExtraParams);
if ($this->HasCustomDashboard()) {
$oEdit = new JSPopupMenuItem('UI:Dashboard:Edit', Dict::S('UI:Dashboard:EditCustom'), "return EditDashboard('{$this->sId}', '$sFile', $sJSExtraParams)");
@@ -1254,12 +1264,12 @@ EOF
$sOkButtonLabel = Dict::S('UI:Button:Save');
$sCancelButtonLabel = Dict::S('UI:Button:Cancel');
$sId = addslashes($this->sId);
$sLayoutClass = addslashes($this->sLayoutClass);
$sId = utils::HtmlEntities($this->sId);
$sLayoutClass = utils::HtmlEntities($this->sLayoutClass);
$sAutoReload = $this->bAutoReload ? 'true' : 'false';
$sAutoReloadSec = (string) $this->iAutoReloadSec;
$sTitle = addslashes($this->sTitle);
$sFile = addslashes($this->GetDefinitionFile());
$sTitle = utils::HtmlEntities($this->sTitle);
$sFile = utils::HtmlEntities($this->GetDefinitionFile());
$sUrl = utils::GetAbsoluteUrlAppRoot().'pages/ajax.render.php';
$sReloadURL = $this->GetReloadURL();
@@ -1544,6 +1554,29 @@ JS
return $this->sDefinitionFile;
}
/**
* @param string $sDashboardFileRelative can also be an absolute path (compatibility with old URL)
*
* @return string full path to the Dashboard file
* @throws \SecurityException if path isn't under approot
* @uses utils::RealPath()
* @since 2.7.8 3.0.3 3.1.0 N°4449 remove FPD
*/
public static function GetDashboardFileFromRelativePath($sDashboardFileRelative)
{
if (utils::RealPath($sDashboardFileRelative, APPROOT)) {
// compatibility with old URL containing absolute path !
return $sDashboardFileRelative;
}
$sDashboardFile = APPROOT.$sDashboardFileRelative;
if (false === utils::RealPath($sDashboardFile, APPROOT)) {
throw new SecurityException('Invalid dashboard file !');
}
return $sDashboardFile;
}
/**
* @param string $sDefinitionFile
*/

View File

@@ -16,6 +16,7 @@
// You should have received a copy of the GNU Affero General Public License
// along with iTop. If not, see <http://www.gnu.org/licenses/>
use Combodo\iTop\Application\Helper\WebResourcesHelper;
use Combodo\iTop\Application\UI\Base\Component\Dashlet\DashletContainer;
use Combodo\iTop\Application\UI\Base\Component\Dashlet\DashletFactory;
use Combodo\iTop\Application\UI\Base\Component\Html\Html;
@@ -202,6 +203,24 @@ abstract class Dashlet
$this->OnUpdate();
}
/**
* @return array Rel. path to the app. root of the JS files required by the dashlet
* @since 3.0.0
*/
public function GetJSFilesRelPaths(): array
{
return [];
}
/**
* @return array Rel. path to the app. root of the CSS files required by the dashlet
* @since 3.0.0
*/
public function GetCSSFilesRelPaths(): array
{
return [];
}
/**
* @param \WebPage $oPage
* @param bool $bEditMode
@@ -224,6 +243,9 @@ abstract class Dashlet
$oDashletContainer->AddCSSClasses($this->aCSSClasses);
}
$oDashletContainer->AddMultipleJsFilesRelPaths($this->GetJSFilesRelPaths());
$oDashletContainer->AddMultipleCssFilesRelPaths($this->GetCSSFilesRelPaths());
try {
if (get_class($this->oModelReflection) == 'ModelReflectionRuntime') {
$oBlock = $this->Render($oPage, $bEditMode, $aExtraParams);
@@ -240,7 +262,7 @@ abstract class Dashlet
}
} catch (OqlException $e) {
$oDashletContainer->AddCSSClass("dashlet-content");
$oDashletContainer->AddHtml('<p>'.$e->GetUserFriendlyDescription().'</p>');
$oDashletContainer->AddHtml('<p>'.utils::HtmlEntities($e->GetUserFriendlyDescription()).'</p>');
} catch (Exception $e) {
$oDashletContainer->AddCSSClass("dashlet-content");
$oDashletContainer->AddHtml('<p>'.$e->getMessage().'</p>');
@@ -604,8 +626,7 @@ class DashletUnknown extends Dashlet
$oDashletContainer = new DashletContainer(null, ['dashlet-content']);
$oDashletContainer->AddHtml('<div class="dashlet-ukn-image"><img src="'.$sIconUrl.'" /></div>');
$oDashletContainer->AddHtml('<div class="dashlet-ukn-text">'.$sExplainText.'</div>');
$oDashletContainer->AddHtml('<div class="dashlet-ukn-image"><img src="'.$sIconUrl.'" /></div><div class="dashlet-ukn-text">'.$sExplainText.'</div>');
return $oDashletContainer;
}
@@ -624,8 +645,7 @@ class DashletUnknown extends Dashlet
$oDashletContainer = new DashletContainer(null, ['dashlet-content']);
$oDashletContainer->AddHtml('<div class="dashlet-ukn-image"><img src="'.$sIconUrl.'" /></div>');
$oDashletContainer->AddHtml('<div class="dashlet-ukn-text">'.$sExplainText.'</div>');
$oDashletContainer->AddHtml('<div class="dashlet-ukn-image"><img src="'.$sIconUrl.'" /></div><div class="dashlet-ukn-text">'.$sExplainText.'</div>');
return $oDashletContainer;
}
@@ -906,18 +926,22 @@ class DashletObjectList extends Dashlet
$sShowMenu = $this->aProperties['menu'] ? '1' : '0';
$oFilter = $this->GetDBSearch($aExtraParams);
$sClass = $oFilter->GetClass();
$oPanel = PanelUIBlockFactory::MakeForClass($sClass, Dict::S($sTitle))
->AddCSSClass('ibo-datatable-panel');
//$oPanel = PanelUIBlockFactory::MakeForClass($sClass, Dict::S($sTitle))
// ->AddCSSClass('ibo-datatable-panel');
$oBlock = new DisplayBlock($oFilter, 'list');
$aParams = array(
'menu' => $sShowMenu,
'table_id' => self::APPUSERPREFERENCES_PREFIX.$this->sId,
'surround_with_panel' => false,
'surround_with_panel' => true,
'max_height' => '500px',
"panel_title" => Dict::S($sTitle),
"panel_class" => $sClass,
);
$sBlockId = 'block_'.$this->sId.($bEditMode ? '_edit' : ''); // make a unique id (edition occurring in the same DOM)
$oBlock->DisplayIntoContentBlock($oPanel, $oPage, $sBlockId, array_merge($aExtraParams, $aParams));
//$oBlock->DisplayIntoContentBlock($oPanel, $oPage, $sBlockId, array_merge($aExtraParams, $aParams));
$oPanel = $oBlock->GetDisplay($oPage, $sBlockId, array_merge($aExtraParams, $aParams));
return $oPanel;
}
@@ -984,6 +1008,8 @@ HTML;
$oField = new DesignerLongTextField('query', Dict::S('UI:DashletObjectList:Prop-Query'), $this->aProperties['query']);
$oField->SetMandatory();
$oField->AddCSSClass("ibo-query-oql");
$oField->AddCSSClass("ibo-is-code");
$oForm->AddField($oField);
$oField = new DesignerBooleanField('menu', Dict::S('UI:DashletObjectList:Prop-Menu'), $this->aProperties['menu']);
@@ -1020,6 +1046,8 @@ HTML;
$oField = new DesignerHiddenField('query', Dict::S('UI:DashletObjectList:Prop-Query'), $sOQL);
$oField->SetMandatory();
$oField->AddCSSClass("ibo-query-oql");
$oField->AddCSSClass("ibo-is-code");
$oForm->AddField($oField);
$oField = new DesignerBooleanField('menu', Dict::S('UI:DashletObjectList:Prop-Menu'), $this->aProperties['menu']);
@@ -1256,15 +1284,21 @@ abstract class DashletGroupBy extends Dashlet
break;
}
$oPanel = PanelUIBlockFactory::MakeForClass($sClass, Dict::S($sTitle));
//$oPanel = \Combodo\iTop\Application\UI\Base\Layout\UIContentBlockUIBlockFactory::MakeStandard();
//PanelUIBlockFactory::MakeForClass($sClass, Dict::S($sTitle));
$sBlockId = 'block_'.$this->sId.($bEditMode ? '_edit' : ''); // make a unique id (edition occurring in the same DOM)
$oBlock = new DisplayBlock($oFilter, $sType);
$oBlock->DisplayIntoContentBlock($oPanel, $oPage, $sBlockId, array_merge($aExtraParams, $aParams));
//$oBlock->DisplayIntoContentBlock($oPanel, $oPage, $sBlockId, array_merge($aExtraParams, $aParams));
$aExtraParams["surround_with_panel"] = true;
$aExtraParams["panel_title"] = Dict::S($sTitle);
$aExtraParams["panel_class"] = $sClass;
$oPanel = $oBlock->GetDisplay($oPage, $sBlockId, array_merge($aExtraParams, $aParams));
if ($bEditMode) {
$oPanel->AddHtml('<div class="dashlet-blocker"></div>');
$oPanel->AddHtml('<div class="ibo-dashlet-blocker dashlet-blocker"></div>');
}
return $oPanel;
}
@@ -1363,10 +1397,11 @@ abstract class DashletGroupBy extends Dashlet
$oField = new DesignerLongTextField('query', Dict::S('UI:DashletGroupBy:Prop-Query'), $this->aProperties['query']);
$oField->SetMandatory();
$oField->AddCSSClass("ibo-query-oql");
$oField->AddCSSClass("ibo-is-code");
$oForm->AddField($oField);
try
{
try {
// Group by field: build the list of possible values (attribute codes + ...)
$aGroupBy = $this->GetGroupByOptions($this->aProperties['query']);
@@ -1620,16 +1655,15 @@ abstract class DashletGroupBy extends Dashlet
$oField = new DesignerHiddenField('query', Dict::S('UI:DashletGroupBy:Prop-Query'), $sOQL);
$oField->SetMandatory();
$oField->AddCSSClass("ibo-query-oql");
$oField->AddCSSClass("ibo-is-code");
$oForm->AddField($oField);
if (!is_null($sOQL))
{
if (!is_null($sOQL)) {
$oField = new DesignerComboField('group_by', Dict::S('UI:DashletGroupBy:Prop-GroupBy'), null);
$aGroupBy = $this->GetGroupByOptions($sOQL);
$oField->SetAllowedValues($aGroupBy);
}
else
{
} else {
// Creating a form for reading parameters!
$oField = new DesignerTextField('group_by', Dict::S('UI:DashletGroupBy:Prop-GroupBy'), null);
}
@@ -1666,6 +1700,28 @@ class DashletGroupByPie extends DashletGroupBy
);
}
/**
* @inheritDoc
*/
public function GetJSFilesRelPaths(): array
{
return array_merge(
parent::GetJSFilesRelPaths(),
WebResourcesHelper::GetJSFilesRelPathsForC3JS()
);
}
/**
* @inheritDoc
*/
public function GetCSSFilesRelPaths(): array
{
return array_merge(
parent::GetCSSFilesRelPaths(),
WebResourcesHelper::GetCSSFilesRelPathsForC3JS()
);
}
/**
* @inheritdoc
*/
@@ -2173,6 +2229,8 @@ class DashletHeaderDynamic extends Dashlet
$oField = new DesignerLongTextField('query', Dict::S('UI:DashletHeaderDynamic:Prop-Query'), $this->aProperties['query']);
$oField->SetMandatory();
$oField->AddCSSClass("ibo-query-oql");
$oField->AddCSSClass("ibo-is-code");
$oForm->AddField($oField);
try

View File

@@ -258,6 +258,66 @@
</argument>
</arguments>
</method>
<method id="SetComputedDate">
<arguments>
<argument id="1">
<type>attcode</type>
<mandatory>true</mandatory>
<type_restrictions>
<operation>allow</operation>
<types>
<type id="AttributeDate"/>
<type id="AttributeDateTime"/>
</types>
</type_restrictions>
</argument>
<argument id="2">
<type>string</type>
<mandatory>false</mandatory>
</argument>
<argument id="3">
<type>attcode</type>
<mandatory>false</mandatory>
<type_restrictions>
<operation>allow</operation>
<types>
<type id="AttributeDate"/>
<type id="AttributeDateTime"/>
</types>
</type_restrictions>
</argument>
</arguments>
</method>
<method id="SetComputedDateIfNull">
<arguments>
<argument id="1">
<type>attcode</type>
<mandatory>true</mandatory>
<type_restrictions>
<operation>allow</operation>
<types>
<type id="AttributeDate"/>
<type id="AttributeDateTime"/>
</types>
</type_restrictions>
</argument>
<argument id="2">
<type>string</type>
<mandatory>false</mandatory>
</argument>
<argument id="3">
<type>attcode</type>
<mandatory>false</mandatory>
<type_restrictions>
<operation>allow</operation>
<types>
<type id="AttributeDate"/>
<type id="AttributeDateTime"/>
</types>
</type_restrictions>
</argument>
</arguments>
</method>
<method id="SetCurrentDate">
<arguments>
<argument id="1">
@@ -409,30 +469,6 @@
</argument>
</arguments>
</method>
<method id="PrefillCreationForm">
<arguments>
<argument id="1">
<type>reference</type>
<mandatory>true</mandatory>
</argument>
</arguments>
</method>
<method id="PrefillTransitionForm">
<arguments>
<argument id="1">
<type>reference</type>
<mandatory>true</mandatory>
</argument>
</arguments>
</method>
<method id="PrefillSearchForm">
<arguments>
<argument id="1">
<type>reference</type>
<mandatory>true</mandatory>
</argument>
</arguments>
</method>
</methods>
</class>
</classes>

View File

@@ -386,7 +386,7 @@ EOF;
if (!$oPage->IsPrintableVersion())
{
$sMenuTitle = Dict::S('UI:ConfigureThisList');
$sHtml = '<div class="itop_popup toolkit_menu" id="tk_'.$this->iListId.'"><ul><li><i class="fas fa-tools"></i><i class="fas fa-caret-down"></i><ul>';
$sHtml = '<div class="itop_popup toolkit_menu" id="tk_'.$this->iListId.'"><ul><li aria-label="'.Dict::S('UI:Menu:Toolkit').'"><i class="fas fa-tools"></i><i class="fas fa-caret-down"></i><ul>';
$oMenuItem1 = new JSPopupMenuItem('iTop::ConfigureList', $sMenuTitle, "$('#datatable_dlg_".$this->iListId."').dialog('open');");
$aActions = array(

View File

@@ -10,6 +10,7 @@ use Combodo\iTop\Application\UI\Base\Component\Button\ButtonUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Dashlet\DashletFactory;
use Combodo\iTop\Application\UI\Base\Component\DataTable\DataTableUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Html\Html;
use Combodo\iTop\Application\UI\Base\Component\Panel\PanelUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Pill\PillFactory;
use Combodo\iTop\Application\UI\Base\Component\PopoverMenu\PopoverMenu;
use Combodo\iTop\Application\UI\Base\Component\PopoverMenu\PopoverMenuItem\PopoverMenuItemFactory;
@@ -171,6 +172,10 @@ class DisplayBlock
/**positive or negative*/
'max_height',
/** string Max. height of the list, if not specified will occupy all the available height no matter the pagination */
'localize_values',
/** param for export.php */
'refresh_action',
/**to add refresh button in datatable*/
], DataTableUIBlockFactory::GetAllowedParams()),
'list_search' => array_merge([
'update_history',
@@ -189,6 +194,8 @@ class DisplayBlock
/** string */
'open',
/** bool open by default the search */
'submit_on_load',
/** bool submit the search on loading page */
'class', /** class name */
'search_header_force_dropdown', /** Html for <select> to choose the class to search */
'this',
@@ -198,6 +205,8 @@ class DisplayBlock
/** string search root class */
'open',
/** bool open the search panel by default */
'submit_on_load',
/** bool submit the search on loading page */
'result_list_outer_selector',
/** string js selector of the search result display */
'search_header_force_dropdown',
@@ -257,6 +266,16 @@ class DisplayBlock
'withJSRefreshCallBack',
/** true if dashboard page */
'from_dashboard_page',
/** bool true if list may be render in panel block */
'surround_with_panel',
/** string title of panel block */
'panel_title',
/** string true if panel title should be displayed as html */
'panel_title_is_html',
/** string class for panel block style */
'panel_class',
/** string class for panel block style */
'panel_icon',
];
if (isset($aAllowedParams[$sStyle])) {
@@ -285,7 +304,7 @@ class DisplayBlock
}
}
}
public function GetFilter()
{
return $this->m_oFilter;
@@ -452,10 +471,8 @@ class DisplayBlock
$oHtml->AddSubBlock($this->GetRenderContent($oPage, $aExtraParams, $sId));
} catch (Exception $e) {
if (UserRights::IsAdministrator()) {
$sExceptionContent = <<<HTML
Exception thrown:<br>
<code>{$e->getMessage()}</code>
HTML;
$sExceptionContent = 'Exception thrown:<br><code>'.utils::Sanitize($e->getMessage(), '', utils::ENUM_SANITIZATION_FILTER_STRING).'</code>';
$oExceptionAlert = AlertUIBlockFactory::MakeForFailure('Cannot display results', $sExceptionContent);
$oHtml->AddSubBlock($oExceptionAlert);
}
@@ -522,8 +539,10 @@ HTML;
* @throws DictExceptionMissingString
* @throws MySQLException
* @throws Exception
*
* @since 2.7.7 3.0.1 3.1.0 N°3129 add type hinting to $aExtraParams
*/
public function GetRenderContent(WebPage $oPage, array $aExtraParams = [], string $sId = null)
public function GetRenderContent(WebPage $oPage, array $aExtraParams, string $sId)
{
$sHtml = '';
$oBlock = null;
@@ -836,7 +855,7 @@ JS
{
$oField = new FieldExpression($sFilterCode, $oFilter->GetClassAlias());
$sListExpr = '('.implode(', ', CMDBSource::Quote($condition)).')';
$sOQLCondition = $oField->Render()." IN $sListExpr";
$sOQLCondition = $oField->RenderExpression()." IN $sListExpr";
$oNewCondition = Expression::FromOQL($sOQLCondition);
return $oNewCondition;
}
@@ -997,9 +1016,10 @@ JS
$aCountsQueryResults[$aCountGroupBySingleResult[0]] = $aCountGroupBySingleResult[1];
}
$oAttDef = MetaModel::GetAttributeDef($sClass, $sStateAttrCode);
$aValues = $oAttDef->GetAllowedValues();
foreach ($aStates as $sStateValue) {
$oAttDef = MetaModel::GetAttributeDef($sClass, $sStateAttrCode);
$aStateLabels[$sStateValue] = $oAttDef->GetAsPlainText($sStateValue);
$aStateLabels[$sStateValue] = $aValues[$sStateValue] ?? '';
$aCounts[$sStateValue] = (array_key_exists($sStateValue, $aCountsQueryResults))
? $aCountsQueryResults[$sStateValue]
: 0;
@@ -1025,14 +1045,30 @@ JS
$aCount = $aCounts[$sStateValue];
$sHyperlink = $aCount['link'];
$sCountLabel = $aCount['label'];
$oPill = PillFactory::MakeForState($sClass, $sStateValue)
->SetUrl($sHyperlink)
->SetTooltip($sStateLabel)
->AddHtml("<span class=\"ibo-dashlet-header-dynamic--count\">$sCountLabel</span>")
->AddHtml("<span class=\"ibo-dashlet-header-dynamic--label ibo-text-truncated-with-ellipsis\">$sStateLabel</span>");
$oPill = PillFactory::MakeForState($sClass, $sStateValue);
// N°5849 - Unencode label for ExternalKey attribute because friendlyname is already html encoded thanks to DBObject::GetName() in AttributeExternalKey::GetAllowedValues(). (A fix in this function may have too much impact).
if ($oAttDef instanceof AttributeExternalKey) {
$sPillTooltip = utils::HtmlEntityDecode($sStateLabel);
$sPillLabel = $sStateLabel;
} else {
$sPillTooltip = $sStateLabel;
$sPillLabel = utils::HtmlEntities($sStateLabel);
}
$oPill->SetTooltip($sPillTooltip)
->AddHtml("<span class=\"ibo-dashlet-header-dynamic--count\">$sCountLabel</span><span class=\"ibo-dashlet-header-dynamic--label ibo-text-truncated-with-ellipsis\">".$sPillLabel."</span>");
if ($sHyperlink != '-') {
$oPill->SetUrl($sHyperlink);
}
$oBlock->AddSubBlock($oPill);
}
$aExtraParams['query_params'] = $this->m_oFilter->GetInternalParams();
if(isset($aExtraParams['query_params']['this->object()'])){
$aExtraParams['query_params']['this->class'] = get_class($aExtraParams['query_params']['this->object()']);
$aExtraParams['query_params']['this->id'] = $aExtraParams['query_params']['this->object()']->GetKey();
unset($aExtraParams['query_params']['this->object()']);
}
$aRefreshParams = ['filter' => $this->m_oFilter->ToOQL(), "extra_params" => json_encode($aExtraParams)];
$oBlock->SetJSRefresh(
"$('#".$oBlock->GetId()."').block();
@@ -1173,11 +1209,24 @@ JS
),
);
$sFormat = isset($aExtraParams['format']) ? $aExtraParams['format'] : 'UI:Pagination:HeaderNoSelection';
$sTitle = Dict::Format($sFormat, $iTotalCount);
$aExtraParams['query_params'] = $this->m_oFilter->GetInternalParams();
$aOption['dom'] = 'pl';
$oBlock = DataTableUIBlockFactory::MakeForStaticData($sTitle, $aAttribs, $aData, null, $aExtraParams, $this->m_oFilter->ToOQL(), $aOption);
if (isset($aExtraParams["surround_with_panel"]) && $aExtraParams["surround_with_panel"]) {
$sTitle = Dict::Format($sFormat, $iTotalCount);
$oBlock = PanelUIBlockFactory::MakeForClass($aExtraParams["panel_class"], $aExtraParams["panel_title"]);
$oBlock->AddSubTitleBlock(new Html($sTitle));
$oBlock->AddCSSClass('ibo-datatable-panel');
if(isset($aExtraParams["panel_icon"]) && strlen($aExtraParams["panel_icon"]) > 0){
$oBlock->SetIcon($aExtraParams["panel_icon"]);
}
$oDataTable = DataTableUIBlockFactory::MakeForStaticData("", $aAttribs, $aData, null, $aExtraParams, $this->m_oFilter->ToOQL(), $aOption);
$oBlock->AddSubBlock($oDataTable);
} else {
$sTitle = Dict::Format($sFormat, $iTotalCount);
$oBlock = DataTableUIBlockFactory::MakeForStaticData($sTitle, $aAttribs, $aData, null, $aExtraParams, $this->m_oFilter->ToOQL(), $aOption);
}
} else {
// Simply count the number of elements in the set
@@ -1186,7 +1235,15 @@ JS
if (isset($aExtraParams['format'])) {
$sFormat = $aExtraParams['format'];
}
$oBlock = new Html('<p>'.Dict::Format($sFormat, $iCount).'</p>');
if (isset($aExtraParams["surround_with_panel"]) && $aExtraParams["surround_with_panel"]) {
$oBlock = PanelUIBlockFactory::MakeForClass($aExtraParams["panel_class"], $aExtraParams["panel_title"]);
if(isset($aExtraParams["panel_icon"]) && strlen($aExtraParams["panel_icon"]) > 0){
$oBlock->SetIcon($aExtraParams["panel_icon"]);
}
$oBlock->AddSubBlock(new Html('<p>'.Dict::Format($sFormat, $iCount).'</p>'));
} else {
$oBlock = new Html('<p>'.Dict::Format($sFormat, $iCount).'</p>');
}
}
return $oBlock;
@@ -1273,6 +1330,22 @@ JS
$oBlock->bNotAuthorized = true;
}
} else {
if (isset($aExtraParams['update_history']) && true == $aExtraParams['update_history']) {
$sSearchFilter = $this->m_oSet->GetFilter()->serialize();
// Limit the size of the URL (N°1585 - request uri too long)
if (strlen($sSearchFilter) < SERVER_MAX_URL_LENGTH) {
$oBlock->sEventAttachedData = json_encode(array(
'filter' => $sSearchFilter,
'breadcrumb_id' => "ui-search-".$this->m_oSet->GetClass(),
'breadcrumb_label' => MetaModel::GetName($this->m_oSet->GetClass()),
'breadcrumb_max_count' => utils::GetConfig()->Get('breadcrumb.max_count'),
'breadcrumb_instance_id' => MetaModel::GetConfig()->GetItopInstanceid(),
'breadcrumb_icon' => 'fas fa-search',
'breadcrumb_icon_type' => iTopWebPage::ENUM_BREADCRUMB_ENTRY_ICON_TYPE_CSS_CLASSES,
));
}
}
// The list is made of only 1 class of objects, actions on the list are possible
if (($this->m_oSet->CountWithLimit(1) > 0) && (UserRights::IsActionAllowed($this->m_oSet->GetClass(), UR_ACTION_READ, $this->m_oSet) == UR_ALLOWED_YES)) {
$oBlock->AddSubBlock(cmdbAbstractObject::GetDisplaySetBlock($oPage, $this->m_oSet, $aExtraParams));
@@ -1299,25 +1372,19 @@ JS
$oBlock->bCreateNew = true;
}
}
}
if (isset($aExtraParams['update_history']) && true == $aExtraParams['update_history']) {
$sSearchFilter = $this->m_oSet->GetFilter()->serialize();
// Limit the size of the URL (N°1585 - request uri too long)
if (strlen($sSearchFilter) < SERVER_MAX_URL_LENGTH) {
$oBlock->sEventAttachedData = json_encode(array(
'filter' => $sSearchFilter,
'breadcrumb_id' => "ui-search-".$this->m_oSet->GetClass(),
'breadcrumb_label' => MetaModel::GetName($this->m_oSet->GetClass()),
'breadcrumb_max_count' => utils::GetConfig()->Get('breadcrumb.max_count'),
'breadcrumb_instance_id' => MetaModel::GetConfig()->GetItopInstanceid(),
'breadcrumb_icon' => 'fas fa-search',
'breadcrumb_icon_type' => iTopWebPage::ENUM_BREADCRUMB_ENTRY_ICON_TYPE_CSS_CLASSES,
));
if (isset($aExtraParams["surround_with_panel"]) && $aExtraParams["surround_with_panel"]) {
$oPanel = PanelUIBlockFactory::MakeForClass($aExtraParams["panel_class"], $aExtraParams["panel_title"]);
if(isset($aExtraParams["panel_icon"]) && strlen($aExtraParams["panel_icon"]) > 0){
$oPanel->SetIcon($aExtraParams["panel_icon"]);
}
$oPanel->AddSubBlock($oBlock);
return $oPanel;
}
}
}
}
return $oBlock;
}
@@ -1506,6 +1573,16 @@ JS
$oBlock->sUrl = $sUrl;
if (isset($aExtraParams["surround_with_panel"]) && $aExtraParams["surround_with_panel"]) {
$oPanel = PanelUIBlockFactory::MakeForClass($aExtraParams["panel_class"], $aExtraParams["panel_title"]);
if(isset($aExtraParams["panel_icon"]) && strlen($aExtraParams["panel_icon"]) > 0){
$oPanel->SetIcon($aExtraParams["panel_icon"]);
}
$oPanel->AddSubBlock($oBlock);
return $oPanel;
}
return $oBlock;
}
@@ -1534,6 +1611,7 @@ JS
$iTotalCount = 0;
$aURLs = array();
foreach ($aRes as $iRow => $aRow) {
$sValue = $aRow['grouped_by_1'];
$sHtmlValue = $oGroupByExp->MakeValueLabel($this->m_oFilter, $sValue, $sValue);
@@ -1544,6 +1622,7 @@ JS
'value' => (float)$aRow[$sFctVar],
);
// Build the search for this subset
$oSubsetSearch = $this->m_oFilter->DeepClone();
$oCondition = new BinaryExpression($oGroupByExp, '=', new ScalarExpression($sValue));
@@ -1560,9 +1639,13 @@ JS
switch ($sChartType) {
case 'bars':
$aNames = array();
$iMaxNbCharsInLabel = 0;
$aNames = [];
foreach ($aValues as $idx => $aValue) {
$aNames[$idx] = $aValue['label'];
if ($iMaxNbCharsInLabel < mb_strlen($aValue['label'])) {
$iMaxNbCharsInLabel = mb_strlen($aValue['label']);
}
}
$oBlock = new BlockChartAjaxBars();
$oBlock->sJSNames = json_encode($aNames);
@@ -1570,23 +1653,43 @@ JS
$oBlock->sId = $sId;
$oBlock->sJSURLs = $sJSURLs;
$oBlock->sURLForRefresh = str_replace("'", "\'", $sUrl);
$oBlock->iMaxNbCharsInLabel = $iMaxNbCharsInLabel;
break;
case 'pie':
$aColumns = array();
$aNames = array();
$aColumns = [];
$aNames = [];
foreach ($aValues as $idx => $aValue) {
$aColumns[] = array('series_'.$idx, (float)$aValue['value']);
$aNames['series_'.$idx] = $aValue['label'];
}
$iNbLinesToAddForName = 0;
if (count($aNames) > 50) {
// Calculation of the number of legends line add to the height of the graph to have a maximum of 5 legend columns
$iNbLinesIncludedInChartHeight = 10;
$iNbLinesToAddForName = ceil(count($aNames) / 5) - $iNbLinesIncludedInChartHeight;
}
$oBlock = new BlockChartAjaxPie();
$oBlock->sJSColumns = json_encode($aColumns);
$oBlock->sJSNames = json_encode($aNames);
$oBlock->sId = $sId;
$oBlock->sJSURLs = $sJSURLs;
$oBlock->sURLForRefresh = str_replace("'", "\'", $sUrl);
$oBlock->iNbLinesToAddForName = $iNbLinesToAddForName;
break;
}
if (isset($aExtraParams["surround_with_panel"]) && $aExtraParams["surround_with_panel"]) {
$oPanel = PanelUIBlockFactory::MakeForClass($aExtraParams["panel_class"], $aExtraParams["panel_title"]);
if(isset($aExtraParams["panel_icon"]) && strlen($aExtraParams["panel_icon"]) > 0){
$oPanel->SetIcon($aExtraParams["panel_icon"]);
}
$oPanel->AddSubBlock($oBlock);
return $oPanel;
}
return $oBlock;
}
@@ -1661,7 +1764,24 @@ class HistoryBlock extends DisplayBlock
$this->iLimitCount = $iCount;
}
public function GetRenderContent(WebPage $oPage, array $aExtraParams = [], string $sId = null)
/**
* @param \WebPage $oPage
* @param array $aExtraParams
* @param string $sId
*
* @return string
* @throws \ArchivedObjectException
* @throws \CoreException
* @throws \CoreUnexpectedValue
* @throws \DictExceptionMissingString
* @throws \MissingQueryArgument
* @throws \MySQLException
* @throws \MySQLHasGoneAwayException
*
* @since 2.7.7 3.0.1 3.1.0 N°3129 Remove default value for $aExtraParams and add type hinting for PHP 8.0 compatibility
* (var is unused, and all calls were already made using a default value)
*/
public function GetRenderContent(WebPage $oPage, array $aExtraParams, string $sId)
{
$sHtml = '';
$bTruncated = false;
@@ -1802,11 +1922,10 @@ class MenuBlock extends DisplayBlock
* @throws \DictExceptionMissingString
* @throws \MissingQueryArgument
* @throws \MySQLException
* @throws \MySQLHasGoneAwayException
* @throws \OQLException
* @throws \ReflectionException
*
* @since 2.7.7 3.0.1 3.1.0 N°3129 Remove default value and add type hinting on $aExtraParams for PHP 8.0 compatibility
*/
public function GetRenderContent(WebPage $oPage, array $aExtraParams = [], string $sId = null)
public function GetRenderContent(WebPage $oPage, array $aExtraParams, string $sId)
{
$oRenderBlock = new UIContentBlock();
@@ -1817,7 +1936,7 @@ class MenuBlock extends DisplayBlock
$sClass = $this->m_oFilter->GetClass();
$oSet = new CMDBObjectSet($this->m_oFilter);
$sRefreshAction = $aExtraParams['sRefreshAction'] ?? '';
$sRefreshAction = $aExtraParams['refresh_action'] ?? '';
/** @var array $aRegularActions Any action other than a transition */
$aRegularActions = [];
@@ -2153,14 +2272,20 @@ class MenuBlock extends DisplayBlock
}
if ($oPopupMenuItemsBlock->HasSubBlocks()) {
$oRenderBlock->AddSubBlock($oPopupMenuItemsBlock);
} else {
foreach ($oPopupMenuItemsBlock->GetJsFilesRelPaths() as $sJsPath) {
$oRenderBlock->AddJsFileRelPath($sJsPath);
}
foreach ($oPopupMenuItemsBlock->GetCssFilesRelPaths() as $sCssPath) {
$oRenderBlock->AddCssFileRelPath($sCssPath);
}
}
// Extract favorite actions from their menus
$aFavoriteRegularActions = [];
$aFavoriteTransitionActions = [];
$aCallSpec = [$sClass, 'GetShortcutActions'];
if (is_callable($aCallSpec)) {
$aShortcutActions = call_user_func($aCallSpec, $sClass);
if (is_callable([$sClass, 'GetShortcutActions'])) {
/** @var cmdbAbstractObject $sClass */
$aShortcutActions = $sClass::GetShortcutActions($sClass);
foreach ($aShortcutActions as $key) {
// Regular actions
if (isset($aRegularActions[$key])) {
@@ -2255,13 +2380,25 @@ class MenuBlock extends DisplayBlock
$sIconClass = 'fas fa-share-alt';
$sLabel = '';
break;
default:
if (isset($aAction['icon_class']) && (strlen($aAction['icon_class']) > 0)) {
$sIconClass = $aAction['icon_class'];
$sLabel = '';
}
}
$sTarget = isset($aAction['target']) ? $aAction['target'] : '';
$oActionButton = ButtonUIBlockFactory::MakeLinkNeutral($sUrl, $sLabel, $sIconClass, $sTarget, $sActionId);
$oActionButton = ButtonUIBlockFactory::MakeLinkNeutral($sUrl, $sLabel, $sIconClass, $sTarget, utils::Sanitize($sActionId, '', utils::ENUM_SANITIZATION_FILTER_ELEMENT_IDENTIFIER));
// ResourceId should not be sanitized
$oActionButton->AddDataAttribute('resource-id', $sActionId);
$oActionButton->AddCSSClasses(['ibo-action-button', 'ibo-regular-action-button']);
if (empty($sLabel)) {
$oActionButton->SetTooltip(Dict::S($sActionId));
if (empty($aAction['tooltip'])) {
$oActionButton->SetTooltip(Dict::S($sActionId));
} else {
$oActionButton->SetTooltip($aAction['tooltip']);
}
}
$oActionsToolbar->AddSubBlock($oActionButton);
}
@@ -2269,7 +2406,7 @@ class MenuBlock extends DisplayBlock
// - Refresh
if ($sRefreshAction != '') {
$oActionButton = ButtonUIBlockFactory::MakeAlternativeNeutral('', 'UI:Button:Refresh');
$oActionButton->SetIconClass('fas fa-sync')
$oActionButton->SetIconClass('fas fa-sync-alt')
->SetOnClickJsCode($sRefreshAction)
->SetTooltip(Dict::S('UI:Button:Refresh'))
->AddCSSClasses(['ibo-action-button', 'ibo-regular-action-button']);

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/ErrorPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/ErrorPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -44,15 +44,15 @@ class CoreCannotSaveObjectException extends CoreException
public function getHtmlMessage()
{
$sTitle = Dict::S('UI:Error:SaveFailed');
$sContent = "<span><strong>{$sTitle}</strong></span>";
$sContent = "<span><strong>".utils::HtmlEntities($sTitle)."</strong></span>";
if (count($this->aIssues) == 1) {
$sIssue = reset($this->aIssues);
$sContent .= " <span>{$sIssue}</span>";
$sContent .= " <span>".utils::HtmlEntities($sIssue)."</span>";
} else {
$sContent .= '<ul>';
foreach ($this->aIssues as $sError) {
$sContent .= "<li>$sError</li>";
$sContent .= "<li>".utils::HtmlEntities($sError)."</li>";
}
$sContent .= '</ul>';
}
@@ -60,6 +60,24 @@ class CoreCannotSaveObjectException extends CoreException
return $sContent;
}
public function getTextMessage()
{
$sTitle = Dict::S('UI:Error:SaveFailed');
$sContent = utils::HtmlEntities($sTitle);
if (count($this->aIssues) == 1) {
$sIssue = reset($this->aIssues);
$sContent .= utils::HtmlEntities($sIssue);
} else {
foreach ($this->aIssues as $sError) {
$sContent .= " ".utils::HtmlEntities($sError).", ";
}
}
return $sContent;
}
public function getIssues()
{
return $this->aIssues;

View File

@@ -0,0 +1,36 @@
<?php
/**
* @since 2.7.10 3.0.4 3.1.1 3.2.0 N°6458 object creation
*/
class InvalidExternalKeyValueException extends CoreUnexpectedValue
{
private const ENUM_PARAMS_OBJECT = 'current_object';
private const ENUM_PARAMS_ATTCODE = 'attcode';
private const ENUM_PARAMS_ATTVALUE = 'attvalue';
private const ENUM_PARAMS_USER = 'current_user';
public function __construct($oObject, $sAttCode, $aContextData = null, $oPrevious = null)
{
$aContextData[self::ENUM_PARAMS_OBJECT] = get_class($oObject) . '::' . $oObject->GetKey();
$aContextData[self::ENUM_PARAMS_ATTCODE] = $sAttCode;
$aContextData[self::ENUM_PARAMS_ATTVALUE] = $oObject->Get($sAttCode);
$oCurrentUser = UserRights::GetUserObject();
if (false === is_null($oCurrentUser)) {
$aContextData[self::ENUM_PARAMS_USER] = get_class($oCurrentUser) . '::' . $oCurrentUser->GetKey();
}
parent::__construct('Attribute pointing to an object that is either non existing or not readable by the current user', $aContextData, '', $oPrevious);
}
public function GetAttCode(): string
{
return $this->getContextData()[self::ENUM_PARAMS_ATTCODE];
}
public function GetAttValue(): string
{
return $this->getContextData()[self::ENUM_PARAMS_ATTVALUE];
}
}

View File

@@ -0,0 +1,13 @@
<?php
/*
* @copyright Copyright (C) 2010-2021 Combodo SARL
* @license http://opensource.org/licenses/AGPL-3.0
*/
/**
* @since 2.7.8 3.0.3 3.1.0 N°5538
*/
class MySQLTransactionNotClosedException extends MySQLException
{
}

View File

@@ -102,12 +102,20 @@ class DesignerForm
$sReturn .= '<fieldset>';
$sReturn .= '<legend>'.$sLabel.'</legend>';
}
/** @var \DesignerFormField $oField */
foreach($aFields as $oField) {
$aRow = $oField->Render($oP, $sFormId);
if ($oField->IsVisible()) {
$sValidation = '<span class="prop_apply ibo-prop--apply">'.$this->GetValidationArea($oField->GetFieldId()).'</span>';
$sValidation = '<span class="prop_apply ibo-prop--apply ibo-button ibo-is-alternative">'.$this->GetValidationArea($oField->GetFieldId()).'</span>';
$sField = $aRow['value'].$sValidation;
$aDetails[] = array('label' => $aRow['label'], 'value' => $sField);
$aDetails[] = array(
'label' => $aRow['label'],
'value' => $sField,
'attcode' => $oField->GetCode(),
'attlabel' => $aRow['label'],
'inputid' => $this->GetFieldId($oField->GetCode()),
'inputtype' => $oField->GetInputType(),
);
} else {
$sHiddenFields .= $aRow['value'];
}
@@ -203,51 +211,41 @@ class DesignerForm
$sActionUrl = addslashes($this->sSubmitTo);
$sJSSubmitParams = json_encode($this->aSubmitParams);
$sFormId = $this->GetFormId();
if ($this->oParentForm == null)
{
if ($this->oParentForm == null) {
$sReturn = '<form id="'.$sFormId.'" onsubmit="return false;">';
$sReturn .= '<table class="prop_table">';
$sReturn .= '<thead><tr><th class="prop_header">'.Dict::S('UI:Form:Property').'</th><th class="prop_header">'.Dict::S('UI:Form:Value').'</th><th colspan="2" class="prop_header">&nbsp;</th></tr></thead><tbody>';
$sReturn .= '<thead><tr><th class="ibo-prop-header">'.Dict::S('UI:Form:Property').'</th><th class="ibo-prop-header">'.Dict::S('UI:Form:Value').'</th><th colspan="2" class="ibo-prop-header">&nbsp;</th></tr></thead><tbody>';
}
$sHiddenFields = '';
foreach($this->aFieldSets as $sLabel => $aFields)
{
foreach ($this->aFieldSets as $sLabel => $aFields) {
$aDetails = array();
if ($sLabel != '')
{
if ($sLabel != '') {
$sReturn .= $this->StartRow().'<th colspan="4">'.$sLabel.'</th>'.$this->EndRow();
}
foreach($aFields as $oField)
{
foreach ($aFields as $oField) {
$aRow = $oField->Render($oP, $sFormId, 'property');
if ($oField->IsVisible())
{
if ($oField->IsVisible()) {
$sFieldId = $this->GetFieldId($oField->GetCode());
$sValidation = $this->GetValidationArea($sFieldId, '<span data-tooltip-content="Apply"><i class="fas fa-check"></i></span>');
$sValidationFields = '</td><td class="prop_icon prop_apply ibo-prop--apply">'.$sValidation.'</td><td class="prop_icon prop_cancel ibo-prop--cancel"><span data-tooltip-content="Revert"><i class="fas fa-times"></i></span></td>'.$this->EndRow();
$sPath = $this->GetHierarchyPath().'/'.$oField->GetCode();
if (is_null($aRow['label']))
{
$sReturn .= $this->StartRow($sFieldId).'<td class="prop_value ibo-field--value" colspan="2">'.$aRow['value'];
$sValidation = $this->GetValidationArea($sFieldId, '<div class="ibo-button ibo-is-alternative ibo-is-success" data-tooltip-content="'.Dict::Format('UI:DashboardEdit:Apply').'"><i class="fas fa-check"></i></div>');
$sValidationFields = '</td><td class="prop_icon prop_apply ibo-prop--apply" >'.$sValidation.'</td><td class="prop_icon prop_cancel ibo-prop--cancel"><span><div class="ibo-button ibo-is-alternative ibo-is-neutral" data-tooltip-content="'.Dict::Format('UI:DashboardEdit:Revert').'"><i class="fas fa-undo"></i></div></span></td>'
.$this->EndRow();
if (is_null($aRow['label'])) {
$sReturn .= $this->StartRow($sFieldId).'<td class="prop_value" colspan="2">'.$aRow['value'];
} else {
$sReturn .= $this->StartRow($sFieldId).'<td class="prop_label">'.$aRow['label'].'</td><td class="prop_value">'.$aRow['value'];
}
else
{
$sReturn .= $this->StartRow($sFieldId).'<td class="prop_label ibo-field--label">'.$aRow['label'].'</td><td class="prop_value ibo-field--value">'.$aRow['value'];
}
if (!($oField instanceof DesignerFormSelectorField) && !($oField instanceof DesignerMultipleSubFormField))
{
if (!($oField instanceof DesignerFormSelectorField) && !($oField instanceof DesignerMultipleSubFormField)) {
$sReturn .= $sValidationFields;
}
$sNotifyParentSelectorJS = is_null($sNotifyParentSelector) ? 'null' : "'".addslashes($sNotifyParentSelector)."'";
$sAutoApply = $oField->IsAutoApply() ? 'true' : 'false';
$sHandlerEquals = $oField->GetHandlerEquals();
$sHandlerGetValue = $oField->GetHandlerGetValue();
$sWidgetClass = $oField->GetWidgetClass();
$sJSExtraParams = '';
if (count($oField->GetWidgetExtraParams()) > 0)
@@ -356,7 +354,7 @@ EOF
<<<EOF
$('#$sDialogId').dialog({
height: 'auto',
maxHeight: $(window).height() - 8,
maxHeight: $(window).height() * 0.9,
width: $iDialogWidth,
modal: true,
autoOpen: $sAutoOpen,
@@ -712,11 +710,27 @@ class DesignerFormField
$this->bMandatory = false;
$this->bReadOnly = false;
$this->bAutoApply = false;
$this->aCSSClasses = array('ibo-input');
$this->aCSSClasses = [];
if (ContextTag::Check(ContextTag::TAG_CONSOLE)) {
$this->aCSSClasses[] = 'ibo-input';
}
$this->bDisplayed = true;
$this->aWidgetExtraParams = array();
}
/**
* Important, for now we use constants from the \cmdbAbstractObject class, introducing a coupling that should not exist.
* This has been traced under N°4241 and will be discussed during the next modernization batch.
*
* @return string|null Return the input type of the field
* @see \cmdbAbstractObject::ENUM_INPUT_TYPE_XXX
* @since 3.0.0
*/
public function GetInputType(): ?string
{
return cmdbAbstractObject::ENUM_INPUT_TYPE_SINGLE_INPUT;
}
/**
* @return string
*/
@@ -1054,7 +1068,18 @@ class DesignerLongTextField extends DesignerTextField
public function __construct($sCode, $sLabel = '', $defaultValue = '')
{
parent::__construct($sCode, $sLabel, $defaultValue);
$this->aCSSClasses[] = 'ibo-input-text';
if (ContextTag::Check(ContextTag::TAG_CONSOLE)) {
$this->aCSSClasses[] = 'ibo-input-text';
}
}
/**
* @inheritDoc
*/
public function GetInputType(): string
{
return cmdbAbstractObject::ENUM_INPUT_TYPE_TEXTAREA;
}
public function Render(WebPage $oP, $sFormId, $sRenderMode='dialog')
@@ -1180,14 +1205,35 @@ class DesignerComboField extends DesignerFormField
$this->bMultipleSelection = false;
$this->bOtherChoices = false;
$this->sNullLabel = Dict::S('UI:SelectOne');
$this->aCSSClasses[] = 'ibo-input-select';
if (ContextTag::Check(ContextTag::TAG_CONSOLE)) {
$this->aCSSClasses[] = 'ibo-input-select';
}
$this->bAutoApply = true;
$this->bSorted = true; // Sorted by default
}
public function SetAllowedValues($aAllowedValues)
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
if ($this->bMultipleSelection) {
return cmdbAbstractObject::ENUM_INPUT_TYPE_DROPDOWN_MULTIPLE_CHOICES;
}
else {
return cmdbAbstractObject::ENUM_INPUT_TYPE_DROPDOWN_RAW;
}
}
public function SetAllowedValues(?array $aAllowedValues)
{
// Make sure to have an actual array for values
if (is_null($aAllowedValues)) {
$aAllowedValues = [];
}
$this->aAllowedValues = $aAllowedValues;
}
@@ -1226,7 +1272,7 @@ class DesignerComboField extends DesignerFormField
$sChecked = $this->defaultValue ? 'checked' : '';
$sMandatory = $this->bMandatory ? 'true' : 'false';
$sReadOnly = $this->IsReadOnly() ? 'disabled="disabled"' : '';
if ($this->IsSorted())
if ($this->IsSorted() )
{
asort($this->aAllowedValues);
}
@@ -1264,31 +1310,27 @@ class DesignerComboField extends DesignerFormField
{
if ($this->bMultipleSelection)
{
$sHtml = "<select $sCSSClasses multiple size=\"8\"id=\"$sId\" name=\"$sName\">";
$sHtml = "<span><select $sCSSClasses multiple size=\"8\"id=\"$sId\" name=\"$sName\">";
}
else
{
$sHtml = "<select $sCSSClasses id=\"$sId\" name=\"$sName\">";
$sHtml = "<span class=\"ibo-input-select-wrapper\"><select $sCSSClasses id=\"$sId\" name=\"$sName\">";
if ($this->sNullLabel != '')
{
$sHtml .= "<option value=\"\">".$this->sNullLabel."</option>";
}
}
foreach($this->aAllowedValues as $sKey => $sDisplayValue)
{
if ($this->bMultipleSelection)
{
foreach ($this->aAllowedValues as $sKey => $sDisplayValue) {
if ($this->bMultipleSelection) {
$sSelected = in_array($sKey, $this->defaultValue) ? 'selected' : '';
}
else
{
} else {
$sSelected = ($sKey == $this->defaultValue) ? 'selected' : '';
}
// Quick and dirty: display the menu parents as a tree
$sHtmlValue = str_replace(' ', '&nbsp;', htmlentities($sDisplayValue, ENT_QUOTES, 'UTF-8'));
$sHtmlValue = str_replace(' ', '&nbsp;', $sDisplayValue);
$sHtml .= "<option value=\"".htmlentities($sKey, ENT_QUOTES, 'UTF-8')."\" $sSelected>$sHtmlValue</option>";
}
$sHtml .= "</select>";
$sHtml .= "</select></span>";
if ($this->bOtherChoices)
{
$sHtml .= '<br/><input type="checkbox" id="other_chk_'.$sId.'"><label for="other_chk_'.$sId.'">&nbsp;Other:</label>&nbsp;<input type="text" id="other_'.$sId.'" name="other_'.$sName.'" size="30"/>';
@@ -1319,7 +1361,17 @@ class DesignerBooleanField extends DesignerFormField
{
parent::__construct($sCode, $sLabel, $defaultValue);
$this->bAutoApply = true;
$this->aCSSClasses[] = 'ibo-input-checkbox';
if (ContextTag::Check(ContextTag::TAG_CONSOLE)) {
$this->aCSSClasses[] = 'ibo-input-checkbox';
}
}
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
return cmdbAbstractObject::ENUM_INPUT_TYPE_CHECKBOX;
}
public function Render(WebPage $oP, $sFormId, $sRenderMode='dialog')
@@ -1380,6 +1432,14 @@ class DesignerHiddenField extends DesignerFormField
{
parent::__construct($sCode, $sLabel, $defaultValue);
}
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
return null;
}
public function IsVisible()
{
@@ -1407,6 +1467,14 @@ class DesignerIconSelectionField extends DesignerFormField
$this->bAutoApply = true;
$this->sUploadUrl = null;
}
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
return cmdbAbstractObject::ENUM_INPUT_TYPE_DROPDOWN_DECORATED;
}
public function SetAllowedValues($aAllowedValues)
{
@@ -1423,28 +1491,33 @@ class DesignerIconSelectionField extends DesignerFormField
$sId = $this->oForm->GetFieldId($this->sCode);
$sName = $this->oForm->GetFieldName($this->sCode);
$idx = 0;
foreach($this->aAllowedValues as $index => $aValue)
{
if ($aValue['value'] == $this->defaultValue)
{
$idxFallback = 0;
foreach ($this->aAllowedValues as $index => $aValue) {
if ($aValue['value'] == $this->defaultValue) {
$idx = $index;
break;
}
//fallback if url of default value contains ../
//for contact, icon is http://localhost/env-production/itop-structure/../../images/icons/icons8-customer.svg => not found http://localhost/images/icons/icons8-customer.svg
if (basename($aValue['value']) == basename($this->defaultValue)) {
$idxFallback = $index;
}
}
if ($idx == 0) {
$idx = $idxFallback;
}
$sJSItems = json_encode($this->aAllowedValues);
$sPostUploadTo = ($this->sUploadUrl == null) ? 'null' : "'{$this->sUploadUrl}'";
if (!$this->IsReadOnly())
{
if (!$this->IsReadOnly()) {
$sDefaultValue = ($this->defaultValue !== '') ? $this->defaultValue : $this->aAllowedValues[$idx]['value'];
$sValue = "<input type=\"hidden\" id=\"$sId\" name=\"$sName\" value=\"{$sDefaultValue}\"/>";
$sCSSClasses = ContextTag::Check(ContextTag::TAG_CONSOLE) ? 'class="ibo-input-select-wrapper"' : '';
$sValue = "<span $sCSSClasses><input type=\"hidden\" id=\"$sId\" name=\"$sName\" value=\"{$sDefaultValue}\"/></span>";
$oP->add_ready_script(
<<<EOF
<<<EOF
$('#$sId').icon_select({current_idx: $idx, items: $sJSItems, post_upload_to: $sPostUploadTo});
EOF
);
}
else
{
} else {
$sValue = '<span style="display:inline-block;line-height:48px;height:48px;"><span><img style="vertical-align:middle" src="'.$this->aAllowedValues[$idx]['icon'].'" />&nbsp;'.htmlentities($this->aAllowedValues[$idx]['label'], ENT_QUOTES, 'UTF-8').'</span></span>';
}
$sReadOnly = $this->IsReadOnly() ? 'disabled' : '';
@@ -1459,18 +1532,21 @@ class RunTimeIconSelectionField extends DesignerIconSelectionField
public function __construct($sCode, $sLabel = '', $defaultValue = '')
{
parent::__construct($sCode, $sLabel, $defaultValue);
$aFolderList = [
APPROOT.'env-'.utils::GetCurrentEnvironment() => utils::GetAbsoluteUrlModulesRoot(),
APPROOT.'images/icons' => utils::GetAbsoluteUrlAppRoot().'images/icons',
];
if (count(self::$aAllIcons) == 0) {
foreach ($aFolderList as $sFolderPath => $sUrlPrefix) {
$aIcons = self::FindIconsOnDisk($sFolderPath);
ksort($aIcons);
if (count(self::$aAllIcons) == 0)
{
self::$aAllIcons = self::FindIconsOnDisk(APPROOT.'env-'.utils::GetCurrentEnvironment());
ksort(self::$aAllIcons);
foreach ($aIcons as $sFilePath) {
self::$aAllIcons[] = array('value' => $sFilePath, 'label' => basename($sFilePath), 'icon' => $sUrlPrefix.$sFilePath);
}
}
}
$aValues = array();
foreach(self::$aAllIcons as $sFilePath)
{
$aValues[] = array('value' => $sFilePath, 'label' => basename($sFilePath), 'icon' => utils::GetAbsoluteUrlModulesRoot().$sFilePath);
}
$this->SetAllowedValues($aValues);
$this->SetAllowedValues(self::$aAllIcons);
}
static protected function FindIconsOnDisk($sBaseDir, $sDir = '')
@@ -1501,26 +1577,29 @@ class RunTimeIconSelectionField extends DesignerIconSelectionField
SetupUtils::builddir(dirname($sCacheFile));
file_put_contents($sCacheFile, $sAvailableIcons, LOCK_EX);
}
return $aFiles;
}
static protected function _FindIconsOnDisk($sBaseDir, $sDir = '')
static protected function _FindIconsOnDisk($sBaseDir, $sDir = '', &$aFilesSpecs = [])
{
$aResult = array();
$aResult = [];
// Populate automatically the list of icon files
if ($hDir = @opendir($sBaseDir.'/'.$sDir))
{
while (($sFile = readdir($hDir)) !== false)
{
if ($hDir = @opendir($sBaseDir.'/'.$sDir)) {
while (($sFile = readdir($hDir)) !== false) {
$aMatches = array();
if (($sFile != '.') && ($sFile != '..') && ($sFile != 'lifecycle') && is_dir($sBaseDir.'/'.$sDir.'/'.$sFile))
{
if (($sFile != '.') && ($sFile != '..') && ($sFile != 'lifecycle') && is_dir($sBaseDir.'/'.$sDir.'/'.$sFile)) {
$sDirSubPath = ($sDir == '') ? $sFile : $sDir.'/'.$sFile;
$aResult = array_merge($aResult, self::_FindIconsOnDisk($sBaseDir, $sDirSubPath));
$aResult = array_merge($aResult, self::_FindIconsOnDisk($sBaseDir, $sDirSubPath, $aFilesSpecs));
}
if (preg_match("/\.(png|jpg|jpeg|gif)$/i", $sFile, $aMatches)) // png, jp(e)g and gif are considered valid
$sSize = filesize($sBaseDir.'/'.$sDir.'/'.$sFile);
if (isset($aFilesSpecs[$sFile]) && $aFilesSpecs[$sFile] == $sSize) {
continue;
}
if (preg_match("/\.(png|jpg|jpeg|gif|svg)$/i", $sFile, $aMatches)) // png, jp(e)g, gif and svg are considered valid
{
$aResult[$sFile.'_'.$sDir] = $sDir.'/'.$sFile;
$aFilesSpecs[$sFile] = $sSize;
}
}
closedir($hDir);
@@ -1566,6 +1645,14 @@ class DesignerSortableField extends DesignerFormField
parent::__construct($sCode, $sLabel, $defaultValue);
$this->aAllowedValues = array();
}
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
return null;
}
public function SetAllowedValues($aAllowedValues)
{
@@ -1602,7 +1689,17 @@ class DesignerFormSelectorField extends DesignerFormField
$this->defaultRealValue = $defaultValue;
$this->aSubForms = array();
$this->bSorted = true;
$this->aCSSClasses[] = 'ibo-input-select';
if (ContextTag::Check(ContextTag::TAG_CONSOLE)) {
$this->aCSSClasses[] = 'ibo-input-select';
}
}
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
return null;
}
public function IsSorted()
@@ -1645,27 +1742,23 @@ class DesignerFormSelectorField extends DesignerFormField
{
$sId = $this->oForm->GetFieldId($this->sCode);
$sName = $this->oForm->GetFieldName($this->sCode);
$sReadOnly = $this->IsReadOnly() ? 'disabled="disabled"' : '';
$sReadOnly = $this->IsReadOnly() ? 'disabled="disabled"' : '';
$this->aCSSClasses[] = 'formSelector';
$sCSSClasses = '';
if (count($this->aCSSClasses) > 0)
{
if (count($this->aCSSClasses) > 0) {
$sCSSClasses = 'class="'.implode(' ', $this->aCSSClasses).'"';
}
if ($this->IsSorted())
{
if ($this->IsSorted()) {
uasort($this->aSubForms, array(get_class($this), 'SortOnFormLabel'));
}
if ($this->IsReadOnly())
{
if ($this->IsReadOnly()) {
$sDisplayValue = '';
$sHiddenValue = '';
foreach($this->aSubForms as $iKey => $aFormData)
{
foreach ($this->aSubForms as $iKey => $aFormData) {
if ($iKey == $this->defaultValue) // Default value is actually the index
{
$sDisplayValue = htmlentities($aFormData['label'], ENT_QUOTES, 'UTF-8');
@@ -1674,35 +1767,29 @@ class DesignerFormSelectorField extends DesignerFormField
}
}
$sHtml = "<span $sCSSClasses>".$sDisplayValue.$sHiddenValue."</span>";
}
else
{
$sHtml = "<select $sCSSClasses id=\"$sId\" name=\"$sName\" $sReadOnly>";
foreach($this->aSubForms as $iKey => $aFormData)
{
} else {
$sHtml = "<span class=\"ibo-input-select-wrapper\"><select $sCSSClasses id=\"$sId\" name=\"$sName\" $sReadOnly>";
foreach ($this->aSubForms as $iKey => $aFormData) {
$sDisplayValue = htmlentities($aFormData['label'], ENT_QUOTES, 'UTF-8');
$sValue = htmlentities($aFormData['value'], ENT_QUOTES, 'UTF-8');
$sSelected = ($iKey == $this->defaultValue) ? 'selected' : '';
$sHtml .= "<option data-value=\"$sValue\" value=\"$iKey\" $sSelected>".$sDisplayValue."</option>";
}
$sHtml .= "</select>";
$sHtml .= "</select></span>";
}
if ($sRenderMode == 'property')
{
$sHtml .= '</td><td class="prop_icon prop_apply"><span title="Apply" class="ui-icon ui-icon-circle-check"/></td><td class="prop_icon prop_cancel"><span title="Revert" class="ui-icon ui-icon-circle-close"/></td></tr>';
if ($sRenderMode == 'property') {
$sHtml .= '</td><td class="prop_icon prop_apply ibo-prop--apply"><span><button class="ibo-button ibo-is-alternative ibo-is-success" data-tooltip-content="'.Dict::Format('UI:DashboardEdit:Apply').'"><i class="fas fa-check"></i></button></span></td><td class="prop_icon prop_cancel ibo-prop--cancel"><span><button class="ibo-button ibo-is-alternative ibo-is-neutral" data-tooltip-content="'.Dict::Format('UI:DashboardEdit:Revert').'"><i class="fas fa-times"></i></button></span></td></tr>';
}
foreach($this->aSubForms as $sKey => $aFormData)
{
foreach ($this->aSubForms as $sKey => $aFormData) {
$sId = $this->oForm->GetFieldId($this->sCode);
$sStyle = (($sKey == $this->defaultValue) && $this->oForm->IsDisplayed()) ? '' : 'style="display:none"';
$oSubForm = $aFormData['form'];
$oSubForm->SetParentForm($this->oForm);
$oSubForm->CopySubmitParams($this->oForm);
$oSubForm->SetPrefix($this->oForm->GetPrefix().$sKey.'_');
if ($sRenderMode == 'property')
{
if ($sRenderMode == 'property') {
// Note: Managing the visibility of nested subforms had several implications
// 1) Attributes are displayed in a table and we have to group them in as many tbodys as necessary to hide/show the various options depending on the current selection
// 2) It is not possible to nest tbody tags. Therefore, it is not possible to manage the visibility the same way as it is done for the dialog mode (using nested divs).
@@ -1800,6 +1887,14 @@ class DesignerSubFormField extends DesignerFormField
parent::__construct('', $sLabel, '');
$this->oSubForm = $oSubForm;
}
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
return null;
}
public function Render(WebPage $oP, $sFormId, $sRenderMode='dialog')
{
@@ -1844,6 +1939,14 @@ class DesignerStaticTextField extends DesignerFormField
parent::__construct($sCode, $sLabel, $defaultValue);
}
/**
* @inheritDoc
*/
public function GetInputType(): ?string
{
return null;
}
public function Render(WebPage $oP, $sFormId, $sRenderMode='dialog')
{
return array('label' => $this->sLabel, 'value' => $this->defaultValue);

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/iTopWebPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/iTopWebPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/iTopWizardWebPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/iTopWizardWebPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -1,4 +1,7 @@
<?php
use Combodo\iTop\Application\Helper\Session;
/**
* Class LoginBasic
*
@@ -20,19 +23,19 @@ class LoginBasic extends AbstractLoginFSMExtension
protected function OnModeDetection(&$iErrorCode)
{
if (!isset($_SESSION['login_mode']))
if (!Session::IsSet('login_mode'))
{
if (isset($_SERVER['HTTP_AUTHORIZATION']) && !empty($_SERVER['HTTP_AUTHORIZATION']))
{
$_SESSION['login_mode'] = 'basic';
Session::Set('login_mode', 'basic');
}
elseif (isset($_SERVER['REDIRECT_HTTP_AUTHORIZATION']) && !empty($_SERVER['REDIRECT_HTTP_AUTHORIZATION']))
{
$_SESSION['login_mode'] = 'basic';
Session::Set('login_mode', 'basic');
}
elseif (isset($_SERVER['PHP_AUTH_USER']))
{
$_SESSION['login_mode'] = 'basic';
Session::Set('login_mode', 'basic');
}
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
@@ -40,10 +43,10 @@ class LoginBasic extends AbstractLoginFSMExtension
protected function OnReadCredentials(&$iErrorCode)
{
if (!isset($_SESSION['login_mode']) || $_SESSION['login_mode'] == 'basic')
if (!Session::IsSet('login_mode') || Session::Get('login_mode') == 'basic')
{
list($sAuthUser, $sAuthPwd) = $this->GetAuthUserAndPassword();
$_SESSION['login_temp_auth_user'] = $sAuthUser;
list($sAuthUser) = $this->GetAuthUserAndPassword();
Session::Set('login_temp_auth_user', $sAuthUser);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
@@ -51,32 +54,37 @@ class LoginBasic extends AbstractLoginFSMExtension
protected function OnCheckCredentials(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'basic')
if (Session::Get('login_mode') == 'basic')
{
list($sAuthUser, $sAuthPwd) = $this->GetAuthUserAndPassword();
if (!UserRights::CheckCredentials($sAuthUser, $sAuthPwd, $_SESSION['login_mode'], 'internal'))
if (!UserRights::CheckCredentials($sAuthUser, $sAuthPwd, Session::Get('login_mode'), 'internal'))
{
$iErrorCode = LoginWebPage::EXIT_CODE_WRONGCREDENTIALS;
return LoginWebPage::LOGIN_FSM_ERROR;
}
Session::Set('auth_user', $sAuthUser);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
protected function OnCredentialsOK(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'basic')
if (Session::Get('login_mode') == 'basic')
{
list($sAuthUser) = $this->GetAuthUserAndPassword();
LoginWebPage::OnLoginSuccess($sAuthUser, 'internal', $_SESSION['login_mode']);
LoginWebPage::OnLoginSuccess(Session::Get('auth_user'), 'internal', Session::Get('login_mode'));
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
protected function OnError(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'basic')
if (Session::Get('login_mode') == 'basic')
{
$iOnExit = LoginWebPage::getIOnExit();
if ($iOnExit === LoginWebPage::EXIT_RETURN)
{
return LoginWebPage::LOGIN_FSM_RETURN; // Error, exit FSM
}
LoginWebPage::HTTP401Error();
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
@@ -84,9 +92,9 @@ class LoginBasic extends AbstractLoginFSMExtension
protected function OnConnected(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'basic')
if (Session::Get('login_mode') == 'basic')
{
$_SESSION['can_logoff'] = true;
Session::Set('can_logoff', true);
return LoginWebPage::CheckLoggedUser($iErrorCode);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;

View File

@@ -4,6 +4,8 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Application\Helper\Session;
/**
* Class LoginDefaultBefore
*/
@@ -23,7 +25,7 @@ class LoginDefaultBefore extends AbstractLoginFSMExtension
{
$iErrorCode = LoginWebPage::EXIT_CODE_OK;
unset($_SESSION['login_temp_auth_user']);
Session::Unset('login_temp_auth_user');
// Check if proposed login mode is present and allowed
$aAllowedLoginTypes = MetaModel::GetConfig()->GetAllowedLoginTypes();
@@ -32,11 +34,11 @@ class LoginDefaultBefore extends AbstractLoginFSMExtension
if ($index !== false)
{
// Force login mode
$_SESSION['login_mode'] = $sProposedLoginMode;
Session::Set('login_mode', $sProposedLoginMode);
}
else
{
unset($_SESSION['login_mode']);
Session::Unset('login_mode');
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
@@ -77,7 +79,7 @@ class LoginDefaultAfter extends AbstractLoginFSMExtension implements iLogoutExte
{
self::ResetLoginSession();
$iOnExit = LoginWebPage::getIOnExit();
if ($iOnExit == LoginWebPage::EXIT_RETURN)
if ($iOnExit === LoginWebPage::EXIT_RETURN)
{
return LoginWebPage::LOGIN_FSM_RETURN; // Error, exit FSM
}
@@ -91,8 +93,14 @@ class LoginDefaultAfter extends AbstractLoginFSMExtension implements iLogoutExte
protected function OnCredentialsOk(&$iErrorCode)
{
if (!isset($_SESSION['login_mode']))
if (!Session::IsSet('login_mode'))
{
// N°6358 - if EXIT_RETURN was asked, send an error
if (LoginWebPage::getIOnExit() === LoginWebPage::EXIT_RETURN) {
$iErrorCode = LoginWebPage::EXIT_CODE_WRONGCREDENTIALS;
return LoginWebPage::LOGIN_FSM_ERROR;
}
// If no plugin validated the user, exit
self::ResetLoginSession();
exit();
@@ -110,7 +118,12 @@ class LoginDefaultAfter extends AbstractLoginFSMExtension implements iLogoutExte
protected function OnConnected(&$iErrorCode)
{
unset($_SESSION['login_temp_auth_user']);
Session::Unset('login_temp_auth_user');
if (is_null(UserRights::GetUserObject())){
//N°7085 avoid infinite loop
IssueLog::Error("No user logged in. exit");
exit(-1);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
@@ -118,12 +131,12 @@ class LoginDefaultAfter extends AbstractLoginFSMExtension implements iLogoutExte
private static function ResetLoginSession()
{
LoginWebPage::ResetSession();
foreach (array_keys($_SESSION) as $sKey)
foreach (Session::ListVariables() as $sKey)
{
if (utils::StartsWith($sKey, 'login_'))
{
unset($_SESSION[$sKey]);
Session::Unset($sKey);
}
}
}
}
}

View File

@@ -1,5 +1,7 @@
<?php
use Combodo\iTop\Application\Helper\Session;
/**
* Class LoginExternal
*
@@ -22,12 +24,12 @@ class LoginExternal extends AbstractLoginFSMExtension
protected function OnModeDetection(&$iErrorCode)
{
if (!isset($_SESSION['login_mode']))
if (!Session::IsSet('login_mode'))
{
$sAuthUser = $this->GetAuthUser();
if ($sAuthUser && (strlen($sAuthUser) > 0))
{
$_SESSION['login_mode'] = 'external';
Session::Set('login_mode', 'external');
}
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
@@ -35,33 +37,33 @@ class LoginExternal extends AbstractLoginFSMExtension
protected function OnCheckCredentials(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'external')
if (Session::Get('login_mode') == 'external')
{
$sAuthUser = $this->GetAuthUser();
if (!UserRights::CheckCredentials($sAuthUser, '', $_SESSION['login_mode'], 'external'))
if (!UserRights::CheckCredentials($sAuthUser, '', Session::Get('login_mode'), 'external'))
{
$iErrorCode = LoginWebPage::EXIT_CODE_WRONGCREDENTIALS;
return LoginWebPage::LOGIN_FSM_ERROR;
}
Session::Set('auth_user', $sAuthUser);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
protected function OnCredentialsOK(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'external')
if (Session::Get('login_mode') == 'external')
{
$sAuthUser = $this->GetAuthUser();
LoginWebPage::OnLoginSuccess($sAuthUser, 'external', $_SESSION['login_mode']);
LoginWebPage::OnLoginSuccess(Session::Get('auth_user'), 'external', Session::Get('login_mode'));
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
protected function OnConnected(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'external')
if (Session::Get('login_mode') == 'external')
{
$_SESSION['can_logoff'] = false;
Session::Set('can_logoff', false);
return LoginWebPage::CheckLoggedUser($iErrorCode);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
@@ -69,8 +71,13 @@ class LoginExternal extends AbstractLoginFSMExtension
protected function OnError(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'external')
if (Session::Get('login_mode') == 'external')
{
$iOnExit = LoginWebPage::getIOnExit();
if ($iOnExit === LoginWebPage::EXIT_RETURN)
{
return LoginWebPage::LOGIN_FSM_RETURN; // Error, exit FSM
}
LoginWebPage::HTTP401Error();
}
return LoginWebPage::LOGIN_FSM_CONTINUE;

View File

@@ -5,6 +5,8 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Application\Helper\Session;
/**
* Class LoginForm
*
@@ -29,8 +31,7 @@ class LoginForm extends AbstractLoginFSMExtension implements iLoginUIExtension
*/
protected function OnReadCredentials(&$iErrorCode)
{
if (!isset($_SESSION['login_mode']) || ($_SESSION['login_mode'] == 'form'))
{
if (!Session::IsSet('login_mode') || Session::Get('login_mode') == 'form') {
$sAuthUser = utils::ReadPostedParam('auth_user', '', 'raw_data');
$sAuthPwd = utils::ReadPostedParam('auth_pwd', null, 'raw_data');
if ($this->bForceFormOnError || empty($sAuthUser) || empty($sAuthPwd))
@@ -43,6 +44,10 @@ class LoginForm extends AbstractLoginFSMExtension implements iLoginUIExtension
exit;
}
if (LoginWebPage::getIOnExit() === LoginWebPage::EXIT_RETURN) {
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
// No credentials yet, display the form
$oPage = LoginWebPage::NewLoginWebPage();
$oPage->DisplayLoginForm($this->bForceFormOnError);
@@ -50,9 +55,8 @@ class LoginForm extends AbstractLoginFSMExtension implements iLoginUIExtension
$this->bForceFormOnError = false;
exit;
}
$_SESSION['login_temp_auth_user'] = $sAuthUser;
$_SESSION['login_mode'] = 'form';
Session::Set('login_temp_auth_user', $sAuthUser);
Session::Set('login_mode', 'form');
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
@@ -62,15 +66,16 @@ class LoginForm extends AbstractLoginFSMExtension implements iLoginUIExtension
*/
protected function OnCheckCredentials(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'form')
if (Session::Get('login_mode') == 'form')
{
$sAuthUser = utils::ReadPostedParam('auth_user', '', 'raw_data');
$sAuthPwd = utils::ReadPostedParam('auth_pwd', null, 'raw_data');
if (!UserRights::CheckCredentials($sAuthUser, $sAuthPwd, $_SESSION['login_mode'], 'internal'))
if (!UserRights::CheckCredentials($sAuthUser, $sAuthPwd, Session::Get('login_mode'), 'internal'))
{
$iErrorCode = LoginWebPage::EXIT_CODE_WRONGCREDENTIALS;
return LoginWebPage::LOGIN_FSM_ERROR;
}
Session::Set('auth_user', $sAuthUser);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
@@ -80,19 +85,10 @@ class LoginForm extends AbstractLoginFSMExtension implements iLoginUIExtension
*/
protected function OnCredentialsOK(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'form')
if (Session::Get('login_mode') == 'form')
{
if (isset($_SESSION['auth_user']))
{
// If FSM reenter this state (example 2FA) then the auth_user is not resubmitted
$sAuthUser = $_SESSION['auth_user'];
}
else
{
$sAuthUser = utils::ReadPostedParam('auth_user', '', 'raw_data');
}
// Store 'auth_user' in session for further use
LoginWebPage::OnLoginSuccess($sAuthUser, 'internal', $_SESSION['login_mode']);
LoginWebPage::OnLoginSuccess(Session::Get('auth_user'), 'internal', Session::Get('login_mode'));
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
@@ -102,7 +98,7 @@ class LoginForm extends AbstractLoginFSMExtension implements iLoginUIExtension
*/
protected function OnError(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'form')
if (Session::Get('login_mode') == 'form')
{
$this->bForceFormOnError = true;
}
@@ -114,9 +110,9 @@ class LoginForm extends AbstractLoginFSMExtension implements iLoginUIExtension
*/
protected function OnConnected(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'form')
if (Session::Get('login_mode') == 'form')
{
$_SESSION['can_logoff'] = true;
Session::Set('can_logoff', true);
return LoginWebPage::CheckLoggedUser($iErrorCode);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;

View File

@@ -7,6 +7,7 @@
*/
use Combodo\iTop\Application\Branding;
use Combodo\iTop\TwigExtension;
/**
@@ -238,16 +239,9 @@ class LoginTwigRenderer
public function GetDefaultVars()
{
$sLogo = 'itop-logo-external.png';
$sBrandingLogo = 'login-logo.png';
$sVersionShort = Dict::Format('UI:iTopVersion:Short', ITOP_APPLICATION, ITOP_VERSION);
$sIconUrl = Utils::GetConfig()->Get('app_icon_url');
$sDisplayIcon = utils::GetAbsoluteUrlAppRoot().'images/'.$sLogo.'?t='.utils::GetCacheBusterTimestamp();
if (file_exists(MODULESROOT.'branding/'.$sBrandingLogo))
{
$sDisplayIcon = utils::GetAbsoluteUrlModulesRoot().'branding/'.$sBrandingLogo.'?t='.utils::GetCacheBusterTimestamp();
}
$sDisplayIcon = Branding::GetLoginLogoAbsoluteUrl();
$aVars = array(
'sAppRootUrl' => utils::GetAbsoluteUrlAppRoot(),

View File

@@ -1,5 +1,7 @@
<?php
use Combodo\iTop\Application\Helper\Session;
/**
* Class LoginURL
*
@@ -26,13 +28,13 @@ class LoginURL extends AbstractLoginFSMExtension
protected function OnModeDetection(&$iErrorCode)
{
if (!isset($_SESSION['login_mode']) && !$this->bErrorOccurred)
if (!Session::IsSet('login_mode') && !$this->bErrorOccurred)
{
$sAuthUser = utils::ReadParam('auth_user', '', false, 'raw_data');
$sAuthPwd = utils::ReadParam('auth_pwd', null, false, 'raw_data');
if (!empty($sAuthUser) && !empty($sAuthPwd))
{
$_SESSION['login_mode'] = 'url';
Session::Set('login_mode', 'url');
}
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
@@ -40,41 +42,41 @@ class LoginURL extends AbstractLoginFSMExtension
protected function OnReadCredentials(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'url')
if (Session::Get('login_mode') == 'url')
{
$_SESSION['login_temp_auth_user'] = utils::ReadParam('auth_user', '', false, 'raw_data');
Session::Set('login_temp_auth_user', utils::ReadParam('auth_user', '', false, 'raw_data'));
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
protected function OnCheckCredentials(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'url')
if (Session::Get('login_mode') == 'url')
{
$sAuthUser = utils::ReadParam('auth_user', '', false, 'raw_data');
$sAuthPwd = utils::ReadParam('auth_pwd', null, false, 'raw_data');
if (!UserRights::CheckCredentials($sAuthUser, $sAuthPwd, $_SESSION['login_mode'], 'internal'))
if (!UserRights::CheckCredentials($sAuthUser, $sAuthPwd, Session::Get('login_mode'), 'internal'))
{
$iErrorCode = LoginWebPage::EXIT_CODE_WRONGCREDENTIALS;
return LoginWebPage::LOGIN_FSM_ERROR;
}
Session::Set('auth_user', $sAuthUser);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
protected function OnCredentialsOK(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'url')
if (Session::Get('login_mode') == 'url')
{
$sAuthUser = utils::ReadParam('auth_user', '', false, 'raw_data');
LoginWebPage::OnLoginSuccess($sAuthUser, 'internal', $_SESSION['login_mode']);
LoginWebPage::OnLoginSuccess(Session::Get('auth_user'), 'internal', Session::Get('login_mode'));
}
return LoginWebPage::LOGIN_FSM_CONTINUE;
}
protected function OnError(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'url')
if (Session::Get('login_mode') == 'url')
{
$this->bErrorOccurred = true;
}
@@ -83,9 +85,9 @@ class LoginURL extends AbstractLoginFSMExtension
protected function OnConnected(&$iErrorCode)
{
if ($_SESSION['login_mode'] == 'url')
if (Session::Get('login_mode') == 'url')
{
$_SESSION['can_logoff'] = true;
Session::Set('can_logoff', true);
return LoginWebPage::CheckLoggedUser($iErrorCode);
}
return LoginWebPage::LOGIN_FSM_CONTINUE;

View File

@@ -1,5 +1,5 @@
<?php
// Copyright (C) 2010-2021 Combodo SARL
// Copyright (C) 2010-2023 Combodo SARL
//
// This file is part of iTop.
//
@@ -24,6 +24,9 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Application\Branding;
use Combodo\iTop\Application\Helper\Session;
/**
* Web page used for displaying the login form
*/
@@ -32,7 +35,7 @@ class LoginWebPage extends NiceWebPage
{
const EXIT_PROMPT = 0;
const EXIT_HTTP_401 = 1;
const EXIT_RETURN = 2;
const EXIT_RETURN = 2; // Non interactive mode (ajax, rest, ...)
const EXIT_CODE_OK = 0;
const EXIT_CODE_MISSINGLOGIN = 1;
@@ -85,7 +88,7 @@ class LoginWebPage extends NiceWebPage
parent::__construct($sTitle);
$this->SetStyleSheet();
$this->no_cache();
$this->add_xframe_options();
$this->add_http_headers();
}
public function SetStyleSheet()
@@ -102,6 +105,7 @@ class LoginWebPage extends NiceWebPage
/**
* @param $oUser
* @param array $aProfiles
* @param $sOrigin
*
* @return array
* @throws \CoreException
@@ -109,7 +113,7 @@ class LoginWebPage extends NiceWebPage
*/
public static function SynchronizeProfiles(&$oUser, array $aProfiles, $sOrigin)
{
$oProfilesSet = $oUser->Get(profile_list);
$oProfilesSet = $oUser->Get('profile_list');
//delete old profiles
$aExistingProfiles = [];
while ($oProfile = $oProfilesSet->Fetch())
@@ -139,16 +143,9 @@ class LoginWebPage extends NiceWebPage
public function DisplayLoginHeader($bMainAppLogo = false)
{
$sLogo = 'itop-logo-external.png';
$sBrandingLogo = 'login-logo.png';
$sVersionShort = Dict::Format('UI:iTopVersion:Short', ITOP_APPLICATION, ITOP_VERSION);
$sIconUrl = Utils::GetConfig()->Get('app_icon_url');
$sDisplayIcon = utils::GetAbsoluteUrlAppRoot().'images/'.$sLogo.'?t='.utils::GetCacheBusterTimestamp();
if (file_exists(MODULESROOT.'branding/'.$sBrandingLogo))
{
$sDisplayIcon = utils::GetAbsoluteUrlModulesRoot().'branding/'.$sBrandingLogo.'?t='.utils::GetCacheBusterTimestamp();
}
$sDisplayIcon = Branding::GetLoginLogoAbsoluteUrl();
$this->add("<div id=\"login-logo\"><a href=\"".htmlentities($sIconUrl, ENT_QUOTES,
self::PAGES_CHARSET)."\"><img title=\"$sVersionShort\" src=\"$sDisplayIcon\"></a></div>\n");
}
@@ -245,7 +242,7 @@ class LoginWebPage extends NiceWebPage
}
// This token allows the user to change the password without knowing the previous one
$sToken = substr(md5(APPROOT.uniqid()), 0, 16);
$sToken = bin2hex(random_bytes(32));
$oUser->Set('reset_pwd_token', $sToken);
CMDBObject::SetTrackInfo('Reset password');
$oUser->AllowWrite(true);
@@ -389,14 +386,20 @@ class LoginWebPage extends NiceWebPage
$this->output();
}
public static function ResetSession()
public static function ResetSession($bFullCleanup = false)
{
// Unset all of the session variables.
unset($_SESSION['auth_user']);
unset($_SESSION['login_state']);
unset($_SESSION['can_logoff']);
unset($_SESSION['archive_mode']);
unset($_SESSION['impersonate_user']);
if ($bFullCleanup) {
// Unset all of the session variables.
foreach (array_keys($_SESSION) as $sKey) {
Session::Unset($sKey);
}
} else {
Session::Unset('auth_user');
Session::Unset('login_state');
Session::Unset('can_logoff');
Session::Unset('archive_mode');
Session::Unset('impersonate_user');
}
UserRights::_ResetSessionCache();
// If it's desired to kill the session, also delete the session cookie.
// Note: This will destroy the session, and not just the session data!
@@ -442,11 +445,11 @@ class LoginWebPage extends NiceWebPage
}
$bLoginDebug = MetaModel::GetConfig()->Get('login_debug');
if (!isset($_SESSION['login_state']) || ($_SESSION['login_state'] == self::LOGIN_STATE_ERROR))
if (Session::Get('login_state') == self::LOGIN_STATE_ERROR)
{
$_SESSION['login_state'] = self::LOGIN_STATE_START;
Session::Set('login_state', self::LOGIN_STATE_START);
}
$sLoginState = $_SESSION['login_state'];
$sLoginState = Session::Get('login_state');
$sSessionLog = '';
if ($bLoginDebug)
@@ -487,6 +490,7 @@ class LoginWebPage extends NiceWebPage
$iResponse = $oLoginFSMExtensionInstance->LoginAction($sLoginState, $iErrorCode);
if ($iResponse == self::LOGIN_FSM_RETURN)
{
Session::WriteClose();
return $iErrorCode; // Asked to exit FSM, generally login OK
}
if ($iResponse == self::LOGIN_FSM_ERROR)
@@ -500,7 +504,7 @@ class LoginWebPage extends NiceWebPage
// Every plugin has nothing else to do in this state, go forward
$sLoginState = self::AdvanceLoginFSMState($sLoginState);
$_SESSION['login_state'] = $sLoginState;
Session::Set('login_state', $sLoginState);
}
catch (Exception $e)
{
@@ -526,7 +530,7 @@ class LoginWebPage extends NiceWebPage
if ($bFilterWithMode)
{
$sCurrentLoginMode = isset($_SESSION['login_mode']) ? $_SESSION['login_mode'] : '';
$sCurrentLoginMode = Session::Get('login_mode', '');
}
else
{
@@ -665,8 +669,8 @@ class LoginWebPage extends NiceWebPage
$oLog->DBInsertNoReload();
}
$_SESSION['auth_user'] = $sAuthUser;
$_SESSION['login_mode'] = $sLoginMode;
Session::Set('auth_user', $sAuthUser);
Session::Set('login_mode', $sLoginMode);
UserRights::_InitSessionCache();
}
@@ -681,10 +685,10 @@ class LoginWebPage extends NiceWebPage
*/
public static function CheckLoggedUser(&$iErrorCode)
{
if (isset($_SESSION['auth_user']))
if (Session::IsSet('auth_user'))
{
// Already authenticated
$bRet = UserRights::Login($_SESSION['auth_user']); // Login & set the user's language
$bRet = UserRights::Login(Session::Get('auth_user')); // Login & set the user's language
if ($bRet)
{
$iErrorCode = self::EXIT_CODE_OK;
@@ -712,11 +716,11 @@ class LoginWebPage extends NiceWebPage
public static function SetLoginModeAndReload($sNewLoginMode)
{
if (isset($_SESSION['login_mode']) && ($_SESSION['login_mode'] == $sNewLoginMode))
if (Session::Get('login_mode') == $sNewLoginMode)
{
return;
}
$_SESSION['login_mode'] = $sNewLoginMode;
Session::Set('login_mode', $sNewLoginMode);
self::HTTPReload();
}
@@ -829,9 +833,9 @@ class LoginWebPage extends NiceWebPage
{
CMDBObject::SetTrackOrigin('custom-extension');
$sInfo = 'External User provisioning';
if (isset($_SESSION['login_mode']))
if (Session::IsSet('login_mode'))
{
$sInfo .= " ({$_SESSION['login_mode']})";
$sInfo .= " (".Session::Get('login_mode').")";
}
CMDBObject::SetTrackInfo($sInfo);
@@ -883,9 +887,9 @@ class LoginWebPage extends NiceWebPage
{
CMDBObject::SetTrackOrigin('custom-extension');
$sInfo = 'External User provisioning';
if (isset($_SESSION['login_mode']))
if (Session::IsSet('login_mode'))
{
$sInfo .= " ({$_SESSION['login_mode']})";
$sInfo .= " (".Session::Get('login_mode').")";
}
CMDBObject::SetTrackInfo($sInfo);
@@ -924,9 +928,9 @@ class LoginWebPage extends NiceWebPage
// Now synchronize the profiles
$sOrigin = 'External User provisioning';
if (isset($_SESSION['login_mode']))
if (Session::IsSet('login_mode'))
{
$sOrigin .= " ({$_SESSION['login_mode']})";
$sOrigin .= " (".Session::Get('login_mode').")";
}
$aExistingProfiles = self::SynchronizeProfiles($oUser, $aProfiles, $sOrigin);
if ($oUser->IsModified())
@@ -960,7 +964,7 @@ class LoginWebPage extends NiceWebPage
}
else
{
if ($iOnExit == self::EXIT_RETURN)
if ($iOnExit === self::EXIT_RETURN)
{
return self::EXIT_CODE_PORTALUSERNOTAUTHORIZED;
}
@@ -1011,12 +1015,11 @@ class LoginWebPage extends NiceWebPage
$sMessage = self::HandleOperations($operation); // May exit directly
$iRet = self::Login($iOnExit);
if ($iRet == self::EXIT_CODE_OK)
{
if ($bMustBeAdmin && !UserRights::IsAdministrator())
{
if ($iOnExit == self::EXIT_RETURN)
if ($iOnExit === self::EXIT_RETURN)
{
return self::EXIT_CODE_MUSTBEADMIN;
}
@@ -1032,7 +1035,7 @@ class LoginWebPage extends NiceWebPage
}
$iRet = call_user_func(array(self::$sHandlerClass, 'ChangeLocation'), $sRequestedPortalId, $iOnExit);
}
if ($iOnExit == self::EXIT_RETURN)
if ($iOnExit === self::EXIT_RETURN)
{
return $iRet;
}
@@ -1091,19 +1094,23 @@ class LoginWebPage extends NiceWebPage
}
else if ($operation == 'change_pwd')
{
if (isset($_SESSION['auth_user']))
if (Session::IsSet('auth_user'))
{
$sAuthUser = $_SESSION['auth_user'];
$sAuthUser = Session::Get('auth_user');
$sIssue = Session::Get('pwd_issue');
Session::Unset('pwd_issue');
$bFailedLogin = ($sIssue != null); // Force the "failed login" flag to display the "issue" message
UserRights::Login($sAuthUser); // Set the user's language
$oPage = self::NewLoginWebPage();
$oPage->DisplayChangePwdForm();
$oPage->DisplayChangePwdForm($bFailedLogin, $sIssue);
$oPage->output();
exit;
}
}
else if ($operation == 'check_pwd_policy')
{
$sAuthUser = $_SESSION['auth_user'];
$sAuthUser = Session::Get('auth_user');
UserRights::Login($sAuthUser); // Set the user's language
$aPwdMap = array();
@@ -1121,9 +1128,9 @@ class LoginWebPage extends NiceWebPage
}
if ($operation == 'do_change_pwd')
{
if (isset($_SESSION['auth_user']))
if (Session::IsSet('auth_user'))
{
$sAuthUser = $_SESSION['auth_user'];
$sAuthUser = Session::Get('auth_user');
UserRights::Login($sAuthUser); // Set the user's language
$sOldPwd = utils::ReadPostedParam('old_pwd', '', 'raw_data');
$sNewPwd = utils::ReadPostedParam('new_pwd', '', 'raw_data');

View File

@@ -77,17 +77,28 @@ function _MaintenanceHtmlMessage($sMessage)
*/
function _MaintenanceJsonMessage($sTitle, $sMessage)
{
@include_once(APPROOT."/application/ajaxwebpage.class.inc.php");
if (class_exists('ajax_page'))
if (class_exists('JsonPage'))
{
$oP = new ajax_page($sTitle);
$oP = new JsonPage($sTitle);
$oP->add_header('Access-Control-Allow-Origin: *');
$oP->SetContentType('application/json');
$oP->add('{"code":100, "message":"'.$sMessage.'"}');
$aMessage = [
'code' => 100,
'message' =>$sMessage
];
$oP->AddData($aMessage);
$oP->Output();
}
else
{
_MaintenanceTextMessage($sMessage);
} else {
@include_once(APPROOT."/application/ajaxwebpage.class.inc.php");
if (class_exists('ajax_page')) {
$oP = new ajax_page($sTitle);
$oP->add_header('Access-Control-Allow-Origin: *');
$oP->SetContentType('application/json');
$oP->add('{"code":100, "message":"'.$sMessage.'"}');
$oP->Output();
} else {
_MaintenanceTextMessage($sMessage);
}
}
}

View File

@@ -4,7 +4,7 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Application\UI\Base\Component\Title\TitleUIBlockFactory;
use Combodo\iTop\Application\Helper\WebResourcesHelper;
require_once(APPROOT.'/application/utils.inc.php');
require_once(APPROOT.'/application/template.class.inc.php');
@@ -58,6 +58,10 @@ class ApplicationMenu
* @var array
*/
static $aMenusIndex = array();
/**
* @var array
*/
static $aMenusById = [];
/**
* @var string
*/
@@ -166,6 +170,7 @@ class ApplicationMenu
$aBacktrace = debug_backtrace();
$sFile = isset($aBacktrace[2]["file"]) ? $aBacktrace[2]["file"] : $aBacktrace[1]["file"];
self::$aMenusIndex[$index] = array('node' => $oMenuNode, 'children' => array(), 'parent' => $sParentId, 'rank' => $fRank, 'source_file' => $sFile);
self::$aMenusById[$oMenuNode->GetMenuId()] = $index;
}
else
{
@@ -260,6 +265,14 @@ class ApplicationMenu
/** @var \MenuGroup $oMenuNode */
$oMenuNode = static::GetMenuNode($sMenuGroupIdx);
if (!($oMenuNode instanceof MenuGroup)) {
IssueLog::Error('Menu node was not displayed as a menu group as it is actually not a menu group', LogChannels::CONSOLE, [
'menu_node_class' => get_class($oMenuNode),
'menu_node_label' => $oMenuNode->GetLabel(),
]);
continue;
}
$aMenuGroups[] = [
'sId' => $oMenuNode->GetMenuID(),
'sIconCssClasses' => $oMenuNode->GetDecorationClasses(),
@@ -506,17 +519,11 @@ EOF
*/
public static function GetMenuIndexById($sTitle)
{
$index = -1;
/** @var MenuNode[] $aMenu */
foreach(self::$aMenusIndex as $aMenu)
{
if ($aMenu['node']->GetMenuId() == $sTitle)
{
$index = $aMenu['node']->GetIndex();
break;
}
if (isset(self::$aMenusById[$sTitle])) {
return self::$aMenusById[$sTitle];
}
return $index;
return -1;
}
/**
@@ -654,8 +661,7 @@ abstract class MenuNode
$this->sMenuId = $sMenuId;
$this->iParentIndex = $iParentIndex;
$this->aReflectionProperties = array();
if (strlen($sEnableClass) > 0)
{
if (utils::IsNotNullOrEmptyString($sEnableClass)) {
$this->aReflectionProperties['enable_class'] = $sEnableClass;
$this->aReflectionProperties['enable_action'] = $iActionCode;
$this->aReflectionProperties['enable_permission'] = $iAllowedResults;
@@ -715,9 +721,10 @@ abstract class MenuNode
{
// Count the entries up to 99
$oSearch = DBSearch::FromOQL($sOQL);
$oSearch->SetShowObsoleteData(utils::ShowObsoleteData());
DBSearchHelper::AddContextFilter($oSearch);
$oSet = new DBObjectSet($oSearch);
$iCount = $oSet->CountWithLimit(99);
if ($iCount > 99) {
@@ -1125,18 +1132,20 @@ class OQLMenuNode extends MenuNode
{
$sUsageId = utils::GetSafeId($sUsageId);
$oSearch = DBObjectSearch::FromOQL($sOql);
//$sIcon = MetaModel::GetClassIcon($oSearch->GetClass(), false);
$sClass= $oSearch->GetClass();
$sIcon = MetaModel::GetClassIcon($sClass, false);
if ($bSearchPane) {
$aParams = array_merge(array('open' => $bSearchOpen, 'table_id' => $sUsageId), $aExtraParams);
$aParams = array_merge(['open' => $bSearchOpen, 'table_id' => $sUsageId, 'submit_on_load' => false], $aExtraParams);
$oBlock = new DisplayBlock($oSearch, 'search', false /* Asynchronous */, $aParams);
$oBlock->Display($oPage, 0);
$oPage->add("<div class='sf_results_area ibo-add-margin-top-250' data-target='search_results'>");
}
//$oPage->add("<p class=\"page-header\">$sIcon ".utils::HtmlEntities(Dict::S($sTitle))."</p>");
$oPage->add("<div class='sf_results_area' data-target='search_results'>");
$oTitle = TitleUIBlockFactory::MakeForPage($sTitle);
$oPage->AddUiBlock($oTitle);
else {
$oPage->add("<div class='sf_results_area' data-target='search_results'>");
}
$aExtraParams['panel_class'] =$sClass;
$aExtraParams['panel_title'] = $sTitle;
$aExtraParams['panel_icon'] = $sIcon;
$aParams = array_merge(array('table_id' => $sUsageId), $aExtraParams);
$oBlock = new DisplayBlock($oSearch, 'list', false /* Asynchronous */, $aParams);
@@ -1209,7 +1218,8 @@ class SearchMenuNode extends MenuNode
$oPage->SetBreadCrumbEntry("menu-".$this->sMenuId, $this->GetTitle(), '', '', 'fas fa-search', iTopWebPage::ENUM_BREADCRUMB_ENTRY_ICON_TYPE_CSS_CLASSES);
$oSearch = new DBObjectSearch($this->sClass);
$aParams = array_merge(array('table_id' => 'Menu_'.utils::GetSafeId($this->GetMenuId())), $aExtraParams);
$sUsageId = 'Menu_'.utils::GetSafeId($this->GetMenuId());
$aParams = array_merge(array('table_id' =>$sUsageId), $aExtraParams);
$oBlock = new DisplayBlock($oSearch, 'search', false /* Asynchronous */, $aParams);
$oBlock->Display($oPage, 0);
}
@@ -1415,6 +1425,8 @@ class DashboardMenuNode extends MenuNode
$oDashboard = $this->GetDashboard();
if ($oDashboard != null)
{
WebResourcesHelper::EnableC3JSToWebPage($oPage);
$sDivId = utils::Sanitize($this->sMenuId, '', 'element_identifier');
$oPage->add('<div id="'.$sDivId.'" class="ibo-dashboard" data-role="ibo-dashboard">');
$aExtraParams['dashboard_div_id'] = $sDivId;

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/NiceWebPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/NiceWebPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/PDFPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/PDFPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -126,7 +126,7 @@ class QueryOQL extends Query
function DisplayBareProperties(WebPage $oPage, $bEditMode = false, $sPrefix = '', $aExtraParams = array())
{
$aFieldsMap = parent::DisplayBareProperties($oPage, $bEditMode, $sPrefix, $aExtraParams);
$oPage->add_script("$('[name=\"attr_oql\"]').addClass('ibo-queryoql'); $('[data-attribute-code=\"oql\"]').addClass('ibo-queryoql');");
$oPage->add_script("$('[name=\"attr_oql\"]').addClass('ibo-query-oql ibo-is-code'); $('[data-attribute-code=\"oql\"]').addClass('ibo-query-oql ibo-is-code');");
if (!$bEditMode) {
$sFields = trim($this->Get('fields'));

View File

@@ -288,7 +288,8 @@ class ShortcutOQL extends Shortcut
$oPage->add_ready_script(
<<<JS
// Note: the title gets deleted by the validation mechanism
$("#attr_auto_reload_sec").tooltip({items: 'input', content: '$sRateTitle'});
$("#attr_auto_reload_sec").attr('data-tooltip-content', '$sRateTitle');
CombodoTooltip.InitTooltipFromMarkup($("#attr_auto_reload_sec"));
$("#attr_auto_reload_sec").prop('disabled', !$('#attr_auto_reload').is(':checked'));
$('#attr_auto_reload').change( function(ev) {

View File

@@ -15,9 +15,12 @@
//
// You should have received a copy of the GNU Affero General Public License
// along with iTop. If not, see <http://www.gnu.org/licenses/>
use Combodo\iTop\Application\Helper\Session;
require_once(APPROOT.'/core/cmdbobject.class.inc.php');
require_once(APPROOT.'/application/utils.inc.php');
require_once(APPROOT.'/core/contexttag.class.inc.php');
require_once(APPROOT.'/core/kpi.class.inc.php');
/**
@@ -27,6 +30,9 @@ require_once(APPROOT.'/core/contexttag.class.inc.php');
* @license http://opensource.org/licenses/AGPL-3.0
*/
ExecutionKPI::EnableDuration(1);
ExecutionKPI::EnableMemory(1);
// This storage is freed on error (case of allowed memory exhausted)
$sReservedMemory = str_repeat('*', 1024 * 1024);
register_shutdown_function(function()
@@ -35,41 +41,38 @@ register_shutdown_function(function()
$sReservedMemory = null;
if (!is_null($err = error_get_last()) && ($err['type'] == E_ERROR))
{
// Remove stack trace from MySQLException
// Remove stack trace from MySQLException (since 2.7.2 see N°3174)
$sMessage = $err['message'];
if (strpos($sMessage, 'MySQLException') !== false)
{
if (strpos($sMessage, 'MySQLException') !== false) {
$iStackTracePos = strpos($sMessage, 'Stack trace:');
if ($iStackTracePos !== false)
{
if ($iStackTracePos !== false) {
$sMessage = substr($sMessage, 0, $iStackTracePos);
}
}
IssueLog::error($sMessage, null, $err);
if (strpos($err['message'], 'Allowed memory size of') !== false)
{
// Log additional info but message from $err (since 2.7.6 N°4174)
$aErrToLog = $err;
unset($aErrToLog['message']);
IssueLog::error($sMessage, null, $aErrToLog);
if (strpos($err['message'], 'Allowed memory size of') !== false) {
$sLimit = ini_get('memory_limit');
echo "<p>iTop: Allowed memory size of $sLimit exhausted, contact your administrator to increase 'memory_limit' in php.ini</p>\n";
}
elseif (strpos($err['message'], 'Maximum execution time') !== false)
{
} elseif (strpos($err['message'], 'Maximum execution time') !== false) {
$sLimit = ini_get('max_execution_time');
echo "<p>iTop: Maximum execution time of $sLimit exceeded, contact your administrator to increase 'max_execution_time' in php.ini</p>\n";
}
else
{
} else {
echo "<p>iTop: An error occurred, check server error log for more information.</p>\n";
}
}
});
$oKPI = new ExecutionKPI();
Session::Start();
$oKPI->ComputeAndReport("Session Start");
session_name('itop-'.md5(APPROOT));
session_start();
$sSwitchEnv = utils::ReadParam('switch_env', null);
$bAllowCache = true;
if (($sSwitchEnv != null) && (file_exists(APPCONF.$sSwitchEnv.'/'.ITOP_CONFIG_FILE)) && isset($_SESSION['itop_env']) && ($_SESSION['itop_env'] !== $sSwitchEnv))
if (($sSwitchEnv != null) && file_exists(APPCONF.$sSwitchEnv.'/'.ITOP_CONFIG_FILE) &&( Session::Get('itop_env') !== $sSwitchEnv))
{
$_SESSION['itop_env'] = $sSwitchEnv;
Session::Set('itop_env', $sSwitchEnv);
$sEnv = $sSwitchEnv;
$bAllowCache = false;
// Reset the opcache since otherwise the PHP "model" files may still be cached !!
@@ -85,14 +88,20 @@ if (($sSwitchEnv != null) && (file_exists(APPCONF.$sSwitchEnv.'/'.ITOP_CONFIG_FI
}
// TODO: reset the credentials as well ??
}
else if (isset($_SESSION['itop_env']))
else if (Session::IsSet('itop_env'))
{
$sEnv = $_SESSION['itop_env'];
$sEnv = Session::Get('itop_env');
}
else
{
$sEnv = ITOP_DEFAULT_ENV;
$_SESSION['itop_env'] = ITOP_DEFAULT_ENV;
Session::Set('itop_env', ITOP_DEFAULT_ENV);
}
$sConfigFile = APPCONF.$sEnv.'/'.ITOP_CONFIG_FILE;
MetaModel::Startup($sConfigFile, false /* $bModelOnly */, $bAllowCache, false /* $bTraceSourceFiles */, $sEnv);
try {
MetaModel::Startup($sConfigFile, false /* $bModelOnly */, $bAllowCache, false /* $bTraceSourceFiles */, $sEnv);
}
catch (MySQLException $e) {
IssueLog::Debug($e->getMessage());
throw new MySQLException('Could not connect to the DB server', []);
}

View File

@@ -27,6 +27,7 @@ class ThemeHandler
{
const IMAGE_EXTENSIONS = ['png', 'gif', 'jpg', 'jpeg'];
/** @var \CompileCSSService */
private static $oCompileCSSService;
public static function GetAppRootWithSlashes()
@@ -315,11 +316,6 @@ class ThemeHandler
// Loading files to import and stylesheet to compile, also getting most recent modification time on overall files
$sTmpThemeScssContent = '';
$oFindStylesheetObject = new FindStylesheetObject();
if (isset($aThemeParameters['variable_imports'])) {
foreach ($aThemeParameters['variable_imports'] as $sImport) {
static::FindStylesheetFile($sImport, $aImportsPaths, $oFindStylesheetObject);
}
}
if (isset($aThemeParameters['utility_imports'])) {
foreach ($aThemeParameters['utility_imports'] as $sImport) {
@@ -337,6 +333,12 @@ class ThemeHandler
$sTmpThemeScssContent .= '@import "'.$sStylesheet.'";'."\n";
}
if (isset($aThemeParameters['variable_imports'])) {
foreach ($aThemeParameters['variable_imports'] as $sImport) {
static::FindStylesheetFile($sImport, $aImportsPaths, $oFindStylesheetObject);
}
}
$iStyleLastModified = $oFindStylesheetObject->GetLastModified();
$aIncludedImages=static::GetIncludedImages($aThemeParametersWithVersion, $oFindStylesheetObject->GetAllStylesheetPaths(), $sThemeId);
@@ -904,7 +906,8 @@ CSS;
foreach($aImportsPaths as $sPath)
{
$sFilePath = $sPath.'/'.$sFileURI;
$sAlterableFileURI = $sFileURI;
$sFilePath = $sPath.'/'.$sAlterableFileURI;
$sImportedFile = realpath($sFilePath);
if ($sImportedFile === false){
// Handle shortcut syntax : @import "typo" ;
@@ -912,7 +915,7 @@ CSS;
$sFilePath2 = "$sFilePath.scss";
$sImportedFile = realpath($sFilePath2);
if ($sImportedFile){
self::FindStylesheetFile("$sFileURI.scss", [ $sPath ], $oFindStylesheetObject, $bImports);
self::FindStylesheetFile("$sAlterableFileURI.scss", [ $sPath ], $oFindStylesheetObject, $bImports);
$sImportedFile = false;
}
}
@@ -922,7 +925,7 @@ CSS;
// file matched: _typo.scss
$sShortCut = substr($sFilePath, strrpos($sFilePath, '/') + 1);
$sFilePath = static::ReplaceLastOccurrence($sShortCut, "_$sShortCut.scss", $sFilePath);
$sFileURI = static::ReplaceLastOccurrence($sShortCut, "_$sShortCut.scss", $sFileURI);
$sAlterableFileURI = static::ReplaceLastOccurrence($sShortCut, "_$sShortCut.scss", $sAlterableFileURI);
$sImportedFile = realpath($sFilePath);
}
@@ -930,14 +933,14 @@ CSS;
&& (!$oFindStylesheetObject->AlreadyFetched($sImportedFile)))
{
if ($bImports){
$oFindStylesheetObject->AddImport($sFileURI, $sImportedFile);
$oFindStylesheetObject->AddImport($sAlterableFileURI, $sImportedFile);
}else{
$oFindStylesheetObject->AddStylesheet($sFileURI, $sImportedFile);
$oFindStylesheetObject->AddStylesheet($sAlterableFileURI, $sImportedFile);
}
$oFindStylesheetObject->UpdateLastModified($sImportedFile);
//Regexp matching on all included scss files : @import 'XXX.scss';
$sDirUri = dirname($sFileURI);
$sDirUri = dirname($sAlterableFileURI);
preg_match_all('/@import \s*[\"\']([^\"\']*)\s*[\"\']\s*;/', file_get_contents($sImportedFile), $aMatches);
if ( (is_array($aMatches)) && (count($aMatches)!==0) ){
foreach ($aMatches[1] as $sImportedFile){

View File

@@ -29,7 +29,7 @@ class ThemeHandlerService
{
}
public function CompileTheme($sThemeId, $bSetup = false, $sSetupCompilationTimestamp="", $aThemeParameters = null, $aImportsPaths = null, $sWorkingPath = null){
return ThemeHandler::CompileTheme($sThemeId, $bSetup, $sSetupCompilationTimestamp="", $aThemeParameters, $aImportsPaths, $sWorkingPath);
public function CompileTheme($sThemeId, $bSetup = false, $sSetupCompilationTimestamp = "", $aThemeParameters = null, $aImportsPaths = null, $sWorkingPath = null){
return ThemeHandler::CompileTheme($sThemeId, $bSetup, $sSetupCompilationTimestamp, $aThemeParameters, $aImportsPaths, $sWorkingPath);
}
}

View File

@@ -15,6 +15,7 @@
//
// You should have received a copy of the GNU Affero General Public License
// along with iTop. If not, see <http://www.gnu.org/licenses/>
use Combodo\iTop\Application\Helper\Session;
/**
* This class records the pending "transactions" corresponding to forms that have not been
@@ -26,8 +27,6 @@
* @copyright Copyright (C) 2010-2021 Combodo SARL
* @license http://opensource.org/licenses/AGPL-3.0
*/
class privUITransaction
{
/**
@@ -99,9 +98,12 @@ class privUITransaction
}
/**
* The original (and by default) mechanism for storing transaction information
* as an array in the $_SESSION variable
* The original mechanism for storing transaction information as an array in the $_SESSION variable
*
* Warning, since 2.6.0 the session is regenerated on each login (see PR #20) !
* Also, we saw some problems when using memcached as the PHP session implementation (see N°1835)
*
* @see \Combodo\iTop\Application\Helper\Session
*/
class privUITransactionSession
{
@@ -112,15 +114,15 @@ class privUITransactionSession
*/
public static function GetNewTransactionId()
{
if (!isset($_SESSION['transactions']))
if (!Session::IsSet('transactions'))
{
$_SESSION['transactions'] = array();
Session::Set('transactions', []);
}
// Strictly speaking, the two lines below should be grouped together
// by a critical section
// sem_acquire($rSemIdentified);
$id = static::GetUserPrefix() . str_replace(array('.', ' '), '', microtime()); //1 + count($_SESSION['transactions']);
$_SESSION['transactions'][$id] = true;
$id = static::GetUserPrefix() . str_replace(array('.', ' '), '', microtime());
Session::Set(['transactions', $id], true);
// sem_release($rSemIdentified);
return (string)$id;
@@ -137,17 +139,17 @@ class privUITransactionSession
public static function IsTransactionValid($id, $bRemoveTransaction = true)
{
$bResult = false;
if (isset($_SESSION['transactions']))
if (Session::IsSet('transactions'))
{
// Strictly speaking, the eight lines below should be grouped together
// inside the same critical section as above
// sem_acquire($rSemIdentified);
if (isset($_SESSION['transactions'][$id]))
if (Session::IsSet(['transactions', $id]))
{
$bResult = true;
if ($bRemoveTransaction)
{
unset($_SESSION['transactions'][$id]);
Session::Unset(['transactions', $id]);
}
}
// sem_release($rSemIdentified);
@@ -162,14 +164,14 @@ class privUITransactionSession
*/
public static function RemoveTransaction($id)
{
if (isset($_SESSION['transactions']))
if (Session::IsSet('transactions'))
{
// Strictly speaking, the three lines below should be grouped together
// inside the same critical section as above
// sem_acquire($rSemIdentified);
if (isset($_SESSION['transactions'][$id]))
if (Session::IsSet(['transactions', $id]))
{
unset($_SESSION['transactions'][$id]);
Session::Unset(['transactions', $id]);
}
// sem_release($rSemIdentified);
}
@@ -194,9 +196,35 @@ class privUITransactionSession
*/
class privUITransactionFile
{
/** @var int Value to use when no user logged */
const UNAUTHENTICATED_USER_ID = -666;
/**
* @return int current user id, or {@see self::UNAUTHENTICATED_USER_ID} if no user logged
*
* @since 2.6.5 2.7.6 3.0.0 N°4289 method creation
*/
private static function GetCurrentUserId()
{
$iCurrentUserId = UserRights::GetConnectedUserId();
if ('' === $iCurrentUserId) {
$iCurrentUserId = static::UNAUTHENTICATED_USER_ID;
}
return $iCurrentUserId;
}
/**
* Create a new transaction id, store it in the session and return its id
*
* @param void
*
* @return int The new transaction identifier
*
* @throws \SecurityException
* @throws \Exception
*
* @since 2.6.5 2.7.6 3.0.0 security hardening + throws SecurityException if no user logged
*/
public static function GetNewTransactionId()
{
@@ -213,24 +241,36 @@ class privUITransactionFile
throw new Exception('Failed to create the directory "'.APPROOT.'data/transactions". Ajust the rights on the parent directory or let an administrator create the transactions directory and give the web sever enough rights to write into it.');
}
}
if (!is_writable(APPROOT.'data/transactions'))
{
throw new Exception('The directory "'.APPROOT.'data/transactions" must be writable to the application.');
}
self::CleanupOldTransactions();
$id = basename(tempnam(APPROOT.'data/transactions', static::GetUserPrefix()));
self::Info('GetNewTransactionId: Created transaction: '.$id);
return (string)$id;
$iCurrentUserId = static::GetCurrentUserId();
self::CleanupOldTransactions();
$sTransactionIdFullPath = tempnam(APPROOT.'data/transactions', static::GetUserPrefix());
file_put_contents($sTransactionIdFullPath, $iCurrentUserId, LOCK_EX);
$sTransactionIdFileName = basename($sTransactionIdFullPath);
self::Info('GetNewTransactionId: Created transaction: '.$sTransactionIdFileName);
return $sTransactionIdFileName;
}
/**
* Check whether a transaction is valid or not and (optionally) remove the valid transaction from
* the session so that another call to IsTransactionValid for the same transaction id
* will return false
*
* @param int $id Identifier of the transaction, as returned by GetNewTransactionId
* @param bool $bRemoveTransaction True if the transaction must be removed
*
* @return bool True if the transaction is valid, false otherwise
*
* @since 2.6.5 2.7.6 3.0.0 N°4289 security hardening
*/
public static function IsTransactionValid($id, $bRemoveTransaction = true)
{
@@ -244,53 +284,53 @@ class privUITransactionFile
clearstatcache(true, $sFilepath);
$bResult = file_exists($sFilepath);
if ($bResult)
if (false === $bResult) {
self::Info("IsTransactionValid: Transaction '$id' not found. Pending transactions:\n".implode("\n", self::GetPendingTransactions()));
return false;
}
$iCurrentUserId = static::GetCurrentUserId();
$sTransactionIdUserId = file_get_contents($sFilepath);
if ($iCurrentUserId != $sTransactionIdUserId) {
self::Info("IsTransactionValid: Transaction '$id' not existing for current user. Pending transactions:\n".implode("\n", self::GetPendingTransactions()));
return false;
}
if ($bRemoveTransaction)
{
if ($bRemoveTransaction)
$bResult = @unlink($sFilepath);
if (!$bResult)
{
$bResult = @unlink($sFilepath);
if (!$bResult)
{
self::Error('IsTransactionValid: FAILED to remove transaction '.$id);
}
else
{
self::Info('IsTransactionValid: OK. Removed transaction: '.$id);
}
self::Error('IsTransactionValid: FAILED to remove transaction '.$id);
}
else
{
self::Info('IsTransactionValid: OK. Removed transaction: '.$id);
}
}
else
{
self::Info("IsTransactionValid: Transaction '$id' not found. Pending transactions for this user:\n".implode("\n", self::GetPendingTransactions()));
}
return $bResult;
}
/**
* Removes the transaction specified by its id
* @param int $id The Identifier (as returned by GetNewTransactionId) of the transaction to be removed.
* @return void
* @return bool true if the token can be removed
*
* @since 2.6.5 2.7.6 3.0.0 N°4289 security hardening
*/
public static function RemoveTransaction($id)
{
$bSuccess = true;
$sFilepath = APPROOT.'data/transactions/'.$id;
clearstatcache(true, $sFilepath);
if(!file_exists($sFilepath))
{
$bSuccess = false;
self::Error("RemoveTransaction: Transaction '$id' not found. Pending transactions for this user:\n".implode("\n", self::GetPendingTransactions()));
/** @noinspection PhpRedundantOptionalArgumentInspection */
$bResult = static::IsTransactionValid($id, true);
if (false === $bResult) {
self::Error("RemoveTransaction: Transaction '$id' is invalid. Pending transactions:\n"
.implode("\n", self::GetPendingTransactions()));
return false;
}
$bSuccess = @unlink($sFilepath);
if (!$bSuccess)
{
self::Error('RemoveTransaction: FAILED to remove transaction '.$id);
}
else
{
self::Info('RemoveTransaction: OK '.$id);
}
return $bSuccess;
return true;
}
/**
@@ -363,22 +403,35 @@ class privUITransactionFile
{
self::Write('Error | '.$sText);
}
protected static function IsLogEnabled() {
$oConfig = MetaModel::GetConfig();
if (is_null($oConfig)) {
return false;
}
$bLogTransactions = $oConfig->Get('log_transactions');
if (true === $bLogTransactions) {
return true;
}
return false;
}
protected static function Write($sText)
{
$bLogEnabled = MetaModel::GetConfig()->Get('log_transactions');
if ($bLogEnabled)
{
if (false === static::IsLogEnabled()) {
return;
}
$hLogFile = @fopen(APPROOT.'log/transactions.log', 'a');
if ($hLogFile !== false)
{
if ($hLogFile !== false) {
flock($hLogFile, LOCK_EX);
$sDate = date('Y-m-d H:i:s');
fwrite($hLogFile, "$sDate | $sText\n");
fflush($hLogFile);
flock($hLogFile, LOCK_UN);
fclose($hLogFile);
}
}
}
}

View File

@@ -2,15 +2,22 @@
namespace Combodo\iTop;
use AttributeDate;
use AttributeDateTime;
use Dict;
use Exception;
use MetaModel;
use Twig_Environment;
use Twig_SimpleFilter;
use Twig_SimpleFunction;
use utils;
/**
* Class TwigExtension
*
* @author Guillaume Lajarige <guillaume.lajarige@combodo.com>
* @package Combodo\iTop
* @deprecated 3.1.0 N°4034
*/
class TwigExtension
{
/**
@@ -48,6 +55,10 @@ class TwigExtension
{
return AttributeDateTime::GetFormat()->Format($sDate);
}
if (preg_match('@^\d\d\d\d-\d\d-\d\d$@', trim($sDate)))
{
return AttributeDate::GetFormat()->Format($sDate);
}
}
catch (Exception $e)
{
@@ -80,30 +91,14 @@ class TwigExtension
// Filter to add itopversion to an url
$oTwigEnv->addFilter(new Twig_SimpleFilter('add_itop_version', function ($sUrl) {
if (strpos($sUrl, '?') === false)
{
$sUrl = $sUrl."?itopversion=".ITOP_VERSION;
}
else
{
$sUrl = $sUrl."&itopversion=".ITOP_VERSION;
}
$sUrl = utils::AddParameterToUrl($sUrl, 'itopversion', ITOP_VERSION);
return $sUrl;
}));
// Filter to add a module's version to an url
$oTwigEnv->addFilter(new Twig_SimpleFilter('add_module_version', function ($sUrl, $sModuleName) {
$sModuleVersion = utils::GetCompiledModuleVersion($sModuleName);
if (strpos($sUrl, '?') === false)
{
$sUrl = $sUrl."?moduleversion=".$sModuleVersion;
}
else
{
$sUrl = $sUrl."&moduleversion=".$sModuleVersion;
}
$sUrl = utils::AddParameterToUrl($sUrl, 'moduleversion', $sModuleVersion);
return $sUrl;
}));
@@ -115,14 +110,6 @@ class TwigExtension
return utils::IsDevelopmentEnvironment();
}));
// Function to get configuration parameter
// Usage in twig: {{ get_config_parameter('foo') }}
$oTwigEnv->addFunction(new Twig_SimpleFunction('get_config_parameter', function($sParamName)
{
$oConfig = MetaModel::GetConfig();
return $oConfig->Get($sParamName);
}));
// Function to get the URL of a static page in a module
// Usage in twig: {{ get_static_page_module_url('itop-my-module', 'path-to-my-page') }}
$oTwigEnv->addFunction(new Twig_SimpleFunction('get_static_page_module_url', function($sModuleName, $sPage)
@@ -137,4 +124,5 @@ class TwigExtension
return utils::GetAbsoluteUrlModulePage($sModuleName, $sPage);
}));
}
}

View File

@@ -4,6 +4,11 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Application\UI\Base\Component\Form\FormUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Input\InputUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Layout\UIContentBlockUIBlockFactory;
use Combodo\iTop\Core\MetaModel\FriendlyNameType;
require_once(APPROOT.'/application/displayblock.class.inc.php');
/**
@@ -57,6 +62,8 @@ class UIExtKeyWidget
protected $sAttCode;
protected $bSearchMode;
//public function __construct($sAttCode, $sClass, $sTitle, $oAllowedValues, $value, $iInputId, $bMandatory, $sNameSuffix = '', $sFieldPrefix = '', $sFormPrefix = '')
/**
* @param \WebPage $oPage
* @param string $sAttCode
@@ -76,6 +83,7 @@ class UIExtKeyWidget
* @throws \Exception
*
* @since 3.0.0 N°3750 new $sInputType parameter
* @since 2.7.7 3.0.1 3.1.0 N°3129 Add default value for $aArgs for PHP 8.0 compat
*/
public static function DisplayFromAttCode(
$oPage, $sAttCode, $sClass, $sTitle, $oAllowedValues, $value, $iInputId, $bMandatory, $sFieldName = '', $sFormPrefix = '',
@@ -186,7 +194,7 @@ class UIExtKeyWidget
$bIsAutocomplete = $oAllowedValues->CountExceeds($iMaxComboLength);
$sWrapperCssClass = $bIsAutocomplete ? 'ibo-input-select-autocomplete-wrapper' : 'ibo-input-select-wrapper';
$sHTMLValue = "<div class=\"field_input_zone field_input_extkey ibo-input-wrapper ibo-input-select-wrapper--with-buttons $sWrapperCssClass\" data-attcode=\"".$this->sAttCode."\" data-validation=\"untouched\">";
$sHTMLValue = "<div class=\"field_input_zone field_input_extkey ibo-input-wrapper ibo-input-select-wrapper--with-buttons $sWrapperCssClass\" data-attcode=\"".$this->sAttCode."\" data-validation=\"untouched\" data-accessibility-selectize-label=\"$sTitle\">";
// We just need to compare the number of entries with MaxComboLength, so no need to get the real count.
if (!$bIsAutocomplete) {
@@ -194,42 +202,45 @@ class UIExtKeyWidget
$sHelpText = ''; //$this->oAttDef->GetHelpOnEdition();
//$sHTMLValue .= "<div class=\"field_select_wrapper\">\n";
$aOptions = [];
$sDisplayValue = "";
$aOption = [];
$aOption['value'] = "";
$aOption['label'] = Dict::S('UI:SelectOne');
array_push($aOptions,$aOption);
array_push($aOptions, $aOption);
$oAllowedValues->Rewind();
$bAddingValue=false;
$sClassAllowed = $oAllowedValues->GetClass();
$bAddingValue = false;
$aComplementAttributeSpec = MetaModel::GetComplementAttributeSpec($oAllowedValues->GetClass());
// N°4792 - load only the required fields
$aFieldsToLoad = [];
$aComplementAttributeSpec = MetaModel::GetNameSpec($oAllowedValues->GetClass(), FriendlyNameType::COMPLEMENTARY);
$sFormatAdditionalField = $aComplementAttributeSpec[0];
$aAdditionalField = $aComplementAttributeSpec[1];
if (count($aAdditionalField)>0)
{
$bAddingValue=true;
if (count($aAdditionalField) > 0) {
$bAddingValue = true;
$aFieldsToLoad[$sClassAllowed] = $aAdditionalField;
}
while($oObj = $oAllowedValues->Fetch())
{
$aOption=[];
$sObjectImageAttCode = MetaModel::GetImageAttributeCode($sClassAllowed);
if (!empty($sObjectImageAttCode)) {
$aFieldsToLoad[$sClassAllowed][] = $sObjectImageAttCode;
}
$aFieldsToLoad[$sClassAllowed][] = 'friendlyname';
$oAllowedValues->OptimizeColumnLoad($aFieldsToLoad);
$bInitValue = false;
while ($oObj = $oAllowedValues->Fetch()) {
$aOption = [];
$aOption['value'] = $oObj->GetKey();
$aOption['label'] = $oObj->GetName();//.'<span class=\"object-ref-icon fas fa-eye-slash object-obsolete fa-1x fa-fw\"></span>';
$aOption['label'] = $oObj->GetName();
$aOption['search_label'] = utils::HtmlEntityDecode($oObj->GetName());
if (($oAllowedValues->Count() == 1) && ($bMandatory == 'true') )
{
if (($oAllowedValues->Count() == 1) && ($bMandatory == 'true')) {
// When there is only once choice, select it by default
$sDisplayValue=$oObj->GetName();
if($value != $oObj->GetKey())
{
$value=$oObj->GetKey();
}
}
else {
if ((is_array($value) && in_array($oObj->GetKey(), $value)) || ($value == $oObj->GetKey())) {
$sDisplayValue = $oObj->GetName();
if ($value != $oObj->GetKey()) {
$value = $oObj->GetKey();
$bInitValue = true;
}
}
if ($oObj->IsObsolete()) {
@@ -240,23 +251,36 @@ class UIExtKeyWidget
foreach ($aAdditionalField as $sAdditionalField) {
array_push($aArguments, $oObj->Get($sAdditionalField));
}
$aOption['additional_field'] = vsprintf($sFormatAdditionalField, $aArguments);
$aOption['additional_field'] = utils::HtmlEntities(vsprintf($sFormatAdditionalField, $aArguments));
}
if (!empty($sObjectImageAttCode)) {
// Try to retrieve image for contact
/** @var \ormDocument $oImage */
$oImage = $oObj->Get($sObjectImageAttCode);
if (!$oImage->IsEmpty()) {
$aOption['picture_url'] = $oImage->GetDisplayURL($sClassAllowed, $oObj->GetKey(), $sObjectImageAttCode);
$aOption['initials'] = '';
} else {
$aOption['initials'] = utils::FormatInitialsForMedallion(utils::ToAcronym($oObj->Get('friendlyname')));
}
}
array_push($aOptions, $aOption);
}
$sInputType = CmdbAbstractObject::ENUM_INPUT_TYPE_DROPDOWN_DECORATED;
$sHTMLValue .= "<select title=\"$sHelpText\" name=\"{$sAttrFieldPrefix}{$sFieldName}\" id=\"$this->iId\" tabindex=\"0\"></select>";
$sJsonOptions = json_encode($aOptions);
$sHTMLValue .= "<select class=\"ibo-input-select-placeholder\" title=\"$sHelpText\" name=\"{$sAttrFieldPrefix}{$sFieldName}\" id=\"$this->iId\" tabindex=\"0\"></select>";
$sJsonOptions = str_replace("'", "\'", str_replace('\\', '\\\\', json_encode($aOptions)));
$oPage->add_ready_script(
<<<EOF
oACWidget_{$this->iId} = new ExtKeyWidget('{$this->iId}', '{$this->sTargetClass}', '$sFilter', '$sTitle', true, $sWizHelper, '{$this->sAttCode}', $sJSSearchMode, $sJSDoSearch);
oACWidget_{$this->iId}.emptyHtml = "<div style=\"background: #fff; border:0; text-align:center; vertical-align:middle;\"><p>$sMessage</p></div>";
oACWidget_{$this->iId}.AddSelectize('$sJsonOptions','$value');
$('#$this->iId').on('update', function() { oACWidget_{$this->iId}.Update(); } );
$('#$this->iId').on('change', function() { $(this).trigger('extkeychange') } );
$('#$this->iId').on('change', function() { $(this).trigger('extkeychange'); } );
EOF
);
if ($bInitValue) {
$oPage->add_ready_script("$('#$this->iId').one('validate', function() { $(this).trigger('change'); } );");
}
$sHTMLValue .= "<div class=\"ibo-input-select--action-buttons\">";
}
else
@@ -300,12 +324,12 @@ EOF
EOF
);
$sHTMLValue .= "<div class=\"ibo-input-select--action-buttons\">";
$sHTMLValue .= " <div class=\"ibo-input-select--action-button ibo-input-select--action-button--clear ibo-is-hidden\" id=\"mini_clear_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.Clear();\" data-tooltip-content='".Dict::S('UI:Button:Clear')."'><i class=\"fas fa-times\"></i></div>";
$sHTMLValue .= " <a href=\"#\" class=\"ibo-input-select--action-button ibo-input-select--action-button--clear ibo-is-hidden\" id=\"mini_clear_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.Clear();\" data-tooltip-content='".Dict::S('UI:Button:Clear')."'><i class=\"fas fa-times\"></i></a>";
}
if ($bCreate && $bExtensions) {
$sCallbackName = (MetaModel::IsAbstract($this->sTargetClass)) ? 'SelectObjectClass' : 'CreateObject';
$sHTMLValue .= "<div class=\"ibo-input-select--action-button ibo-input-select--action-button--create\" id=\"mini_add_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.{$sCallbackName}();\" data-tooltip-content='".Dict::S('UI:Button:Create')."'><i class=\"fas fa-plus\"></i></div>";
$sHTMLValue .= "<a href=\"#\" class=\"ibo-input-select--action-button ibo-input-select--action-button--create\" id=\"mini_add_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.{$sCallbackName}();\" data-tooltip-content='".Dict::S('UI:Button:Create')."'><i class=\"fas fa-plus\"></i></a>";
$oPage->add_ready_script(
<<<JS
if ($('#ajax_{$this->iId}').length == 0)
@@ -316,7 +340,7 @@ JS
);
}
if ($bExtensions && MetaModel::IsHierarchicalClass($this->sTargetClass) !== false) {
$sHTMLValue .= "<div class=\"ibo-input-select--action-button ibo-input-select--action-button--hierarchy\" id=\"mini_tree_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.HKDisplay();\" data-tooltip-content='".Dict::S('UI:Button:SearchInHierarchy')."'><i class=\"fas fa-sitemap\"></i></div>";
$sHTMLValue .= "<a href=\"#\" class=\"ibo-input-select--action-button ibo-input-select--action-button--hierarchy\" id=\"mini_tree_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.HKDisplay();\" data-tooltip-content='".Dict::S('UI:Button:SearchInHierarchy')."'><i class=\"fas fa-sitemap\"></i></a>";
$oPage->add_ready_script(
<<<JS
if ($('#ac_tree_{$this->iId}').length == 0)
@@ -327,7 +351,7 @@ JS
);
}
if ($oAllowedValues->CountExceeds($iMaxComboLength)) {
$sHTMLValue .= " <div class=\"ibo-input-select--action-button ibo-input-select--action-button--search\" id=\"mini_search_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.Search();\" data-tooltip-content='".Dict::S('UI:Button:Search')."'><i class=\"fas fa-search\"></i></div>";
$sHTMLValue .= " <a href=\"#\" class=\"ibo-input-select--action-button ibo-input-select--action-button--search\" id=\"mini_search_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.Search();\" data-tooltip-content='".Dict::S('UI:Button:Search')."'><i class=\"fas fa-search\"></i></a>";
}
$sHTMLValue .= "</div>";
$sHTMLValue .= "</div>";
@@ -521,7 +545,7 @@ JS
$sHTMLValue .= "<option value=\"\">$sDisplayValue</option>\n";
}
} else {
$sHTMLValue .= "<select title=\"$sHelpText\" name=\"{$sAttrFieldPrefix}{$sFieldName}\" id=\"$this->iId\">\n";
$sHTMLValue .= "<select class=\"ibo-input-select-placeholder\" title=\"$sHelpText\" name=\"{$sAttrFieldPrefix}{$sFieldName}\" id=\"$this->iId\">\n";
$sHTMLValue .= "<option value=\"\">".Dict::S('UI:SelectOne')."</option>\n";
}
@@ -593,7 +617,7 @@ EOF
// the input for the auto-complete
$sHTMLValue .= "<input class=\"field_autocomplete ibo-input-select\" type=\"text\" id=\"label_$this->iId\" value=\"$sDisplayValue\"/>";
$sHTMLValue .= "<span class=\"field_input_btn\"><div class=\"mini_button\" id=\"mini_search_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.Search();\"><i class=\"fas fa-search\"></i></div></span>";
$sHTMLValue .= "<div class=\"ibo-input-select--action-buttons\"><span class=\"field_input_btn\"><div class=\"mini_button ibo-input-select--action-button\" id=\"mini_search_{$this->iId}\" onClick=\"oACWidget_{$this->iId}.Search();\"><i class=\"fas fa-search\"></i></div></span></div>";
// another hidden input to store & pass the object's Id
$sHTMLValue .= "<input type=\"hidden\" id=\"$this->iId\" name=\"{$sAttrFieldPrefix}{$sFieldName}\" value=\"".htmlentities($value, ENT_QUOTES, 'UTF-8')."\" />\n";
@@ -687,14 +711,14 @@ JS
HTML
);
$sDialogTitle = addslashes($sTitle);
$sDialogTitleSanitized = addslashes(utils::HtmlToText($sTitle));
$oPage->add_ready_script(<<<JS
$('#ac_dlg_{$this->iId}').dialog({
width: $(window).width()*0.8,
height: $(window).height()*0.8,
autoOpen: false,
modal: true,
title: '$sDialogTitle',
title: '$sDialogTitleSanitized',
resizeStop: oACWidget_{$this->iId}.UpdateSizes,
close: oACWidget_{$this->iId}.OnClose,
buttons: [
@@ -755,14 +779,14 @@ JS
* @param DBObject $oObj The current object for the OQL context
* @param string $sContains The text of the autocomplete to filter the results
* @param string $sOutputFormat
* @param null $sOperation for the values @see ValueSetObjects->LoadValues()
* @param null $sOperation for the values @see ValueSetObjects->LoadValues() not used since 3.0.0
*
* @throws CoreException
* @throws OQLException
*
* @since 2.7.7 3.0.1 3.1.0 N°3129 Remove default value for $oObj for PHP 8.0 compatibility
*/
public function AutoComplete(
WebPage $oP, $sFilter, $oObj = null, $sContains = '', $sOutputFormat = self::ENUM_OUTPUT_FORMAT_CSV, $sOperation = null
)
public function AutoComplete(WebPage $oP, $sFilter, $oObj, $sContains, $sOutputFormat = self::ENUM_OUTPUT_FORMAT_CSV, $sOperation = null )
{
if (is_null($sFilter)) {
throw new Exception('Implementation: null value for allowed values definition');
@@ -776,13 +800,13 @@ JS
$oValuesSet->SetSort(false);
$oValuesSet->SetModifierProperty('UserRightsGetSelectFilter', 'bSearchMode', $this->bSearchMode);
$oValuesSet->SetLimit($iMax);
$aValuesContains = $oValuesSet->GetValuesForAutocomplete(array('this' => $oObj, 'current_extkey_id' => $iCurrentExtKeyId), $sContains, 'start_with');
asort($aValuesContains);
$aValues = $aValuesContains;
$aValuesStartWith = $oValuesSet->GetValuesForAutocomplete(array('this' => $oObj, 'current_extkey_id' => $iCurrentExtKeyId), $sContains, 'start_with');
asort($aValuesStartWith);
$aValues = $aValuesStartWith;
if (sizeof($aValues) < $iMax) {
$aValuesContains = $oValuesSet->GetValuesForAutocomplete(array('this' => $oObj, 'current_extkey_id' => $iCurrentExtKeyId), $sContains, 'contains');
asort($aValuesContains);
$iSize = sizeof($aValuesContains);
$iSize = sizeof($aValues);
foreach ($aValuesContains as $sKey => $sFriendlyName)
{
if (!isset($aValues[$sKey]))
@@ -798,28 +822,33 @@ JS
elseif (!in_array($sContains, $aValues))
{
$aValuesEquals = $oValuesSet->GetValuesForAutocomplete(array('this' => $oObj, 'current_extkey_id' => $iCurrentExtKeyId), $sContains, 'equals');
$aValues = array_merge($aValuesEquals, $aValues);
// Note: Here we cannot use array_merge as it would reindex the numeric keys starting from 0 when keys are actually the objects ID.
// As a workaround we use array_replace as it does preserve numeric keys. It's ok if some values from $aValuesEquals are replaced with values from $aValues as they contain the same data.
$aValues = array_replace($aValuesEquals, $aValues);
}
switch($sOutputFormat)
{
case static::ENUM_OUTPUT_FORMAT_JSON:
$aJsonMap = array();
foreach ($aValues as $sKey => $aValue)
{
if ($aValue['additional_field'] != '')
{
$aJsonMap[] = array('value' => $sKey, 'label' => $aValue['label'], 'obsolescence_flag' => $aValue['obsolescence_flag'], 'additional_field' => $aValue['additional_field']);
}
else
{
$aJsonMap[] = array('value' => $sKey, 'label' => $aValue['label'], 'obsolescence_flag' => $aValue['obsolescence_flag']);
}
}
$aJsonMap = array();
foreach ($aValues as $sKey => $aValue) {
$aElt = ['value' => $sKey, 'label' => utils::EscapeHtml($aValue['label']), 'obsolescence_flag' => $aValue['obsolescence_flag']];
if ($aValue['additional_field'] != '') {
$aElt['additional_field'] = utils::EscapeHtml($aValue['additional_field']);
}
$oP->SetContentType('application/json');
$oP->add(json_encode($aJsonMap));
if (array_key_exists('initials', $aValue)) {
$aElt['initials'] = utils::FormatInitialsForMedallion($aValue['initials']);
if (array_key_exists('picture_url', $aValue)) {
$aElt['picture_url'] = $aValue['picture_url'];
}
}
$aJsonMap[] = $aElt;
}
$oP->SetContentType('application/json');
$oP->add(json_encode($aJsonMap));
break;
case static::ENUM_OUTPUT_FORMAT_CSV:
@@ -876,7 +905,7 @@ JS
{
// For security reasons: check that the "proposed" class is actually a subclass of the linked class
// and that the current user is allowed to create objects of this class
$aSubClasses = MetaModel::EnumChildClasses($this->sTargetClass);
$aSubClasses = MetaModel::EnumChildClasses($this->sTargetClass, ENUM_CHILD_CLASSES_ALL);
$aPossibleClasses = array();
foreach($aSubClasses as $sCandidateClass)
{
@@ -886,26 +915,18 @@ JS
}
}
$sDialogTitle = '';
$oPage->add('<div id="ac_create_'.$this->iId.'"><div class="wizContainer" style="vertical-align:top;"><div id="dcr_'.$this->iId.'">');
$oPage->add('<form>');
$sClassLabel = MetaModel::GetName($this->sTargetClass);
$oPage->add('<p>'.Dict::Format('UI:SelectTheTypeOf_Class_ToCreate', $sClassLabel));
$oPage->add('<nobr><select name="class">');
asort($aPossibleClasses);
foreach($aPossibleClasses as $sClassName => $sClassLabel)
{
$oPage->add("<option value=\"$sClassName\">$sClassLabel</option>");
}
$oPage->add('</select>');
$oPage->add('&nbsp; <button type="submit" class="action" style="margin-top:15px;"><span>' . Dict::S('UI:Button:Ok') . '</span></button></nobr></p>');
$oPage->add('</form>');
$oPage->add('</div></div></div>');
$oPage->add_ready_script("\$('#ac_create_$this->iId').dialog({ width: 'auto', height: 'auto', maxHeight: $(window).height() - 50, autoOpen: false, modal: true, title: '$sDialogTitle'});\n");
$oPage->add_ready_script("$('#dcr_{$this->iId} form').removeAttr('onsubmit');");
$oPage->add_ready_script("$('#dcr_{$this->iId} form').on('submit.uilinksWizard', oACWidget_{$this->iId}.DoSelectObjectClass);");
$sDialogTitle = Dict::Format('UI:CreationTitle_Class', $sClassLabel);;
$oBlock = UIContentBlockUIBlockFactory::MakeStandard('ac_create_'.$this->iId,['ibo-is-visible']);
$oPage->AddSubBlock($oBlock);
$oClassForm = FormUIBlockFactory::MakeStandard();
$oBlock->AddSubBlock($oClassForm);
$oClassForm->AddSubBlock(cmdbAbstractObject::DisplayBlockSelectClassToCreate( $sClassLabel, $this->sTargetClass, $aPossibleClasses));
$sDialogTitleEscaped = addslashes($sDialogTitle);
$oPage->add_ready_script("$('#ac_create_$this->iId').dialog({ width: 'auto', height: 'auto', maxHeight: $(window).height() - 50, autoOpen: false, modal: true, title: '$sDialogTitleEscaped'});\n");
$oPage->add_ready_script("$('#ac_create_{$this->iId} form').removeAttr('onsubmit');");
$oPage->add_ready_script("$('#ac_create_{$this->iId} form').find('select').attr('id', 'ac_create_{$this->iId}_select');");
$oPage->add_ready_script("$('#ac_create_{$this->iId} form').on('submit.uilinksWizard', oACWidget_{$this->iId}.DoSelectObjectClass);");
}
/**
@@ -963,7 +984,7 @@ HTML
);
$oPage->add_ready_script(<<<JS
$('#ac_create_{$this->iId}').dialog({ width: 'auto', height: 'auto', maxHeight: $(window).height() - 50, autoOpen: false, modal: true});
$('#ac_create_{$this->iId}').dialog({ width: $(window).width() * 0.6, height: 'auto', maxHeight: $(window).height() - 50, autoOpen: false, modal: true});
$('#dcr_{$this->iId} form').removeAttr('onsubmit');
$('#dcr_{$this->iId} form').on('submit.uilinksWizard', oACWidget_{$this->iId}.DoCreateObject);
JS
@@ -976,7 +997,7 @@ JS
public function DisplayHierarchy(WebPage $oPage, $sFilter, $currValue, $oObj)
{
$sDialogTitle = addslashes(Dict::Format('UI:HierarchyOf_Class', MetaModel::GetName($this->sTargetClass)));
$oPage->add('<div id="dlg_tree_'.$this->iId.'"><div class="wizContainer" style="vertical-align:top;"><div style="overflow:auto;background:#fff;margin-bottom:5px;" id="tree_'.$this->iId.'">');
$oPage->add('<div id="dlg_tree_'.$this->iId.'"><div class="wizContainer" style="vertical-align:top;"><div style="margin-bottom:5px;" id="tree_'.$this->iId.'">');
$oPage->add('<table style="width:100%"><tr><td>');
if (is_null($sFilter))
{
@@ -997,16 +1018,46 @@ JS
if ($bHasChildLeafs)
{
$oPage->add('<div class="treecontrol" id="treecontrolid"><a href="?#">'.Dict::S("UI:Treeview:CollapseAll").'</a> | <a href="?#">'.Dict::S("UI:Treeview:ExpandAll").'</a></div>');
$oPage->add('<span class="treecontrol ibo-button-group" id="treecontrolid"><a class="ibo-button ibo-is-regular ibo-is-neutral" href="?#">'.Dict::S("UI:Treeview:CollapseAll").'</a><a class="ibo-button ibo-is-regular ibo-is-neutral" href="?#">'.Dict::S("UI:Treeview:ExpandAll").'</a></span>');
}
$oPage->add("<input type=\"button\" class=\"ibo-button ibo-is-regular ibo-is-neutral\" id=\"btn_cancel_{$this->iId}\" value=\"".Dict::S('UI:Button:Cancel')."\" onClick=\"$('#dlg_tree_{$this->iId}').dialog('close');\">&nbsp;&nbsp;");
$oPage->add("<input type=\"button\" class=\"ibo-button ibo-is-regular ibo-is-primary\" id=\"btn_ok_{$this->iId}\" value=\"".Dict::S('UI:Button:Ok')."\" onClick=\"oACWidget_{$this->iId}.DoHKOk();\">");
$oPage->add('</div></div>');
$sOkButtonLabel = Dict::S('UI:Button:Ok');
$sCancelButtonLabel = Dict::S('UI:Button:Cancel');
$oPage->add_ready_script("\$('#tree_$this->iId ul').treeview({ control: '#treecontrolid', persist: 'false'});\n");
$oPage->add_ready_script("\$('#dlg_tree_$this->iId').dialog({ width: 'auto', height: 'auto', autoOpen: true, modal: true, title: '$sDialogTitle', resizeStop: oACWidget_{$this->iId}.OnHKResize, close: oACWidget_{$this->iId}.OnHKClose });\n");
$oPage->add_ready_script(<<<JS
$('#dlg_tree_$this->iId').dialog({
width: 'auto',
height: 'auto',
autoOpen: true,
modal: true,
title: '$sDialogTitle',
open: function() {
$(this).css("max-height", parseInt($(window).height()*0.7)+'px');
},
buttons: [
{
text: "$sCancelButtonLabel",
click: function() { $(this).dialog( "close" ); }
},
{
text: "$sOkButtonLabel",
class: "ibo-is-primary",
click: function() {
oACWidget_{$this->iId}.DoHKOk();
},
},
],
resizeStop: oACWidget_{$this->iId}.OnHKResize,
close: oACWidget_{$this->iId}.OnHKClose
});
$('#dlg_tree_$this->iId + .ui-dialog-buttonpane .ui-dialog-buttonset').prepend($('#treecontrolid'));
JS
);
}
/**

View File

@@ -15,6 +15,7 @@
//
// You should have received a copy of the GNU Affero General Public License
// along with iTop. If not, see <http://www.gnu.org/licenses/>
use Combodo\iTop\Application\Helper\WebResourcesHelper;
/**
* Class UIHTMLEditorWidget
@@ -64,7 +65,7 @@ class UIHTMLEditorWidget
$sHelpText = $this->m_sHelpText;
$sValidationField = $this->m_sValidationField;
$sHtmlValue = "<div class=\"field_input_zone field_input_html\"><textarea class=\"htmlEditor\" title=\"$sHelpText\" name=\"attr_{$this->m_sFieldPrefix}{$sCode}\" rows=\"10\" cols=\"10\" id=\"$iId\">$sValue</textarea></div>$sValidationField";
$sHtmlValue = "<div class=\"field_input_zone field_input_html ibo-input-wrapper\"><textarea class=\"htmlEditor ibo-input-richtext-placeholder\" title=\"$sHelpText\" name=\"attr_{$this->m_sFieldPrefix}{$sCode}\" id=\"$iId\">$sValue</textarea></div>$sValidationField";
// Replace the text area with CKEditor
// To change the default settings of the editor,
@@ -83,6 +84,7 @@ class UIHTMLEditorWidget
}
$sConfigJS = json_encode($aConfig);
WebResourcesHelper::EnableCKEditorToWebPage($oPage);
$oPage->add_ready_script("$('#$iId').ckeditor(function() { /* callback code */ }, $sConfigJS);"); // Transform $iId into a CKEdit
// Please read...

View File

@@ -75,9 +75,15 @@ class UILinksWidgetDirect
* @param array $aArgs
* @param string $sFormPrefix
* @param DBObject $oCurrentObj
*
* @since 2.7.7 3.0.1 3.1.0 N°3129 Remove default value for $aArgs for PHP 8.0 compatibility (handling wrong values at method start)
*/
public function Display(WebPage $oPage, $oValue, $aArgs = array(), $sFormPrefix, $oCurrentObj)
public function Display(WebPage $oPage, $oValue, $aArgs, $sFormPrefix, $oCurrentObj)
{
if (empty($aArgs)) {
$aArgs = [];
}
$oLinksetDef = MetaModel::GetAttributeDef($this->sClass, $this->sAttCode);
switch($oLinksetDef->GetEditMode())
{
@@ -127,8 +133,10 @@ class UILinksWidgetDirect
* @param string $sFormPrefix
* @param DBObject $oCurrentObj
* @param bool $bDisplayMenu
*
* @since 2.7.7 3.0.1 3.1.0 N°3129 Remove default value for $aArgs for PHP 8.0 compatibility (protected method, always called with default value)
*/
protected function DisplayAsBlock(WebPage $oPage, $oValue, $aArgs = array(), $sFormPrefix, $oCurrentObj, $bDisplayMenu)
protected function DisplayAsBlock(WebPage $oPage, $oValue, $aArgs, $sFormPrefix, $oCurrentObj, $bDisplayMenu)
{
$oLinksetDef = MetaModel::GetAttributeDef($this->sClass, $this->sAttCode);
$sTargetClass = $oLinksetDef->GetLinkedClass();
@@ -197,14 +205,29 @@ class UILinksWidgetDirect
if ($sRealClass != '')
{
$oPage->add("<h1>".MetaModel::GetClassIcon($sRealClass)."&nbsp;".Dict::Format('UI:CreationTitle_Class', MetaModel::GetName($sRealClass))."</h1>\n");
$oLinksetDef = MetaModel::GetAttributeDef($this->sClass, $this->sAttCode);
$sExtKeyToMe = $oLinksetDef->GetExtKeyToMe();
$aFieldFlags = array( $sExtKeyToMe => OPT_ATT_HIDDEN);
$oObj = DBObject::MakeDefaultInstance($sRealClass);
$aPrefillParam = array('source_obj' => $oSourceObj);
$oObj->PrefillForm('creation_from_editinplace', $aPrefillParam);
cmdbAbstractObject::DisplayCreationForm($oPage, $sRealClass, $oObj, array(), array('formPrefix' => $this->sInputid, 'noRelations' => true, 'fieldsFlags' => $aFieldFlags));
$aFormExtraParams = array(
'formPrefix' => $this->sInputid,
'noRelations' => true,
'fieldsFlags' => $aFieldFlags,
'js_handlers' => [
'cancel_button_on_click' =>
<<<JS
function() {
// Do nothing, already handled by linksdirectwidget.js
};
JS
,
],
);
cmdbAbstractObject::DisplayCreationForm($oPage, $sRealClass, $oObj, array(), $aFormExtraParams);
}
else
{
@@ -229,8 +252,10 @@ class UILinksWidgetDirect
* @param string $sFormPrefix
* @param DBObject $oCurrentObj
* @param array $aButtons
*
* @since 2.7.7 3.0.1 3.1.0 N°3129 Remove default value for $aArgs for PHP 8.0 compatibility (protected method, caller already handles it)
*/
protected function DisplayEditInPlace(WebPage $oPage, $oValue, $aArgs = array(), $sFormPrefix, $oCurrentObj, $aButtons = array('create', 'delete'))
protected function DisplayEditInPlace(WebPage $oPage, $oValue, $aArgs, $sFormPrefix, $oCurrentObj, $aButtons = array('create', 'delete'))
{
$aAttribs = $this->GetTableConfig();
$oValue->Rewind();
@@ -297,7 +322,7 @@ class UILinksWidgetDirect
}
$oHiddenCriteria = $oHiddenFilter->GetCriteria();
$aArgs = $oHiddenFilter->GetInternalParams();
$sHiddenCriteria = $oHiddenCriteria->Render($aArgs);
$sHiddenCriteria = $oHiddenCriteria->RenderExpression(false, $aArgs);
$oLinkSetDef = MetaModel::GetAttributeDef($this->sClass, $this->sAttCode);
$valuesDef = $oLinkSetDef->GetValuesDef();
@@ -474,6 +499,33 @@ HTML
}
return $oPage->GetTableRow($aRow, $aAttribs);
}
/**
* @param WebPage $oPage
* @param $sRealClass
* @param $aValues
* @param int $iTempId
*
* @return array
*/
public function GetFormRow($oPage, $sRealClass, $aValues, $iTempId)
{
if ($sRealClass == '')
{
$sRealClass = $this->sLinkedClass;
}
$oLinkObj = new $sRealClass();
$oLinkObj->UpdateObjectFromPostedForm($this->sInputid);
$aAttribs = $this->GetTableConfig();
$aRow = array();
$aRow[] = '<input type="checkbox" class="selectList'.$this->sInputid.'" value="'.($iTempId).'"/>';
foreach($this->aZlist as $sLinkedAttCode)
{
$aRow[] = $oLinkObj->GetAsHTML($sLinkedAttCode);
}
return $aRow;
}
/**
* Initializes the default search parameters based on 1) a 'current' object and 2) the silos defined by the context

View File

@@ -100,15 +100,18 @@ class UILinksWidget
* @param array $aArgs Extra context arguments
* @param DBObject $oCurrentObj The object to which all the elements of the linked set refer to
* @param int $iUniqueId A unique identifier of new links
* @param boolean $bReadOnly Display link as editable or read-only. Default is false (editable)
* @param bool $bReadOnly Display link as editable or read-only. Default is false (editable)
* @param bool $bAllowRemoteExtKeyEdit If true, the ext. key to the remote object can be edited, otherwise it will be read-only
*
* @return array The HTML fragment of the one-row form
* @throws \ArchivedObjectException
* @throws \CoreException
* @throws \CoreUnexpectedValue
* @throws \Exception
*
* @since 3.1.0 3.0.4 3.0.3-1 N°6124 - Workaround performance problem on the modification of an object with an n:n relation having a large volume
*/
protected function GetFormRow(WebPage $oP, DBObject $oLinkedObj, $linkObjOrId, $aArgs, $oCurrentObj, $iUniqueId, $bReadOnly = false)
protected function GetFormRow(WebPage $oP, DBObject $oLinkedObj, $linkObjOrId, $aArgs, $oCurrentObj, $iUniqueId, $bReadOnly = false, $bAllowRemoteExtKeyEdit = true)
{
$sPrefix = "$this->m_sAttCode{$this->m_sNameSuffix}";
$aRow = array();
@@ -139,8 +142,11 @@ class UILinksWidget
$aRow['form::checkbox'] = "<input class=\"selection\" data-remote-id=\"$iRemoteObjKey\" data-link-id=\"$iKey\" data-unique-id=\"$iUniqueId\" type=\"checkbox\" onClick=\"oWidget".$this->m_iInputId.".OnSelectChange();\" value=\"$iKey\">";
foreach ($this->m_aEditableFields as $sFieldCode)
{
// N°6124 - Force remote ext. key as read-only if too many items in the linkset
$bReadOnlyField = ($sFieldCode === $this->m_sExtKeyToRemote) && (false === $bAllowRemoteExtKeyEdit);
$sSafeFieldId = $this->GetFieldId($linkObjOrId->GetKey(), $sFieldCode);
$this->AddRowForFieldCode($aRow, $sFieldCode, $aArgs, $linkObjOrId, $oP, $sNameSuffix, $sSafeFieldId);
$this->AddRowForFieldCode($aRow, $sFieldCode, $aArgs, $linkObjOrId, $oP, $sNameSuffix, $sSafeFieldId, $bReadOnlyField);
$aFieldsMap[$sFieldCode] = $sSafeFieldId;
}
}
@@ -201,8 +207,11 @@ EOF
foreach($this->m_aEditableFields as $sFieldCode)
{
// N°6124 - Force remote ext. key as read-only if too many items in the linkset
$bReadOnlyField = ($sFieldCode === $this->m_sExtKeyToRemote) && (false === $bAllowRemoteExtKeyEdit);
$sSafeFieldId = $this->GetFieldId($iUniqueId, $sFieldCode);
$this->AddRowForFieldCode($aRow, $sFieldCode, $aArgs, $oNewLinkObj, $oP, $sNameSuffix, $sSafeFieldId);
$this->AddRowForFieldCode($aRow, $sFieldCode, $aArgs, $oNewLinkObj, $oP, $sNameSuffix, $sSafeFieldId, $bReadOnlyField);
$aFieldsMap[$sFieldCode] = $sSafeFieldId;
$sValue = $oNewLinkObj->Get($sFieldCode);
@@ -255,11 +264,24 @@ JS
return $aRow;
}
private function AddRowForFieldCode(&$aRow, $sFieldCode, &$aArgs, $oLnk, $oP, $sNameSuffix, $sSafeFieldId): void
/**
* @param $aRow
* @param $sFieldCode
* @param $aArgs
* @param $oLnk
* @param $oP
* @param $sNameSuffix
* @param $sSafeFieldId
* @param bool $bReadOnlyField If true, the field will be read-only, otherwise it can be edited
*
* @return void
* @since 3.1.0 3.0.4 3.0.3-1 N°6124 - Workaround performance problem on the modification of an object with an n:n relation having a large volume
*/
private function AddRowForFieldCode(&$aRow, $sFieldCode, &$aArgs, $oLnk, $oP, $sNameSuffix, $sSafeFieldId, $bReadOnlyField = false): void
{
if (($sFieldCode === $this->m_sExtKeyToRemote))
{
// current field is the lnk extkey to the remote class
// Current field is the lnk extkey to the remote class
$aArgs['replaceDependenciesByRemoteClassFields'] = true;
$sRowFieldCode = 'static::key';
$aArgs['wizHelperRemote'] = $aArgs['wizHelper'].'_remote';
@@ -281,20 +303,31 @@ JS
$sDisplayValue = $oLnk->GetEditValue($sFieldCode);
$oAttDef = MetaModel::GetAttributeDef($this->m_sLinkedClass, $sFieldCode);
$aRow[$sRowFieldCode] = '<div class="field_container" style="border:none;"><div class="field_data"><div class="field_value">'
.cmdbAbstractObject::GetFormElementForField(
$oP,
$this->m_sLinkedClass,
$sFieldCode,
$oAttDef,
$sValue,
$sDisplayValue,
$sSafeFieldId,
$sNameSuffix,
0,
$aArgs
)
.'</div></div></div>';
if ($bReadOnlyField) {
$sFieldForHtml = $sDisplayValue;
} else {
$sFieldForHtml = cmdbAbstractObject::GetFormElementForField(
$oP,
$this->m_sLinkedClass,
$sFieldCode,
$oAttDef,
$sValue,
$sDisplayValue,
$sSafeFieldId,
$sNameSuffix,
0,
$aArgs
);
}
$aRow[$sRowFieldCode] = <<<HTML
<div class="field_container" style="border:none;">
<div class="field_data">
<div class="field_value">$sFieldForHtml</div>
</div>
</div>
HTML
;
}
private function GetFieldId($iLnkId, $sFieldCode, $bSafe = true)
@@ -374,7 +407,9 @@ JS
$oBlock->sRemoteClass = $this->m_sRemoteClass;
$oValue->Rewind();
$bAllowRemoteExtKeyEdit = $oValue->Count() <= utils::GetConfig()->Get('link_set_max_edit_ext_key');
$aForm = array();
$iMaxAddedId = 0;
$iAddedId = -1; // Unique id for new links
while ($oCurrentLink = $oValue->Fetch())
{
@@ -395,8 +430,12 @@ JS
} else {
$key = $oCurrentLink->GetKey();
}
$aForm[$key] = $this->GetFormRow($oPage, $oLinkedObj, $oCurrentLink, $aArgs, $oCurrentObj, $key, $bReadOnly);
$iMaxAddedId = max($iMaxAddedId, $key);
$aForm[$key] = $this->GetFormRow($oPage, $oLinkedObj, $oCurrentLink, $aArgs, $oCurrentObj, $key, $bReadOnly, $bAllowRemoteExtKeyEdit);
}
$oBlock->iMaxAddedId = (int) $iMaxAddedId;
$oDataTable = DataTableUIBlockFactory::MakeForForm("{$this->m_sAttCode}{$this->m_sNameSuffix}", $this->m_aTableConfig, $aForm);
$oDataTable->SetOptions(['select_mode' => 'custom']);
$oBlock->AddSubBlock($oDataTable);
@@ -566,10 +605,11 @@ JS
$aLinkedObjectIds = utils::ReadMultipleSelection($oFullSetFilter);
$iAdditionId = $iMaxAddedId + 1;
$bAllowRemoteExtKeyEdit = count($aLinkedObjectIds) <= utils::GetConfig()->Get('link_set_max_edit_ext_key');
foreach ($aLinkedObjectIds as $iObjectId) {
$oLinkedObj = MetaModel::GetObject($this->m_sRemoteClass, $iObjectId, false);
if (is_object($oLinkedObj)) {
$aRow = $this->GetFormRow($oP, $oLinkedObj, $iObjectId, array(), $oCurrentObj, $iAdditionId); // Not yet created link get negative Ids
$aRow = $this->GetFormRow($oP, $oLinkedObj, $iObjectId, array(), $oCurrentObj, $iAdditionId, false /* Default value */, $bAllowRemoteExtKeyEdit); // Not yet created link get negative Ids
$aData = [];
foreach ($aRow as $item) {
$aData[] = $item;

View File

@@ -49,6 +49,8 @@ class UIPasswordWidget
*/
public function Display(WebPage $oPage, $aArgs = array())
{
$oPage->add_dict_entry('UI:Component:Input:Password:DoesNotMatch');
$sCode = $this->sAttCode.$this->sNameSuffix;
$iWidgetIndex = self::$iWidgetIndex;
@@ -57,11 +59,12 @@ class UIPasswordWidget
$sConfirmPasswordValue = $aPasswordValues ? $aPasswordValues['confirm'] : '*****';
$sChangedValue = (($sPasswordValue != '*****') || ($sConfirmPasswordValue != '*****')) ? 1 : 0;
$sHtmlValue = '';
$sHtmlValue .= '<div class="field_input_zone field_input_onewaypassword">';
$sHtmlValue .= '<input type="password" maxlength="255" name="attr_'.$sCode.'[value]" id="'.$this->iId.'" value="'.htmlentities($sPasswordValue, ENT_QUOTES, 'UTF-8').'"/>';
$sHtmlValue .= '<input type="password" maxlength="255" id="'.$this->iId.'_confirm" value="'.htmlentities($sConfirmPasswordValue, ENT_QUOTES, 'UTF-8').'" name="attr_'.$sCode.'[confirm]"/>';
$sHtmlValue .= '<span>'.Dict::S('UI:PasswordConfirm').'</span>';
$sHtmlValue .= '<input id="'.$this->iId.'_reset" type="button" value="'.Dict::S('UI:Button:ResetPassword').'" onClick="ResetPwd(\''.$this->iId.'\');">';
$sHtmlValue .= '<div class="field_input_zone field_input_onewaypassword ibo-input-wrapper ibo-input-one-way-password-wrapper">';
$sHtmlValue .= '<input class="ibo-input" type="password" maxlength="255" name="attr_'.$sCode.'[value]" id="'.$this->iId.'" value="'.htmlentities($sPasswordValue, ENT_QUOTES, 'UTF-8').'"/>';
$sHtmlValue .= '<div class="ibo-input-wrapper ibo-input-wrapper--with-buttons"><input class="ibo-input" type="password" maxlength="255" id="'.$this->iId.'_confirm" value="'.htmlentities($sConfirmPasswordValue, ENT_QUOTES, 'UTF-8').'" name="attr_'.$sCode.'[confirm]"/>';
$sHtmlValue .= '<div class="ibo-input-select--action-buttons"><div class="ibo-input-select--action-button ibo-input-select--action-button--create" data-tooltip-content="'.Dict::S('UI:PasswordConfirm').'"><i class="fas fa-question-circle"></i></div></div></div>';
$sHtmlValue .= '<button id="'.$this->iId.'_reset" class="ibo-button ibo-is-regular ibo-is-neutral" onClick="ResetPwd(\''.$this->iId.'\');">';
$sHtmlValue .= '<span class="ibo-button--icon fas fa-undo"></span><span class="ibo-button--label">'.Dict::S('UI:Button:ResetPassword').'</span></button>';
$sHtmlValue .= '<input type="hidden" id="'.$this->iId.'_changed" name="attr_'.$sCode.'[changed]" value="'.$sChangedValue.'"/>';
$sHtmlValue .= '</div>';

View File

@@ -60,7 +60,7 @@ class UISearchFormForeignKeys
$oPage->add(<<<HTML
<form id="ObjectsAddForm_{$this->m_iInputId}">
<div id="SearchResultsToAdd_{$this->m_iInputId}" style="vertical-align:top;background: #fff;height:100%;overflow:auto;padding:0;border:0;">
<div id="SearchResultsToAdd_{$this->m_iInputId}" style="vertical-align:top;height:100%;overflow:auto;padding:0;border:0;">
<div style="background: #fff; border:0; text-align:center; vertical-align:middle;"><p>{$sEmptyList}</p></div>
</div>
<input type="hidden" id="count_{$this->m_iInputId}" value="0"/>

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/WebPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/WebPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -347,10 +347,11 @@ class WizardHelper
/**
* @return string JS code to be executed for fields update
* @since 3.0.0 N°3198
* @deprecated 3.0.3-2 3.0.4 3.1.1 3.2.0 Use {@see \WizardHelper::AddJsForUpdateFields()} instead
*/
public function GetJsForUpdateFields()
{
$sWizardHelperJsVar = ($this->m_aData['m_sWizHelperJsVarName']) ?? 'oWizardHelper'.$this->GetFormPrefix();
$sWizardHelperJsVar = (!is_null($this->m_aData['m_sWizHelperJsVarName'])) ? utils::Sanitize($this->m_aData['m_sWizHelperJsVarName'], '', utils::ENUM_SANITIZATION_FILTER_PARAMETER) : 'oWizardHelper'.$this->GetFormPrefix();
$sWizardHelperJson = $this->ToJSON();
return <<<JS
@@ -359,15 +360,39 @@ class WizardHelper
JS;
}
/**
* Add necessary JS snippets (to the page) to be executed for fields update
*
* @param \WebPage $oPage
* @return void
* @since 3.0.3-2 3.0.4 3.1.1 3.2.0 N°6766
*/
public function AddJsForUpdateFields(WebPage $oPage)
{
$sWizardHelperJsVar = (!is_null($this->m_aData['m_sWizHelperJsVarName'])) ? utils::Sanitize($this->m_aData['m_sWizHelperJsVarName'], '', utils::ENUM_SANITIZATION_FILTER_PARAMETER) : 'oWizardHelper'.$this->GetFormPrefix();
$sWizardHelperJson = $this->ToJSON();
$oPage->add_script(<<<JS
{$sWizardHelperJsVar}.m_oData = {$sWizardHelperJson};
{$sWizardHelperJsVar}.UpdateFields();
JS
);
$oPage->add_ready_script(<<<JS
if ({$sWizardHelperJsVar}.m_oDependenciesUpdatedPromiseResolve !== null){
{$sWizardHelperJsVar}.m_oDependenciesUpdatedPromiseResolve();
}
JS
);
}
static function ParseJsonSet($oMe, $sLinkClass, $sExtKeyToMe, $sJsonSet)
{
$aSet = json_decode($sJsonSet, true); // true means hash array instead of object
$oSet = CMDBObjectSet::FromScratch($sLinkClass);
foreach ($aSet as $aLinkObj)
{
foreach ($aSet as $aLinkObj) {
$oLink = MetaModel::NewObject($sLinkClass);
foreach ($aLinkObj as $sAttCode => $value)
{
foreach ($aLinkObj as $sAttCode => $value) {
$oAttDef = MetaModel::GetAttributeDef($sLinkClass, $sAttCode);
if (($oAttDef->IsExternalKey()) && ($value != '') && ($value > 0))
{

View File

@@ -1,6 +1,6 @@
<?php
/**
* @deprecated will be removed in 3.1.0 - moved to sources/application/WebPage/XMLPage.php, now loadable using autoloader
* @deprecated 3.0.0 will be removed in 3.1.0 - moved to sources/application/WebPage/XMLPage.php, now loadable using autoloader
* @license http://opensource.org/licenses/AGPL-3.0
* @copyright Copyright (C) 2010-2021 Combodo SARL
*/

View File

@@ -3,4 +3,33 @@
define('APPROOT', dirname(__FILE__).'/');
define('APPCONF', APPROOT.'conf/');
/**
* iTop Datamodel XML format version
*
* It was also used in iTop 3.0.0 to get iTop core version (instead of {@see ITOP_VERSION} which gives the application version).
* To address this need you should now use {@see ITOP_CORE_VERSION}
*
* @see ITOP_CORE_VERSION to get full iTop core version
*/
define('ITOP_DESIGN_LATEST_VERSION', '3.0');
/**
* Constant containing the iTop core version, whatever application was built
*
* Note that in iTop 3.0.0 we used {@see ITOP_DESIGN_LATEST_VERSION} to get core version.
* When releasing, both constants should be updated : see `.make/release/update-versions.php` for that !
*
* @since 2.7.7 3.0.1 3.1.0 N°4714 constant creation
* @used-by utils::GetItopVersionWikiSyntax()
* @used-by iTopModulesPhpVersionIntegrationTest
*/
define('ITOP_CORE_VERSION', '3.0.4');
/**
* @var string
* @since 3.0.4 3.1.0 3.2.0 N°6274 Allow to test if PHPUnit is currently running. Starting with PHPUnit 9.5 we'll be able to replace it with $GLOBALS['phpunit_version']
* @since 3.0.4 3.1.1 3.2.0 N°6976 Fix constant name (DeprecatedCallsLog error handler was never set)
*/
const ITOP_PHPUNIT_RUNNING_CONSTANT_NAME = 'ITOP_PHPUNIT_RUNNING';
require_once APPROOT.'bootstrap.inc.php';

View File

@@ -44,11 +44,8 @@ define('ITOP_DEFAULT_ENV', 'production');
define('MAINTENANCE_MODE_FILE', APPROOT.'data/.maintenance');
define('READONLY_MODE_FILE', APPROOT.'data/.readonly');
if (function_exists('microtime')) {
$fItopStarted = microtime(true);
} else {
$fItopStarted = 1000 * time();
}
$fItopStarted = microtime(true);
$iItopInitialMemory = memory_get_usage(true);
if (!isset($GLOBALS['bBypassAutoload']) || $GLOBALS['bBypassAutoload'] == false) {
require_once APPROOT.'/lib/autoload.php';
@@ -71,7 +68,7 @@ if (file_exists(MAINTENANCE_MODE_FILE) && !$bBypassMaintenance)
http_response_code(503);
// Display message depending on the request
include(APPROOT.'application/maintenancemsg.php');
$sSAPIName = strtoupper(trim(php_sapi_name()));
$sSAPIName = strtoupper(trim(PHP_SAPI));
switch (true)
{

View File

@@ -1,8 +1,10 @@
{
"name": "combodo/itop",
"description": "IT Operations Portal",
"type": "project",
"license": "AGPLv3",
"license": "AGPL-3.0-only",
"require": {
"php": ">=7.1.3",
"php": ">=7.1.3 <8.1.0",
"ext-ctype": "*",
"ext-dom": "*",
"ext-gd": "*",
@@ -10,22 +12,29 @@
"ext-json": "*",
"ext-mysqli": "*",
"ext-soap": "*",
"combodo/tcpdf": "6.3.5",
"nikic/php-parser": "^3.1",
"pear/archive_tar": "1.4.13",
"pelago/emogrifier": "2.1.0",
"scssphp/scssphp": "1.0.6",
"swiftmailer/swiftmailer": "5.4.12",
"symfony/console": "3.4.*",
"symfony/dotenv": "3.4.*",
"symfony/framework-bundle": "3.4.*",
"symfony/polyfill-php70": "1.*",
"symfony/twig-bundle": "3.4.*",
"symfony/yaml": "3.4.*"
"combodo/tcpdf": "~6.4.4",
"firebase/php-jwt": "~6.4.0",
"guzzlehttp/guzzle": "^6.5.8",
"guzzlehttp/psr7": "~1.9.1",
"laminas/laminas-mail": "^2.11",
"laminas/laminas-servicemanager": "^3.5",
"league/oauth2-google": "^3.0",
"nikic/php-parser": "~4.13.2",
"pear/archive_tar": "~1.4.14",
"pelago/emogrifier": "~3.1.0",
"scssphp/scssphp": "^1.10.3",
"swiftmailer/swiftmailer": "~6.3.0",
"symfony/console": "~3.4.47",
"symfony/dotenv": "~3.4.47",
"symfony/framework-bundle": "~3.4.47",
"symfony/twig-bundle": "~3.4.47",
"symfony/yaml": "~3.4.47",
"thenetworg/oauth2-azure": "^2.0",
"twig/twig": "~1.43.1"
},
"require-dev": {
"symfony/stopwatch": "3.4.*",
"symfony/web-profiler-bundle": "3.4.*"
"symfony/stopwatch": "~3.4.47",
"symfony/web-profiler-bundle": "~3.4.47"
},
"suggest": {
"ext-libsodium": "Required to use the AttributeEncryptedString.",
@@ -37,32 +46,23 @@
},
"config": {
"platform": {
"php": "7.2.0"
"php": "7.1.3"
},
"vendor-dir": "lib",
"preferred-install": {
"*": "dist"
},
"sort-packages": true,
"classmap-authoritative": true
"classmap-authoritative": true,
"platform-check": true
},
"autoload": {
"classmap": [
"core",
"application",
"sources/application",
"sources/Composer",
"sources/Controller",
"sources/Form",
"sources/Renderer"
"sources"
],
"exclude-from-classmap": [
"core/dbobjectsearch.class.php",
"core/legacy/dbobjectsearchlegacy.class.php",
"core/querybuildercontext.class.inc.php",
"core/legacy/querybuildercontextlegacy.class.inc.php",
"core/querybuilderexpressions.class.inc.php",
"core/legacy/querybuilderexpressionslegacy.class.inc.php",
"core/oql/build/PHP/",
"core/apc-emulation.php",
"application/startup.inc.php",

2842
composer.lock generated

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,74 @@
<?php
/*
* @copyright Copyright (C) 2010-2021 Combodo SARL
* @license http://opensource.org/licenses/AGPL-3.0
*/
namespace Combodo\iTop\Core;
use mysqli;
/**
* mysqli object is really hard to mock as it contains lots of attributes & methods ! Thought we need to mock it to test transactions !
*
* To solve this, a new attribute exists and is only used in specific use cases, so there are just few things to mock.
*
* This object adds more readability than previous model with 2 attributes in {@see CMDBSource}.
*
* @used-by \CMDBSource
*
* @since 3.0.0 N°4325 Object creation
* This wrapper handles the 2 {@mysqli myqsli} attributes that were previously in {@see CMDBSource}
* To allow testing we added a second mysqli object (N°3513 in 2.7.5) and code became a bit confusing :/
* With this wrapper everything is in the same place, and we can express the intention more clearly !
*/
class DbConnectionWrapper
{
/** @var mysqli */
protected static $oDbCnxStandard;
/**
* Can contain a genuine mysqli object, or a mock that would emulate {@see mysqli::query()}
*
* @var mysqli
* @used-by \Combodo\iTop\Test\UnitTest\Core\TransactionsTest
*/
protected static $oDbCnxMockableForQuery;
/**
* @param bool $bIsForQuery set to true if using {@see mysqli::query()}
*
* @return \mysqli|null
*/
public static function GetDbConnection(bool $bIsForQuery = false): ?mysqli
{
if ($bIsForQuery) {
return static::$oDbCnxMockableForQuery;
}
return static::$oDbCnxStandard;
}
public static function SetDbConnection(?mysqli $oMysqli): void
{
static::$oDbCnxStandard = $oMysqli;
static::SetDbConnectionMockForQuery($oMysqli);
}
/**
* Use this to register a mock that will handle {@see mysqli::query()}
*
* @param \mysqli|null $oMysqli
* @since 3.0.4 3.1.1 3.2.0 Param $oMysqli becomes nullable
*/
public static function SetDbConnectionMockForQuery(?mysqli $oMysqli = null): void
{
if (is_null($oMysqli)) {
// Reset to standard connection
static::$oDbCnxMockableForQuery = static::$oDbCnxStandard;
}
else {
static::$oDbCnxMockableForQuery = $oMysqli;
}
}
}

View File

@@ -66,9 +66,8 @@ class MyHelpers
// getmicrotime()
// format sss.mmmuuupppnnn
public static function getmicrotime()
{
list($usec, $sec) = explode(" ",microtime());
return ((float)$usec + (float)$sec);
{
return microtime(true);
}
/*
@@ -420,6 +419,7 @@ class MyHelpers
//}
return $sOutput;
}
}
/**
@@ -524,5 +524,3 @@ class Str
return (strtolower($sString) == $sString);
}
}
?>

View File

@@ -51,6 +51,7 @@ abstract class Action extends cmdbAbstractObject
"db_table" => "priv_action",
"db_key_field" => "id",
"db_finalclass_field" => "realclass",
'style' => new ormStyle(null, null, null, null, null, '../images/icons/icons8-in-transit.svg'),
);
MetaModel::Init_Params($aParams);
//MetaModel::Init_InheritAttributes();
@@ -117,6 +118,39 @@ abstract class Action extends cmdbAbstractObject
return false;
}
}
/**
* @inheritDoc
* @since 3.0.0
*/
public function AfterInsert()
{
parent::AfterInsert();
$this->DoCheckIfHasTrigger();
}
/**
* @inheritDoc
* @since 3.0.0
*/
public function AfterUpdate()
{
parent::AfterUpdate();
$this->DoCheckIfHasTrigger();
}
/**
* Check if the Action has at least 1 trigger linked. Otherwise, it adds a warning.
* @return void
* @since 3.0.0
*/
protected function DoCheckIfHasTrigger()
{
$oTriggersSet = $this->Get('trigger_list');
if ($oTriggersSet->Count() === 0) {
$this->m_aCheckWarnings[] = Dict::S('Action:WarningNoTriggerLinked');
}
}
}
/**
@@ -166,6 +200,17 @@ abstract class ActionNotification extends Action
*/
class ActionEmail extends ActionNotification
{
/**
* @var string
* @since 3.0.1
*/
const ENUM_HEADER_NAME_MESSAGE_ID = 'Message-ID';
/**
* @var string
* @since 3.0.1
*/
const ENUM_HEADER_NAME_REFERENCES = 'References';
/**
* @inheritDoc
*/
@@ -173,13 +218,13 @@ class ActionEmail extends ActionNotification
{
$aParams = array
(
"category" => "grant_by_profile,core/cmdb,application",
"key_type" => "autoincrement",
"name_attcode" => "name",
"state_attcode" => "",
"reconc_keys" => array('name'),
"db_table" => "priv_action_email",
"db_key_field" => "id",
"category" => "grant_by_profile,core/cmdb,application",
"key_type" => "autoincrement",
"name_attcode" => "name",
"state_attcode" => "",
"reconc_keys" => array('name'),
"db_table" => "priv_action_email",
"db_key_field" => "id",
"db_finalclass_field" => "",
);
MetaModel::Init_Params($aParams);
@@ -232,7 +277,7 @@ class ActionEmail extends ActionNotification
protected function FindRecipients($sRecipAttCode, $aArgs)
{
$sOQL = $this->Get($sRecipAttCode);
if (strlen($sOQL) == '') return '';
if (strlen($sOQL) === 0) return '';
try
{
@@ -366,8 +411,7 @@ class ActionEmail extends ActionNotification
{
$this->m_iRecipients = 0;
$this->m_aMailErrors = array();
$bRes = false; // until we do succeed in sending the email
// Determine recipients
//
$sTo = $this->FindRecipients('to', $aContextArgs);
@@ -381,37 +425,48 @@ class ActionEmail extends ActionNotification
$sSubject = MetaModel::ApplyParams($this->Get('subject'), $aContextArgs);
$sBody = MetaModel::ApplyParams($this->Get('body'), $aContextArgs);
$oObj = $aContextArgs['this->object()'];
$sMessageId = sprintf('iTop_%s_%d_%f@%s.openitop.org', get_class($oObj), $oObj->GetKey(), microtime(true /* get as float*/), MetaModel::GetEnvironmentId());
$sReference = '<'.$sMessageId.'>';
$sMessageId = $this->GenerateIdentifierForHeaders($oObj, static::ENUM_HEADER_NAME_MESSAGE_ID);
$sReference = $this->GenerateIdentifierForHeaders($oObj, static::ENUM_HEADER_NAME_REFERENCES);
}
catch(Exception $e)
{
ApplicationContext::SetUrlMakerClass($sPreviousUrlMaker);
throw $e;
}
ApplicationContext::SetUrlMakerClass($sPreviousUrlMaker);
if (!is_null($oLog))
{
catch (Exception $e) {
/** @noinspection PhpUnhandledExceptionInspection */
throw $e;
}
finally {
ApplicationContext::SetUrlMakerClass($sPreviousUrlMaker);
}
if (!is_null($oLog)) {
// Note: we have to secure this because those values are calculated
// inside the try statement, and we would like to keep track of as
// many data as we could while some variables may still be undefined
if (isset($sTo)) $oLog->Set('to', $sTo);
if (isset($sCC)) $oLog->Set('cc', $sCC);
if (isset($sBCC)) $oLog->Set('bcc', $sBCC);
if (isset($sFrom)) $oLog->Set('from', empty($sFromLabel) ? $sFrom : "$sFromLabel <$sFrom>");
if (isset($sSubject)) $oLog->Set('subject', $sSubject);
if (isset($sBody)) $oLog->Set('body', $sBody);
if (isset($sTo)) {
$oLog->Set('to', $sTo);
}
if (isset($sCC)) {
$oLog->Set('cc', $sCC);
}
if (isset($sBCC)) {
$oLog->Set('bcc', $sBCC);
}
if (isset($sFrom)) {
$oLog->Set('from', $sFrom);
}
if (isset($sSubject)) {
$oLog->Set('subject', $sSubject);
}
if (isset($sBody)) {
$oLog->Set('body', $sBody);
}
}
$sStyles = file_get_contents(APPROOT.'css/email.css');
$sStyles .= MetaModel::GetConfig()->Get('email_css');
$oEmail = new EMail();
if ($this->IsBeingTested())
{
if ($this->IsBeingTested()) {
$oEmail->SetSubject('TEST['.$sSubject.']');
$sTestBody = $sBody;
$sTestBody .= "<div style=\"border: dashed;\">\n";
@@ -421,8 +476,8 @@ class ActionEmail extends ActionNotification
$sTestBody .= "<li>TO: $sTo</li>\n";
$sTestBody .= "<li>CC: $sCC</li>\n";
$sTestBody .= "<li>BCC: $sBCC</li>\n";
$sTestBody .= empty($sFromLabel) ? "<li>From: $sFrom</li>\n": "<li>From: $sFromLabel &lt;$sFrom&gt;</li>\n";
$sTestBody .= empty($sReplyToLabel) ? "<li>Reply-To: $sReplyTo</li>\n": "<li>Reply-To: $sReplyToLabel &lt;$sReplyTo&gt;</li>\n";
$sTestBody .= empty($sFromLabel) ? "<li>From: $sFrom</li>\n" : "<li>From: $sFromLabel &lt;$sFrom&gt;</li>\n";
$sTestBody .= empty($sReplyToLabel) ? "<li>Reply-To: $sReplyTo</li>\n" : "<li>Reply-To: $sReplyToLabel &lt;$sReplyTo&gt;</li>\n";
$sTestBody .= "<li>References: $sReference</li>\n";
$sTestBody .= "</ul>\n";
$sTestBody .= "</p>\n";
@@ -432,9 +487,9 @@ class ActionEmail extends ActionNotification
$oEmail->SetRecipientFrom($sFrom, $sFromLabel);
$oEmail->SetReferences($sReference);
$oEmail->SetMessageId($sMessageId);
}
else
{
// Note: N°4849 We pass the "References" identifier instead of the "Message-ID" on purpose as we want notifications emails to group around the triggering iTop object, not just the users' replies to the notification
$oEmail->SetInReplyTo($sReference);
} else {
$oEmail->SetSubject($sSubject);
$oEmail->SetBody($sBody, 'text/html', $sStyles);
$oEmail->SetRecipientTO($sTo);
@@ -444,6 +499,8 @@ class ActionEmail extends ActionNotification
$oEmail->SetRecipientReplyTo($sReplyTo, $sReplyToLabel);
$oEmail->SetReferences($sReference);
$oEmail->SetMessageId($sMessageId);
// Note: N°4849 We pass the "References" identifier instead of the "Message-ID" on purpose as we want notifications emails to group around the triggering iTop object, not just the users' replies to the notification
$oEmail->SetInReplyTo($sReference);
}
if (isset($aContextArgs['attachments']))
@@ -470,26 +527,64 @@ class ActionEmail extends ActionNotification
{
case EMAIL_SEND_OK:
return "Sent";
case EMAIL_SEND_PENDING:
return "Pending";
case EMAIL_SEND_ERROR:
return "Errors: ".implode(', ', $aErrors);
}
}
}
else
{
if (is_array($this->m_aMailErrors) && count($this->m_aMailErrors) > 0)
{
} else {
if (is_array($this->m_aMailErrors) && count($this->m_aMailErrors) > 0) {
$sError = implode(', ', $this->m_aMailErrors);
}
else
{
} else {
$sError = 'Unknown reason';
}
return 'Notification was not sent: '.$sError;
}
}
/**
* @param \DBObject $oObject
* @param string $sHeaderName {@see \ActionEmail::ENUM_HEADER_NAME_REFERENCES}, {@see \ActionEmail::ENUM_HEADER_NAME_MESSAGE_ID}
*
* @return string The formatted identifier for $sHeaderName based on $oObject
* @throws \Exception
* @since 3.0.1 N°4849
*/
protected function GenerateIdentifierForHeaders(DBObject $oObject, string $sHeaderName): string
{
$sObjClass = get_class($oObject);
$sObjId = $oObject->GetKey();
$sAppName = utils::Sanitize(ITOP_APPLICATION_SHORT, '', utils::ENUM_SANITIZATION_FILTER_VARIABLE_NAME);
switch ($sHeaderName) {
case static::ENUM_HEADER_NAME_MESSAGE_ID:
case static::ENUM_HEADER_NAME_REFERENCES:
// Prefix
$sPrefix = sprintf('%s_%s_%d', $sAppName, $sObjClass, $sObjId);
if ($sHeaderName === static::ENUM_HEADER_NAME_MESSAGE_ID) {
$sPrefix .= sprintf('_%F', microtime(true /* get as float*/));
}
// Suffix
$sSuffix = sprintf('@%s.openitop.org', MetaModel::GetEnvironmentId());
// Identifier
$sIdentifier = $sPrefix.$sSuffix;
if ($sHeaderName === static::ENUM_HEADER_NAME_REFERENCES) {
$sIdentifier = "<$sIdentifier>";
}
return $sIdentifier;
}
// Requested header name invalid
$sErrorMessage = sprintf('%s: Could not generate identifier for header "%s", only %s are supported', static::class, $sHeaderName, implode(' / ', [static::ENUM_HEADER_NAME_MESSAGE_ID, static::ENUM_HEADER_NAME_REFERENCES]));
IssueLog::Error($sErrorMessage, LogChannels::NOTIFICATIONS, [
'Object' => $sObjClass.'::'.$sObjId.' ('.$oObject->GetRawName().')',
'Action' => get_class($this).'::'.$this->GetKey().' ('.$this->GetRawName().')',
]);
throw new Exception($sErrorMessage);
}
}

View File

@@ -110,7 +110,7 @@ class apcFile
*/
static public function GetCacheFileName($sKey = '')
{
$sPath = str_replace(array(' ', '/', '\\', '.'), '-', $sKey);
$sPath = str_replace(array(' ', '/', '\\', '.'), '-', $sKey ?? '');
return utils::GetCachePath().'apc-emul/'.$sPath;
}

View File

@@ -0,0 +1,42 @@
<?php
/**
* Class ApcService
* @since 2.7.6 N°4125
*/
class ApcService {
public function __construct() {
}
/**
* @param string $function_name
* @return bool
* @see function_exists()
*/
public function function_exists($function_name) {
return function_exists($function_name);
}
/**
* @param string|array $key
* @return mixed
* @see apc_fetch()
*/
function apc_fetch($key)
{
return apc_fetch($key);
}
/**
* @param array|string $key
* @param $var
* @param int $ttl
* @return array|bool
* @see apc_store()
*/
function apc_store($key, $var = NULL, $ttl = 0)
{
return apc_store($key, $var, $ttl);
}
}
?>

View File

@@ -157,7 +157,7 @@ abstract class AsyncTask extends DBObject
if (is_array($aRetries) && array_key_exists(get_class($this), $aRetries))
{
$aConfig = $aRetries[get_class($this)];
$iRetryDelay = $aConfig['retry_delay'];
$iRetryDelay = $aConfig['retry_delay'] ?? $iRetryDelay;
}
return $iRetryDelay;
}
@@ -169,11 +169,71 @@ abstract class AsyncTask extends DBObject
if (is_array($aRetries) && array_key_exists(get_class($this), $aRetries))
{
$aConfig = $aRetries[get_class($this)];
$iMaxRetries = $aConfig['max_retries'];
$iMaxRetries = $aConfig['max_retries'] ?? $iMaxRetries;
}
return $iMaxRetries;
}
public function IsRetryDelayExponential()
{
$bExponential = false;
$aRetries = MetaModel::GetConfig()->Get('async_task_retries');
if (is_array($aRetries) && array_key_exists(get_class($this), $aRetries))
{
$aConfig = $aRetries[get_class($this)];
$bExponential = (bool) ($aConfig['exponential_delay'] ?? $bExponential);
}
return $bExponential;
}
public static function CheckRetryConfig(Config $oConfig, $sAsyncTaskClass)
{
$aMessages = [];
$aRetries = $oConfig->Get('async_task_retries');
if (is_array($aRetries) && array_key_exists($sAsyncTaskClass, $aRetries))
{
$aValidKeys = array("retry_delay", "max_retries", "exponential_delay");
$aConfig = $aRetries[$sAsyncTaskClass];
if (!is_array($aConfig))
{
$aMessages[] = Dict::Format('Class:AsyncTask:InvalidConfig_Class_Keys', $sAsyncTaskClass, implode(', ', $aValidKeys));
}
else
{
foreach($aConfig as $key => $value)
{
if (!in_array($key, $aValidKeys))
{
$aMessages[] = Dict::Format('Class:AsyncTask:InvalidConfig_Class_InvalidKey_Keys', $sAsyncTaskClass, $key, implode(', ', $aValidKeys));
}
}
}
}
return $aMessages;
}
/**
* Compute the delay to wait for the "next retry", based on the given parameters
* @param bool $bIsExponential
* @param int $iRetryDelay
* @param int $iMaxRetries
* @param int $iRemainingRetries
* @return int
*/
public static function GetNextRetryDelay($bIsExponential, $iRetryDelay, $iMaxRetries, $iRemainingRetries)
{
if ($bIsExponential)
{
$iExponent = $iMaxRetries - $iRemainingRetries;
if ($iExponent < 0) $iExponent = 0; // Safety net in case on configuration change in the middle of retries
return $iRetryDelay * (2 ** $iExponent);
}
else
{
return $iRetryDelay;
}
}
/**
* Override to notify people that a task cannot be performed
*/
@@ -233,7 +293,7 @@ abstract class AsyncTask extends DBObject
$this->Set('remaining_retries', $this->GetMaxRetries($iErrorCode));
}
$this->Set('last_error', $sErrorMessage);
$this->SetTrim('last_error', $sErrorMessage);
$this->Set('last_error_code', $iErrorCode); // Note: can be ZERO !!!
$this->Set('last_attempt', time());
@@ -241,25 +301,26 @@ abstract class AsyncTask extends DBObject
if ($iRemaining > 0)
{
$iRetryDelay = $this->GetRetryDelay($iErrorCode);
IssueLog::Info('Failed to process async task #'.$this->GetKey().' - reason: '.$sErrorMessage.' - remaining retries: '.$iRemaining.' - next retry in '.$iRetryDelay.'s');
$iNextRetryDelay = static::GetNextRetryDelay($this->IsRetryDelayExponential(), $iRetryDelay, $this->GetMaxRetries($iErrorCode), $iRemaining);
IssueLog::Info('Failed to process async task #'.$this->GetKey().' - reason: '.$sErrorMessage.' - remaining retries: '.$iRemaining.' - next retry in '.$iNextRetryDelay.'s');
if ($this->Get('event_id') != 0)
{
$oEventLog = MetaModel::GetObject('Event', $this->Get('event_id'));
$oEventLog->Set('message', "$sErrorMessage\nFailed to process async task. Remaining retries: '.$iRemaining.'. Next retry in '.$iRetryDelay.'s'");
$oEventLog->Set('message', "$sErrorMessage\nFailed to process async task. Remaining retries: $iRemaining. Next retry in {$iNextRetryDelay}s");
try
{
$oEventLog->DBUpdate();
}
catch (Exception $e)
{
$oEventLog->Set('message', "Failed to process async task. Remaining retries: '.$iRemaining.'. Next retry in '.$iRetryDelay.'s', more details in the log");
$oEventLog->Set('message', "Failed to process async task. Remaining retries: $iRemaining. Next retry in {$iNextRetryDelay}s, more details in the log");
$oEventLog->DBUpdate();
}
}
$this->Set('remaining_retries', $iRemaining - 1);
$this->Set('status', 'planned');
$this->Set('started', null);
$this->Set('planned', time() + $iRetryDelay);
$this->Set('planned', time() + $iNextRetryDelay);
}
else
{
@@ -388,7 +449,12 @@ class AsyncSendEmail extends AsyncTask
return "Bug - the email should be sent in synchronous mode";
case EMAIL_SEND_ERROR:
return "Failed: ".implode(', ', $aIssues);
if (is_array($aIssues)) {
$sMessage = "Sending eMail failed: ".implode(', ', $aIssues);
} else {
$sMessage = "Sending eMail failed.";
}
throw new Exception($sMessage);
}
return '';
}

View File

@@ -705,6 +705,18 @@ abstract class AttributeDefinition
return is_null($proposedValue);
}
/**
* @param mixed $proposedValue
*
* @return bool True if $proposedValue is an actual value set in the attribute, false is the attribute remains "empty"
* @since 3.0.3, 3.1.0 N°5784
*/
public function HasAValue($proposedValue): bool
{
// Default implementation, we don't really know what type $proposedValue will be
return is_null($proposedValue);
}
/**
* force an allowed value (type conversion and possibly forces a value as mySQL would do upon writing!
*
@@ -1384,6 +1396,15 @@ class AttributeDashboard extends AttributeDefinition
{
return '';
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
// Always return false for now, we don't consider a custom version of a dashboard
return false;
}
}
/**
@@ -1685,7 +1706,7 @@ class AttributeLinkedSet extends AttributeDefinition
{
if ($sObjClass == $this->GetLinkedClass())
{
// Simplify the output if the exact class could be determined implicitely
// Simplify the output if the exact class could be determined implicitely
continue;
}
}
@@ -1793,7 +1814,7 @@ class AttributeLinkedSet extends AttributeDefinition
public function GetImportColumns()
{
$aColumns = array();
$aColumns[$this->GetCode()] = 'TEXT';
$aColumns[$this->GetCode()] = 'TEXT'.CMDBSource::GetSqlStringColumnDefinition();
return $aColumns;
}
@@ -2007,7 +2028,7 @@ class AttributeLinkedSet extends AttributeDefinition
{
if ($sObjClass == $this->GetLinkedClass())
{
// Simplify the output if the exact class could be determined implicitely
// Simplify the output if the exact class could be determined implicitely
continue;
}
}
@@ -2233,6 +2254,22 @@ class AttributeLinkedSet extends AttributeDefinition
{
return false;
}
/**
* @inheritDoc
* @param \ormLinkSet $proposedValue
*/
public function HasAValue($proposedValue): bool
{
// Protection against wrong value type
if (false === ($proposedValue instanceof ormLinkSet))
{
return parent::HasAValue($proposedValue);
}
// We test if there is at least 1 item in the linkset (new or existing), not if an item is being added to it.
return $proposedValue->Count() > 0;
}
}
/**
@@ -2412,7 +2449,7 @@ class AttributeDBFieldVoid extends AttributeDefinition
return false;
}
//
//
protected function ScalarToSQL($value)
{
return $value;
@@ -2614,6 +2651,14 @@ class AttributeInteger extends AttributeDBField
return is_null($proposedValue);
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
return utils::IsNotNullOrEmptyString($proposedValue);
}
public function MakeRealValue($proposedValue, $oHostObj)
{
if (is_null($proposedValue))
@@ -2713,6 +2758,19 @@ class AttributeObjectKey extends AttributeDBFieldVoid
return ($proposedValue == 0);
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
return ((int) $proposedValue) !== 0;
}
/**
* @inheritDoc
*
* @param int|DBObject $proposedValue Object key or valid ({@see MetaModel::IsValidObject()}) datamodel object
*/
public function MakeRealValue($proposedValue, $oHostObj)
{
if (is_null($proposedValue))
@@ -2725,7 +2783,6 @@ class AttributeObjectKey extends AttributeDBFieldVoid
}
if (MetaModel::IsValidObject($proposedValue))
{
/** @var \DBObject $proposedValue */
return $proposedValue->GetKey();
}
@@ -2912,6 +2969,14 @@ class AttributeDecimal extends AttributeDBField
return is_null($proposedValue);
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
return utils::IsNotNullOrEmptyString($proposedValue);
}
public function MakeRealValue($proposedValue, $oHostObj)
{
if (is_null($proposedValue))
@@ -3323,6 +3388,14 @@ class AttributeString extends AttributeDBField
return ($proposedValue == '');
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
return utils::IsNotNullOrEmptyString($proposedValue);
}
public function MakeRealValue($proposedValue, $oHostObj)
{
if (is_null($proposedValue))
@@ -4123,7 +4196,8 @@ class AttributeText extends AttributeString
{
// Propose a std link to the object
$sClassLabel = MetaModel::GetName($sClass);
$sReplacement = "<span class=\"wiki_broken_link\">$sClassLabel:$sName" . (!empty($sLabel) ? " ($sLabel)" : "") . "</span>";
$sToolTipForHtml = utils::EscapeHtml(Dict::Format('Core:UnknownObjectLabel', $sClass, $sName));
$sReplacement = "<span class=\"wiki_broken_link ibo-is-broken-hyperlink\" data-tooltip-content=\"$sToolTipForHtml\">$sClassLabel:$sName" . (!empty($sLabel) ? " ($sLabel)" : "") . "</span>";
$sText = str_replace($aMatches[0], $sReplacement, $sText);
// Later: propose a link to create a new object
// Anyhow... there is no easy way to suggest default values based on the given FRIENDLY name
@@ -4158,14 +4232,15 @@ class AttributeText extends AttributeString
{
$sValue = parent::GetAsHTML($sValue, $oHostObject, $bLocalize);
$sValue = self::RenderWikiHtml($sValue);
$sValue = nl2br($sValue);
return "<div $sStyle>".str_replace("\n", "<br>\n", $sValue).'</div>';
return "<div $sStyle>$sValue</div>";
}
else
{
$sValue = self::RenderWikiHtml($sValue, true /* wiki only */);
return "<div class=\"HTML\" $sStyle>".InlineImage::FixUrls($sValue).'</div>';
return "<div class=\"HTML ibo-is-html-content\" $sStyle>".InlineImage::FixUrls($sValue).'</div>';
}
}
@@ -4476,6 +4551,22 @@ class AttributeCaseLog extends AttributeLongText
return ($proposedValue->GetText() == '');
}
/**
* @inheritDoc
* @param \ormCaseLog $proposedValue
*/
public function HasAValue($proposedValue): bool
{
// Protection against wrong value type
if (false === ($proposedValue instanceof ormCaseLog)) {
return parent::HasAValue($proposedValue);
}
// We test if there is at least 1 entry in the log, not if the user is adding one
return $proposedValue->GetEntryCount() > 0;
}
public function ScalarToSQL($value)
{
if (!is_string($value) && !is_null($value))
@@ -4585,7 +4676,13 @@ class AttributeCaseLog extends AttributeLongText
{
if (strlen($proposedValue) > 0)
{
$oCaseLog->AddLogEntry($proposedValue);
//N°5135 - add impersonation information in caselog
if (UserRights::IsImpersonated()){
$sOnBehalfOf = Dict::Format('UI:Archive_User_OnBehalfOf_User', UserRights::GetRealUserFriendlyName(), UserRights::GetUserFriendlyName());
$oCaseLog->AddLogEntry($proposedValue, $sOnBehalfOf, UserRights::GetConnectedUserId());
} else {
$oCaseLog->AddLogEntry($proposedValue);
}
}
}
$ret = $oCaseLog;
@@ -5392,7 +5489,7 @@ class AttributeEnum extends AttributeString
{
if (is_null($sValue))
{
// Unless a specific label is defined for the null value of this enum, use a generic "undefined" label
// Unless a specific label is defined for the null value of this enum, use a generic "undefined" label
$sLabel = Dict::S('Class:'.$this->GetHostClass().'/Attribute:'.$this->GetCode().'/Value:'.$sValue,
Dict::S('Enum:Undefined'));
}
@@ -5414,7 +5511,7 @@ class AttributeEnum extends AttributeString
{
if (is_null($sValue))
{
// Unless a specific label is defined for the null value of this enum, use a generic "undefined" label
// Unless a specific label is defined for the null value of this enum, use a generic "undefined" label
$sDescription = Dict::S('Class:'.$this->GetHostClass().'/Attribute:'.$this->GetCode().'/Value:'.$sValue.'+',
Dict::S('Enum:Undefined'));
}
@@ -5715,7 +5812,7 @@ class AttributeMetaEnum extends AttributeEnum
$aLocalizedValues = array();
foreach($aRawValues as $sKey => $sValue)
{
$aLocalizedValues[$sKey] = Str::pure2html($this->GetValueLabel($sKey));
$aLocalizedValues[$sKey] = $this->GetValueLabel($sKey);
}
return $aLocalizedValues;
@@ -5993,7 +6090,7 @@ class AttributeDateTime extends AttributeDBField
{
// Allow an empty string to be a valid value (synonym for "reset")
$aColumns = array();
$aColumns[$this->GetCode()] = 'VARCHAR(19)';
$aColumns[$this->GetCode()] = 'VARCHAR(19)'.CMDBSource::GetSqlStringColumnDefinition();
return $aColumns;
}
@@ -6074,6 +6171,11 @@ class AttributeDateTime extends AttributeDBField
}
}
/**
* @inheritDoc
*
* @param int|string $proposedValue timestamp ({@see DateTime::getTimestamp()) or date as string, following the {@see GetInternalFormat} format.
*/
public function MakeRealValue($proposedValue, $oHostObj)
{
if (is_null($proposedValue))
@@ -6481,7 +6583,7 @@ class AttributeDate extends AttributeDateTime
{
// Allow an empty string to be a valid value (synonym for "reset")
$aColumns = array();
$aColumns[$this->GetCode()] = 'VARCHAR(10)';
$aColumns[$this->GetCode()] = 'VARCHAR(10)'.CMDBSource::GetSqlStringColumnDefinition();
return $aColumns;
}
@@ -6790,6 +6892,14 @@ class AttributeExternalKey extends AttributeDBFieldVoid
return ($proposedValue == 0);
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
return ((int) $proposedValue) !== 0;
}
public function MakeRealValue($proposedValue, $oHostObj)
{
if (is_null($proposedValue))
@@ -7211,7 +7321,7 @@ class AttributeExternalField extends AttributeDefinition
protected function GetSQLCol($bFullSpec = false)
{
// throw new CoreException("external attribute: does it make any sense to request its type ?");
// throw new CoreException("external attribute: does it make any sense to request its type ?");
$oExtAttDef = $this->GetExtAttDef();
return $oExtAttDef->GetSQLCol($bFullSpec);
@@ -7522,6 +7632,16 @@ class AttributeExternalField extends AttributeDefinition
return $oExtAttDef->IsNull($proposedValue);
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
$oExtAttDef = $this->GetExtAttDef();
return $oExtAttDef->HasAValue($proposedValue);
}
public function MakeRealValue($proposedValue, $oHostObj)
{
$oExtAttDef = $this->GetExtAttDef();
@@ -7656,6 +7776,17 @@ class AttributeExternalField extends AttributeDefinition
*/
class AttributeURL extends AttributeString
{
/**
* @var string
* SCHEME....... USER....................... PASSWORD.......................... HOST/IP........... PORT.......... PATH......................... GET............................................ ANCHOR..........................
* Example: http://User:passWord@127.0.0.1:8888/patH/Page.php?arrayArgument[2]=something:blah20#myAnchor
* @link http://www.php.net/manual/fr/function.preg-match.php#93824 regexp source
* @since 3.0.1 N°4515 handle Alfresco and Sharepoint URLs
* @since 3.0.3 moved from Config to AttributeURL constant
*/
public const DEFAULT_VALIDATION_PATTERN = /** @lang RegExp */
'(https?|ftp)\://([a-zA-Z0-9+!*(),;?&=\$_.-]+(\:[a-zA-Z0-9+!*(),;?&=\$_.-]+)?@)?([a-zA-Z0-9-.]{3,})(\:[0-9]{2,5})?(/([a-zA-Z0-9:%+\$_-]\.?)+)*/?(\?[a-zA-Z+&\$_.-][a-zA-Z0-9;:[\]@&%=+/\$_.,-]*)?(#[a-zA-Z0-9_.-][a-zA-Z0-9+\$_.-]*)?';
/**
* Useless constructor, but if not present PHP 7.4.0/7.4.1 is crashing :( (N°2329)
*
@@ -7812,9 +7943,9 @@ class AttributeBlob extends AttributeDefinition
}
/**
* Users can provide the document from an URL (including an URL on iTop itself)
* for CSV import. Administrators can even provide the path to a local file
* {@inheritDoc}
* {@inheritDoc}
*
* @param string $proposedValue Can be an URL (including an URL to iTop itself), or a local path (CSV import)
*
* @see AttributeDefinition::MakeRealValue()
*/
@@ -8097,6 +8228,20 @@ class AttributeBlob extends AttributeDefinition
return $oFormField;
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
if (false === ($proposedValue instanceof ormDocument)) {
return parent::HasAValue($proposedValue);
}
// Empty file (no content, just a filename) are supported since PR {@link https://github.com/Combodo/combodo-email-synchro/pull/17}, so we check for both empty content and empty filename to determine that a document has no value
return utils::IsNotNullOrEmptyString($proposedValue->GetData()) && utils::IsNotNullOrEmptyString($proposedValue->GetFileName());
}
}
/**
@@ -8128,6 +8273,25 @@ class AttributeImage extends AttributeBlob
return "Image";
}
/**
* {@inheritDoc}
* @see AttributeBlob::MakeRealValue()
*/
public function MakeRealValue($proposedValue, $oHostObj)
{
$oDoc = parent::MakeRealValue($proposedValue, $oHostObj);
if (($oDoc instanceof ormDocument)
&& (false === $oDoc->IsEmpty())
&& ($oDoc->GetMimeType() === 'image/svg+xml')) {
$sCleanSvg = HTMLSanitizer::Sanitize($oDoc->GetData(), 'svg_sanitizer');
$oDoc = new ormDocument($sCleanSvg, $oDoc->GetMimeType(), $oDoc->GetFileName());
}
// The validation of the MIME Type is done by CheckFormat below
return $oDoc;
}
/**
* Check that the supplied ormDocument actually contains an image
* {@inheritDoc}
@@ -8158,24 +8322,27 @@ class AttributeImage extends AttributeBlob
$sRet = '';
$bIsCustomImage = false;
$iMaxWidthPx = $this->Get('display_max_width').'px';
$iMaxHeightPx = $this->Get('display_max_height').'px';
$iMaxWidth = $this->Get('display_max_width');
$sMaxWidthPx = $iMaxWidth.'px';
$iMaxHeight = $this->Get('display_max_height');
$sMaxHeightPx = $iMaxHeight.'px';
$sDefaultImageUrl = $this->Get('default_image');
if ($sDefaultImageUrl !== null) {
$sRet = $this->GetHtmlForImageUrl($sDefaultImageUrl, $iMaxWidthPx, $iMaxHeightPx);
$sRet = $this->GetHtmlForImageUrl($sDefaultImageUrl, $sMaxWidthPx, $sMaxHeightPx);
}
$sCustomImageUrl = $this->GetAttributeImageFileUrl($value, $oHostObject);
if ($sCustomImageUrl !== null) {
$bIsCustomImage = true;
$sRet = $this->GetHtmlForImageUrl($sCustomImageUrl, $iMaxWidthPx, $iMaxHeightPx);
$sRet = $this->GetHtmlForImageUrl($sCustomImageUrl, $sMaxWidthPx, $sMaxHeightPx);
}
$sCssClasses = 'ibo-input-image--image-view attribute-image';
$sCssClasses .= ' '.(($bIsCustomImage) ? 'attribute-image-custom' : 'attribute-image-default');
return '<div class="'.$sCssClasses.'" style="width: '.$iMaxWidthPx.'; height: '.$iMaxHeightPx.';">'.$sRet.'</div>';
// Important: If you change this, mind updating edit_image.js as well
return '<div class="'.$sCssClasses.'" style="max-width: '.$sMaxWidthPx.'; max-height: '.$sMaxHeightPx.'; aspect-ratio: '.$iMaxWidth.' / '.$iMaxHeight.'">'.$sRet.'</div>';
}
/**
@@ -9101,6 +9268,17 @@ class AttributeStopWatch extends AttributeDefinition
return $sRet;
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
// A stopwatch always has a value
return true;
}
}
/**
@@ -9238,7 +9416,7 @@ class AttributeSubItem extends AttributeDefinition
return $res;
}
//
//
// protected function ScalarToSQL($value) {return $value;} // format value as a valuable SQL literal (quoted outside)
public function FromSQLToValue($aCols, $sPrefix = '')
@@ -9586,6 +9764,23 @@ class AttributeOneWayPassword extends AttributeDefinition implements iAttributeN
return '*****';
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
// Protection against wrong value type
if (false === ($proposedValue instanceof ormPassword)) {
// On object creation, the attribute value is "" instead of an ormPassword...
if (is_string($proposedValue)) {
return utils::IsNotNullOrEmptyString($proposedValue);
}
return parent::HasAValue($proposedValue);
}
return $proposedValue->IsEmpty() === false;
}
}
// Indexed array having two dimensions
@@ -9635,6 +9830,15 @@ class AttributeTable extends AttributeDBField
return (count($proposedValue) == 0);
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
return count($proposedValue) > 0;
}
public function GetEditValue($sValue, $oHostObj = null)
{
return '';
@@ -10156,6 +10360,18 @@ abstract class AttributeSet extends AttributeDBFieldVoid
return $proposedValue->Count() == 0;
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
if (false === ($proposedValue instanceof ormSet)) {
return parent::HasAValue($proposedValue);
}
return $proposedValue->Count() > 0;
}
/**
* To be overloaded for localized enums
*
@@ -10282,7 +10498,6 @@ abstract class AttributeSet extends AttributeDBFieldVoid
} else {
$sTooltipContent = <<<HTML
<h4>$sLabel</h4>
<br>
<div>$sDescription</div>
HTML;
$sTooltipHtmlEnabled = 'true';
@@ -10829,7 +11044,7 @@ class AttributeClassAttCodeSet extends AttributeSet
}
}
$sLabelForHtmlAttribute = MetaModel::GetLabel($sAttClass, $sAttCode)." ($sAttCode)";
$sLabelForHtmlAttribute = utils::HtmlEntities(MetaModel::GetLabel($sAttClass, $sAttCode)." ($sAttCode)");
$aLocalizedValues[] = '<span class="attribute-set-item" data-code="'.$sAttCode.'" data-label="'.$sLabelForHtmlAttribute.'" data-description="" data-tooltip-content="'.$sLabelForHtmlAttribute.'">'.$sAttCode.'</span>';
} catch (Exception $e)
{
@@ -11022,7 +11237,7 @@ class AttributeQueryAttCodeSet extends AttributeSet
$aLocalizedValues = array();
foreach ($value as $sAttCode) {
if (isset($aAllowedAttributes[$sAttCode])) {
$sLabelForHtmlAttribute = $aAllowedAttributes[$sAttCode];
$sLabelForHtmlAttribute = utils::HtmlEntities($aAllowedAttributes[$sAttCode]);
$aLocalizedValues[] = '<span class="attribute-set-item" data-code="'.$sAttCode.'" data-label="'.$sLabelForHtmlAttribute.'" data-description="" data-tooltip-content="'.$sLabelForHtmlAttribute.'">'.$sAttCode.'</span>';
}
}
@@ -11571,20 +11786,20 @@ class AttributeTagSet extends AttributeSet
$sTooltipContent = $sTagLabel;
$sTooltipHtmlEnabled = 'false';
} else {
$sTagLabelEscaped = utils::EscapeHtml($sTagLabel);
$sTooltipContent = <<<HTML
<h4>$sTagLabel</h4>
<br>
<h4>$sTagLabelEscaped</h4>
<div>$sTagDescription</div>
HTML;
$sTooltipHtmlEnabled = 'true';
}
$sTooltipContent = utils::EscapeHtml($sTooltipContent);
$sTooltipContent = utils::HtmlEntities($sTooltipContent);
$sHtml .= '<a'.$sLink.' class="attribute-set-item attribute-set-item-'.$sTagCode.'" data-code="'.$sTagCode.'" data-label="'.$sLabelForHtml.'" data-description="'.$sDescriptionForHtml.'" data-tooltip-content="'.$sTooltipContent.'" data-tooltip-html-enabled="'.$sTooltipHtmlEnabled.'">'.$sLabelForHtml.'</a>';
}
else
{
$sHtml .= '<span class="attribute-set-item">'.$oTag.'</span>';
$sHtml .= '<span class="attribute-set-item">'.utils::EscapeHtml($oTag).'</span>';
}
}
$sHtml .= '</span>';
@@ -12544,10 +12759,12 @@ class AttributeCustomFields extends AttributeDefinition
*/
public function ReadValueFromPostedForm($oHostObject, $sFormPrefix)
{
$aRawData = json_decode(utils::ReadPostedParam("attr_{$sFormPrefix}{$this->GetCode()}", '{}', 'raw_data'),
true);
return new ormCustomFieldsValue($oHostObject, $this->GetCode(), $aRawData);
$aRawData = json_decode(utils::ReadPostedParam("attr_{$sFormPrefix}{$this->GetCode()}", '{}', 'raw_data'), true);
if ($aRawData != null) {
return new ormCustomFieldsValue($oHostObject, $this->GetCode(), $aRawData);
} else{
return null;
}
}
public function MakeRealValue($proposedValue, $oHostObject)
@@ -12862,6 +13079,21 @@ class AttributeCustomFields extends AttributeDefinition
return $bEquals;
}
/**
* @inheritDoc
*/
public function HasAValue($proposedValue): bool
{
// Protection against wrong value type
if (false === ($proposedValue instanceof ormCustomFieldsValue)) {
return parent::HasAValue($proposedValue);
}
return count($proposedValue->GetValues()) > 0;
}
}
class AttributeArchiveFlag extends AttributeBoolean

View File

@@ -11,7 +11,7 @@ define('UTF8_BOM', chr(239).chr(187).chr(191)); // 0xEF, 0xBB, 0xBF
/**
* CellChangeSpec
* A series of classes, keeping the information about a given cell: could it be changed or not (and why)?
* A series of classes, keeping the information about a given cell: could it be changed or not (and why)?
*
* @package iTopORM
*/
@@ -144,7 +144,7 @@ class CellStatus_Ambiguous extends CellStatus_Issue
/**
* RowStatus
* A series of classes, keeping the information about a given row: could it be changed or not (and why)?
* A series of classes, keeping the information about a given row: could it be changed or not (and why)?
*
* @package iTopORM
*/
@@ -220,7 +220,7 @@ class RowStatus_Issue extends RowStatus
*/
class BulkChange
{
protected $m_sClass;
protected $m_sClass;
protected $m_aData; // Note: hereafter, iCol maybe actually be any acceptable key (string)
// #@# todo: rename the variables to sColIndex
protected $m_aAttList; // attcode => iCol
@@ -261,7 +261,7 @@ class BulkChange
$this->m_sReportCsvSep = $sSeparator;
$this->m_sReportCsvDelimiter = $sDelimiter;
}
protected function ResolveExternalKey($aRowData, $sAttCode, &$aResults)
{
$oExtKey = MetaModel::GetAttributeDef($this->m_sClass, $sAttCode);
@@ -318,7 +318,7 @@ class BulkChange
{
$aResults = array();
$aErrors = array();
// External keys reconciliation
//
foreach($this->m_aExtKeys as $sAttCode => $aKeyConfig)
@@ -408,12 +408,12 @@ class BulkChange
$aErrors[$sAttCode] = Dict::S('UI:CSVReport-Value-Issue-NotFound');
$aResults[$sAttCode]= new CellStatus_SearchIssue();
break;
case 1:
// Do change the external key attribute
$oTargetObj->Set($sAttCode, $iForeignKey);
break;
default:
$aErrors[$sAttCode] = Dict::Format('UI:CSVReport-Value-Issue-FoundMany', $iCount);
$aResults[$sAttCode]= new CellStatus_Ambiguous($oTargetObj->Get($sAttCode), $iCount, $sOQL);
@@ -446,7 +446,7 @@ class BulkChange
}
}
}
// Set the object attributes
//
foreach ($this->m_aAttList as $sAttCode => $iCol)
@@ -467,30 +467,21 @@ class BulkChange
$iFlags = ($oTargetObj->IsNew())
? $oTargetObj->GetInitialStateAttributeFlags($sAttCode, $aReasons)
: $oTargetObj->GetAttributeFlags($sAttCode, $aReasons);
if ( (($iFlags & OPT_ATT_READONLY) == OPT_ATT_READONLY) && ( $oTargetObj->Get($sAttCode) != $aRowData[$iCol]) ) {
if ((($iFlags & OPT_ATT_READONLY) == OPT_ATT_READONLY) && ($oTargetObj->Get($sAttCode) != $oAttDef->MakeValueFromString($aRowData[$iCol], $this->m_bLocalizedValues))) {
$aErrors[$sAttCode] = Dict::Format('UI:CSVReport-Value-Issue-Readonly', $sAttCode, $oTargetObj->Get($sAttCode), $aRowData[$iCol]);
}
else if ($oAttDef->IsLinkSet() && $oAttDef->IsIndirect())
{
try
{
} else if ($oAttDef->IsLinkSet() && $oAttDef->IsIndirect()) {
try {
$oSet = $oAttDef->MakeValueFromString($aRowData[$iCol], $this->m_bLocalizedValues);
$oTargetObj->Set($sAttCode, $oSet);
}
catch(CoreException $e)
{
catch (CoreException $e) {
$aErrors[$sAttCode] = Dict::Format('UI:CSVReport-Value-Issue-Format', $e->getMessage());
}
}
else
{
} else {
$value = $oAttDef->MakeValueFromString($aRowData[$iCol], $this->m_bLocalizedValues);
if (is_null($value) && (strlen($aRowData[$iCol]) > 0))
{
if (is_null($value) && (strlen($aRowData[$iCol]) > 0)) {
$aErrors[$sAttCode] = Dict::Format('UI:CSVReport-Value-Issue-NoMatch', $sAttCode);
}
else
{
} else {
$res = $oTargetObj->CheckValue($sAttCode, $value);
if ($res === true)
{
@@ -504,7 +495,7 @@ class BulkChange
}
}
}
// Reporting on fields
//
$aChangedFields = $oTargetObj->ListChanges();
@@ -556,7 +547,7 @@ class BulkChange
}
}
}
// Checks
//
$res = $oTargetObj->CheckConsistency();
@@ -567,12 +558,12 @@ class BulkChange
}
return $aResults;
}
protected function PrepareMissingObject(&$oTargetObj, &$aErrors)
{
$aResults = array();
$aErrors = array();
// External keys
//
foreach($this->m_aExtKeys as $sAttCode => $aKeyConfig)
@@ -585,7 +576,7 @@ class BulkChange
$aResults[$iCol] = new CellStatus_Void('?');
}
}
// Update attributes
//
foreach($this->m_aOnDisappear as $sAttCode => $value)
@@ -596,7 +587,7 @@ class BulkChange
}
$oTargetObj->Set($sAttCode, $value);
}
// Reporting on fields
//
$aChangedFields = $oTargetObj->ListChanges();
@@ -616,7 +607,7 @@ class BulkChange
$aResults[$iCol]= new CellStatus_Void($oTargetObj->Get($sAttCode));
}
}
// Checks
//
$res = $oTargetObj->CheckConsistency();
@@ -674,14 +665,14 @@ class BulkChange
}
$aResult[$iRow] = $this->PrepareObject($oTargetObj, $aRowData, $aErrors);
if (count($aErrors) > 0)
{
$sErrors = implode(', ', $aErrors);
$aResult[$iRow]["__STATUS__"] = new RowStatus_Issue(Dict::S('UI:CSVReport-Row-Issue-Attribute'));
return $oTargetObj;
}
// Check that any external key will have a value proposed
$aMissingKeys = array();
foreach (MetaModel::GetExternalKeys($this->m_sClass) as $sExtKeyAttCode => $oExtKey)
@@ -689,7 +680,7 @@ class BulkChange
if (!$oExtKey->IsNullAllowed())
{
if (!array_key_exists($sExtKeyAttCode, $this->m_aExtKeys) && !array_key_exists($sExtKeyAttCode, $this->m_aAttList))
{
{
$aMissingKeys[] = $oExtKey->GetLabel();
}
}
@@ -747,12 +738,12 @@ class BulkChange
$aResult[$iRow]["__STATUS__"] = new RowStatus_Issue(Dict::S('UI:CSVReport-Row-Issue-Attribute'));
return;
}
$aChangedFields = $oTargetObj->ListChanges();
if (count($aChangedFields) > 0)
{
$aResult[$iRow]["__STATUS__"] = new RowStatus_Modify(count($aChangedFields));
// Optionaly record the results
//
if ($oChange)
@@ -796,7 +787,7 @@ class BulkChange
$aResult[$iRow]["__STATUS__"] = new RowStatus_Issue(Dict::S('UI:CSVReport-Row-Issue-Attribute'));
return;
}
$aChangedFields = $oTargetObj->ListChanges();
if (count($aChangedFields) > 0)
{
@@ -821,7 +812,7 @@ class BulkChange
$aResult[$iRow]["__STATUS__"] = new RowStatus_Disappeared(0);
}
}
public function Process(CMDBChange $oChange = null)
{
if ($oChange)
@@ -866,7 +857,7 @@ class BulkChange
foreach ($this->m_aAttList as $sAttCode => $iCol)
{
if ($sAttCode == 'id') continue;
$oAttDef = MetaModel::GetAttributeDef($this->m_sClass, $sAttCode);
if ($oAttDef instanceof AttributeDateTime) // AttributeDate is derived from AttributeDateTime
{
@@ -953,22 +944,22 @@ class BulkChange
{
// The value has to be found or verified
list($sQuery, $aMatches) = $this->ResolveExternalKey($aRowData, $sAttCode, $aResult[$iRow]);
if (count($aMatches) == 1)
{
$oRemoteObj = reset($aMatches); // first item
$valuecondition = $oRemoteObj->GetKey();
$aResult[$iRow][$sAttCode] = new CellStatus_Void($oRemoteObj->GetKey());
}
}
elseif (count($aMatches) == 0)
{
$aResult[$iRow][$sAttCode] = new CellStatus_SearchIssue();
}
}
else
{
$aResult[$iRow][$sAttCode] = new CellStatus_Ambiguous(null, count($aMatches), $sQuery);
}
}
}
}
else
{
@@ -990,7 +981,7 @@ class BulkChange
}
else
{
$oReconciliationFilter->AddCondition($sAttCode, $valuecondition, '=');
$oReconciliationFilter->AddCondition($sAttCode, $valuecondition, '=', true);
}
}
if ($bSkipQuery)
@@ -1110,7 +1101,7 @@ class BulkChange
}
}
$oBulkChanges->Seek(0);
$aDetails = array();
while ($oChange = $oBulkChanges->Fetch())
{
@@ -1199,9 +1190,6 @@ EOF
$.get(GetAbsoluteUrlAppRoot()+'pages/ajax.render.php?{$sAppContext}', {operation: 'displayCSVHistory', showall: bShowAll}, function(data)
{
$('#$sAjaxDivId').html(data);
var table = $('#$sAjaxDivId .listResults');
table.tableHover(); // hover tables
table.tablesorter( { widgets: ['myZebra', 'truncatedList']} ); // sortable and zebra tables
}
);
}
@@ -1277,7 +1265,7 @@ EOF
$oOldTarget = MetaModel::GetObject($oAttDef->GetTargetClass(), $oOperation->Get('oldvalue'));
$sOldValue = $oOldTarget->GetHyperlink();
}
$sNewValue = Dict::S('UI:UndefinedObject');
if ($oOperation->Get('newvalue') != 0)
{
@@ -1303,11 +1291,11 @@ EOF
}
else
{
$aAttributes[$sAttCode] = 1;
$aAttributes[$sAttCode] = 1;
}
}
}
$aDetails = array();
foreach($aObjects as $iUId => $aObjData)
{
@@ -1359,6 +1347,6 @@ EOF
$aConfig[$sAttCode] = array('label' => MetaModel::GetLabel($sClass, $sAttCode), 'description' => MetaModel::GetDescription($sClass, $sAttCode));
}
$oPage->table($aConfig, $aDetails);
}
}
}

View File

@@ -149,7 +149,9 @@ abstract class BulkExport
$this->oSearch = null;
$this->iChunkSize = 0;
$this->sFormatCode = null;
$this->aStatusInfo = array();
$this->aStatusInfo = [
'show_obsolete_data' => utils::ShowObsoleteData(),
];
$this->oBulkExportResult = null;
$this->sTmpFile = '';
$this->bLocalizeOutput = false;
@@ -203,15 +205,17 @@ abstract class BulkExport
if ($oInfo && ($oInfo->Get('user_id') == UserRights::GetUserId()))
{
$sFormatCode = $oInfo->Get('format');
$oSearch = DBObjectSearch::unserialize($oInfo->Get('search'));
$aStatusInfo = json_decode($oInfo->Get('status_info'),true);
$oSearch = DBObjectSearch::unserialize($oInfo->Get('search'));
$oSearch->SetShowObsoleteData($aStatusInfo['show_obsolete_data']);
$oBulkExporter = self::FindExporter($sFormatCode, $oSearch);
if ($oBulkExporter)
{
$oBulkExporter->SetFormat($sFormatCode);
$oBulkExporter->SetObjectList($oSearch);
$oBulkExporter->SetChunkSize($oInfo->Get('chunk_size'));
$oBulkExporter->SetStatusInfo(json_decode($oInfo->Get('status_info'), true));
$oBulkExporter->SetStatusInfo($aStatusInfo);
$oBulkExporter->SetLocalizeOutput($oInfo->Get('localize_output'));
@@ -289,6 +293,7 @@ abstract class BulkExport
*/
public function SetObjectList(DBSearch $oSearch)
{
$oSearch->SetShowObsoleteData($this->aStatusInfo['show_obsolete_data']);
$this->oSearch = $oSearch;
}

View File

@@ -1,22 +1,4 @@
<?php
// Copyright (C) 2010-2021 Combodo SARL
//
// This file is part of iTop.
//
// iTop is free software; you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// iTop is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Affero General Public License for more details.
//
// You should have received a copy of the GNU Affero General Public License
// along with iTop. If not, see <http://www.gnu.org/licenses/>
/**
* Persistent class (internal) cmdbChange
*
@@ -24,6 +6,7 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Core\CMDBChange\CMDBChangeOrigin;
/**
* A change as requested/validated at once by user, may groups many atomic changes
@@ -53,7 +36,7 @@ class CMDBChange extends DBObject
MetaModel::Init_AddAttribute(new AttributeDateTime("date", array("allowed_values"=>null, "sql"=>"date", "default_value"=>"", "is_null_allowed"=>false, "depends_on"=>array())));
MetaModel::Init_AddAttribute(new AttributeString("userinfo", array("allowed_values"=>null, "sql"=>"userinfo", "default_value"=>null, "is_null_allowed"=>true, "depends_on"=>array())));
MetaModel::Init_AddAttribute(new AttributeExternalKey("user_id", array("allowed_values"=>null, "sql"=>"user_id", "targetclass"=>"User", "is_null_allowed"=>true, "on_target_delete"=>DEL_MANUAL, "depends_on"=>array())));
MetaModel::Init_AddAttribute(new AttributeEnum("origin", array("allowed_values"=>new ValueSetEnum('interactive,csv-interactive,csv-import.php,webservice-soap,webservice-rest,synchro-data-source,email-processing,custom-extension'), "sql"=>"origin", "default_value"=>"interactive", "is_null_allowed"=>true, "depends_on"=>array())));
MetaModel::Init_AddAttribute(new AttributeEnum("origin", array("allowed_values"=>new ValueSetEnum(implode(',', [CMDBChangeOrigin::INTERACTIVE, CMDBChangeOrigin::CSV_INTERACTIVE, CMDBChangeOrigin::CSV_IMPORT, CMDBChangeOrigin::WEBSERVICE_SOAP, CMDBChangeOrigin::WEBSERVICE_REST, CMDBChangeOrigin::SYNCHRO_DATA_SOURCE, CMDBChangeOrigin::EMAIL_PROCESSING, CMDBChangeOrigin::CUSTOM_EXTENSION])), "sql"=>"origin", "default_value"=>CMDBChangeOrigin::INTERACTIVE, "is_null_allowed"=>true, "depends_on"=>array())));
}
/**

View File

@@ -79,22 +79,30 @@ class CMDBChangeOp extends DBObject implements iCMDBChangeOp
/**
* @inheritDoc
*/
*/
public function GetDescription()
{
return '';
}
/**
* Safety net: in case the change is not given, let's guarantee that it will
* be set to the current ongoing change (or create a new one)
*/
* Safety net:
* * if change isn't persisted yet, use the current change and persist it if needed
* * in case the change is not given, let's guarantee that it will be set to the current ongoing change (or create a new one)
*
* @since 2.7.7 3.0.2 3.1.0 N°3717 do persist the current change if needed
*/
protected function OnInsert()
{
if ($this->Get('change') <= 0)
{
$this->Set('change', CMDBObject::GetCurrentChange());
$iChange = $this->Get('change');
if (($iChange <= 0) || (is_null($iChange))) {
$oChange = CMDBObject::GetCurrentChange();
if ($oChange->IsNew()) {
$oChange->DBWrite();
}
$this->Set('change', $oChange);
}
parent::OnInsert();
}
}
@@ -342,20 +350,30 @@ class CMDBChangeOpSetAttributeURL extends CMDBChangeOpSetAttribute
{
$aParams = array
(
"category" => "core/cmdb",
"key_type" => "",
"name_attcode" => "change",
"state_attcode" => "",
"reconc_keys" => array(),
"db_table" => "priv_changeop_setatt_url",
"db_key_field" => "id",
"category" => "core/cmdb",
"key_type" => "",
"name_attcode" => "change",
"state_attcode" => "",
"reconc_keys" => array(),
"db_table" => "priv_changeop_setatt_url",
"db_key_field" => "id",
"db_finalclass_field" => "",
);
MetaModel::Init_Params($aParams);
MetaModel::Init_InheritAttributes();
MetaModel::Init_AddAttribute(new AttributeURL("oldvalue", array("allowed_values"=>null, "sql"=>"oldvalue", "target" => '_blank', "default_value"=>null, "is_null_allowed"=>true, "depends_on"=>array())));
MetaModel::Init_AddAttribute(new AttributeURL("newvalue", array("allowed_values"=>null, "sql"=>"newvalue", "target" => '_blank', "default_value"=>null, "is_null_allowed"=>true, "depends_on"=>array())));
// N°4910 (oldvalue), N°5423 (newvalue)
// We cannot have validation here, as AttributeUrl validation is field dependant.
// The validation will be done when editing the iTop object, it isn't the history API responsibility
//
// Pattern is retrieved using this order :
// 1. try to get the pattern from the field definition (datamodel)
// 2. from the iTop config
// 3. config parameter default value
// see \AttributeURL::GetValidationPattern
MetaModel::Init_AddAttribute(new AttributeURL("oldvalue", array("allowed_values" => null, "sql" => "oldvalue", "target" => '_blank', "default_value" => null, "is_null_allowed" => true, "depends_on" => array(), "validation_pattern" => '.*')));
MetaModel::Init_AddAttribute(new AttributeURL("newvalue", array("allowed_values" => null, "sql" => "newvalue", "target" => '_blank', "default_value" => null, "is_null_allowed" => true, "depends_on" => array(), "validation_pattern" => '.*')));
// Display lists
MetaModel::Init_SetZListItems('details', array('date', 'userinfo', 'attcode', 'oldvalue', 'newvalue')); // Attributes to be displayed for the complete details
MetaModel::Init_SetZListItems('list', array('date', 'userinfo', 'attcode', 'oldvalue', 'newvalue')); // Attributes to be displayed for a list
@@ -454,7 +472,7 @@ class CMDBChangeOpSetAttributeBlob extends CMDBChangeOpSetAttribute
$sDisplayLabel = Dict::S('UI:OpenDocumentInNewWindow_');
$sDisplayUrl = $oPrevDoc->GetDisplayURL(get_class($this), $this->GetKey(), 'prevdata');
$sDownloadLabel = Dict::Format('UI:DownloadDocument_');
$sDownloadLabel = Dict::S('UI:DownloadDocument_');
$sDownloadUrl = $oPrevDoc->GetDownloadURL(get_class($this), $this->GetKey(), 'prevdata');
$sDocView = <<<HTML
@@ -1077,7 +1095,7 @@ class CMDBChangeOpSetAttributeLinksTune extends CMDBChangeOpSetAttributeLinks
{
$oField = new FieldExpression('objclass', $oSearch->GetClassAlias());
$sListExpr = '('.implode(', ', CMDBSource::Quote($aLinkClasses)).')';
$sOQLCondition = $oField->Render()." IN $sListExpr";
$sOQLCondition = $oField->RenderExpression()." IN $sListExpr";
$oNewCondition = Expression::FromOQL($sOQLCondition);
$oSearch->AddConditionExpression($oNewCondition);
}

View File

@@ -3,7 +3,7 @@
//
// This file is part of iTop.
//
// iTop is free software; you can redistribute it and/or modify
// iTop is free software; you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
@@ -113,6 +113,26 @@ abstract class CMDBObject extends DBObject
self::$m_oCurrChange = $oChange;
}
/**
* @param string $sUserInfo
* @param string $sOrigin
* @param \DateTime $oDate
*
* @throws \CoreException
*
* @since 2.7.7 3.0.2 3.1.0 N°3717 new method to reset current change
*/
public static function SetCurrentChangeFromParams($sUserInfo, $sOrigin = null, $oDate = null)
{
static::SetTrackInfo($sUserInfo);
static::SetTrackOrigin($sOrigin);
static::CreateChange();
if (!is_null($oDate)) {
static::$m_oCurrChange->Set("date", $oDate);
}
}
//
// Todo: simplify the APIs and do not pass the current change as an argument anymore
// SetTrackInfo to be invoked in very few cases (UI.php, CSV import, Data synchro)
@@ -144,6 +164,8 @@ abstract class CMDBObject extends DBObject
* $oMyChange->Set("userinfo", 'this is done by ... for ...');
* $iChangeId = $oMyChange->DBInsert();
*
* **warning** : this will do nothing if current change already exists !
*
* @see SetCurrentChange to specify a CMDBObject instance instead
*
* @param string $sInfo
@@ -161,7 +183,7 @@ abstract class CMDBObject extends DBObject
*
* @param string $sId ID of the user doing the change, null if not done by a user (eg. background task)
*
* @since 3.0.0
* @since 3.0.0 N°2847 following the addition of CMDBChange.user_id
*/
public static function SetTrackUserId($sId)
{
@@ -171,6 +193,8 @@ abstract class CMDBObject extends DBObject
/**
* Provides information about the origin of the change
*
* **warning** : this will do nothing if current change already exists !
*
* @see SetTrackInfo
* @see SetCurrentChange to specify a CMDBObject instance instead
*
@@ -181,19 +205,21 @@ abstract class CMDBObject extends DBObject
{
self::$m_sOrigin = $sOrigin;
}
/**
* Get the additional information (defaulting to user name)
*/
protected static function GetTrackInfo()
*/
public static function GetTrackInfo()
{
if (is_null(self::$m_sInfo))
{
if (is_null(self::$m_sInfo)) {
return CMDBChange::GetCurrentUserName();
}
else
{
return self::$m_sInfo;
} else {
//N°5135 - add impersonation information in activity log/current cmdb change
if (UserRights::IsImpersonated()){
return sprintf("%s (%s)", CMDBChange::GetCurrentUserName(), self::$m_sInfo);
} else {
return self::$m_sInfo;
}
}
}
@@ -206,7 +232,10 @@ abstract class CMDBObject extends DBObject
*/
protected static function GetTrackUserId()
{
if (is_null(self::$m_sUserId))
if (is_null(self::$m_sUserId)
//N°5135 - indicate impersonation inside changelogs
&& (false === UserRights::IsImpersonated())
)
{
return CMDBChange::GetCurrentUserId();
}
@@ -215,10 +244,10 @@ abstract class CMDBObject extends DBObject
return self::$m_sUserId;
}
}
/**
* Get the 'origin' information (defaulting to 'interactive')
*/
*/
protected static function GetTrackOrigin()
{
if (is_null(self::$m_sOrigin))
@@ -243,15 +272,17 @@ abstract class CMDBObject extends DBObject
* @throws \CoreWarning
* @throws \MySQLException
* @throws \OQLException
*
* @since 2.7.7 3.0.2 3.1.0 N°3717 {@see CMDBChange} **will be persisted later** in {@see \CMDBChangeOp::OnInsert} (was done previously directly here)
* This will avoid creating in DB CMDBChange lines without any corresponding CMDBChangeOp
*/
protected static function CreateChange()
public static function CreateChange()
{
self::$m_oCurrChange = MetaModel::NewObject("CMDBChange");
self::$m_oCurrChange->Set("date", time());
self::$m_oCurrChange->Set("userinfo", self::GetTrackInfo());
self::$m_oCurrChange->Set("user_id", self::GetTrackUserId());
self::$m_oCurrChange->Set("origin", self::GetTrackOrigin());
self::$m_oCurrChange->DBInsert();
}
/**
@@ -601,7 +632,7 @@ abstract class CMDBObject extends DBObject
protected function DBCloneTracked_Internal($newKey = null)
{
$newKey = parent::DBClone($newKey);
$oClone = MetaModel::GetObject(get_class($this), $newKey);
$oClone = MetaModel::GetObject(get_class($this), $newKey);
return $newKey;
}
@@ -614,7 +645,7 @@ abstract class CMDBObject extends DBObject
{
return;
}
$ret = parent::DBUpdate();
return $ret;
}
@@ -738,11 +769,11 @@ abstract class CMDBObject extends DBObject
class CMDBObjectSet extends DBObjectSet
{
// this is the public interface (?)
// I have to define those constructors here... :-(
// just to get the right object class in return.
// I have to think again to those things: maybe it will work fine if a have a constructor define here (?)
static public function FromScratch($sClass)
{
$oFilter = new DBObjectSearch($sClass);
@@ -751,7 +782,7 @@ class CMDBObjectSet extends DBObjectSet
// NOTE: THIS DOES NOT WORK IF m_bLoaded is private in the base class (and you will not get any error message)
$oRetSet->m_bLoaded = true; // no DB load
return $oRetSet;
}
}
// create an object set ex nihilo
// input = array of objects
@@ -760,7 +791,7 @@ class CMDBObjectSet extends DBObjectSet
$oRetSet = self::FromScratch($sClass);
$oRetSet->AddObjectArray($aObjects, $sClass);
return $oRetSet;
}
}
static public function FromArrayAssoc($aClasses, $aObjects)
{

View File

@@ -24,13 +24,15 @@
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Core\DbConnectionWrapper;
require_once('MyHelpers.class.inc.php');
require_once(APPROOT.'core/kpi.class.inc.php');
/**
* CMDBSource
* database access wrapper
* database access wrapper
*
* @package iTopORM
*/
@@ -40,6 +42,12 @@ class CMDBSource
const ENUM_DB_VENDOR_MARIADB = 'MariaDB';
const ENUM_DB_VENDOR_PERCONA = 'Percona';
/**
* @since 2.7.10 3.0.4 3.1.2 3.0.2 N°6889 constant creation
* @internal will be removed in a future version
*/
const MYSQL_DEFAULT_PORT = 3306;
/**
* Error: 1205 SQLSTATE: HY000 (ER_LOCK_WAIT_TIMEOUT)
* Message: Lock wait timeout exceeded; try restarting transaction
@@ -66,11 +74,6 @@ class CMDBSource
*/
protected static $m_sDBTlsCA;
/** @var mysqli $m_oMysqli */
protected static $m_oMysqli;
/** @var mysqli or mock used for test purpose, only used in query() method */
protected static $oMySQLiForQuery;
/**
* @var int number of level for nested transactions : 0 if no transaction was ever opened, +1 for each 'START TRANSACTION' sent
* @since 2.7.0 N°679
@@ -135,8 +138,8 @@ class CMDBSource
self::$m_bDBTlsEnabled = empty($bTlsEnabled) ? false : $bTlsEnabled;
self::$m_sDBTlsCA = empty($sTlsCA) ? null : $sTlsCA;
self::$m_oMysqli = self::GetMysqliInstance($sServer, $sUser, $sPwd, $sSource, $bTlsEnabled, $sTlsCA, true);
self::SetMySQLiForQuery(self::$m_oMysqli);
$oMysqli = self::GetMysqliInstance($sServer, $sUser, $sPwd, $sSource, $bTlsEnabled, $sTlsCA, true);
DbConnectionWrapper::SetDbConnection($oMysqli);
}
/**
@@ -150,6 +153,8 @@ class CMDBSource
*
* @return \mysqli
* @throws \MySQLException
*
* @uses IsOpenedDbConnectionUsingTls when asking for a TLS connection, to check if it was really opened using TLS
*/
public static function GetMysqliInstance(
$sDbHost, $sUser, $sPwd, $sSource = '', $bTlsEnabled = false, $sTlsCa = null, $bCheckTlsAfterConnection = false
@@ -214,16 +219,19 @@ class CMDBSource
/**
* @param string $sDbHost initial value ("p:domain:port" syntax)
* @param string $sServer server variable to update
* @param int $iPort port variable to update
* @param int|null $iPort port variable to update, will return null if nothing is specified in $sDbHost
*
* @since 2.7.10 3.0.4 3.1.2 3.2.0 N°6889 will return null in $iPort if port isn't present in $sDbHost. Use {@see MYSQL_DEFAULT_PORT} if needed
*
* @link http://php.net/manual/en/mysqli.persistconns.php documentation for the "p:" prefix (persistent connexion)
*/
public static function InitServerAndPort($sDbHost, &$sServer, &$iPort)
{
$aConnectInfo = explode(':', $sDbHost);
$bUsePersistentConnection = false;
if (strcasecmp($aConnectInfo[0], 'p') == 0)
if (strcasecmp($aConnectInfo[0], 'p') === 0)
{
// we might have "p:" prefix to use persistent connections (see http://php.net/manual/en/mysqli.persistconns.php)
$bUsePersistentConnection = true;
$sServer = $aConnectInfo[0].':'.$aConnectInfo[1];
}
@@ -241,10 +249,6 @@ class CMDBSource
{
$iPort = (int)($aConnectInfo[1]);
}
else
{
$iPort = 3306;
}
}
/**
@@ -252,41 +256,41 @@ class CMDBSource
* parameters were used.<br>
* This method can be called to ensure that the DB connection really uses TLS.
*
* <p>We're using this object connection : {@link self::$m_oMysqli}
* <p>We're using our own mysqli instance to do the check as this check is done when creating the mysqli instance : the consumer
* might want a dedicated object, and if so we don't want to overwrite the one saved in CMDBSource !<br>
* This is the case for example with {@see \iTopMutex} !
*
* @param \mysqli $oMysqli
*
* @return boolean true if the connection was really established using TLS
* @return boolean true if the connection was really established using TLS, false otherwise
* @throws \MySQLException
*
* @used-by GetMysqliInstance
* @uses IsMySqlVarNonEmpty
* @uses 'ssl_version' MySQL var
* @uses 'ssl_cipher' MySQL var
*/
private static function IsOpenedDbConnectionUsingTls($oMysqli)
{
if (self::$m_oMysqli == null)
{
self::$m_oMysqli = $oMysqli;
}
$bNonEmptySslVersionVar = self::IsMySqlVarNonEmpty('ssl_version');
$bNonEmptySslCipherVar = self::IsMySqlVarNonEmpty('ssl_cipher');
$bNonEmptySslVersionVar = self::IsMySqlVarNonEmpty('ssl_version', $oMysqli);
$bNonEmptySslCipherVar = self::IsMySqlVarNonEmpty('ssl_cipher', $oMysqli);
return ($bNonEmptySslVersionVar && $bNonEmptySslCipherVar);
}
/**
* @param string $sVarName
* @param mysqli $oMysqli connection to use for the query
*
* @return bool
* @throws \MySQLException
*
* @uses SHOW STATUS queries
* @uses 'SHOW SESSION STATUS' queries
*/
private static function IsMySqlVarNonEmpty($sVarName)
private static function IsMySqlVarNonEmpty($sVarName, $oMysqli)
{
try
{
$sResult = self::QueryToScalar("SHOW SESSION STATUS LIKE '$sVarName'", 1);
$sResult = self::QueryToScalar("SHOW SESSION STATUS LIKE '$sVarName'", 1, $oMysqli);
}
catch (MySQLQueryHasNoResultException $e)
{
@@ -345,11 +349,18 @@ class CMDBSource
{
// In case we don't have rights to enumerate the databases
// Let's try to connect directly
return @((bool)self::$m_oMysqli->query("USE `$sSource`"));
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
return @((bool)DbConnectionWrapper::GetDbConnection(true)->query("USE `$sSource`"));
}
}
/**
* @return string
* @throws \MySQLException
*
* @uses \CMDBSource::QueryToCol() so needs a connection opened !
*/
public static function GetDBVersion()
{
$aVersions = self::QueryToCol('SELECT Version() as version', 'version');
@@ -361,14 +372,16 @@ class CMDBSource
*/
public static function GetServerInfo()
{
return mysqli_get_server_info ( self::$m_oMysqli );
return mysqli_get_server_info(DbConnectionWrapper::GetDbConnection());
}
/**
* Get the DB vendor between MySQL and its main forks
* @return string
*
* @uses \CMDBSource::GetServerVariable() so needs a connection opened !
*/
static public function GetDBVendor()
public static function GetDBVendor()
{
$sDBVendor = static::ENUM_DB_VENDOR_MYSQL;
@@ -392,9 +405,9 @@ class CMDBSource
*/
public static function SelectDB($sSource)
{
if (!((bool)self::$m_oMysqli->query("USE `$sSource`")))
{
throw new MySQLException('Could not select DB', array('db_name'=>$sSource));
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
if (!((bool)DbConnectionWrapper::GetDbConnection(true)->query("USE `$sSource`"))) {
throw new MySQLException('Could not select DB', array('db_name' => $sSource));
}
self::$m_sDBName = $sSource;
}
@@ -422,6 +435,7 @@ class CMDBSource
{
self::$m_sDBName = '';
}
self::_TablesInfoCacheReset(); // reset the table info cache!
}
public static function CreateTable($sQuery)
@@ -445,51 +459,29 @@ class CMDBSource
/**
* @return \mysqli
*
* @since 2.5.0 N°1260
*/
public static function GetMysqli()
{
return self::$m_oMysqli;
}
/**
* @return
*/
private static function GetMySQLiForQuery()
{
return self::$oMySQLiForQuery;
}
/**
* Used for test purpose (mysqli mock)
* @param $oMySQLi
*/
private static function SetMySQLiForQuery($oMySQLi)
{
self::$oMySQLiForQuery = $oMySQLi;
return DbConnectionWrapper::GetDbConnection(false);
}
public static function GetErrNo()
{
if (self::$m_oMysqli->errno != 0)
{
return self::$m_oMysqli->errno;
}
else
{
return self::$m_oMysqli->connect_errno;
if (DbConnectionWrapper::GetDbConnection()->errno != 0) {
return DbConnectionWrapper::GetDbConnection()->errno;
} else {
return DbConnectionWrapper::GetDbConnection()->connect_errno;
}
}
public static function GetError()
{
if (self::$m_oMysqli->error != '')
{
return self::$m_oMysqli->error;
}
else
{
return self::$m_oMysqli->connect_error;
if (DbConnectionWrapper::GetDbConnection()->error != '') {
return DbConnectionWrapper::GetDbConnection()->error;
} else {
return DbConnectionWrapper::GetDbConnection()->connect_error;
}
}
@@ -529,7 +521,8 @@ class CMDBSource
// Quote if not a number or a numeric string
if ($bAlways || is_string($value))
{
$value = $cQuoteStyle . self::$m_oMysqli->real_escape_string($value) . $cQuoteStyle;
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
$value = $cQuoteStyle.DbConnectionWrapper::GetDbConnection()->real_escape_string($value).$cQuoteStyle;
}
return $value;
}
@@ -555,10 +548,9 @@ class CMDBSource
/**
* @param string $sSQLQuery
*
* @return \mysqli_result|null
* @throws \MySQLException
* @throws \MySQLHasGoneAwayException
* @throws \CoreException
* @return mysqli_result|null
* @throws MySQLException
* @throws MySQLHasGoneAwayException
*
* @since 2.7.0 N°679 handles nested transactions
*/
@@ -590,7 +582,7 @@ class CMDBSource
/**
* Send the query directly to the DB. **Be extra cautious with this !**
*
* Use {@link Query} if you're not sure.
* Use {@see Query} if you're not sure.
*
* @internal
*
@@ -606,32 +598,32 @@ class CMDBSource
{
$sShortSQL = substr(preg_replace("/\s+/", " ", substr($sSql, 0, 180)), 0, 150);
if (substr_compare($sShortSQL, "SELECT", 0, strlen("SELECT")) !== 0) {
IssueLog::Trace("$sShortSQL", 'cmdbsource');
IssueLog::Trace("$sShortSQL", LogChannels::CMDB_SOURCE);
}
$oKPI = new ExecutionKPI();
try
{
$oResult = self::GetMySQLiForQuery()->query($sSql);
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
$oResult = DbConnectionWrapper::GetDbConnection(true)->query($sSql);
}
catch (mysqli_sql_exception $e)
{
self::LogDeadLock($e);
self::LogDeadLock($e, true);
throw new MySQLException('Failed to issue SQL query', array('query' => $sSql, $e));
}
$oKPI->ComputeStats('Query exec (mySQL)', $sSql);
if ($oResult === false)
{
} finally {
$oKPI->ComputeStats('Query exec (mySQL)', $sSql);
}
if ($oResult === false) {
$aContext = array('query' => $sSql);
$iMySqlErrorNo = self::$m_oMysqli->errno;
$iMySqlErrorNo = DbConnectionWrapper::GetDbConnection(true)->errno;
$aMySqlHasGoneAwayErrorCodes = MySQLHasGoneAwayException::getErrorCodes();
if (in_array($iMySqlErrorNo, $aMySqlHasGoneAwayErrorCodes))
{
if (in_array($iMySqlErrorNo, $aMySqlHasGoneAwayErrorCodes)) {
throw new MySQLHasGoneAwayException(self::GetError(), $aContext);
}
$e = new MySQLException('Failed to issue SQL query', $aContext);
self::LogDeadLock($e);
self::LogDeadLock($e, true);
throw $e;
}
@@ -639,24 +631,31 @@ class CMDBSource
}
/**
* @param \Exception $e
* @param Exception $e
* @param bool $bForQuery to get the proper DB connection
* @param bool $bCheckMysqliErrno if false won't try to check for mysqli::errno value
*
* @since 2.7.1
* @since 3.0.0 N°4325 add new optional parameter to use the correct DB connection
* @since 3.0.4 3.1.1 3.2.0 N°6643 new bCheckMysqliErrno parameter as a workaround for mysqli::errno cannot be mocked
*/
private static function LogDeadLock(Exception $e)
private static function LogDeadLock(Exception $e, $bForQuery = false, $bCheckMysqliErrno = true)
{
// checks MySQL error code
$iMySqlErrorNo = self::$m_oMysqli->errno;
if (!in_array($iMySqlErrorNo, array(self::MYSQL_ERRNO_WAIT_TIMEOUT, self::MYSQL_ERRNO_DEADLOCK)))
{
return;
if ($bCheckMysqliErrno) {
$iMySqlErrorNo = DbConnectionWrapper::GetDbConnection($bForQuery)->errno;
if (!in_array($iMySqlErrorNo, array(self::MYSQL_ERRNO_WAIT_TIMEOUT, self::MYSQL_ERRNO_DEADLOCK))) {
return;
}
} else {
$iMySqlErrorNo = "N/A";
}
// Get error info
$sUser = UserRights::GetUser();
$oError = self::$m_oMysqli->query('SHOW ENGINE INNODB STATUS');
if ($oError !== false)
{
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
$oError = DbConnectionWrapper::GetDbConnection(true)->query('SHOW ENGINE INNODB STATUS');
if ($oError !== false) {
$aData = $oError->fetch_all(MYSQLI_ASSOC);
$sInnodbStatus = $aData[0];
}
@@ -676,7 +675,10 @@ class CMDBSource
);
DeadLockLog::Info($sMessage, $iMySqlErrorNo, $aLogContext);
IssueLog::Error($sMessage, LogChannels::DEADLOCK, $e->getMessage());
IssueLog::Error($sMessage, LogChannels::DEADLOCK, [
'exception.class' => get_class($e),
'exception.message' => $e->getMessage(),
]);
}
/**
@@ -693,14 +695,13 @@ class CMDBSource
private static function StartTransaction()
{
$aStackTrace = debug_backtrace(DEBUG_BACKTRACE_PROVIDE_OBJECT , 3);
$sCaller = 'From '.$aStackTrace[1]['file'].'('.$aStackTrace[1]['line'].'): '.$aStackTrace[2]['class'].'->'.$aStackTrace[2]['function'].'()';
$bHasExistingTransactions = self::IsInsideTransaction();
if (!$bHasExistingTransactions)
{
IssueLog::Trace("START TRANSACTION $sCaller", 'cmdbsource');
if (!$bHasExistingTransactions) {
IssueLog::Trace("START TRANSACTION was sent to the DB", LogChannels::CMDB_SOURCE, ['stacktrace' => $aStackTrace]);
self::DBQuery('START TRANSACTION');
} else {
IssueLog::Trace("Ignore nested (".self::$m_iTransactionLevel.") START TRANSACTION $sCaller", 'cmdbsource');
IssueLog::Trace("START TRANSACTION ignored as a transaction is already opened", LogChannels::CMDB_SOURCE, ['stacktrace' => $aStackTrace]);
}
self::AddTransactionLevel();
@@ -719,22 +720,25 @@ class CMDBSource
private static function Commit()
{
$aStackTrace = debug_backtrace(DEBUG_BACKTRACE_PROVIDE_OBJECT , 3);
$sCaller = 'From '.$aStackTrace[1]['file'].'('.$aStackTrace[1]['line'].'): '.$aStackTrace[2]['class'].'->'.$aStackTrace[2]['function'].'()';
if (!self::IsInsideTransaction())
{
if(isset($aStackTrace[2]['class']) && isset($aStackTrace[2]['function'])) {
$sCaller = 'From '.$aStackTrace[1]['file'].'('.$aStackTrace[1]['line'].'): '.$aStackTrace[2]['class'].'->'.$aStackTrace[2]['function'].'()';
} else {
$sCaller = 'From '.$aStackTrace[1]['file'].'('.$aStackTrace[1]['line'].') ';
}
if (!self::IsInsideTransaction()) {
// should not happen !
IssueLog::Error("No Transaction COMMIT $sCaller", 'cmdbsource');
IssueLog::Error("No Transaction COMMIT $sCaller", LogChannels::CMDB_SOURCE);
throw new MySQLNoTransactionException('Trying to commit transaction whereas none have been started !', null);
}
self::RemoveLastTransactionLevel();
if (self::IsInsideTransaction())
{
IssueLog::Trace("Ignore nested (".self::$m_iTransactionLevel.") COMMIT $sCaller", 'cmdbsource');
if (self::IsInsideTransaction()) {
IssueLog::Trace("Ignore nested (".self::$m_iTransactionLevel.") COMMIT $sCaller", LogChannels::CMDB_SOURCE);
return;
}
IssueLog::Trace("COMMIT $sCaller", 'cmdbsource');
IssueLog::Trace("COMMIT $sCaller", LogChannels::CMDB_SOURCE);
self::DBQuery('COMMIT');
}
@@ -754,21 +758,24 @@ class CMDBSource
private static function Rollback()
{
$aStackTrace = debug_backtrace(DEBUG_BACKTRACE_PROVIDE_OBJECT , 3);
$sCaller = 'From '.$aStackTrace[1]['file'].'('.$aStackTrace[1]['line'].'): '.$aStackTrace[2]['class'].'->'.$aStackTrace[2]['function'].'()';
if (!self::IsInsideTransaction())
{
if(isset($aStackTrace[2]['class']) && isset($aStackTrace[2]['function'])) {
$sCaller = 'From '.$aStackTrace[1]['file'].'('.$aStackTrace[1]['line'].'): '.$aStackTrace[2]['class'].'->'.$aStackTrace[2]['function'].'()';
} else {
$sCaller = 'From '.$aStackTrace[1]['file'].'('.$aStackTrace[1]['line'].') ';
}
if (!self::IsInsideTransaction()) {
// should not happen !
IssueLog::Error("No Transaction ROLLBACK $sCaller", 'cmdbsource');
IssueLog::Error("No Transaction ROLLBACK $sCaller", LogChannels::CMDB_SOURCE);
throw new MySQLNoTransactionException('Trying to commit transaction whereas none have been started !', null);
}
self::RemoveLastTransactionLevel();
if (self::IsInsideTransaction())
{
IssueLog::Trace("Ignore nested (".self::$m_iTransactionLevel.") ROLLBACK $sCaller", 'cmdbsource');
if (self::IsInsideTransaction()) {
IssueLog::Trace("Ignore nested (".self::$m_iTransactionLevel.") ROLLBACK $sCaller", LogChannels::CMDB_SOURCE);
return;
}
IssueLog::Trace("ROLLBACK $sCaller", 'cmdbsource');
IssueLog::Trace("ROLLBACK $sCaller", LogChannels::CMDB_SOURCE);
self::DBQuery('ROLLBACK');
}
@@ -832,7 +839,7 @@ class CMDBSource
public static function GetInsertId()
{
$iRes = self::$m_oMysqli->insert_id;
$iRes = DbConnectionWrapper::GetDbConnection()->insert_id;
if (is_null($iRes))
{
return 0;
@@ -864,26 +871,28 @@ class CMDBSource
/**
* @param string $sSql
* @param int $iCol beginning at 0
* @param mysqli $oMysqli if not null will query using this connection, otherwise will use {@see GetMySQLiForQuery}
*
* @return string corresponding cell content on the first line
* @throws \MySQLException
* @throws \MySQLQueryHasNoResultException
* @since 2.7.5-2 2.7.6 3.0.0 N°4215 new optional mysqli param
*/
public static function QueryToScalar($sSql, $iCol = 0)
public static function QueryToScalar($sSql, $iCol = 0, $oMysqli = null)
{
$oMysqliForQuery = $oMysqli ?: DbConnectionWrapper::GetDbConnection(true);
$oKPI = new ExecutionKPI();
try
{
$oResult = self::GetMySQLiForQuery()->query($sSql);
try {
/** @noinspection NullPointerExceptionInspection this shouldn't happen : either cnx is passed or the DB was init */
$oResult = $oMysqliForQuery->query($sSql);
}
catch(mysqli_sql_exception $e)
{
catch (mysqli_sql_exception $e) {
$oKPI->ComputeStats('Query exec (mySQL)', $sSql);
throw new MySQLException('Failed to issue SQL query', array('query' => $sSql, $e));
}
$oKPI->ComputeStats('Query exec (mySQL)', $sSql);
if ($oResult === false)
{
if ($oResult === false) {
throw new MySQLException('Failed to issue SQL query', array('query' => $sSql));
}
@@ -904,17 +913,19 @@ class CMDBSource
/**
* @param string $sSql
* @param int $iMode
*
* @return array
* @throws \MySQLException if query cannot be processed
*/
public static function QueryToArray($sSql)
public static function QueryToArray($sSql, $iMode = MYSQLI_BOTH)
{
$aData = array();
$oKPI = new ExecutionKPI();
try
{
$oResult = self::GetMySQLiForQuery()->query($sSql);
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
$oResult = DbConnectionWrapper::GetDbConnection(true)->query($sSql);
}
catch(mysqli_sql_exception $e)
{
@@ -927,7 +938,7 @@ class CMDBSource
throw new MySQLException('Failed to issue SQL query', array('query' => $sSql));
}
while ($aRow = $oResult->fetch_array(MYSQLI_BOTH))
while ($aRow = $oResult->fetch_array($iMode))
{
$aData[] = $aRow;
}
@@ -964,7 +975,8 @@ class CMDBSource
$aData = array();
try
{
$oResult = self::$m_oMysqli->query($sSql);
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
$oResult = DbConnectionWrapper::GetDbConnection(true)->query($sSql);
}
catch(mysqli_sql_exception $e)
{
@@ -996,7 +1008,8 @@ class CMDBSource
{
try
{
$oResult = self::GetMySQLiForQuery()->query($sSql);
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
$oResult = DbConnectionWrapper::GetDbConnection(true)->query($sSql);
}
catch(mysqli_sql_exception $e)
{
@@ -1021,7 +1034,7 @@ class CMDBSource
public static function AffectedRows()
{
return self::$m_oMysqli->affected_rows;
return DbConnectionWrapper::GetDbConnection()->affected_rows;
}
public static function FetchArray($oResult)
@@ -1139,7 +1152,7 @@ class CMDBSource
*
* We still need to do a case sensitive comparison for enum values !
*
* A better solution would be to generate SQL field definitions ({@link GetFieldSpec} method) based on the DB used... But for
* A better solution would be to generate SQL field definitions ({@see GetFieldSpec} method) based on the DB used... But for
* now (N°2490 / SF #1756 / PR #91) we did implement this simpler solution
*
* @see GetFieldDataTypeAndOptions extracts all info from the SQL field definition
@@ -1155,8 +1168,8 @@ class CMDBSource
*/
public static function IsSameFieldTypes($sItopGeneratedFieldType, $sDbFieldType)
{
list($sItopFieldDataType, $sItopFieldTypeOptions, $sItopFieldOtherOptions) = static::GetFieldDataTypeAndOptions($sItopGeneratedFieldType);
list($sDbFieldDataType, $sDbFieldTypeOptions, $sDbFieldOtherOptions) = static::GetFieldDataTypeAndOptions($sDbFieldType);
[$sItopFieldDataType, $sItopFieldTypeOptions, $sItopFieldOtherOptions] = static::GetFieldDataTypeAndOptions($sItopGeneratedFieldType);
[$sDbFieldDataType, $sDbFieldTypeOptions, $sDbFieldOtherOptions] = static::GetFieldDataTypeAndOptions($sDbFieldType);
if (strcasecmp($sItopFieldDataType, $sDbFieldDataType) !== 0)
{
@@ -1484,7 +1497,8 @@ class CMDBSource
$sSql = "SELECT * FROM `$sTable`";
try
{
$oResult = self::GetMySQLiForQuery()->query($sSql);
/** @noinspection NullPointerExceptionInspection this shouldn't be called with un-init DB */
$oResult = DbConnectionWrapper::GetDbConnection(true)->query($sSql);
}
catch(mysqli_sql_exception $e)
{
@@ -1594,7 +1608,19 @@ class CMDBSource
return false;
}
/**
public static function GetClusterNb()
{
$result = 0;
$sSql = "SHOW STATUS LIKE 'wsrep_cluster_size';";
$aRows = self::QueryToArray($sSql);
if (count($aRows) > 0)
{
$result = $aRows[0]['Value'];
}
return intval($result);
}
/**
* @see https://dev.mysql.com/doc/refman/5.7/en/charset-database.html
* @return string query to upgrade database charset and collation if needed, null if not
* @throws \MySQLException

View File

@@ -22,7 +22,15 @@
define('ITOP_APPLICATION', 'iTop');
define('ITOP_APPLICATION_SHORT', 'iTop');
define('ITOP_VERSION', '3.0.0-dev');
/**
* Constant containing the application version
* Warning: this might be different from iTop core version!
*
* @see ITOP_CORE_VERSION to get iTop core version
*/
define('ITOP_VERSION', '3.0.3-dev');
define('ITOP_VERSION_NAME', 'Fullmoon');
define('ITOP_REVISION', 'svn');
define('ITOP_BUILD_DATE', '$WCNOW$');
@@ -107,7 +115,15 @@ class Config
protected $m_aSettings = [
'log_level_min' => [
'type' => 'array',
'description' => 'Optional min log level per channel',
'description' => 'Optional min log level, per channel.',
'default' => '',
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'log_level_min.write_in_db' => [
'type' => 'array',
'description' => 'Optional min log level IN DB, per channel.',
'default' => '',
'value' => '',
'source_of_value' => '',
@@ -464,6 +480,14 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'link_set_max_edit_ext_key' => [
'type' => 'integer',
'description' => 'Maximum number of items in the link that allow editing the remote external key. Above that limit, remote external key cannot be edited. Mind that setting this limit too high can have a negative impact on performances.',
'default' => 50,
'value' => 50,
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'tag_set_item_separator' => [
'type' => 'string',
'description' => 'Tag set from string: tag label separator',
@@ -473,13 +497,21 @@ class Config
'show_in_conf_sample' => true,
],
'cron_max_execution_time' => [
'type' => 'integer',
'description' => 'Duration (seconds) of the page cron.php, must be shorter than php setting max_execution_time and shorter than the web server response timeout',
'default' => 600,
'value' => 600,
'source_of_value' => '',
'type' => 'integer',
'description' => 'Duration (seconds) of the cron.php script : if exceeded the script will exit even if there are remaining tasks to process. Must be shorter than php max_execution_time setting (note than when using CLI, this is set to 0 by default which means unlimited). If cron.php is ran via web, it must be shorter than the web server response timeout.',
'default' => 600,
'value' => 600,
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'cron_task_max_execution_time' => [
'type' => 'integer',
'description' => 'Background tasks will use this value (integer) multiplicated by its periodicity (in seconds) as max duration per cron execution. 0 is unlimited time',
'default' => 0,
'value' => 0,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'cron_sleep' => [
'type' => 'integer',
'description' => 'Duration (seconds) before cron.php checks again if something must be done',
@@ -506,7 +538,7 @@ class Config
],
'email_transport' => [
'type' => 'string',
'description' => 'Mean to send emails: PHPMail (uses the function mail()) or SMTP (implements the client protocol)',
'description' => 'Mean to send emails: PHPMail (uses the function mail()), SMTP (implements the client protocol) or SMTP_OAuth (connect to the server using OAuth 2.0)',
'default' => "PHPMail",
'value' => "PHPMail",
'source_of_value' => '',
@@ -528,7 +560,7 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'email_transport_smtp.encryption' => [
'email_transport_smtp.encryption' => [
'type' => 'string',
'description' => 'tls or ssl (optional)',
'default' => "",
@@ -536,20 +568,36 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'email_transport_smtp.username' => [
'type' => 'string',
'description' => 'Authentication user (optional)',
'default' => "",
'value' => "",
'source_of_value' => '',
'email_transport_smtp.username' => [
'type' => 'string',
'description' => 'Authentication user (optional)',
'default' => "",
'value' => "",
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'email_transport_smtp.password' => [
'type' => 'string',
'description' => 'Authentication password (optional)',
'default' => "",
'value' => "",
'source_of_value' => '',
'email_transport_smtp.password' => [
'type' => 'string',
'description' => 'Authentication password (optional)',
'default' => "",
'value' => "",
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'email_transport_smtp.allow_self_signed' => [
'type' => 'bool',
'description' => 'Allow self signed peer certificates',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'email_transport_smtp.verify_peer' => [
'type' => 'bool',
'description' => 'Verify peer certificate',
'default' => true,
'value' => true,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'email_css' => [
@@ -600,6 +648,13 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
/**
* The timezone is automatically set using this parameter in \utils::InitTimeZone
* This method is called almost everywhere, cause it's called in \MetaModel::LoadConfig and exec.php... but you might
* need to get it yourself !
*
* @used-by utils::InitTimeZone()
*/
'timezone' => [
'type' => 'string',
'description' => 'Timezone (reference: http://php.net/manual/en/timezones.php). If empty, it will be left unchanged and MUST be explicitly configured in PHP',
@@ -843,15 +898,20 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'impact_analysis_lazy_loading' => [
'type' => 'bool',
'description' => 'In the impact analysis view: display the analysis or filter before display',
'default' => false,
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'url_validation_pattern' => [
'type' => 'string',
'description' => 'Regular expression to validate/detect the format of an URL (URL attributes and Wiki formatting for Text attributes)',
'default' => '(https?|ftp)\://([a-zA-Z0-9+!*(),;?&=\$_.-]+(\:[a-zA-Z0-9+!*(),;?&=\$_.-]+)?@)?([a-zA-Z0-9-.]{3,})(\:[0-9]{2,5})?(/([a-zA-Z0-9%+\$_-]\.?)+)*/?(\?[a-zA-Z+&\$_.-][a-zA-Z0-9;:[\]@&%=+/\$_.-]*)?(#[a-zA-Z_.-][a-zA-Z0-9+\$_.-]*)?',
// SHEME.......... USER....................... PASSWORD.......................... HOST/IP........... PORT.......... PATH........................ GET............................................ ANCHOR............................
// Example: http://User:passWord@127.0.0.1:8888/patH/Page.php?arrayArgument[2]=something:blah20#myAnchor
// Origin of this regexp: http://www.php.net/manual/fr/function.preg-match.php#93824
'value' => '',
'source_of_value' => '',
'type' => 'string',
'description' => 'Regular expression to validate/detect the format of an URL (URL attributes and Wiki formatting for Text attributes)',
'default' => AttributeURL::DEFAULT_VALIDATION_PATTERN,
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'email_validation_pattern' => [
@@ -929,6 +989,14 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'log_kpi_generate_legacy_report' => [
'type' => 'bool',
'description' => 'Generate the legacy KPI report (kpi.html)',
'default' => true,
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'max_linkset_output' => [
'type' => 'integer',
'description' => 'Maximum number of items shown when getting a list of related items in an email, using the form $this->some_list$. 0 means no limit.',
@@ -967,8 +1035,8 @@ class Config
'type' => 'integer',
'description' => 'Maximum length of the history table (in the "History" tab on each object) before it gets truncated. Latest modifications are displayed first.',
// examples... not used
'default' => 50,
'value' => 50,
'default' => 200,
'value' => 200,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
@@ -1062,72 +1130,88 @@ class Config
'show_in_conf_sample' => false,
],
'transactions_gc_threshold' => [
'type' => 'integer',
'description' => 'probability in percent for the garbage collector to be triggered (100 mean always)',
'default' => 10, // added in itop 2.7.4, before the GC was always called
'value' => '',
'source_of_value' => '',
'type' => 'integer',
'description' => 'probability in percent for the garbage collector to be triggered (100 mean always)',
'default' => 10, // added in itop 2.7.4, before the GC was always called
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'log_transactions' => [
'type' => 'bool',
'description' => 'Whether or not to enable the debug log for the transactions.',
'default' => false,
'value' => '',
'source_of_value' => '',
'type' => 'bool',
'description' => 'Whether or not to enable the debug log for the transactions.',
'default' => false,
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'concurrent_lock_enabled' => [
'type' => 'bool',
'description' => 'Whether or not to activate the locking mechanism in order to prevent concurrent edition of the same object.',
'default' => false,
'value' => '',
'source_of_value' => '',
'type' => 'bool',
'description' => 'Whether or not to activate the locking mechanism in order to prevent concurrent edition of the same object.',
'default' => false,
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'concurrent_lock_expiration_delay' => [
'type' => 'integer',
'description' => 'Delay (in seconds) for a concurrent lock to expire',
'default' => 120,
'value' => '',
'source_of_value' => '',
'type' => 'integer',
'description' => 'Delay (in seconds) for a concurrent lock to expire',
'default' => 120,
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'concurrent_lock_override_profiles' => [
'type' => 'array',
'description' => 'The list of profiles allowed to "kill" a lock',
'default' => ['Administrator'],
'value' => '',
'source_of_value' => '',
'type' => 'array',
'description' => 'The list of profiles allowed to "kill" a lock',
'default' => ['Administrator'],
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'force_transition_confirmation' => [
'type' => 'bool',
'description' => 'If set to true force confirmation in all transition even if there is no field to complete',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'html_sanitizer' => [
'type' => 'string',
'description' => 'The class to use for HTML sanitization: HTMLDOMSanitizer, HTMLPurifierSanitizer or HTMLNullSanitizer',
'default' => 'HTMLDOMSanitizer',
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'svg_sanitizer' => [
'type' => 'string',
'description' => 'The class to use for HTML sanitization: HTMLDOMSanitizer, HTMLPurifierSanitizer or HTMLNullSanitizer',
'default' => 'HTMLDOMSanitizer',
'description' => 'The class to use for SVG sanitization : allow to provide a custom made sanitizer',
'default' => 'SVGDOMSanitizer',
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'inline_image_max_display_width' => [
'type' => 'integer',
'description' => 'The maximum width (in pixels) when displaying images inside an HTML formatted attribute. Images will be displayed using this this maximum width.',
'default' => '250',
'value' => '',
'source_of_value' => '',
'type' => 'integer',
'description' => 'The maximum width (in pixels) when displaying images inside an HTML formatted attribute. Images will be displayed using this this maximum width.',
'default' => '250',
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'inline_image_max_storage_width' => [
'type' => 'integer',
'description' => 'The maximum width (in pixels) when uploading images to be used inside an HTML formatted attribute. Images larger than the given size will be downsampled before storing them in the database.',
'default' => '1600',
'value' => '',
'source_of_value' => '',
'type' => 'integer',
'description' => 'The maximum width (in pixels) when uploading images to be used inside an HTML formatted attribute. Images larger than the given size will be downsampled before storing them in the database.',
'default' => '1600',
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'draft_attachments_lifetime' => [
'type' => 'integer',
'description' => 'Lifetime (in seconds) of drafts\' attachments and inline images: after this duration, the garbage collector will delete them.',
'type' => 'integer',
'description' => 'Lifetime (in seconds) of drafts\' attachments and inline images: after this duration, the garbage collector will delete them.',
'default' => 86400,
'value' => '',
'source_of_value' => '',
@@ -1141,6 +1225,38 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'compatibility.include_moved_js_files' => [
'type' => 'bool',
'description' => 'Include back JS files which are now only included when necessary to ease usage of not migrated extensions',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'compatibility.include_deprecated_js_files' => [
'type' => 'bool',
'description' => 'Include the deprecated JS files (in iTop previous version) to ease usage of not migrated extensions',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'compatibility.include_moved_css_files' => [
'type' => 'bool',
'description' => 'Include back CSS files which are now only included when necessary to ease usage of not migrated extensions',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'compatibility.include_deprecated_css_files' => [
'type' => 'bool',
'description' => 'Include the deprecated CSS files (in iTop previous version) to ease usage of not migrated extensions',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'navigation_menu.show_menus_count' => [
'type' => 'bool',
'description' => 'Display count badges for OQL menu entries',
@@ -1237,6 +1353,30 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'activity_panel.prefilter_state_changes_on_logs' => [
'type' => 'bool',
'description' => 'Whether the "State changes" filter should be set by default on all log tabs.',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'activity_panel.prefilter_edits_on_logs' => [
'type' => 'bool',
'description' => 'Whether the "Edits" filter should be set by default on all log tabs.',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'activity_panel.hide_avatars' => [
'type' => 'array',
'description' => 'GUIs IDs ("backoffice", "itop-portal" for the standard end-users portal, ...) in which the user avatars should be hidden and replaced if possible by their initials (eg. array("backoffice", "itop-portal", "another-portal-id"))',
'default' => [],
'value' => [],
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'activity_panel.show_author_name_below_entries' => [
'type' => 'bool',
'description' => 'Whether or not to show the author friendlyname next to the date on the last entry.',
@@ -1263,7 +1403,7 @@ class Config
],
'mentions.allowed_classes' => [
'type' => 'array',
'description' => 'Classes which can be mentioned through the autocomplete in the caselogs. Key of the array must be a single character that will trigger the autocomplete (eg. "@" => "Person")',
'description' => 'Classes which can be mentioned through the autocomplete in the caselogs. Key of the array must be a single character that will trigger the autocomplete, value must be a DM class (eg. "@" => "Person", "?" => "FAQ")',
'default' => [
'@' => 'Person',
],
@@ -1303,6 +1443,14 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'allow_rest_services_via_tokens' => [
'type' => 'bool',
'description' => 'When set to true, REST endpoint token authorization works even with secure_rest_services set.',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'search_manual_submit' => [
'type' => 'array',
'description' => 'Force manual submit of search all requests',
@@ -1343,14 +1491,6 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'use_legacy_dbsearch' => [
'type' => 'bool',
'description' => 'If set, DBSearch will use legacy SQL query generation',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'query_cache_enabled' => [
'type' => 'bool',
'description' => 'If set, DBSearch will use cache for query generation',
@@ -1391,6 +1531,30 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'security.enable_header_xcontent_type_options' => [
'type' => 'bool',
'description' => 'If set to false, iTop will stop sending the X-Content-Type-Options HTTP header. This header could trigger CORB protection on certain resources (JSON, XML, HTML, text) therefore blocking them.',
'default' => true,
'value' => '',
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'security.disable_inline_documents_sandbox' => [
'type' => 'bool',
'description' => 'If true then the sandbox for documents displayed in a browser tab will be disabled; enabling scripts and other interactive content. Note that setting this to true will open the application to potential XSS attacks!',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'security.hide_administrators' => [
'type' => 'bool',
'description' => 'If true, non-administrator users will not be able to see the administrator accounts, the Administrator profile and the links between the administrator accounts and their profiles.',
'default' => false,
'value' => false,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'behind_reverse_proxy' => [
'type' => 'bool',
'description' => 'If true, then proxies custom header (X-Forwarded-*) are taken into account. Use only if the webserver is not publicly accessible (reachable only by the reverse proxy)',
@@ -1399,6 +1563,14 @@ class Config
'source_of_value' => '',
'show_in_conf_sample' => true,
],
'developer_mode.enabled' => [
'type' => 'bool',
'description' => 'If true then unlocks dev env functionalities, see \utils::IsDevelopmentEnvironment',
'default' => null,
'value' => null,
'source_of_value' => '',
'show_in_conf_sample' => false,
],
'theme.enable_precompilation' => [
'type' => 'bool',
'description' => 'If false, theme compilation will not use any precompiled file setup optimization.)',
@@ -1496,6 +1668,16 @@ class Config
return $this->m_aSettings[$sPropCode]['value'];
}
/**
* @return mixed
*
* @since 3.0.1 N°4515
*/
public function GetDefault(string $sPropCode)
{
return $this->m_aSettings[$sPropCode]['default'];
}
/**
* Whether the $sPropCode parameter has a custom value or the default one.
*
@@ -1722,7 +1904,7 @@ class Config
}
if (strlen($sNoise) > 0)
{
// Note: sNoise is an html output, but so far it was ok for me (e.g. showing the entire call stack)
// Note: sNoise is an html output, but so far it was ok for me (e.g. showing the entire call stack)
throw new ConfigException('Syntax error in configuration file',
array('file' => $sConfigFile, 'error' => '<tt>'.htmlentities($sNoise, ENT_QUOTES, 'UTF-8').'</tt>'));
}
@@ -2011,6 +2193,24 @@ class Config
$this->m_sAllowedLoginTypes = implode('|', $aAllowedLoginTypes);
}
/**
* @since 2.7.11 N°7085
* Add login mode if not configured already
* @param string $sLoginMode
*
* @return void
*/
public function AddAllowedLoginTypes($sLoginMode)
{
$aAllowedLoginTypes = $this->GetAllowedLoginTypes();
if (in_array($sLoginMode, $aAllowedLoginTypes)){
return;
}
$aAllowedLoginTypes[] = $sLoginMode;
$this->SetAllowedLoginTypes($aAllowedLoginTypes);
}
public function SetExternalAuthenticationVariable($sExtAuthVariable)
{
$this->m_sExtAuthVariable = $sExtAuthVariable;
@@ -2532,7 +2732,7 @@ class ConfigPlaceholdersResolver
}
$sPattern = '/\%(env|server)\((\w+)\)(?:\?:(\w*))?\%/'; //3 capturing groups, ie `%env(HTTP_PORT)?:8080%` produce: `env` `HTTP_PORT` and `8080`.
if (! preg_match_all($sPattern, $rawValue, $aMatchesCollection, PREG_SET_ORDER))
{
return $rawValue;

View File

@@ -1,8 +1,11 @@
<?php
/**
* This file is only here for compatibility issues. Will be removed in iTop 3.1.0 (N°3664)
* This file is only here for compatibility reasons.
* It will be removed in future iTop versions (N°6533)
*
* @deprecated 3.0.0 N°3663 Exception classes were moved to `/application/exceptions`, use autoloader instead of require !
*/
require_once '../approot.inc.php';
DeprecatedCallsLog::NotifyDeprecatedFile('Classes were moved to /application/exceptions');
require_once __DIR__ . '/../approot.inc.php';
DeprecatedCallsLog::NotifyDeprecatedFile('Classes were moved to /application/exceptions and can be used directly with the autoloader');

View File

@@ -188,8 +188,8 @@ final class ItopCounter
if (!$hDBLink)
{
throw new Exception("Could not connect to the DB server (host=$sDBHost, user=$sDBUser): ".mysqli_connect_error().' (mysql errno: '.mysqli_connect_errno().')');
}
throw new MySQLException('Could not connect to the DB server '.mysqli_connect_error().' (mysql errno: '.mysqli_connect_errno(), array('host' => $sDBHost, 'user' => $sDBUser));
}
return $hDBLink;
}

View File

@@ -12,6 +12,7 @@ use Combodo\iTop\Application\UI\Base\Component\Input\SelectUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Panel\PanelUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Layout\MultiColumn\Column\ColumnUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Layout\MultiColumn\MultiColumnUIBlockFactory;
use Combodo\iTop\Application\Helper\ExportHelper;
/**
* Bulk export: CSV export
@@ -114,6 +115,7 @@ class CSVBulkExport extends TabularBulkExport
case 'csv_options':
$oPanel = PanelUIBlockFactory::MakeNeutral(Dict::S('Core:BulkExport:CSVOptions'));
$oPanel->AddSubBlock(ExportHelper::GetAlertForExcelMaliciousInjection());
$oMulticolumn = MultiColumnUIBlockFactory::MakeStandard();
$oPanel->AddSubBlock($oMulticolumn);
@@ -164,7 +166,7 @@ class CSVBulkExport extends TabularBulkExport
foreach ($aQualifiers as $sVal => $sLabel) {
$oRadio = InputUIBlockFactory::MakeForInputWithLabel($sLabel, "text-qualifier", htmlentities($sVal, ENT_QUOTES, 'UTF-8'), $sLabel, "radio");
$oRadio->GetInput()->SetIsChecked(($sVal == $sRawSeparator));
$oRadio->GetInput()->SetIsChecked(($sVal == $sRawQualifier));
$oRadio->SetBeforeInput(false);
$oRadio->GetInput()->AddCSSClass('ibo-input--label-right');
$oRadio->GetInput()->AddCSSClass('ibo-input-checkbox');
@@ -220,16 +222,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'); });

File diff suppressed because it is too large Load Diff

View File

@@ -416,6 +416,10 @@ class DBObjectSearch extends DBSearch
* @param string $sFilterCode
* @param mixed $value
* @param string $sOpCode operator to use : 'IN', 'NOT IN', 'Contains',' Begins with', 'Finishes with', ...
* If no operator is specified then :
* * for id field we will use "="
* * for other fields we will call the corresponding {@link AttributeDefinition::GetSmartConditionExpression} method impl
* to generate the expression
* @param bool $bParseSearchString
*
* @throws \CoreException
@@ -465,14 +469,14 @@ class DBObjectSearch extends DBSearch
if (!is_array($value)) $value = array($value);
if (count($value) === 0) throw new Exception('AddCondition '.$sOpCode.': Value cannot be an empty array.');
$sListExpr = '('.implode(', ', CMDBSource::Quote($value)).')';
$sOQLCondition = $oField->Render()." IN $sListExpr";
$sOQLCondition = $oField->RenderExpression()." IN $sListExpr";
break;
case 'NOTIN':
if (!is_array($value)) $value = array($value);
if (count($value) === 0) throw new Exception('AddCondition '.$sOpCode.': Value cannot be an empty array.');
$sListExpr = '('.implode(', ', CMDBSource::Quote($value)).')';
$sOQLCondition = $oField->Render()." NOT IN $sListExpr";
$sOQLCondition = $oField->RenderExpression()." NOT IN $sListExpr";
break;
case 'Contains':
@@ -1099,22 +1103,39 @@ class DBObjectSearch extends DBSearch
public function Filter($sClassAlias, DBSearch $oFilter)
{
// If the conditions are the correct ones for Intersect
if (MetaModel::IsParentClass($oFilter->GetFirstJoinedClass(),$this->GetFirstJoinedClass()))
{
if (MetaModel::IsParentClass($oFilter->GetFirstJoinedClass(), $this->GetFirstJoinedClass())) {
return $this->Intersect($oFilter);
}
/** @var \DBObjectSearch $oFilteredSearch */
$oFilteredSearch = $this->DeepClone();
$oFilterExpression = self::FilterSubClass($oFilteredSearch, $sClassAlias, $oFilter, $this->m_aClasses);
if ($oFilterExpression === false)
{
throw new CoreException("Limitation: cannot filter search");
if ($oFilter instanceof DBUnionSearch) {
$aFilters = $oFilter->GetSearches();
} else {
$aFilters = [$oFilter];
}
$oFilteredSearch->AddConditionExpression($oFilterExpression);
$aSearches = [];
foreach ($aFilters as $oRightFilter) {
/** @var \DBObjectSearch $oFilteredSearch */
$oFilteredSearch = $this->DeepClone();
$oFilterExpression = self::FilterSubClass($oFilteredSearch, $sClassAlias, $oRightFilter, $this->m_aClasses);
if ($oFilterExpression === false) {
throw new CoreException("Limitation: cannot filter search");
}
return $oFilteredSearch;
$oFilteredSearch->AddConditionExpression($oFilterExpression);
$aSearches[] = $oFilteredSearch;
}
if (count($aSearches) == 0) {
throw new CoreException('Filtering '.$this->ToOQL().' by '.$oFilter->ToOQL().' failed');
}
if (count($aSearches) == 1) {
// return a DBObjectSearch
return $aSearches[0];
}
return new DBUnionSearch($aSearches);
}
/**
@@ -1180,22 +1201,10 @@ class DBObjectSearch extends DBSearch
* @throws \CoreException
*/
public function Intersect(DBSearch $oFilter)
{
return $this->IntersectSubClass($oFilter, $this->m_aClasses);
}
/**
* @param \DBSearch $oFilter
* @param array $aRootClasses classes of the root search (for aliases)
*
* @return \DBUnionSearch|mixed
* @throws \CoreException
*/
protected function IntersectSubClass(DBSearch $oFilter, $aRootClasses)
{
if ($oFilter instanceof DBUnionSearch)
{
// Develop!
// Develop!
$aFilters = $oFilter->GetSearches();
}
else
@@ -1206,56 +1215,61 @@ class DBObjectSearch extends DBSearch
$aSearches = array();
foreach ($aFilters as $oRightFilter)
{
// Limitation: the queried class must be the first declared class
if ($oRightFilter->GetFirstJoinedClassAlias() != $oRightFilter->GetClassAlias())
{
throw new CoreException("Limitation: cannot merge two queries if the queried class ({$oRightFilter->GetClass()} AS {$oRightFilter->GetClassAlias()}) is not the first joined class ({$oRightFilter->GetFirstJoinedClass()} AS {$oRightFilter->GetFirstJoinedClassAlias()})");
}
/** @var \DBObjectSearch $oLeftFilter */
$oLeftFilter = $this->DeepClone();
$oRightFilter = $oRightFilter->DeepClone();
$bAllowAllData = ($oLeftFilter->IsAllDataAllowed() && $oRightFilter->IsAllDataAllowed());
if ($bAllowAllData)
{
$oLeftFilter->AllowAllData();
}
if ($oLeftFilter->GetFirstJoinedClass() != $oRightFilter->GetClass())
{
if (MetaModel::IsParentClass($oLeftFilter->GetFirstJoinedClass(), $oRightFilter->GetClass()))
{
// Specialize $oLeftFilter
$oLeftFilter->ChangeClass($oRightFilter->GetClass(), $oLeftFilter->GetFirstJoinedClassAlias());
}
elseif (MetaModel::IsParentClass($oRightFilter->GetFirstJoinedClass(), $oLeftFilter->GetClass()))
{
// Specialize $oRightFilter
$oRightFilter->ChangeClass($oLeftFilter->GetClass());
}
else
{
throw new CoreException("Attempting to merge a filter of class '{$oLeftFilter->GetClass()}' with a filter of class '{$oRightFilter->GetClass()}'");
}
}
$aAliasTranslation = array();
$oLeftFilter->RenameNestedQueriesAliasesInNameSpace($aRootClasses, $aAliasTranslation);
$oLeftFilter->MergeWith_InNamespace($oRightFilter, $aRootClasses, $aAliasTranslation);
$oRightFilter->RenameNestedQueriesAliasesInNameSpace($aRootClasses, $aAliasTranslation);
$oLeftFilter->TransferConditionExpression($oRightFilter, $aAliasTranslation);
$aSearches[] = $oLeftFilter;
$aSearches[] = $this->IntersectSubClass($oRightFilter, $this->m_aClasses);
}
if (count($aSearches) == 1)
{
// return a DBObjectSearch
return $aSearches[0];
}
else
{
return new DBUnionSearch($aSearches);
return new DBUnionSearch($aSearches);
}
/**
* @param \DBObjectSearch $oRightFilter
* @param array $aRootClasses classes of the root search (for aliases)
*
* @return \DBObjectSearch
* @throws \CoreException
*/
protected function IntersectSubClass(DBObjectSearch $oRightFilter, array $aRootClasses): DBObjectSearch
{
// Limitation: the queried class must be the first declared class
if ($oRightFilter->GetFirstJoinedClassAlias() != $oRightFilter->GetClassAlias()) {
throw new CoreException("Limitation: cannot merge two queries if the queried class ({$oRightFilter->GetClass()} AS {$oRightFilter->GetClassAlias()}) is not the first joined class ({$oRightFilter->GetFirstJoinedClass()} AS {$oRightFilter->GetFirstJoinedClassAlias()})");
}
/** @var \DBObjectSearch $oLeftFilter */
$oLeftFilter = $this->DeepClone();
/** @var DBObjectSearch $oRightFilter */
$oRightFilter = $oRightFilter->DeepClone();
$bAllowAllData = ($oLeftFilter->IsAllDataAllowed() && $oRightFilter->IsAllDataAllowed());
if ($bAllowAllData) {
$oLeftFilter->AllowAllData();
}
if ($oLeftFilter->GetFirstJoinedClass() != $oRightFilter->GetClass()) {
if (MetaModel::IsParentClass($oLeftFilter->GetFirstJoinedClass(), $oRightFilter->GetClass())) {
// Specialize $oLeftFilter
$oLeftFilter->ChangeClass($oRightFilter->GetClass(), $oLeftFilter->GetFirstJoinedClassAlias());
} elseif (MetaModel::IsParentClass($oRightFilter->GetFirstJoinedClass(), $oLeftFilter->GetClass())) {
// Specialize $oRightFilter
$oRightFilter->ChangeClass($oLeftFilter->GetFirstJoinedClass());
} else {
throw new CoreException("Attempting to merge a filter of class '{$oLeftFilter->GetClass()}' with a filter of class '{$oRightFilter->GetClass()}'");
}
}
$aAliasTranslation = array();
$oLeftFilter->RenameNestedQueriesAliasesInNameSpace($aRootClasses, $aAliasTranslation);
$oLeftFilter->MergeWith_InNamespace($oRightFilter, $aRootClasses, $aAliasTranslation);
$oRightFilter->RenameNestedQueriesAliasesInNameSpace($aRootClasses, $aAliasTranslation);
$oLeftFilter->TransferConditionExpression($oRightFilter, $aAliasTranslation);
return $oLeftFilter;
}
/**
@@ -1368,7 +1382,7 @@ class DBObjectSearch extends DBSearch
public function GetQueryParams($bExcludeMagicParams = true)
{
$aParams = array();
$this->m_oSearchCondition->Render($aParams, true);
$this->m_oSearchCondition->RenderExpression(false, $aParams, true);
if ($bExcludeMagicParams)
{
@@ -1457,7 +1471,7 @@ class DBObjectSearch extends DBSearch
$sRes .= ' ' . $this->GetFirstJoinedClass() . ' AS `' . $this->GetFirstJoinedClassAlias() . '`';
$sRes .= $this->ToOQL_Joins();
$sRes .= " WHERE ".$this->m_oSearchCondition->Render($aParams, $bRetrofitParams);
$sRes .= " WHERE ".$this->m_oSearchCondition->RenderExpression(false, $aParams, $bRetrofitParams);
if ($bWithAllowAllFlag && $this->m_bAllowAllData)
{

View File

@@ -141,7 +141,7 @@ class DBObjectSet implements iDBObjectSetIterator
{
$sRet = '';
$this->Rewind();
$sRet .= "Set (".$this->m_oFilter->ToOQL().")<br/>\n";
$sRet .= "Set (".$this->m_oFilter->ToOQL(true).")<br/>\n";
$sRet .= "Query: <pre style=\"font-size: smaller; display:inline;\">".$this->m_oFilter->MakeSelectQuery().")</pre>\n";
$sRet .= $this->Count()." records<br/>\n";
@@ -154,6 +154,7 @@ class DBObjectSet implements iDBObjectSetIterator
}
$sRet .= "</ul>\n";
}
$this->Rewind();
return $sRet;
}
@@ -766,7 +767,10 @@ class DBObjectSet implements iDBObjectSetIterator
try
{
$oKPI = new ExecutionKPI();
$this->m_oSQLResult = CMDBSource::Query($sSQL);
$sOQL = $this->GetPseudoOQL($this->m_oFilter, $this->GetRealSortOrder(), $this->m_iLimitCount, $this->m_iLimitStart, false);
$oKPI->ComputeStats('OQL Query Exec', $sOQL);
} catch (MySQLException $e)
{
// 1116 = ER_TOO_MANY_TABLES
@@ -846,8 +850,11 @@ class DBObjectSet implements iDBObjectSetIterator
{
if (is_null($this->m_iNumTotalDBRows))
{
$oKPI = new ExecutionKPI();
$sSQL = $this->m_oFilter->MakeSelectQuery(array(), $this->m_aArgs, null, null, 0, 0, true);
$resQuery = CMDBSource::Query($sSQL);
$sOQL = $this->GetPseudoOQL($this->m_oFilter, array(), 0, 0, true);
$oKPI->ComputeStats('OQL Query Exec', $sOQL);
if (!$resQuery) return 0;
$aRow = CMDBSource::FetchArray($resQuery);
@@ -858,6 +865,42 @@ class DBObjectSet implements iDBObjectSetIterator
return $this->m_iNumTotalDBRows + count($this->m_aAddedObjects); // Does it fix Trac #887 ??
}
/**
* @param \DBSearch $oFilter
* @param array $aOrder
* @param int $iLimitCount
* @param int $iLimitStart
* @param bool $bCount
*
* @return string
*/
private function GetPseudoOQL($oFilter, $aOrder, $iLimitCount, $iLimitStart, $bCount)
{
$sOQL = '';
if ($bCount) {
$sOQL .= 'COUNT ';
}
$sOQL .= $oFilter->ToOQL();
if ($iLimitCount > 0) {
$sOQL .= ' LIMIT ';
if ($iLimitStart > 0) {
$sOQL .= "$iLimitStart, ";
}
$sOQL .= "$iLimitCount";
}
if (count($aOrder) > 0) {
$sOQL .= ' ORDER BY ';
$aOrderBy = [];
foreach ($aOrder as $sAttCode => $bAsc) {
$aOrderBy[] = $sAttCode.' '.($bAsc ? 'ASC' : 'DESC');
}
$sOQL .= implode(', ', $aOrderBy);
}
return $sOQL;
}
/**
* Check if the count exceeds a given limit
*
@@ -874,8 +917,11 @@ class DBObjectSet implements iDBObjectSetIterator
{
if (is_null($this->m_iNumTotalDBRows))
{
$oKPI = new ExecutionKPI();
$sSQL = $this->m_oFilter->MakeSelectQuery(array(), $this->m_aArgs, null, null, $iLimit + 2, 0, true);
$resQuery = CMDBSource::Query($sSQL);
$sOQL = $this->GetPseudoOQL($this->m_oFilter, array(), $iLimit + 2, 0, true);
$oKPI->ComputeStats('OQL Query Exec', $sOQL);
if ($resQuery)
{
$aRow = CMDBSource::FetchArray($resQuery);
@@ -886,7 +932,7 @@ class DBObjectSet implements iDBObjectSetIterator
{
$iCount = 0;
}
}
}
else
{
$iCount = $this->m_iNumTotalDBRows;
@@ -911,8 +957,11 @@ class DBObjectSet implements iDBObjectSetIterator
{
if (is_null($this->m_iNumTotalDBRows))
{
$oKPI = new ExecutionKPI();
$sSQL = $this->m_oFilter->MakeSelectQuery(array(), $this->m_aArgs, null, null, $iLimit + 2, 0, true);
$resQuery = CMDBSource::Query($sSQL);
$sOQL = $this->GetPseudoOQL($this->m_oFilter, array(), $iLimit + 2, 0, true);
$oKPI->ComputeStats('OQL Query Exec', $sOQL);
if ($resQuery)
{
$aRow = CMDBSource::FetchArray($resQuery);
@@ -923,7 +972,7 @@ class DBObjectSet implements iDBObjectSetIterator
{
$iCount = 0;
}
}
}
else
{
$iCount = $this->m_iNumTotalDBRows;

View File

@@ -18,23 +18,6 @@
*/
$bUseLegacyDBSearch = utils::GetConfig()->Get('use_legacy_dbsearch');
if ($bUseLegacyDBSearch)
{
// excluded from autoload
require_once (APPROOT.'core/legacy/querybuilderexpressionslegacy.class.inc.php');
require_once (APPROOT.'core/legacy/querybuildercontextlegacy.class.inc.php');
require_once(APPROOT.'core/legacy/dbobjectsearchlegacy.class.php');
}
else
{
// excluded from autoload
require_once (APPROOT.'core/querybuilderexpressions.class.inc.php');
require_once (APPROOT.'core/querybuildercontext.class.inc.php');
require_once(APPROOT.'core/dbobjectsearch.class.php');
}
/**
* An object search
*
@@ -63,22 +46,23 @@ else
abstract class DBSearch
{
/** @internal */
/** @internal */
const JOIN_POINTING_TO = 0;
/** @internal */
/** @internal */
const JOIN_REFERENCED_BY = 1;
protected $m_bNoContextParameters = false;
/** @var array For {@see iQueryModifier} impl */
protected $m_aModifierProperties = array();
protected $m_bArchiveMode = false;
protected $m_bShowObsoleteData = true;
/**
* DBSearch constructor.
*
* @api
* @see DBSearch::FromOQL()
*/
/**
* DBSearch constructor.
*
* @api
* @see DBSearch::FromOQL()
*/
public function __construct()
{
$this->Init();
@@ -789,14 +773,14 @@ abstract class DBSearch
* @see DBSearch::ToOQL()
*
* @param string $sQuery The OQL to convert to a DBSearch
* @param mixed[string] $aParams array of <mixed> params index by <string> name
* @param array $aParams array of <mixed> params index by <string> name
* @param ModelReflection|null $oMetaModel The MetaModel to use when checking the consistency of the OQL
*
* @return DBObjectSearch|DBUnionSearch
*
* @throws OQLException
*/
static public function FromOQL($sQuery, $aParams = null, ModelReflection $oMetaModel=null)
public static function FromOQL($sQuery, $aParams = null, ModelReflection $oMetaModel=null)
{
if (empty($sQuery))
{
@@ -901,11 +885,11 @@ abstract class DBSearch
return;
}
if (count($aColumns) == 0)
{
$aColumns = array_keys(MetaModel::ListAttributeDefs($this->GetClass()));
// Add the standard id (as first column)
array_unshift($aColumns, 'id');
if (count($aColumns) == 0)
{
$aColumns = array_keys(MetaModel::ListAttributeDefs($this->GetClass()));
// Add the standard id (as first column)
array_unshift($aColumns, 'id');
}
$aQueryCols = CMDBSource::GetColumns($resQuery, $sSQL);
@@ -935,6 +919,55 @@ abstract class DBSearch
return $aRes;
}
/**
* Selects a column ($sAttCode) from the specified class ($sClassAlias - default main class) of the DBsearch object and gives the result as an array
* @param string $sAttCode
* @param string|null $sClassAlias
*
* @return array
* @throws ConfigException
* @throws CoreException
* @throws MissingQueryArgument
* @throws MySQLException
* @throws MySQLHasGoneAwayException
*/
public function SelectAttributeToArray(string $sAttCode, ?string $sClassAlias = null):array
{
if(is_null($sClassAlias)) {
$sClassAlias = $this->GetClassAlias();
}
$sClass = $this->GetClass();
if($sAttCode === 'id'){
$aAttToLoad[$sClassAlias]=[];
} else {
$aAttToLoad[$sClassAlias][$sAttCode] = MetaModel::GetAttributeDef($sClass, $sAttCode);
}
$sSQL = $this->MakeSelectQuery([], [], $aAttToLoad);
$resQuery = CMDBSource::Query($sSQL);
if (!$resQuery)
{
return [];
}
$sColName = $sClassAlias.$sAttCode;
$aRes = [];
while ($aRow = CMDBSource::FetchArray($resQuery))
{
$aMappedRow = array();
if($sAttCode === 'id') {
$aMappedRow[$sAttCode] = $aRow[$sColName];
} else {
$aMappedRow[$sAttCode] = $aAttToLoad[$sClassAlias][$sAttCode]->FromSQLToValue($aRow, $sColName);
}
$aRes[] = $aMappedRow;
}
CMDBSource::FreeResult($resQuery);
return $aRes;
}
////////////////////////////////////////////////////////////////////////////
//
// Construction of the SQL queries
@@ -1658,7 +1691,7 @@ abstract class DBSearch
$oSet = new DBObjectSet($this);
if (MetaModel::IsStandaloneClass($sClass))
{
$oSet->OptimizeColumnLoad(array($this->GetClassAlias() => array('')));
$oSet->OptimizeColumnLoad(array($this->GetClassAlias() => array()));
$aIds = array($sClass => $oSet->GetColumnAsArray('id'));
}
else
@@ -1723,4 +1756,16 @@ abstract class DBSearch
{
$this->SetShowObsoleteData(utils::ShowObsoleteData());
}
/**
* To ease the debug of filters
* @internal
*
* @return string
*
*/
public function __toString()
{
return $this->ToOQL(true);
}
}

View File

@@ -416,7 +416,11 @@ class DBUnionSearch extends DBSearch
$aSearches = array();
foreach ($this->aSearches as $oSearch)
{
$aSearches[] = $oSearch->Filter($sClassAlias, $oFilter);
if (!$oSearch->IsAllDataAllowed()) {
$aSearches[] = $oSearch->Filter($sClassAlias, $oFilter);
} else {
$aSearches[] = $oSearch;
}
}
return new DBUnionSearch($aSearches);
}

View File

@@ -242,7 +242,7 @@ class DeletionPlan
public function SetDeletionIssues($oObject, $aIssues, $bSecurityIssue)
{
if (count($aIssues) > 0)
if (count($aIssues ?? []) > 0)
{
$sClass = get_class($oObject);
$iId = $oObject->GetKey();

View File

@@ -26,8 +26,10 @@
namespace Combodo\iTop;
use \DOMDocument;
use \DOMFormatException;
use DOMDocument;
use DOMFormatException;
use IssueLog;
use LogAPI;
/**
* Class \Combodo\iTop\DesignDocument
@@ -64,9 +66,13 @@ class DesignDocument extends DOMDocument
* @param $filename
* @param int $options
*/
public function load($filename, $options = 0)
public function load($filename, $options = null)
{
parent::load($filename, LIBXML_NOBLANKS);
libxml_clear_errors();
if (parent::load($filename, LIBXML_NOBLANKS) === false) {
$aErrors = libxml_get_errors();
IssueLog::Error("Error loading $filename", LogAPI::CHANNEL_DEFAULT, $aErrors);
}
}
/**
@@ -77,10 +83,10 @@ class DesignDocument extends DOMDocument
*
* @return int
*/
public function save($filename, $options = 0)
public function save($filename, $options = null)
{
$this->documentElement->setAttribute('xmlns:xsi', "http://www.w3.org/2001/XMLSchema-instance");
return parent::save($filename, LIBXML_NOBLANKS);
return parent::save($filename);
}
/**

View File

@@ -3,7 +3,7 @@
//
// This file is part of iTop.
//
// iTop is free software; you can redistribute it and/or modify
// iTop is free software; you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
@@ -35,6 +35,8 @@ class Dict
protected static $m_aLanguages = array(); // array( code => array( 'description' => '...', 'localized_description' => '...') ...)
protected static $m_aData = array();
protected static $m_sApplicationPrefix = null;
/** @var \ApcService $m_oApcService */
protected static $m_oApcService = null;
/**
* @param $sLanguageCode
@@ -54,10 +56,11 @@ class Dict
* @param $sLanguageCode
*
* @throws \DictExceptionUnknownLanguage
* @since 3.0.4 3.1.1 3.2.0 Param $sLanguageCode becomes nullable
*/
public static function SetUserLanguage($sLanguageCode)
public static function SetUserLanguage($sLanguageCode = null)
{
if (!array_key_exists($sLanguageCode, self::$m_aLanguages))
if (!is_null($sLanguageCode) && !array_key_exists($sLanguageCode, self::$m_aLanguages))
{
throw new DictExceptionUnknownLanguage($sLanguageCode);
}
@@ -113,50 +116,69 @@ class Dict
* @return string
*/
public static function S($sStringCode, $sDefault = null, $bUserLanguageOnly = false)
{
$aInfo = self::GetLabelAndLangCode($sStringCode, $sDefault, $bUserLanguageOnly);
return $aInfo['label'];
}
/**
* Returns a localised string from the dictonary with its associated lang code
*
* @param string $sStringCode The code identifying the dictionary entry
* @param string $sDefault Default value if there is no match in the dictionary
* @param bool $bUserLanguageOnly True to allow the use of the default language as a fallback, false otherwise
*
* @return array{
* lang: string, label: string
* } with localized label string and used lang code
*/
private static function GetLabelAndLangCode($sStringCode, $sDefault = null, $bUserLanguageOnly = false)
{
// Attempt to find the string in the user language
//
self::InitLangIfNeeded(self::GetUserLanguage());
$sLangCode = self::GetUserLanguage();
self::InitLangIfNeeded($sLangCode);
if (!array_key_exists(self::GetUserLanguage(), self::$m_aData))
if (! array_key_exists($sLangCode, self::$m_aData))
{
IssueLog::Warning("Cannot find $sLangCode in all registered dictionaries.");
// It may happen, when something happens before the dictionaries get loaded
return $sStringCode;
return [ 'label' => $sStringCode, 'lang' => $sLangCode ];
}
$aCurrentDictionary = self::$m_aData[self::GetUserLanguage()];
if (array_key_exists($sStringCode, $aCurrentDictionary))
$aCurrentDictionary = self::$m_aData[$sLangCode];
if (is_array($aCurrentDictionary) && array_key_exists($sStringCode, $aCurrentDictionary))
{
return $aCurrentDictionary[$sStringCode];
return [ 'label' => $aCurrentDictionary[$sStringCode], 'lang' => $sLangCode ];
}
if (!$bUserLanguageOnly)
{
// Attempt to find the string in the default language
//
self::InitLangIfNeeded(self::$m_sDefaultLanguage);
$aDefaultDictionary = self::$m_aData[self::$m_sDefaultLanguage];
if (array_key_exists($sStringCode, $aDefaultDictionary))
if (is_array($aDefaultDictionary) && array_key_exists($sStringCode, $aDefaultDictionary))
{
return $aDefaultDictionary[$sStringCode];
return [ 'label' => $aDefaultDictionary[$sStringCode], 'lang' => self::$m_sDefaultLanguage ];
}
// Attempt to find the string in english
//
self::InitLangIfNeeded('EN US');
$aDefaultDictionary = self::$m_aData['EN US'];
if (array_key_exists($sStringCode, $aDefaultDictionary))
if (is_array($aDefaultDictionary) && array_key_exists($sStringCode, $aDefaultDictionary))
{
return $aDefaultDictionary[$sStringCode];
return [ 'label' => $aDefaultDictionary[$sStringCode], 'lang' => 'EN US' ];
}
}
// Could not find the string...
//
if (is_null($sDefault))
{
return $sStringCode;
return [ 'label' => $sStringCode, 'lang' => null ];
}
return $sDefault;
return [ 'label' => $sDefault, 'lang' => null ];
}
@@ -172,19 +194,25 @@ class Dict
*/
public static function Format($sFormatCode /*, ... arguments ....*/)
{
$sLocalizedFormat = self::S($sFormatCode);
['label' => $sLocalizedFormat, 'lang' => $sLangCode] = self::GetLabelAndLangCode($sFormatCode);
$aArguments = func_get_args();
array_shift($aArguments);
if ($sLocalizedFormat == $sFormatCode)
{
// Make sure the information will be displayed (ex: an error occuring before the dictionary gets loaded)
return $sFormatCode.' - '.implode(', ', $aArguments);
}
return vsprintf($sLocalizedFormat, $aArguments);
try{
return vsprintf($sLocalizedFormat, $aArguments);
} catch(\Throwable $e){
\IssueLog::Error("Cannot format dict key", null, ["sFormatCode" => $sFormatCode, "sLangCode" => $sLangCode, 'exception_msg' => $e->getMessage() ]);
return $sFormatCode.' - '.implode(', ', $aArguments);
}
}
/**
* Initialize a the entries for a given language (replaces the former Add() method)
* @param string $sLanguageCode Code identifying the language i.e. 'FR-FR', 'EN-US'
@@ -194,7 +222,7 @@ class Dict
{
self::$m_aData[$sLanguageCode] = $aEntries;
}
/**
* Set the list of available languages
* @param hash $aLanguagesList
@@ -203,7 +231,26 @@ class Dict
{
self::$m_aLanguages = $aLanguagesList;
}
/**
* @since 2.7.6 N°4125
* @return \ApcService
*/
public static function GetApcService() {
if (self::$m_oApcService === null){
self::$m_oApcService = new ApcService();
}
return self::$m_oApcService;
}
/**
* @since 2.7.6 N°4125
* @param \ApcService $m_oApcService
*/
public static function SetApcService($oApcService) {
self::$m_oApcService = $oApcService;
}
/**
* Load a language from the language dictionary, if not already loaded
* @param string $sLangCode Language code
@@ -212,20 +259,23 @@ class Dict
public static function InitLangIfNeeded($sLangCode)
{
if (array_key_exists($sLangCode, self::$m_aData)) return true;
$bResult = false;
if (function_exists('apc_fetch') && (self::$m_sApplicationPrefix !== null))
if (self::GetApcService()->function_exists('apc_fetch')
&& (self::$m_sApplicationPrefix !== null))
{
// Note: For versions of APC older than 3.0.17, fetch() accepts only one parameter
//
self::$m_aData[$sLangCode] = apc_fetch(self::$m_sApplicationPrefix.'-dict-'.$sLangCode);
if (self::$m_aData[$sLangCode] === false)
{
self::$m_aData[$sLangCode] = self::GetApcService()->apc_fetch(self::$m_sApplicationPrefix.'-dict-'.$sLangCode);
if (self::$m_aData[$sLangCode] === false) {
unset(self::$m_aData[$sLangCode]);
}
else
{
} else if (! is_array(self::$m_aData[$sLangCode])) {
// N°4125: we dont fix dictionnary corrupted cache (on iTop side).
// but we log an error in a dedicated channel to let itop administrator be aware of a potential APCu issue to fix.
IssueLog::Error("APCu corrupted data (with $sLangCode dictionnary). APCu configuration and running version should be troubleshooted...", LogChannels::APC);
$bResult = true;
} else {
$bResult = true;
}
}
@@ -233,16 +283,17 @@ class Dict
{
$sDictFile = APPROOT.'env-'.utils::GetCurrentEnvironment().'/dictionaries/'.str_replace(' ', '-', strtolower($sLangCode)).'.dict.php';
require_once($sDictFile);
if (function_exists('apc_store') && (self::$m_sApplicationPrefix !== null))
if (self::GetApcService()->function_exists('apc_store')
&& (self::$m_sApplicationPrefix !== null))
{
apc_store(self::$m_sApplicationPrefix.'-dict-'.$sLangCode, self::$m_aData[$sLangCode]);
self::GetApcService()->apc_store(self::$m_sApplicationPrefix.'-dict-'.$sLangCode, self::$m_aData[$sLangCode]);
}
$bResult = true;
}
return $bResult;
}
/**
* Enable caching (cached using APC)
* @param string $sApplicationPrefix The prefix for uniquely identiying this iTop instance
@@ -275,25 +326,24 @@ class Dict
*
* @param $sSourceCode
* @param $sDestCode
* @since 3.0.1 Not clone sSourceCode entry if sDestCode entry already exist
*/
public static function CloneString($sSourceCode, $sDestCode)
{
foreach(self::$m_aLanguages as $sLanguageCode => $foo)
{
if (isset(self::$m_aData[$sLanguageCode][$sSourceCode]))
{
foreach(self::$m_aLanguages as $sLanguageCode => $foo) {
if (isset(self::$m_aData[$sLanguageCode][$sSourceCode]) && !isset(self::$m_aData[$sLanguageCode][$sDestCode] )) {
self::$m_aData[$sLanguageCode][$sDestCode] = self::$m_aData[$sLanguageCode][$sSourceCode];
}
}
}
public static function MakeStats($sLanguageCode, $sLanguageRef = 'EN US')
{
$aMissing = array(); // Strings missing for the target language
$aUnexpected = array(); // Strings defined for the target language, but not found in the reference dictionary
$aNotTranslated = array(); // Strings having the same value in both dictionaries
$aOK = array(); // Strings having different values in both dictionaries
foreach (self::$m_aData[$sLanguageRef] as $sStringCode => $sValue)
{
if (!array_key_exists($sStringCode, self::$m_aData[$sLanguageCode]))
@@ -301,7 +351,7 @@ class Dict
$aMissing[$sStringCode] = $sValue;
}
}
foreach (self::$m_aData[$sLanguageCode] as $sStringCode => $sValue)
{
if (!array_key_exists($sStringCode, self::$m_aData[$sLanguageRef]))
@@ -324,7 +374,7 @@ class Dict
}
return array($aMissing, $aUnexpected, $aNotTranslated, $aOK);
}
public static function Dump()
{
MyHelpers::var_dump_html(self::$m_aData);
@@ -347,7 +397,7 @@ class Dict
// No need to actually load the strings since it's only used to know the list of languages
// at setup time !!
}
/**
* Export all the dictionary entries - of the given language - whose code matches the given prefix
* missing entries in the current language will be replaced by entries in the default language
@@ -360,7 +410,7 @@ class Dict
self::InitLangIfNeeded(self::$m_sDefaultLanguage);
$aEntries = array();
$iLength = strlen($sStartingWith);
// First prefill the array with entries from the default language
foreach(self::$m_aData[self::$m_sDefaultLanguage] as $sCode => $sEntry)
{
@@ -369,7 +419,7 @@ class Dict
$aEntries[$sCode] = $sEntry;
}
}
// Now put (overwrite) the entries for the user language
foreach(self::$m_aData[self::GetUserLanguage()] as $sCode => $sEntry)
{

File diff suppressed because it is too large Load Diff

View File

@@ -1,5 +1,5 @@
<?php
// Copyright (C) 2010-2021 Combodo SARL
// Copyright (C) 2010-2022 Combodo SARL
//
// This file is part of iTop.
//
@@ -20,10 +20,13 @@
/**
* Send an email (abstraction for synchronous/asynchronous modes)
*
* @copyright Copyright (C) 2010-2021 Combodo SARL
* @copyright Copyright (C) 2010-2022 Combodo SARL
* @license http://opensource.org/licenses/AGPL-3.0
*/
use Combodo\iTop\Core\Email\EmailFactory;
use Combodo\iTop\Core\Email\iEMail;
Swift_Preferences::getInstance()->setCharset('UTF-8');
@@ -31,31 +34,61 @@ define ('EMAIL_SEND_OK', 0);
define ('EMAIL_SEND_PENDING', 1);
define ('EMAIL_SEND_ERROR', 2);
class EMail
class EMail implements iEMail
{
/**
* @see self::LoadConfig()
* @var Config
* @since 2.7.7 3.0.2 3.1.0 N°3169 N°5102 Move attribute to children classes
* @since 2.7.8 3.0.3 3.1.0 N°4947 pull up the attribute back to the Email class as config init is done here
*/
protected static $m_oConfig = null;
protected $oMailer;
// Serialization formats
const ORIGINAL_FORMAT = 1; // Original format, consisting in serializing the whole object, inculding the Swift Mailer's object.
// Did not work with attachements since their binary representation cannot be stored as a valid UTF-8 string
// Did not work with attachements since their binary representation cannot be stored as a valid UTF-8 string
const FORMAT_V2 = 2; // New format, only the raw data are serialized (base64 encoded if needed)
protected static $m_oConfig = null;
protected $m_aData; // For storing data to serialize
public function LoadConfig($sConfigFile = ITOP_DEFAULT_CONFIG_FILE)
{
if (is_null(self::$m_oConfig))
{
self::$m_oConfig = new Config($sConfigFile);
}
}
protected $m_oMessage;
public function __construct()
{
$this->m_aData = array();
$this->m_oMessage = Swift_Message::newInstance();
$this->SetRecipientFrom(MetaModel::GetConfig()->Get('email_default_sender_address'), MetaModel::GetConfig()->Get('email_default_sender_label'));
$this->oMailer = EmailFactory::GetMailer();
}
/**
* Sets {@see m_oConfig} if current attribute is null
*
* @returns \Config the current {@see m_oConfig} value
* @throws \ConfigException
* @throws \CoreException
*
* @uses utils::GetConfig()
*
* @since 2.7.7 3.0.2 3.1.0 N°3169 N°5102 Move method to children classes
* @since 2.7.8 3.0.3 3.1.0 N°4947 Pull up to the parent class, and remove `$sConfigFile` param
*/
public function LoadConfig()
{
if (is_null(static::$m_oConfig)) {
static::$m_oConfig = utils::GetConfig();
}
return static::$m_oConfig;
}
/**
* @return void
* @throws \ConfigException
* @throws \CoreException
* @since 2.7.8 3.0.3 3.1.0 N°4947 Method creation, to factorize same code in children classes
*/
protected function InitRecipientFrom()
{
$oConfig = $this->LoadConfig();
$this->SetRecipientFrom(
$oConfig->Get('email_default_sender_address'),
$oConfig->Get('email_default_sender_label')
);
}
/**
@@ -66,489 +99,110 @@ class EMail
*/
public function SerializeV2()
{
return serialize($this->m_aData);
return $this->oMailer->SerializeV2();
}
/**
* Custom de-serialization method
*
* @param string $sSerializedMessage The serialized representation of the message
*
* @return \Email
* @throws \ArchivedObjectException
* @throws \CoreException
* @throws \Symfony\Component\CssSelector\Exception\SyntaxErrorException
*/
static public function UnSerializeV2($sSerializedMessage)
{
$aData = unserialize($sSerializedMessage);
$oMessage = new Email();
if (array_key_exists('body', $aData))
{
$oMessage->SetBody($aData['body']['body'], $aData['body']['mimeType']);
}
if (array_key_exists('message_id', $aData))
{
$oMessage->SetMessageId($aData['message_id']);
}
if (array_key_exists('bcc', $aData))
{
$oMessage->SetRecipientBCC($aData['bcc']);
}
if (array_key_exists('cc', $aData))
{
$oMessage->SetRecipientCC($aData['cc']);
}
if (array_key_exists('from', $aData))
{
$oMessage->SetRecipientFrom($aData['from']['address'], $aData['from']['label']);
}
if (array_key_exists('reply_to', $aData))
{
$oMessage->SetRecipientReplyTo($aData['reply_to']['address'], $aData['reply_to']['label']);
}
if (array_key_exists('to', $aData))
{
$oMessage->SetRecipientTO($aData['to']);
}
if (array_key_exists('subject', $aData))
{
$oMessage->SetSubject($aData['subject']);
}
if (array_key_exists('headers', $aData))
{
foreach($aData['headers'] as $sKey => $sValue)
{
$oMessage->AddToHeader($sKey, $sValue);
}
}
if (array_key_exists('parts', $aData))
{
foreach($aData['parts'] as $aPart)
{
$oMessage->AddPart($aPart['text'], $aPart['mimeType']);
}
}
if (array_key_exists('attachments', $aData))
{
foreach($aData['attachments'] as $aAttachment)
{
$oMessage->AddAttachment(base64_decode($aAttachment['data']), $aAttachment['filename'], $aAttachment['mimeType']);
}
}
return $oMessage;
}
protected function SendAsynchronous(&$aIssues, $oLog = null)
{
try
{
AsyncSendEmail::AddToQueue($this, $oLog);
}
catch(Exception $e)
{
$aIssues = array($e->GetMessage());
return EMAIL_SEND_ERROR;
}
$aIssues = array();
return EMAIL_SEND_PENDING;
}
protected function SendSynchronous(&$aIssues, $oLog = null)
{
// If the body of the message is in HTML, embed all images based on attachments
$this->EmbedInlineImages();
$this->LoadConfig();
$sTransport = self::$m_oConfig->Get('email_transport');
switch ($sTransport)
{
case 'SMTP':
$sHost = self::$m_oConfig->Get('email_transport_smtp.host');
$sPort = self::$m_oConfig->Get('email_transport_smtp.port');
$sEncryption = self::$m_oConfig->Get('email_transport_smtp.encryption');
$sUserName = self::$m_oConfig->Get('email_transport_smtp.username');
$sPassword = self::$m_oConfig->Get('email_transport_smtp.password');
$oTransport = Swift_SmtpTransport::newInstance($sHost, $sPort, $sEncryption);
if (strlen($sUserName) > 0)
{
$oTransport->setUsername($sUserName);
$oTransport->setPassword($sPassword);
}
break;
case 'Null':
$oTransport = Swift_NullTransport::newInstance();
break;
case 'LogFile':
$oTransport = Swift_LogFileTransport::newInstance();
$oTransport->setLogFile(APPROOT.'log/mail.log');
break;
case 'PHPMail':
default:
$oTransport = Swift_MailTransport::newInstance();
}
$oMailer = Swift_Mailer::newInstance($oTransport);
$aFailedRecipients = array();
$this->m_oMessage->setMaxLineLength(0);
$oKPI = new ExecutionKPI();
try
{
$iSent = $oMailer->send($this->m_oMessage, $aFailedRecipients);
if ($iSent === 0)
{
// Beware: it seems that $aFailedRecipients sometimes contains the recipients that actually received the message !!!
IssueLog::Warning('Email sending failed: Some recipients were invalid, aFailedRecipients contains: '.implode(', ', $aFailedRecipients));
$aIssues = array('Some recipients were invalid.');
$oKPI->ComputeStats('Email Sent', 'Error received');
return EMAIL_SEND_ERROR;
}
else
{
$aIssues = array();
$oKPI->ComputeStats('Email Sent', 'Succeded');
return EMAIL_SEND_OK;
}
}
catch (Exception $e)
{
$oKPI->ComputeStats('Email Sent', 'Error received');
throw $e;
}
}
/**
* Reprocess the body of the message (if it is an HTML message)
* to replace the URL of images based on attachments by a link
* to an embedded image (i.e. cid:....)
*/
protected function EmbedInlineImages()
{
if ($this->m_aData['body']['mimeType'] == 'text/html')
{
$oDOMDoc = new DOMDocument();
$oDOMDoc->preserveWhitespace = true;
@$oDOMDoc->loadHTML('<?xml encoding="UTF-8"?>'.$this->m_aData['body']['body']); // For loading HTML chunks where the character set is not specified
$oXPath = new DOMXPath($oDOMDoc);
$sXPath = '//img[@'.InlineImage::DOM_ATTR_ID.']';
$oImagesList = $oXPath->query($sXPath);
if ($oImagesList->length != 0)
{
foreach($oImagesList as $oImg)
{
$iAttId = $oImg->getAttribute(InlineImage::DOM_ATTR_ID);
$oAttachment = MetaModel::GetObject('InlineImage', $iAttId, false, true /* Allow All Data */);
if ($oAttachment)
{
$sImageSecret = $oImg->getAttribute('data-img-secret');
$sAttachmentSecret = $oAttachment->Get('secret');
if ($sImageSecret !== $sAttachmentSecret)
{
// @see N°1921
// If copying from another iTop we could get an IMG pointing to an InlineImage with wrong secret
continue;
}
$oDoc = $oAttachment->Get('contents');
$oSwiftImage = new Swift_Image($oDoc->GetData(), $oDoc->GetFileName(), $oDoc->GetMimeType());
$sCid = $this->m_oMessage->embed($oSwiftImage);
$oImg->setAttribute('src', $sCid);
}
}
}
$sHtmlBody = $oDOMDoc->saveHTML();
$this->m_oMessage->setBody($sHtmlBody, 'text/html', 'UTF-8');
}
return EmailFactory::GetMailer()::UnSerializeV2($sSerializedMessage);
}
public function Send(&$aIssues, $bForceSynchronous = false, $oLog = null)
{
//select a default sender if none is provided.
if(empty($this->m_aData['from']['address']) && !empty($this->m_aData['to'])){
$this->SetRecipientFrom($this->m_aData['to']);
}
if ($bForceSynchronous)
{
return $this->SendSynchronous($aIssues, $oLog);
}
else
{
$bConfigASYNC = MetaModel::GetConfig()->Get('email_asynchronous');
if ($bConfigASYNC)
{
return $this->SendAsynchronous($aIssues, $oLog);
}
else
{
return $this->SendSynchronous($aIssues, $oLog);
}
}
return $this->oMailer->Send($aIssues, $bForceSynchronous, $oLog);
}
public function AddToHeader($sKey, $sValue)
{
if (!array_key_exists('headers', $this->m_aData))
{
$this->m_aData['headers'] = array();
}
$this->m_aData['headers'][$sKey] = $sValue;
if (strlen($sValue) > 0)
{
$oHeaders = $this->m_oMessage->getHeaders();
switch(strtolower($sKey))
{
case 'return-path':
$this->m_oMessage->setReturnPath($sValue);
break;
default:
$oHeaders->addTextHeader($sKey, $sValue);
}
}
$this->oMailer->AddToHeader($sKey, $sValue);
}
public function SetMessageId($sId)
{
$this->m_aData['message_id'] = $sId;
// Note: Swift will add the angle brackets for you
// so let's remove the angle brackets if present, for historical reasons
$sId = str_replace(array('<', '>'), '', $sId);
$oMsgId = $this->m_oMessage->getHeaders()->get('Message-ID');
$oMsgId->SetId($sId);
$this->oMailer->SetMessageId($sId);
}
public function SetReferences($sReferences)
{
$this->AddToHeader('References', $sReferences);
$this->oMailer->SetReferences($sReferences);
}
/**
* Set the "In-Reply-To" header to allow emails to group as a conversation in modern mail clients (GMail, Outlook 2016+, ...)
*
* @link https://en.wikipedia.org/wiki/Email#Header_fields
*
* @param string $sMessageId
*
* @since 3.0.1 N°4849
*/
public function SetInReplyTo(string $sMessageId)
{
$this->AddToHeader('In-Reply-To', $sMessageId);
}
public function SetBody($sBody, $sMimeType = 'text/html', $sCustomStyles = null)
{
if (($sMimeType === 'text/html') && ($sCustomStyles !== null))
{
$emogrifier = new \Pelago\Emogrifier($sBody, $sCustomStyles);
$sBody = $emogrifier->emogrify(); // Adds html/body tags if not already present
}
$this->m_aData['body'] = array('body' => $sBody, 'mimeType' => $sMimeType);
$this->m_oMessage->setBody($sBody, $sMimeType);
$this->oMailer->SetBody($sBody, $sMimeType, $sCustomStyles);
}
public function AddPart($sText, $sMimeType = 'text/html')
{
if (!array_key_exists('parts', $this->m_aData))
{
$this->m_aData['parts'] = array();
}
$this->m_aData['parts'][] = array('text' => $sText, 'mimeType' => $sMimeType);
$this->m_oMessage->addPart($sText, $sMimeType);
$this->oMailer->AddPart($sText, $sMimeType);
}
public function AddAttachment($data, $sFileName, $sMimeType)
{
if (!array_key_exists('attachments', $this->m_aData))
{
$this->m_aData['attachments'] = array();
}
$this->m_aData['attachments'][] = array('data' => base64_encode($data), 'filename' => $sFileName, 'mimeType' => $sMimeType);
$this->m_oMessage->attach(Swift_Attachment::newInstance($data, $sFileName, $sMimeType));
$this->oMailer->AddAttachment($data, $sFileName, $sMimeType);
}
public function SetSubject($sSubject)
{
$this->m_aData['subject'] = $sSubject;
$this->m_oMessage->setSubject($sSubject);
$this->oMailer->SetSubject($sSubject);
}
public function GetSubject()
{
return $this->m_oMessage->getSubject();
return $this->oMailer->GetSubject();
}
/**
* Helper to transform and sanitize addresses
* - get rid of empty addresses
*/
protected function AddressStringToArray($sAddressCSVList)
{
$aAddresses = array();
foreach(explode(',', $sAddressCSVList) as $sAddress)
{
$sAddress = trim($sAddress);
if (strlen($sAddress) > 0)
{
$aAddresses[] = $sAddress;
}
}
return $aAddresses;
}
public function SetRecipientTO($sAddress)
{
$this->m_aData['to'] = $sAddress;
if (!empty($sAddress))
{
$aAddresses = $this->AddressStringToArray($sAddress);
$this->m_oMessage->setTo($aAddresses);
}
$this->oMailer->SetRecipientTO($sAddress);
}
public function GetRecipientTO($bAsString = false)
{
$aRes = $this->m_oMessage->getTo();
if ($aRes === null)
{
// There is no "To" header field
$aRes = array();
}
if ($bAsString)
{
$aStrings = array();
foreach ($aRes as $sEmail => $sName)
{
if (is_null($sName))
{
$aStrings[] = $sEmail;
}
else
{
$sName = str_replace(array('<', '>'), '', $sName);
$aStrings[] = "$sName <$sEmail>";
}
}
return implode(', ', $aStrings);
}
else
{
return $aRes;
}
return $this->oMailer->GetRecipientTO($bAsString);
}
public function SetRecipientCC($sAddress)
{
$this->m_aData['cc'] = $sAddress;
if (!empty($sAddress))
{
$aAddresses = $this->AddressStringToArray($sAddress);
$this->m_oMessage->setCc($aAddresses);
}
$this->oMailer->SetRecipientCC($sAddress);
}
public function SetRecipientBCC($sAddress)
{
$this->m_aData['bcc'] = $sAddress;
if (!empty($sAddress))
{
$aAddresses = $this->AddressStringToArray($sAddress);
$this->m_oMessage->setBcc($aAddresses);
}
$this->oMailer->SetRecipientBCC($sAddress);
}
public function SetRecipientFrom($sAddress, $sLabel = '')
{
$this->m_aData['from'] = array('address' => $sAddress, 'label' => $sLabel);
if ($sLabel != '')
{
$this->m_oMessage->setFrom(array($sAddress => $sLabel));
}
else if (!empty($sAddress))
{
$this->m_oMessage->setFrom($sAddress);
}
$this->oMailer->SetRecipientFrom($sAddress, $sLabel);
}
public function SetRecipientReplyTo($sAddress, $sLabel = '')
{
$this->m_aData['reply_to'] = array('address' => $sAddress, 'label' => $sLabel);
if ($sLabel != '')
{
$this->m_oMessage->setReplyTo(array($sAddress => $sLabel));
}
else if (!empty($sAddress))
{
$this->m_oMessage->setReplyTo($sAddress);
}
}
}
/////////////////////////////////////////////////////////////////////////////////////
/**
* Extension to SwiftMailer: "debug" transport that pretends messages have been sent,
* but just log them to a file.
*
* @package Swift
* @author Denis Flaven
*/
class Swift_Transport_LogFileTransport extends Swift_Transport_NullTransport
{
protected $sLogFile;
/**
* Sends the given message.
*
* @param Swift_Mime_Message $message
* @param string[] $failedRecipients An array of failures by-reference
*
* @return int The number of sent emails
*/
public function send(Swift_Mime_Message $message, &$failedRecipients = null)
{
$hFile = @fopen($this->sLogFile, 'a');
if ($hFile)
{
$sTxt = "================== ".date('Y-m-d H:i:s')." ==================\n";
$sTxt .= $message->toString()."\n";
@fwrite($hFile, $sTxt);
@fclose($hFile);
}
return parent::send($message, $failedRecipients);
}
public function setLogFile($sFilename)
{
$this->sLogFile = $sFilename;
}
}
/**
* Pretends messages have been sent, but just log them to a file.
*
* @package Swift
* @author Denis Flaven
*/
class Swift_LogFileTransport extends Swift_Transport_LogFileTransport
{
/**
* Create a new LogFileTransport.
*/
public function __construct()
{
call_user_func_array(
array($this, 'Swift_Transport_LogFileTransport::__construct'),
Swift_DependencyContainer::getInstance()
->createDependenciesFor('transport.null')
);
}
/**
* Create a new LogFileTransport instance.
*
* @return Swift_LogFileTransport
*/
public static function newInstance()
{
return new self();
$this->oMailer->SetRecipientReplyTo($sAddress);
}
}

View File

@@ -222,6 +222,10 @@ class EventIssue extends Event
//
$this->Set('page', @$GLOBALS['_SERVER']['SCRIPT_NAME']);
if (strlen($this->Get('userinfo')) == 0) {
$this->Set('userinfo', UserRights::GetUserId());
}
if (array_key_exists('_GET', $GLOBALS) && is_array($GLOBALS['_GET']))
{
$this->Set('arguments_get', $GLOBALS['_GET']);

View File

@@ -10,6 +10,7 @@ use Combodo\iTop\Application\UI\Base\Component\Input\InputUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Component\Panel\PanelUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Layout\MultiColumn\Column\ColumnUIBlockFactory;
use Combodo\iTop\Application\UI\Base\Layout\MultiColumn\MultiColumnUIBlockFactory;
use Combodo\iTop\Application\Helper\ExportHelper;
require_once(APPROOT.'application/xlsxwriter.class.php');
@@ -82,6 +83,7 @@ class ExcelBulkExport extends TabularBulkExport
case 'xlsx_options':
$oPanel = PanelUIBlockFactory::MakeNeutral(Dict::S('Core:BulkExport:XLSXOptions'));
$oPanel->AddSubBlock(ExportHelper::GetAlertForExcelMaliciousInjection());
$oMulticolumn = MultiColumnUIBlockFactory::MakeStandard();
$oPanel->AddSubBlock($oMulticolumn);
@@ -111,16 +113,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'); });

Some files were not shown because too many files have changed in this diff Show More