Skip to content

Commit

Permalink
Multiple groups for assets
Browse files Browse the repository at this point in the history
  • Loading branch information
cconard96 committed Apr 30, 2024
1 parent afbfebf commit 2705877
Show file tree
Hide file tree
Showing 60 changed files with 2,208 additions and 597 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ The present file will list all changes made to the project; according to the
- External Links `Link or filename` and `File content` fields now use Twig templates instead of a custom tag syntax.
- Itemtypes associated with External links are now in the main form rather than a separate tab.
- The `Computer_Item` class has been replaced by the `\Glpi\Asset\Asset_PeripheralAsset` class.
- `Group` and `Group in charge` fields for assets may now contain multiple groups.

### Deprecated
- Survey URL tags `TICKETCATEGORY_ID` and `TICKETCATEGORY_NAME` are deprecated and replaced by `ITILCATEGORY_ID` and `ITILCATEGORY_NAME` respectively.
Expand Down Expand Up @@ -136,6 +137,11 @@ The present file will list all changes made to the project; according to the
- `Lock::getLocksQueryInfosByItemType()` has been made private.
- `DBmysql::request()`, `DBmysqlIterator::buildQuery()` and `DBmysqlIterator::execute()` methods signatures changed.
- Some values for the `$type` parameters of several `Stat` methods have changed to match English spelling (technicien -> technician).
- Any class added to `$CFG_GLPI['directconnect_types']` must now use the `Glpi\Features\AssignableItem` trait as multi-group support is required.
- For assets, `groups_id` and `groups_id_tech` fields were changed from integers to arrays and are loaded into the `fields` array after `getFromDB`/`getEmpty`.
If reading directly from the DB, you need to query the new linking table `glpi_groups_items`.
- `Group::getDataItems()` signature changed. The two first parameters `$types` and `$field` were replaced
by a unique boolean `$tech` parameter that is used to compute the `$types` and `$field` values automatically.

#### Deprecated
- Usage of `MAIL_SMTPSSL` and `MAIL_SMTPTLS` constants.
Expand Down
8 changes: 5 additions & 3 deletions inc/define.php
Original file line number Diff line number Diff line change
Expand Up @@ -262,19 +262,21 @@
'SoftwareLicense', 'Certificate', 'Appliance', 'Item_DeviceSimcard', 'Line'
];

// Each type in this array must use the AssignableItem trait to support multiple groups and the expanded read/update permissions
$CFG_GLPI["linkgroup_types"] = ['Computer', 'Monitor', 'NetworkEquipment',
'Peripheral', 'Phone', 'Printer', 'Software',
'SoftwareLicense', 'Certificate', 'Appliance', 'Item_DeviceSimcard', 'Line'
];

$CFG_GLPI["linkuser_tech_types"] = ['Computer', 'ConsumableItem', 'Monitor', 'NetworkEquipment',
'Peripheral', 'Phone', 'Printer', 'Software',
'SoftwareLicense', 'Certificate', 'Appliance', 'DatabaseInstance'
'SoftwareLicense', 'Certificate', 'Appliance', 'DatabaseInstance', 'Enclosure'
];

