<?php /* ** Zabbix ** Copyright (C) 2001-2022 Zabbix SIA ** ** This program is free software; you can redistribute it and/or modify ** it under the terms of the GNU General Public License as published by ** the Free Software Foundation; either version 2 of the License, or ** (at your option) any later version. ** ** This program is distributed in the hope that it will be useful, ** but WITHOUT ANY WARRANTY; without even the implied warranty of ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ** GNU General Public License for more details. ** ** You should have received a copy of the GNU General Public License ** along with this program; if not, write to the Free Software ** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. **/ require_once dirname(__FILE__).'/../include/CAPITest.php'; require_once dirname(__FILE__).'/../include/helpers/CDataHelper.php'; /** * @backup items * @onBefore prepareUpdateData */ class testItem extends CAPITest { protected static $items; public static function getItemCreateData() { $valid_item_types = [ ITEM_TYPE_ZABBIX => '50022', ITEM_TYPE_TRAPPER => null, ITEM_TYPE_SIMPLE => '50022', ITEM_TYPE_INTERNAL => null, ITEM_TYPE_ZABBIX_ACTIVE => null, ITEM_TYPE_EXTERNAL => '50022', ITEM_TYPE_DB_MONITOR => null, ITEM_TYPE_IPMI => '50031', ITEM_TYPE_SSH => '50022', ITEM_TYPE_TELNET => '50022', ITEM_TYPE_CALCULATED => null, ITEM_TYPE_JMX => '50030', ITEM_TYPE_DEPENDENT => null, ITEM_TYPE_HTTPAGENT => '50022', ITEM_TYPE_SNMP => '50029', ITEM_TYPE_SCRIPT => '50022' ]; $item_type_tests = []; foreach ($valid_item_types as $type => $interfaceid) { switch ($type) { case ITEM_TYPE_IPMI: $params = [ 'ipmi_sensor' => '1.2.3' ]; break; case ITEM_TYPE_TRAPPER: $params = [ 'delay' => '0' ]; break; case ITEM_TYPE_TELNET: case ITEM_TYPE_SSH: $params = [ 'username' => 'username', 'authtype' => ITEM_AUTHTYPE_PASSWORD ]; break; case ITEM_TYPE_DEPENDENT: $params = [ 'master_itemid' => '150151', 'delay' => '0' ]; break; case ITEM_TYPE_JMX: $params = [ 'username' => 'username', 'password' => 'password' ]; break; case ITEM_TYPE_HTTPAGENT: $params = [ 'url' => 'http://0.0.0.0' ]; break; case ITEM_TYPE_SNMP: $params = [ 'snmp_oid' => '1.2.3' ]; break; case ITEM_TYPE_SCRIPT: $params = [ 'params' => 'script', 'timeout' => '30s' ]; break; default: $params = []; break; } if ($interfaceid) { $params['interfaceid'] = $interfaceid; } $item_type_tests[] = [ 'request_data' => $params + [ 'name' => 'Item of type '.$type, 'key_' => 'item_of_type_'.$type, 'hostid' => '50009', 'type' => (string) $type, 'value_type' => ITEM_VALUE_TYPE_UINT64, 'delay' => '30s' ], 'expected_error' => null ]; } return [ [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Item with invalid item type', 'key_' => 'item_with_invalid_item_type', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => '100', 'delay' => '30s' ], 'expected_error' => 'Invalid parameter "/1/type": value must be one of '.implode(', ', [ ITEM_TYPE_ZABBIX, ITEM_TYPE_TRAPPER, ITEM_TYPE_SIMPLE, ITEM_TYPE_INTERNAL, ITEM_TYPE_ZABBIX_ACTIVE, ITEM_TYPE_EXTERNAL, ITEM_TYPE_DB_MONITOR, ITEM_TYPE_IPMI, ITEM_TYPE_SSH, ITEM_TYPE_TELNET, ITEM_TYPE_CALCULATED, ITEM_TYPE_JMX, ITEM_TYPE_SNMPTRAP, ITEM_TYPE_DEPENDENT, ITEM_TYPE_HTTPAGENT, ITEM_TYPE_SNMP, ITEM_TYPE_SCRIPT ]).'.' ], // Test update interval for mqtt key of the Agent item type. [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Test mqtt key', 'key_' => 'mqtt.get[0]', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_ZABBIX, 'delay' => '30s' ], 'expected_error' => null ], [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Test mqtt key without delay', 'key_' => 'mqtt.get[1]', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_ZABBIX ], 'expected_error' => 'Incorrect arguments passed to function.' ], [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Test mqtt key with 0 delay', 'key_' => 'mqtt.get[2]', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_ZABBIX, 'delay' => '0' ], 'expected_error' => 'Item will not be refreshed. Specified update interval requires having at least one either flexible or scheduling interval.' ], // Test update interval for mqtt key of the Active agent type. [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Test mqtt key for active agent', 'key_' => 'mqtt.get[3]', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_ZABBIX_ACTIVE ], 'expected_error' => null ], [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Test mqtt key with 0 delay for active agent', 'key_' => 'mqtt.get[4]', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_ZABBIX_ACTIVE, 'delay' => '0' ], 'expected_error' => null ], [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Item with some tags', 'key_' => 'trapper_item_1', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_TRAPPER, 'delay' => '0', 'tags' => [ [ 'tag' => 'tag', 'value' => 'value 1' ], [ 'tag' => 'tag', 'value' => 'value 2' ] ] ], 'expected_error' => null ], [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Test mqtt with wrong key and 0 delay', 'key_' => 'mqt.get[5]', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_ZABBIX_ACTIVE, 'delay' => '0' ], 'expected_error' => 'Item will not be refreshed. Specified update interval requires having at least one either flexible or scheduling interval.' ], // Item preprocessing. [ 'request_data' => [ 'hostid' => '50009', 'name' => 'Test preprocessing 1', 'key_' => 'mqtt.get[5]', 'interfaceid' => '50022', 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_ZABBIX_ACTIVE, 'delay' => '0', 'preprocessing' => [ [ 'type' => ZBX_PREPROC_VALIDATE_NOT_SUPPORTED, 'params' => '', 'error_handler' => ZBX_PREPROC_FAIL_DEFAULT, 'error_handler_params' => '' ] ] ], 'expected_error' => 'Incorrect value for field "error_handler": unexpected value "0".' ], 'HTTP Agent item without direct interface' => [ 'request_data' => [ 'hostid' => '50009', 'name' => 'NoInterfaceItem123', 'key_' => '1234', 'interfaceid' => 0, 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_HTTPAGENT, 'delay' => '30s', 'url' => '192.168.0.1' ], 'expected_error' => null ], 'Sample/Simple Check item requires interface' => [ 'request_data' => [ 'hostid' => '50009', 'name' => 'NoInterfaceItem123', 'key_' => '1234', 'interfaceid' => 0, 'value_type' => ITEM_VALUE_TYPE_UINT64, 'type' => ITEM_TYPE_SIMPLE, 'delay' => '30s', 'url' => '192.168.0.1' ], 'expected_error' => 'No interface found.' ] ] + $item_type_tests; } /** * @dataProvider getItemCreateData */ public function testItem_Create($request_data, $expected_error) { $result = $this->call('item.create', $request_data, $expected_error); if ($expected_error === null) { if ($request_data['type'] === ITEM_TYPE_ZABBIX_ACTIVE && substr($request_data['key_'], 0, 8) === 'mqtt.get') { $request_data['delay'] = CTestArrayHelper::get($request_data, 'delay', '0'); } foreach ($result['result']['itemids'] as $id) { $db_item = CDBHelper::getRow('SELECT hostid, name, key_, type, delay FROM items WHERE itemid='.zbx_dbstr($id)); foreach (['hostid', 'name', 'key_', 'type', 'delay'] as $field) { $this->assertSame($db_item[$field], strval($request_data[$field])); } if (array_key_exists('tags', $request_data)) { $db_tags = DBFetchArray(DBSelect('SELECT tag, value FROM item_tag WHERE itemid='.zbx_dbstr($id))); uasort($request_data['tags'], function ($a, $b) { return strnatcasecmp($a['value'], $b['value']); }); uasort($db_tags, function ($a, $b) { return strnatcasecmp($a['value'], $b['value']); }); $this->assertTrue(array_values($db_tags) === array_values($request_data['tags'])); } } } } public static function prepareUpdateData() { $interfaces = [ [ 'type' => 1, 'main' => 1, 'useip' => 1, 'ip' => '127.0.0.1', 'dns' => '', 'port' => '10050' ] ]; $groups = [ [ 'groupid' => 4 ] ]; $result = CDataHelper::createHosts([ [ 'host' => 'testItem_Update', 'interfaces' => $interfaces, 'groups' => $groups, 'status' => HOST_STATUS_MONITORED, 'items' => [ [ 'name' => 'Agent ping', 'key_' => 'agent.ping', 'type' => ITEM_TYPE_ZABBIX, 'value_type' => ITEM_VALUE_TYPE_UINT64, 'delay' => '1s' ], [ 'name' => 'Agent version', 'key_' => 'agent.version', 'type' => ITEM_TYPE_ZABBIX, 'value_type' => ITEM_VALUE_TYPE_UINT64, 'delay' => '1m' ] ] ] ]); self::$items = $result['itemids']; } public static function getItemUpdateData() { return [ // Test update interval for mqtt key of the Agent item type. [ 'request_data' => [ 'item' => 'testItem_Update:agent.ping', 'key_' => 'mqtt.get[00]', 'delay' => '0' ], 'expected_error' => 'Item will not be refreshed. Specified update interval requires having at least one either flexible or scheduling interval.' ], // Test update interval for wrong mqtt key of the Active agent item type. [ 'request_data' => [ 'item' => 'testItem_Update:agent.ping', 'key_' => 'mqt.get[11]', 'type' => ITEM_TYPE_ZABBIX, 'delay' => '0' ], 'expected_error' => 'Item will not be refreshed. Specified update interval requires having at least one either flexible or scheduling interval.' ], // Change type to active agent and check update interval for mqtt key. [ 'request_data' => [ 'item' => 'testItem_Update:agent.ping', 'key_' => 'mqtt.get[22]', 'type' => ITEM_TYPE_ZABBIX_ACTIVE, 'delay' => '0' ], 'expected_error' => null ], [ 'request_data' => [ 'item' => 'testItem_Update:agent.version', 'name' => 'Test mqtt key for active agent', 'key_' => 'mqtt.get[33]', 'type' => ITEM_TYPE_ZABBIX_ACTIVE ], 'expected_error' => null ] ]; } /** * @dataProvider getItemUpdateData */ public function testItem_Update($request_data, $expected_error) { $request_data['itemid'] = self::$items[$request_data['item']]; unset($request_data['item']); $result = $this->call('item.update', $request_data, $expected_error); if ($expected_error === null) { if ($request_data['type'] === ITEM_TYPE_ZABBIX_ACTIVE && substr($request_data['key_'], 0, 8) === 'mqtt.get') { $request_data['delay'] = CTestArrayHelper::get($request_data, 'delay', '0'); } foreach ($result['result']['itemids'] as $id) { $db_item = CDBHelper::getRow('SELECT key_, type, delay FROM items WHERE itemid='.zbx_dbstr($id)); foreach (['key_', 'type', 'delay'] as $field) { $this->assertSame($db_item[$field], strval($request_data[$field])); } } } } public static function getItemDeleteData() { return [ [ 'item' => ['400720'], 'data' => [ 'discovered_triggerids' => ['30002'], 'dependent_item' => ['400740'], 'dependent_item_disc_triggerids' => ['30004'] ], 'expected_error' => null ] ]; } /** * @dataProvider getItemDeleteData */ public function testItem_Delete($item, $data, $expected_error) { $result = $this->call('item.delete', $item, $expected_error); if ($expected_error === null) { foreach ($result['result']['itemids'] as $id) { $dbResult = 'SELECT * FROM items WHERE itemid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); } // Check that related discovered trigerid is removed with all related data. if (array_key_exists('discovered_triggerids', $data)) { foreach ($data['discovered_triggerids'] as $id) { $dbResult = 'SELECT * FROM triggers WHERE triggerid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); $dbResult = 'SELECT * FROM functions WHERE triggerid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); $dbResult = 'SELECT * FROM trigger_discovery WHERE triggerid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); } } // Check that dependent item is removed. if (array_key_exists('dependent_item', $data)) { foreach ($data['dependent_item'] as $id) { $dbResult = 'SELECT * FROM items WHERE itemid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); } } // Check that discovered trigger of dependent item is removed with all related data. if (array_key_exists('dependent_item_disc_triggerids', $data)) { foreach ($data['dependent_item_disc_triggerids'] as $id) { $dbResult = 'SELECT * FROM triggers WHERE triggerid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); $dbResult = 'SELECT * FROM functions WHERE triggerid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); $dbResult = 'SELECT * FROM trigger_discovery WHERE triggerid='.zbx_dbstr($id); $this->assertEquals(0, CDBHelper::getCount($dbResult)); } } } } }