Skip to content

Commit

Permalink
Add: Available optional features in Capabilities
Browse files Browse the repository at this point in the history
The Capabilities object now has a featureEnabled method that checks if
an optional feature is enabled according to the new GET_FEATURES GMP
command.

This will allow toggling/modifying UI elements for these features
without a redundant setting in the GSA config.
  • Loading branch information
timopollmeier authored and a-h-abdelsalam committed Jul 3, 2024
1 parent 6751192 commit c055f65
Show file tree
Hide file tree
Showing 4 changed files with 88 additions and 4 deletions.
13 changes: 13 additions & 0 deletions src/gmp/capabilities/__tests__/capabilities.js
Original file line number Diff line number Diff line change
Expand Up @@ -215,6 +215,19 @@ describe('Capabilities tests', () => {
}
expect(i).toEqual(4);
});

test('should handle features', () => {
const featureList = [
{name: 'ENABLED_FEATURE_1', _enabled: 1},
{name: 'DISABLED_FEATURE', _enabled: 0},
{name: 'ENABLED_FEATURE_2', _enabled: 1},
];
const caps = new Capabilities(['everything'], featureList);
expect(caps.featureEnabled('ENABLED_FEATURE_1')).toBe(true);
expect(caps.featureEnabled('DISABLED_FEATURE')).toBe(false);
expect(caps.featureEnabled('enabled_feature_2')).toBe(true);
expect(caps.featureEnabled('UNDEFINED_FEATURE')).toBe(false);
});
});

// vim: set ts=2 sw=2 tw=80:
21 changes: 18 additions & 3 deletions src/gmp/capabilities/capabilities.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,10 @@
* SPDX-License-Identifier: AGPL-3.0-or-later
*/


import {isDefined} from 'gmp/utils/identity';
import {map} from 'gmp/utils/array';
import {forEach, map} from 'gmp/utils/array';
import {pluralizeType} from 'gmp/utils/entitytype';
import {parseBoolean} from 'gmp/parser';

const types = {
audit: 'task',
Expand Down Expand Up @@ -51,16 +51,27 @@ const convertType = type => {
};

class Capabilities {
constructor(cap_names) {
constructor(cap_names, featuresList) {
this._has_caps = isDefined(cap_names);
this._has_features = isDefined(featuresList);

let caps;
let featuresEnabled = {};

if (this._has_caps) {
caps = map(cap_names, name => name.toLowerCase());
}

if (this._has_features) {
forEach(featuresList, feature => {
featuresEnabled[feature.name.toUpperCase()] = parseBoolean(
feature._enabled,
);
});
}

this._capabilities = new Set(caps);
this._featuresEnabled = featuresEnabled;
}

[Symbol.iterator]() {
Expand Down Expand Up @@ -102,6 +113,10 @@ class Capabilities {
get length() {
return this._capabilities.size;
}

featureEnabled(feature) {
return this._featuresEnabled[feature.toUpperCase()] == true;
}
}

export default Capabilities;
Expand Down
55 changes: 55 additions & 0 deletions src/gmp/commands/__tests__/user.js
Original file line number Diff line number Diff line change
Expand Up @@ -121,3 +121,58 @@ describe('UserCommand transformSettingName() function tests', () => {
expect(transformSettingName(str4)).toEqual('foobar');
});
});

describe('UserCommand capabilities tests', () => {
test('should get capabilities', () => {
const response = createResponse({
get_capabilities: {
help_response: {
schema: {
command: [
{
name: 'get_reports',
},
{
name: 'get_tasks',
},
],
},
},
get_features_response: {
feature: [
{
_enabled: 1,
name: 'TEST_FEATURE_1',
},
{
_enabled: 1,
name: 'TEST_FEATURE_2',
},
],
},
},
});
const fakeHttp = createHttp(response);
const cmd = new UserCommand(fakeHttp);

cmd.currentCapabilities().then(resp => {
const {data: caps} = resp;

expect(fakeHttp.request).toHaveBeenCalledWith('get', {
args: {
cmd: 'get_capabilities',
},
});

expect(caps._has_caps).toBe(true);
expect(caps.mayAccess('report')).toBe(true);
expect(caps.mayAccess('task')).toBe(true);
expect(caps.mayAccess('user')).toBe(false);

expect(caps._has_features).toBe(true);
expect(caps.featureEnabled('test_feature_1')).toBe(true);
expect(caps.featureEnabled('TEST_FEATURE_2')).toBe(true);
expect(caps.featureEnabled('TEST_FEATURE_3')).toBe(false);
});
});
});
3 changes: 2 additions & 1 deletion src/gmp/commands/users.js
Original file line number Diff line number Diff line change
Expand Up @@ -162,8 +162,9 @@ export class UserCommand extends EntityCommand {
).then(response => {
const {data} = response;
const {command: commands} = data.get_capabilities.help_response.schema;
const featuresList = data.get_capabilities.get_features_response.feature;
const caps = map(commands, command => command.name);
return response.setData(new Capabilities(caps));
return response.setData(new Capabilities(caps, featuresList));
});
}

Expand Down

0 comments on commit c055f65

Please sign in to comment.