$CFG_GLPI["linkgroup_tech_types"] = ['Computer', 'ConsumableItem', 'Monitor', 'NetworkEquipment',
// Each type in this array must use the AssignableItem trait to support multiple groups and the expanded read/update permissions
$CFG_GLPI["linkgroup_tech_types"] = ['CartridgeItem', 'Computer', 'ConsumableItem', 'Monitor', 'NetworkEquipment',
'Peripheral', 'Phone', 'Printer', 'Software',
'SoftwareLicense', 'Certificate', 'Appliance', 'DatabaseInstance'
'SoftwareLicense', 'Certificate', 'Appliance', 'DatabaseInstance', 'Enclosure'
];

$CFG_GLPI["location_types"] = ['Budget', 'CartridgeItem', 'ConsumableItem',
Expand Down
71 changes: 10 additions & 61 deletions inc/relation.constant.php
Original file line number Diff line number Diff line change
Expand Up @@ -714,84 +714,24 @@
],

'glpi_groups' => [
'glpi_appliances' => [
'groups_id_tech',
'groups_id',
],
'glpi_assets_assets' => [
'groups_id_tech',
'groups_id',
],
'glpi_cartridgeitems' => 'groups_id_tech',
'glpi_certificates' => [
'groups_id_tech',
'groups_id',
],
'_glpi_changes_groups' => 'groups_id',
'glpi_changetasks' => 'groups_id_tech',
'glpi_clusters' => 'groups_id_tech',
'glpi_computers' => [
'groups_id_tech',
'groups_id',
],
'glpi_consumableitems' => 'groups_id_tech',
'glpi_databaseinstances' => 'groups_id_tech',
'glpi_domains' => 'groups_id_tech',
'glpi_domainrecords' => 'groups_id_tech',
'glpi_enclosures' => 'groups_id_tech',
'glpi_groups' => 'groups_id',
'_glpi_groups_items' => 'groups_id',
'_glpi_groups_knowbaseitems' => 'groups_id',
'_glpi_groups_problems' => 'groups_id',
'_glpi_groups_reminders' => 'groups_id',
'_glpi_groups_rssfeeds' => 'groups_id',
'_glpi_groups_tickets' => 'groups_id',
'_glpi_groups_users' => 'groups_id',
'glpi_items_devicesimcards' => 'groups_id',
'glpi_itilcategories' => 'groups_id',
'glpi_lines' => 'groups_id',
'glpi_monitors' => [
'groups_id_tech',
'groups_id',
],
'glpi_networkequipments' => [
'groups_id_tech',
'groups_id',
],
'glpi_passivedcequipments' => 'groups_id_tech',
'glpi_pdus' => 'groups_id_tech',
'glpi_peripherals' => [
'groups_id_tech',
'groups_id',
],
'glpi_planningexternalevents' => 'groups_id',
'glpi_phones' => [
'groups_id_tech',
'groups_id',
],
'glpi_printers' => [
'groups_id_tech',
'groups_id',
],
'glpi_problemtasks' => 'groups_id_tech',
'glpi_projects' => 'groups_id',
'glpi_racks' => [
'groups_id_tech',
'groups_id',
],
'glpi_softwarelicenses' => [
'groups_id_tech',
'groups_id',
],
'glpi_softwares' => [
'groups_id_tech',
'groups_id',
],
'glpi_tasktemplates' => 'groups_id_tech',
'glpi_tickettasks' => 'groups_id_tech',
'glpi_unmanageds' => [
'groups_id_tech',
'groups_id',
],
'glpi_users' => 'groups_id',
'glpi_itilvalidationtemplates_targets' => 'groups_id',
],
Expand Down Expand Up @@ -1840,3 +1780,12 @@
$define_mapping_entry($source_table, $target_table_key);
$RELATION[$source_table][$target_table_key][] = ['itemtype_asset', 'items_id_asset'];
}

