From fa85061dca5b50638a5eb43bea24e68c40eb2dc1 Mon Sep 17 00:00:00 2001 From: Domingo Oropeza Date: Mon, 11 Jun 2018 17:42:49 -0400 Subject: [PATCH 1/3] feat(policy): add APN configuration policy Signed-off-by: Domingo Oropeza --- inc/policyapn.class.php | 134 +++++++++++++++++++++++++++++++ inc/policyfactory.class.php | 4 + install/policies/peripherals.php | 16 ++++ tpl/policy_apn_form.html.twig | 22 +++++ 4 files changed, 176 insertions(+) create mode 100644 inc/policyapn.class.php create mode 100644 tpl/policy_apn_form.html.twig diff --git a/inc/policyapn.class.php b/inc/policyapn.class.php new file mode 100644 index 00000000..2f3177f4 --- /dev/null +++ b/inc/policyapn.class.php @@ -0,0 +1,134 @@ +symbol = $policy->getField('symbol'); + $this->unicityRequired = ($policy->getField('unicity') != '0'); + $this->group = $policy->getField('group'); + } + + /** + * @param mixed $value + * @param mixed $itemtype + * @param integer $itemId + * @return bool + */ + public function integrityCheck($value, $itemtype, $itemId) { + // Check the value exists + $inputNames = ['name', 'apn']; + foreach ($inputNames as $key){ + if (!isset($value[$key])) { + Session::addMessageAfterRedirect(sprintf(__('A value for "%s" is mandatory', 'flyvemdm'), $value)); + return false; + } + } + return true; + } + + /** + * @param mixed $value + * @param mixed $itemtype + * @param int $itemId + * @return array|bool + */ + public function getMqttMessage($value, $itemtype, $itemId) { + if (!$this->integrityCheck($value, $itemtype, $itemId)) { + return false; + } + $array = [ + $this->symbol => $value + ]; + return $array; + } + + public function showValueInput($value = '', $itemType = '', $itemId = 0) { + + $value = json_decode($value, JSON_OBJECT_AS_ARRAY); + + $fields = [ + 'apn_name' => ['label' => 'Name', 'type' => 'text'], + 'apn_apn' => ['label' => 'APN', 'type' => 'text'], + 'apn_proxy' => ['label' => 'Proxy', 'type' => 'text'], + 'apn_port' => ['label' => 'Port', 'type' => 'text'], + 'apn_username' => ['label' => 'Username', 'type' => 'text'], + 'apn_password' => ['label' => 'Password', 'type' => 'password'], + 'apn_server' => ['label' => 'Server', 'type' => 'text'], + 'apn_mmsc' => ['label' => 'MMSC', 'type' => 'text'], + 'apn_proxy_mms' => ['label' => 'Proxy MMS', 'type' => 'text'], + 'apn_proxy_mms_port' => ['label' => 'Proxy MMC port', 'type' => 'text'], + 'apn_mmc' => ['label' => 'MMC', 'type' => 'text'], + 'apn_mnc' => ['label' => 'MNC', 'type' => 'text'], + ]; + + $data = []; + foreach ($fields as $inputName => $inputOptions) { + $data['inputs'][] = [ + 'id' => $inputName, + 'label' => $inputOptions['label'], + 'type' => $inputOptions['type'], + 'value' => ($value[$inputName]) ? $value[$inputName] : '', + ]; + } + + $apnAuthType = Dropdown::showFromArray('apn_auth_type', + ['No authentication', 'PAP', 'CHAP', 'CHAP/PAP'], ['display' => false]); + $apnType = Dropdown::showFromArray('apn_type', + ['default', 'mms', 'supl', 'dun', 'hipri', 'fota'], ['display' => false]); + + $data['apnAuthType'] = [ + 'label' => 'Authentication Type', + 'dropdown' => $apnAuthType, + ]; + $data['apnType'] = [ + 'label' => 'APN Type', + 'dropdown' => $apnType, + ]; + + $twig = plugin_flyvemdm_getTemplateEngine(); + return $twig->render('policy_apn_form.html.twig', $data); + } + +} \ No newline at end of file diff --git a/inc/policyfactory.class.php b/inc/policyfactory.class.php index 0f7d95b4..07045b81 100644 --- a/inc/policyfactory.class.php +++ b/inc/policyfactory.class.php @@ -78,6 +78,10 @@ public function createFromPolicy(PluginFlyvemdmPolicy $policyData) { $policy = new PluginFlyvemdmPolicyRemovefile($policyData); break; + case 'apn': + $policy = new PluginFlyvemdmPolicyApn($policyData); + break; + default: return null; } diff --git a/install/policies/peripherals.php b/install/policies/peripherals.php index e1cc63e4..18ab76ce 100644 --- a/install/policies/peripherals.php +++ b/install/policies/peripherals.php @@ -216,4 +216,20 @@ 'apple_min_version' => '0', 'apple_max_version' => '0', ], + + [ + 'name' => __('APN configuration', 'flyvemdm'), + 'symbol' => 'apnConfiguration', + 'group' => 'connectivity', + 'type' => 'apn', + 'type_data' => '', + 'unicity' => 0, + 'plugin_flyvemdm_policycategories_id' => $category, + 'comment' => __('Set-up you APN values manually','flyvemdm'), + 'default_value' => '', + 'recommended_value' => '', + 'is_android_policy' => '1', + 'is_android_system' => '0', + 'is_apple_policy' => '0', + ], ]; \ No newline at end of file diff --git a/tpl/policy_apn_form.html.twig b/tpl/policy_apn_form.html.twig new file mode 100644 index 00000000..52874390 --- /dev/null +++ b/tpl/policy_apn_form.html.twig @@ -0,0 +1,22 @@ +{% for input in inputs %} + + {{ __(input.label) }} + + +{% endfor %} + + + + + + {{ apnAuthType.dropdown|raw }} + + + + + + + + {{ apnType.dropdown|raw }} + + \ No newline at end of file From c17f41498abcd9f9c9e3bfd0ddba47419f22c058 Mon Sep 17 00:00:00 2001 From: Domingo Oropeza Date: Tue, 12 Jun 2018 12:17:19 -0400 Subject: [PATCH 2/3] refactor(policy): update code for APN policy Signed-off-by: Domingo Oropeza --- inc/policyapn.class.php | 80 ++++++++++++--------- install/policies/peripherals.php | 2 +- tests/src/Flyvemdm/Tests/CommonTestCase.php | 1 + tpl/policy_apn_form.html.twig | 44 ++++++------ 4 files changed, 73 insertions(+), 54 deletions(-) diff --git a/inc/policyapn.class.php b/inc/policyapn.class.php index 2f3177f4..099a9038 100644 --- a/inc/policyapn.class.php +++ b/inc/policyapn.class.php @@ -39,11 +39,31 @@ */ class PluginFlyvemdmPolicyApn extends PluginFlyvemdmPolicyBase implements PluginFlyvemdmPolicyInterface { + private $formFields = []; + private $apnAuthType = []; + private $apnType = []; + /** * PluginFlyvemdmPolicyApn constructor. * @param PluginFlyvemdmPolicy $policy */ public function __construct(PluginFlyvemdmPolicy $policy) { + $this->formFields = [ + 'apn_name' => ['label' => __('Name', 'flyvemdm'), 'type' => 'text'], + 'apn_fqn' => ['label' => __('APN', 'flyvemdm'), 'type' => 'text'], + 'apn_proxy' => ['label' => __('Proxy', 'flyvemdm'), 'type' => 'text'], + 'apn_port' => ['label' => __('Port', 'flyvemdm'), 'type' => 'text'], + 'apn_username' => ['label' => __('Username', 'flyvemdm'), 'type' => 'text'], + 'apn_password' => ['label' => __('Password', 'flyvemdm'), 'type' => 'password'], + 'apn_server' => ['label' => __('Server', 'flyvemdm'), 'type' => 'text'], + 'apn_mmsc' => ['label' => __('MMSC', 'flyvemdm'), 'type' => 'text'], + 'apn_proxy_mms' => ['label' => __('Proxy MMS', 'flyvemdm'), 'type' => 'text'], + 'apn_proxy_mms_port' => ['label' => __('Proxy MMC port', 'flyvemdm'), 'type' => 'text'], + 'apn_mmc' => ['label' => __('MMC', 'flyvemdm'), 'type' => 'text'], + 'apn_mnc' => ['label' => __('MNC', 'flyvemdm'), 'type' => 'text'], + ]; + $this->apnType = [__('Default'), 'MMS', 'SUPL', 'DUN', 'HIPRI', 'FOTA']; + $this->apnAuthType = [__('No authentication'), 'PAP', 'CHAP', 'CHAP/PAP']; parent::__construct($policy); $this->symbol = $policy->getField('symbol'); $this->unicityRequired = ($policy->getField('unicity') != '0'); @@ -58,12 +78,13 @@ public function __construct(PluginFlyvemdmPolicy $policy) { */ public function integrityCheck($value, $itemtype, $itemId) { // Check the value exists - $inputNames = ['name', 'apn']; - foreach ($inputNames as $key){ - if (!isset($value[$key])) { - Session::addMessageAfterRedirect(sprintf(__('A value for "%s" is mandatory', 'flyvemdm'), $value)); - return false; - } + if (!isset($value['apn_name']) || !$value['apn_name']) { + Session::addMessageAfterRedirect(__('APN name is mandatory', 'flyvemdm')); + return false; + } + if (!isset($value['apn_fqn']) || !$value['apn_fqn']) { + Session::addMessageAfterRedirect(__('APN value is mandatory', 'flyvemdm')); + return false; } return true; } @@ -75,11 +96,12 @@ public function integrityCheck($value, $itemtype, $itemId) { * @return array|bool */ public function getMqttMessage($value, $itemtype, $itemId) { - if (!$this->integrityCheck($value, $itemtype, $itemId)) { + $decodedValue = json_decode($value, JSON_OBJECT_AS_ARRAY); + if (!$this->integrityCheck($decodedValue, $itemtype, $itemId)) { return false; } $array = [ - $this->symbol => $value + $this->symbol => $value, ]; return $array; } @@ -88,47 +110,39 @@ public function showValueInput($value = '', $itemType = '', $itemId = 0) { $value = json_decode($value, JSON_OBJECT_AS_ARRAY); - $fields = [ - 'apn_name' => ['label' => 'Name', 'type' => 'text'], - 'apn_apn' => ['label' => 'APN', 'type' => 'text'], - 'apn_proxy' => ['label' => 'Proxy', 'type' => 'text'], - 'apn_port' => ['label' => 'Port', 'type' => 'text'], - 'apn_username' => ['label' => 'Username', 'type' => 'text'], - 'apn_password' => ['label' => 'Password', 'type' => 'password'], - 'apn_server' => ['label' => 'Server', 'type' => 'text'], - 'apn_mmsc' => ['label' => 'MMSC', 'type' => 'text'], - 'apn_proxy_mms' => ['label' => 'Proxy MMS', 'type' => 'text'], - 'apn_proxy_mms_port' => ['label' => 'Proxy MMC port', 'type' => 'text'], - 'apn_mmc' => ['label' => 'MMC', 'type' => 'text'], - 'apn_mnc' => ['label' => 'MNC', 'type' => 'text'], - ]; - $data = []; - foreach ($fields as $inputName => $inputOptions) { + foreach ($this->formFields as $inputName => $inputOptions) { $data['inputs'][] = [ - 'id' => $inputName, + 'name' => "value[$inputName]", 'label' => $inputOptions['label'], 'type' => $inputOptions['type'], 'value' => ($value[$inputName]) ? $value[$inputName] : '', ]; } - $apnAuthType = Dropdown::showFromArray('apn_auth_type', - ['No authentication', 'PAP', 'CHAP', 'CHAP/PAP'], ['display' => false]); - $apnType = Dropdown::showFromArray('apn_type', - ['default', 'mms', 'supl', 'dun', 'hipri', 'fota'], ['display' => false]); + $apnAuthType = ($value['apn_auth_type']) ? $value['apn_auth_type'] : 0; + $apnType = ($value['apn_type']) ? $value['apn_type'] : 0; $data['apnAuthType'] = [ - 'label' => 'Authentication Type', - 'dropdown' => $apnAuthType, + 'label' => 'Authentication Type', + 'dropdown' => Dropdown::showFromArray('value[apn_auth_type]', + $this->apnAuthType, + ['display' => false, 'value' => $apnAuthType]), ]; $data['apnType'] = [ - 'label' => 'APN Type', - 'dropdown' => $apnType, + 'label' => 'APN Type', + 'dropdown' => Dropdown::showFromArray('value[apn_type]', + $this->apnType, + ['display' => false, 'value' => $apnType]), ]; $twig = plugin_flyvemdm_getTemplateEngine(); return $twig->render('policy_apn_form.html.twig', $data); } + public function showValue(PluginFlyvemdmTask $task) { + $values = json_decode($task->getField('value'), JSON_OBJECT_AS_ARRAY); + $stringValues = $values['apn_name']; + return $stringValues; + } } \ No newline at end of file diff --git a/install/policies/peripherals.php b/install/policies/peripherals.php index 18ab76ce..c7696b91 100644 --- a/install/policies/peripherals.php +++ b/install/policies/peripherals.php @@ -225,7 +225,7 @@ 'type_data' => '', 'unicity' => 0, 'plugin_flyvemdm_policycategories_id' => $category, - 'comment' => __('Set-up you APN values manually','flyvemdm'), + 'comment' => __('Set-up you APN values manually', 'flyvemdm'), 'default_value' => '', 'recommended_value' => '', 'is_android_policy' => '1', diff --git a/tests/src/Flyvemdm/Tests/CommonTestCase.php b/tests/src/Flyvemdm/Tests/CommonTestCase.php index a27b5903..04d0c54d 100644 --- a/tests/src/Flyvemdm/Tests/CommonTestCase.php +++ b/tests/src/Flyvemdm/Tests/CommonTestCase.php @@ -705,6 +705,7 @@ public static function policyList() { 'Policy/disableStreamSystem', 'Policy/defaultStreamType', 'Policy/periodicGeolocation', + 'Policy/apnConfiguration', ]; } diff --git a/tpl/policy_apn_form.html.twig b/tpl/policy_apn_form.html.twig index 52874390..e89df883 100644 --- a/tpl/policy_apn_form.html.twig +++ b/tpl/policy_apn_form.html.twig @@ -1,22 +1,26 @@ -{% for input in inputs %} + + {% for input in inputs %} + {% if loop.index0 is even %} + + {% endif %} + + + {% if loop.index0 is odd %} + + {% endif %} + {% endfor %} - - + + + + -{% endfor %} - - - - - - - - \ No newline at end of file +
{{ __(input.label) }} + + + {{ apnAuthType.dropdown|raw }} + + + + {{ apnType.dropdown|raw }} +
- - - {{ apnAuthType.dropdown|raw }} -
- - - {{ apnType.dropdown|raw }} -
\ No newline at end of file From 188510dc1b8d9e442db5769d90868c2e8c134d3a Mon Sep 17 00:00:00 2001 From: Domingo Oropeza Date: Tue, 12 Jun 2018 15:31:02 -0400 Subject: [PATCH 3/3] test(policy): add unit tests for APN policy Signed-off-by: Domingo Oropeza --- inc/policyapn.class.php | 5 +- tests/suite-unit/PluginFlyvemdmPolicyApn.php | 134 +++++++++++++++++++ 2 files changed, 136 insertions(+), 3 deletions(-) create mode 100644 tests/suite-unit/PluginFlyvemdmPolicyApn.php diff --git a/inc/policyapn.class.php b/inc/policyapn.class.php index 099a9038..ad17e819 100644 --- a/inc/policyapn.class.php +++ b/inc/policyapn.class.php @@ -21,9 +21,8 @@ * You should have received a copy of the GNU Affero General Public License * along with Flyve MDM Plugin for GLPI. If not, see http://www.gnu.org/licenses/. * ------------------------------------------------------------------------------ - * @author Thierry Bugier * @copyright Copyright © 2018 Teclib - * @license AGPLv3+ http://www.gnu.org/licenses/agpl.txt + * @license http://www.gnu.org/licenses/agpl.txt AGPLv3+ * @link https://github.com/flyve-mdm/glpi-plugin * @link https://flyve-mdm.com/ * ------------------------------------------------------------------------------ @@ -95,7 +94,7 @@ public function integrityCheck($value, $itemtype, $itemId) { * @param int $itemId * @return array|bool */ - public function getMqttMessage($value, $itemtype, $itemId) { + public function getBrokerMessage($value, $itemtype, $itemId) { $decodedValue = json_decode($value, JSON_OBJECT_AS_ARRAY); if (!$this->integrityCheck($decodedValue, $itemtype, $itemId)) { return false; diff --git a/tests/suite-unit/PluginFlyvemdmPolicyApn.php b/tests/suite-unit/PluginFlyvemdmPolicyApn.php new file mode 100644 index 00000000..7fb6aa64 --- /dev/null +++ b/tests/suite-unit/PluginFlyvemdmPolicyApn.php @@ -0,0 +1,134 @@ + 'connectivity', + 'symbol' => 'apnConfiguration', + 'type' => 'apn', + 'type_data' => '', + 'unicity' => '0', + ]; + + protected function validationProvider() { + return [ + 'Check apn_name is not set' => [ + 'data' => [[], null, null], + 'expected' => [false, 'APN name is mandatory'], + ], + 'Check apn_name is not empty' => [ + 'data' => [['apn_name' => ''], null, null], + 'expected' => [false, 'APN name is mandatory'], + ], + 'Check apn_fqn is not set' => [ + 'data' => [['apn_name' => 'lorem'], null, null], + 'expected' => [false, 'APN value is mandatory'], + ], + 'Check apn_fqn is not empty' => [ + 'data' => [['apn_name' => 'lorem', 'apn_fqn' => ''], null, null], + 'expected' => [false, 'APN value is mandatory'], + ], + 'Valid check 1' => [ + 'data' => [['apn_name' => 'lorem', 'apn_fqn' => 'ipsum'], null, null], + 'expected' => [true], + ], + ]; + } + + /** + * @dataProvider validationProvider + * @tags testCreatePolicy + * @param array $data + * @param array $expected + */ + public function testCreatePolicy($data, $expected) { + list($policy) = $this->createNewPolicyInstance(); + $success = $policy->integrityCheck($data[0], $data[1], $data[2]); + $this->boolean($success)->isEqualTo($expected[0]); + if (!$expected[0]) { + $this->string($_SESSION["MESSAGE_AFTER_REDIRECT"][0][0])->isEqualTo($expected[1]); + unset($_SESSION["MESSAGE_AFTER_REDIRECT"]); // to clear the buffer + } + } + + private function createNewPolicyInstance() { + $policyData = new \PluginFlyvemdmPolicy(); + $policyData->fields = $this->dataField; + $policy = $this->newTestedInstance($policyData); + return [$policy, $policyData]; + } + + /** + * @tags testGetBrokerMessage + */ + public function testGetBrokerMessage() { + list($policy) = $this->createNewPolicyInstance(); + + $this->boolean($policy->getBrokerMessage(null, null, null))->isFalse(); + $value = '{"apn_name":"lorem","apn_fqn":"ipsum","apn_auth_type":"0","apn_type":"0"}'; + $result = $policy->getBrokerMessage($value, null, null); + $this->array($result)->hasKeys([$this->dataField['symbol']]) + ->string($result[$this->dataField['symbol']])->contains('"apn_name":"lorem","apn_fqn":"ipsum"'); + } + + /** + * @tags testShowValueInput + */ + public function testShowValueInput() { + list($policy) = $this->createNewPolicyInstance(); + $value = $policy->showValueInput(); + $this->string($value) + ->contains('input type="text" name="value[apn_name]" value=""') + ->contains('input type="text" name="value[apn_fqn]" value=""'); + + $dropdowns = ['apn_auth_type', 'apn_type']; + foreach ($dropdowns as $inputName) { + $matches = null; + preg_match('/.*]*name=\'value\[' . $inputName . '\]\'[^>]*>.*/', + $value, $matches); + $this->array($matches)->hasSize(1); + } + } + + /** + * @tags testShowValue + */ + public function testShowValue() { + list($policy) = $this->createNewPolicyInstance(); + $mockInstance = $this->newMockInstance('\PluginFlyvemdmTask'); + $mockInstance->getMockController()->getField = '{"apn_name":"lorem","apn_fqn":"ipsum","apn_auth_type":"0","apn_type":"0"}'; + $this->string($policy->showValue($mockInstance))->isEqualTo('lorem'); + } +} \ No newline at end of file