// Multiple groups assignments
$assignable_itemtypes = array_unique(array_merge($CFG_GLPI['linkgroup_types'], $CFG_GLPI['linkgroup_tech_types']));
foreach ($assignable_itemtypes as $assignable_itemtype) {
$source_table_key = $assignable_itemtype::getTable();

$define_mapping_entry($source_table_key, '_glpi_groups_items');
$RELATION[$source_table_key]['_glpi_groups_items'][] = ['itemtype', 'items_id'];
}
17 changes: 4 additions & 13 deletions install/migrations/update_10.0.x_to_11.0.0/assets.php
Original file line number Diff line number Diff line change
Expand Up @@ -86,9 +86,7 @@
`contact` varchar(255) DEFAULT NULL,
`contact_num` varchar(255) DEFAULT NULL,
`users_id` int {$default_key_sign} NOT NULL DEFAULT '0',
`groups_id` int {$default_key_sign} NOT NULL DEFAULT '0',
`users_id_tech` int {$default_key_sign} NOT NULL DEFAULT '0',
`groups_id_tech` int {$default_key_sign} NOT NULL DEFAULT '0',
`locations_id` int {$default_key_sign} NOT NULL DEFAULT '0',
`manufacturers_id` int {$default_key_sign} NOT NULL DEFAULT '0',
`states_id` int {$default_key_sign} NOT NULL DEFAULT '0',
Expand All @@ -105,9 +103,7 @@
KEY `assets_assettypes_id` (`assets_assettypes_id`),
KEY `name` (`name`),
KEY `users_id` (`users_id`),
KEY `groups_id` (`groups_id`),
KEY `users_id_tech` (`users_id_tech`),
KEY `groups_id_tech` (`groups_id_tech`),
KEY `locations_id` (`locations_id`),
KEY `manufacturers_id` (`manufacturers_id`),
KEY `states_id` (`states_id`),
Expand All @@ -128,6 +124,10 @@
$migration->addField('glpi_assets_assets', 'is_template', 'bool');
$migration->addKey('glpi_assets_assets', 'is_template');
$migration->addField('glpi_assets_assets', 'template_name', 'string');
$migration->dropKey('glpi_assets_assets', 'groups_id');
$migration->dropField('glpi_assets_assets', 'groups_id');
$migration->dropKey('glpi_assets_assets', 'groups_id_tech');
$migration->dropField('glpi_assets_assets', 'groups_id_tech');
}

if (!$DB->tableExists('glpi_assets_assetmodels')) {
Expand Down Expand Up @@ -212,12 +212,3 @@
]);
}
}

$assignable_asset_rights = [
'computer', 'monitor', 'software', 'networking', 'printer',
'cartridge', 'consumable', 'phone', 'peripheral'
];
foreach ($assignable_asset_rights as $rightname) {
$migration->addRight($rightname, READ_ASSIGNED, [$rightname => READ]);
$migration->addRight($rightname, UPDATE_ASSIGNED, [$rightname => UPDATE]);
}
199 changes: 199 additions & 0 deletions install/migrations/update_10.0.x_to_11.0.0/assignable_items.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,199 @@
<?php

/**
* ---------------------------------------------------------------------
*
* GLPI - Gestionnaire Libre de Parc Informatique
*
* http://glpi-project.org
*
* @copyright 2015-2024 Teclib' and contributors.
* @copyright 2003-2014 by the INDEPNET Development Team.
* @licence https://www.gnu.org/licenses/gpl-3.0.html
*
* ---------------------------------------------------------------------
*
* LICENSE
*
* This file is part of GLPI.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* ---------------------------------------------------------------------
*/

/**
* @var array $ADDTODISPLAYPREF
* @var DB $DB
* @var Migration $migration
*/

$default_charset = DBConnection::getDefaultCharset();
$default_collation = DBConnection::getDefaultCollation();
$default_key_sign = DBConnection::getDefaultPrimaryKeySignOption();

$assignable_itemtypes = [
'Computer' => [
'table' => 'glpi_computers',
'rightname' => 'computer'
],
'Monitor' => [
'table' => 'glpi_monitors',
'rightname' => 'monitor'
],
'Software' => [
'table' => 'glpi_softwares',
'rightname' => 'software'
],
'NetworkEquipment' => [
'table' => 'glpi_networkequipments',
'rightname' => 'networking'
],
'Printer' => [
'table' => 'glpi_printers',
'rightname' => 'printer'
],
'CartridgeItem' => [
'table' => 'glpi_cartridgeitems',
'rightname' => 'cartridge'
],
'ConsumableItem' => [
'table' => 'glpi_consumableitems',
'rightname' => 'consumable'
],
'Phone' => [
'table' => 'glpi_phones',
'rightname' => 'phone'
],
'Peripheral' => [
'table' => 'glpi_peripherals',
'rightname' => 'peripheral'
],
'SoftwareLicense' => [
'table' => 'glpi_softwarelicenses',
'rightname' => 'license'
],
'Certificate' => [
'table' => 'glpi_certificates',
'rightname' => 'certificate'
],
'Appliance' => [
'table' => 'glpi_appliances',
'rightname' => 'appliance'
],
'Item_DeviceSimcard' => [
'table' => 'glpi_items_devicesimcards',
'rightname' => 'device'
],
'Line' => [
'table' => 'glpi_lines',
'rightname' => 'line'
],
'DatabaseInstance' => [
'table' => 'glpi_databaseinstances',
'rightname' => 'databaseinstance'
],
'Cluster' => [
'table' => 'glpi_clusters',
'rightname' => 'cluster'
],
'Enclosure' => [
'table' => 'glpi_enclosures',
'rightname' => 'datacenter'
],
'Domain' => [
'table' => 'glpi_domains',
'rightname' => 'domain'
],
'DomainRecord' => [
'table' => 'glpi_domainrecords',
'rightname' => 'domain'
],
'Rack' => [
'table' => 'glpi_racks',
'rightname' => 'datacenter'
],
'Unmanaged' => [
'table' => 'glpi_unmanageds',
'rightname' => 'unmanaged'
],
];

if ($DB->tableExists('glpi_groups_assets') && !$DB->tableExists('glpi_groups_items')) {
// dev migration
// TODO Delete before GLPI 11.0 release
$migration->renameTable('glpi_groups_assets', 'glpi_groups_items');
}

if (!$DB->tableExists('glpi_groups_items')) {
$query = <<<SQL
CREATE TABLE `glpi_groups_items` (
`id` int unsigned NOT NULL AUTO_INCREMENT,
`groups_id` int {$default_key_sign} NOT NULL DEFAULT '0',
`itemtype` varchar(255) NOT NULL DEFAULT '',
`items_id` int {$default_key_sign} NOT NULL DEFAULT '0',
`type` tinyint NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `unicity` (`groups_id`,`itemtype`,`items_id`, `type`),
KEY `item` (`itemtype`, `items_id`),
KEY `type` (`type`)
) ENGINE=InnoDB DEFAULT CHARSET={$default_charset} COLLATE={$default_collation} ROW_FORMAT=DYNAMIC;
SQL;
$DB->doQueryOrDie($query);
}

foreach ($assignable_itemtypes as $itemtype => $specs) {
$itemtype_table = $specs['table'];
$itemtype_rightname = $specs['rightname'];

$migration->addRight($itemtype_rightname, READ_ASSIGNED, [$itemtype_rightname => READ]);
$migration->addRight($itemtype_rightname, UPDATE_ASSIGNED, [$itemtype_rightname => UPDATE]);

// move groups to the new link table
if ($DB->fieldExists($itemtype_table, 'groups_id')) {
$DB->insert('glpi_groups_items', new \Glpi\DBAL\QuerySubQuery([
'SELECT' => [
new \Glpi\DBAL\QueryExpression('NULL', 'id'),
new \Glpi\DBAL\QueryExpression('1', 'type'),
'id AS items_id',
'groups_id',
new \Glpi\DBAL\QueryExpression($DB::quoteValue($itemtype), 'itemtype')
],
'FROM' => $itemtype_table,
'WHERE' => [
'groups_id' => ['>', 0]
]
]));
}
if ($DB->fieldExists($itemtype_table, 'groups_id_tech')) {
$DB->insert('glpi_groups_items', new \Glpi\DBAL\QuerySubQuery([
'SELECT' => [
new \Glpi\DBAL\QueryExpression('NULL', 'id'),
new \Glpi\DBAL\QueryExpression('2', 'type'),
'id AS items_id',
'groups_id_tech AS groups_id',
new \Glpi\DBAL\QueryExpression($DB::quoteValue($itemtype), 'itemtype')
],
'FROM' => $itemtype_table,
'WHERE' => [
'groups_id_tech' => ['>', 0]
]
]));
}

$migration->dropKey($itemtype_table, 'groups_id');
$migration->dropKey($itemtype_table, 'groups_id_tech');
$migration->dropField($itemtype_table, 'groups_id');
$migration->dropField($itemtype_table, 'groups_id_tech');
}
Loading

0 comments on commit 2705877

Please sign in to comment.