You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
ngcp-panel/t/api-rest/api-subscriber-acl-new.t

523 lines
18 KiB

#!/usr/bin/perl
use strict;
use warnings;
use NGCP::Test;
use Test::More;
use JSON qw/from_json to_json/;
use Data::Dumper;
my $test = NGCP::Test->new();
my $t = $test->generate_sid();
my $c = $test->client();
my $ref = $test->reference_data(
client => $c,
use_persistent => 1,
delete_persistent => 0,
depends => [
{
resource => 'billingprofiles',
hints => [{ name => 'customer billingprofile' }],
name => 'my_billprof'
},
{
resource => 'domains',
name => 'my_domain'
},
{
resource => 'customercontacts',
name => 'my_contact'
},
{
resource => 'customers',
name => 'my_foreign_customer',
hints => [{ field => 'type', value => 'pbxaccount' }],
},
{
resource => 'customers',
name => 'my_filled_customer',
hints => [{ name => 'filled pbxaccount customer' }],
},
{
resource => 'subscribers',
name => 'my_foreign_pilot',
hints => [{ name => 'pbx pilot subscriber'}]
}
],
);
# first, create a pbx customer to work with
my $customer_res = $test->resource(
client => $c,
resource => 'customers',
data => {
billing_profile_id => $ref->data('my_billprof')->{id},
contact_id => $ref->data('my_contact')->{id},
status => 'active',
type => 'pbxaccount',
},
autodelete_created_items => 1,
);
$customer_res->test_post(
name => 'create helper customer',
expected_result => { 'code' => 201 }
);
my $customer = $customer_res->pop_created_item();
# define a reference subscriber pbx
my $sub_res = $test->resource(
client => $c,
resource => 'subscribers',
data => {
customer_id => $customer->{id},
domain_id => $ref->data('my_domain')->{id},
username => "user_$t",
password => "pass_$t",
webusername => "webuser_$t",
webpassword => "webpass_$t",
# TODO: why do we have to explicitly set this to create a pilot?
# should be set automatically on creation of first subscriber
# in pbx customer, no?
is_pbx_pilot => 0,
is_pbx_group => 0,
administrative => 0,
primary_number => { cc => '43', ac => '999', sn => $t },
pbx_extension => undef,
display_name => "Admin Pilot $t",
status => 'active',
},
#print_summary_on_finish => 1,
autodelete_created_items => 1,
);
my $num_res = $test->resource(
client => $c,
resource => 'numbers',
);
$sub_res->test_post(
name => 'create subscribers',
data_replace => [
[
# a pilot with administrative rights
{ field => 'administrative', value => 1 },
{ field => 'is_pbx_pilot', value => 1 },
{ field => 'username', value => "pilot_user_$t" },
{ field => 'password', value => "pilot_pass_$t" },
{ field => 'webusername', value => "pilot_webuser_$t" },
{ field => 'webpassword', value => "pilot_webpass_$t" },
{ field => 'alias_numbers', value =>
[map { { cc => '43', ac => '888', sn => sprintf("$t%d", $_) } } (0 .. 9)]
}
],
[
# an extension with administrative rights
{ field => 'administrative', value => 1 },
{ field => 'primary_number', delete => 1 },
{ field => 'pbx_extension', value => '101' },
{ field => 'username', value => "subadm_user_$t" },
{ field => 'password', value => "subadm_pass_$t" },
{ field => 'webusername', value => "subadm_webuser_$t" },
{ field => 'webpassword', value => "subadm_webpass_$t" },
],
[
# an extension without rights
{ field => 'primary_number', delete => 1 },
{ field => 'pbx_extension', value => '102' },
{ field => 'username', value => "subext_user_$t" },
{ field => 'password', value => "subext_pass_$t" },
{ field => 'webusername', value => "subext_webuser_$t" },
{ field => 'webpassword', value => "subext_webpass_$t" },
]
],
skip_test_fields => [qw/alias_numbers.number_id primary_number.number_id/],
expected_result => { code => 201 }
);
my $sub_ext = $sub_res->pop_created_item();
my $subadm_ext = $sub_res->pop_created_item();
my $subadm_pilot = $sub_res->pop_created_item();
# time to create clients to access the API with the individual subs
my $c_sub_ext = $test->client(
role => 'subscriber',
username => $sub_ext->{webusername} . '@' . $ref->data('my_domain')->{domain},
password => $sub_ext->{webpassword},
);
my $c_subadm_ext = $test->client(
role => 'subscriber',
username => $subadm_ext->{webusername} . '@' . $ref->data('my_domain')->{domain},
password => $subadm_ext->{webpassword},
);
my $c_subadm_pilot = $test->client(
role => 'subscriber',
username => $subadm_pilot->{webusername} . '@' . $ref->data('my_domain')->{domain},
password => $subadm_pilot->{webpassword},
);
my $items;
# test working with subscribers with a subscriber without rights
{
$sub_res->client($c_sub_ext);
my $name = 'unprivileged subscriber get';
# remove stuff from reference data which we don't expect in result
my @blacklist = (qw/
customer_id contract_id domain_id
password webpassword
uuid lock status
create_timestamp modify_timestamp
/);
foreach my $k(@blacklist) {
delete $sub_ext->{$k};
}
$items = $sub_res->test_get(
name => $name,
item => $sub_ext,
expected_links => [qw/
ngcp:reminders ngcp:voicemailsettings ngcp:callforwards
ngcp:subscriberpreferences
/],
expected_fields => [qw/
id domain administrative
primary_number alias_numbers pbx_extension
display_name email timezone
pbx_group_ids is_pbx_pilot is_pbx_group
username webusername
/],
expected_result => { code => 200 }
);
# TODO: by configuration, we should control whether passwords are present or not!
# check if creating/modifying subscribers is forbidden
$sub_res->test_post(
name => 'create subscriber without privileges',
expected_result => {
code => '403',
error_re => 'Read-only resource for authenticated role'
},
);
$sub_res->test_put(
name => 'modify-put subscriber without privileges',
item => $sub_ext,
expected_result => {
code => '403',
error_re => 'Read-only resource for authenticated role'
},
);
$sub_res->test_patch(
name => 'modify-patch subscriber without privileges',
item => $sub_ext,
data_replace => { field => 'username', value => 'test', op => 'replace' },
expected_result => {
code => '403',
error_re => 'Read-only resource for authenticated role'
},
);
# test fetching numbers
$num_res->client($c_sub_ext);
$num_res->test_get(
name => 'get numbers as unprivileged subscriber',
expected_result => { 'code' => 403 }
);
# fake a numbers item and fetch it
$num_res->test_get(
name => 'get numbers item as unprivileged subscriber',
item => { id => 999, cc => '43', ac => '999', sn => '999', subscriber_id => $c_sub_ext->{id} },
expected_result => { 'code' => 403 }
);
# check if we can't access customers
$customer_res->client($c_sub_ext);
$customer_res->test_get(
name => 'get own customer as unprivileged subscriber',
item => $customer,
expected_result => { 'code' => 403 }
);
$customer_res->test_get(
name => 'get foreign customer as unprivileged subscriber',
item => $ref->data('my_foreign_customer'),
expected_result => { 'code' => 403 }
);
}
# test working with subscribers with a subscriberadmin
{
$sub_res->client($c_subadm_ext);
my $name = 'subadmin subscriber get';
my @blacklist = (qw/
contract_id domain_id
password webpassword
uuid lock status
create_timestamp modify_timestamp
/);
foreach my $k(@blacklist) {
delete $subadm_ext->{$k};
}
# get own subscriber
$items = $sub_res->test_get(
name => $name,
item => $subadm_ext,
expected_links => [qw/
ngcp:reminders ngcp:voicemailsettings ngcp:callforwards
ngcp:subscriberpreferences ngcp:customers
/],
expected_result => { code => 200 }
);
my $item = pop @{ $items };
foreach my $k(@blacklist) {
ok(!exists $item->{$k}, "$name - absence of $k");
$test->inc_test_count();
}
# TODO: by configuration, we should control whether passwords are present or not!
# TODO: get sub_ext subscriber
# TODO: get all subscribers of customer
# check if creating/modifying subscribers is ok
$sub_res->test_post(
name => 'create subscribers as subadmin',
data_replace => [
[
# a pilot with administrative rights
{ field => 'administrative', value => 1 },
{ field => 'is_pbx_pilot', value => 1 },
{ field => 'username', value => "pilot_user_subadm_$t" },
{ field => 'password', value => "pilot_pass_subadm_$t" },
{ field => 'webusername', value => "pilot_webuser_subadm_$t" },
{ field => 'webpassword', value => "pilot_webpass_subadm_$t" },
],
[
# an extension with administrative rights
{ field => 'administrative', value => 1 },
{ field => 'primary_number', delete => 1 },
{ field => 'pbx_extension', value => '201' },
{ field => 'username', value => "subadm_user_subadm_$t" },
{ field => 'password', value => "subadm_pass_subadm_$t" },
{ field => 'webusername', value => "subadm_webuser_subadm_$t" },
{ field => 'webpassword', value => "subadm_webpass_subadm_$t" },
],
[
# an extension without rights
{ field => 'primary_number', delete => 1 },
{ field => 'pbx_extension', value => '202' },
{ field => 'username', value => "subext_user_subadm_$t" },
{ field => 'password', value => "subext_pass_subadm_$t" },
{ field => 'webusername', value => "subext_webuser_subadm_$t" },
{ field => 'webpassword', value => "subext_webpass_subadm_$t" },
],
[
# an extension in another customer
{ field => 'primary_number', delete => 1 },
{ field => 'pbx_extension', value => '203' },
{ field => 'username', value => "subext_user_foreign_$t" },
{ field => 'password', value => "subext_pass_foreign_$t" },
{ field => 'webusername', value => "subext_webuser_foreign_$t" },
{ field => 'webpassword', value => "subext_webpass_foreign_$t" },
{ field => 'customer_id', value => $ref->data('my_foreign_customer')->{id} },
]
],
expected_result => [
{ code => 422, error_re => 'Customer already has a pbx pilot subscriber.' },
{ code => 201 },
{ code => 201 },
{ code => 201 }, # this must be checked below whether customer_id is properly set
],
skip_test_fields => [qw/customer_id/], # ... so don't check explicitly here
expected_fields => [qw/
id customer_id domain administrative
primary_number alias_numbers pbx_extension
display_name email timezone
pbx_group_ids is_pbx_pilot is_pbx_group
username webusername
/],
);
$item = $sub_res->pop_created_item();
is($item->{customer_id}, $subadm_ext->{customer_id},
"subscribers - create subscribers as subadmin - foreign customer overridden");
$test->inc_test_count();
my $sub_ext_2 = $item;
$sub_res->push_created_item($sub_ext_2);
# can we change own subscriber?
$sub_res->test_put(
name => 'modify-put subscriber as subadmin',
item => $subadm_ext,
expected_result => {
code => '403',
error_re => 'Read-only resource for authenticated role'
},
);
$sub_res->test_patch(
name => 'modify-patch subscriber as subadmin',
item => $subadm_ext,
data_replace => { field => 'username', value => 'test', op => 'replace' },
expected_result => {
code => '403',
error_re => 'Read-only resource for authenticated role'
},
);
# can we change other subscriber?
$sub_res->test_put(
name => 'modify-put other subscriber as subadmin',
item => $sub_ext,
expected_result => {
code => '403',
error_re => 'Read-only resource for authenticated role'
},
);
$sub_res->test_patch(
name => 'modify-patch other subscriber as subadmin',
item => $sub_ext,
data_replace => { field => 'username', value => 'test', op => 'replace' },
expected_result => {
code => '403',
error_re => 'Read-only resource for authenticated role'
},
);
# can we fetch subscriber details of foreign customer?
$items = $sub_res->test_get(
name => 'fetch subscribers of foreign customer',
query_params => [{ customer_id => $ref->data('my_filled_customer')->{id} }],
expected_count => 0,
expected_result => { code => 200 }
);
# TODO: the above should actually return an error instead of an empty customer?
# test fetching numbers
$num_res->client($c_subadm_ext);
$items = $num_res->test_get(
name => 'get numbers as privileged subscriber',
expected_links => [qw/ngcp:subscribers/],
expected_fields => [qw/id ac cc sn subscriber_id is_primary/],
skip_test_fields => [qw/is_primary/], # don't check explicitly here
expected_result => { 'code' => 200 }
);
my $num_item = pop @{ $items };
my ($num_item_primary, $num_item_alias);
foreach my $num(@{ $num_item->{_embedded}->{'ngcp:numbers'} }) {
if(!$num_item_primary && $num->{is_primary}) {
$num_item_primary = $num;
} elsif(!$num_item_alias) {
$num_item_alias = $num;
}
last if($num_item_primary && $num_item_alias);
}
$num_res->test_put(
name => 'move primary number from pilot to ext',
item => $num_item_primary,
data_replace => {field => 'subscriber_id', value => $sub_ext->{id}},
expected_result => { code => 422, error_re => 'Cannot reassign primary number'},
);
$num_res->test_put(
name => 'move alias number from pilot to ext',
item => $num_item_alias,
data_replace => {field => 'subscriber_id', value => $sub_ext->{id}},
expected_result => { code => 200 },
);
$num_res->test_put(
name => 'move alias number from ext to ext',
item => $num_item_alias,
data_replace => {field => 'subscriber_id', value => $sub_ext_2->{id}},
expected_result => { code => 200 },
);
$num_res->test_put(
name => 'move alias number from ext to pilot',
item => $num_item_alias,
data_replace => {field => 'subscriber_id', value => $subadm_ext->{id}},
expected_result => { code => 200 },
);
$num_res->client($c_sub_ext);
$items = $num_res->test_get(
name => 'individual number fetch as ext',
item => $num_item_alias,
expected_result => { code => 403 }
);
$num_res->client($c_subadm_ext);
# move back to ext again, and check if it's moved to pilot on ext termination
$num_res->test_put(
name => 'move alias number from pilot to ext again',
item => $num_item_alias,
data_replace => {field => 'subscriber_id', value => $sub_ext->{id}},
expected_result => { code => 200 }
);
$sub_res->client($c_sub_ext);
$sub_res->test_delete(
name => 'terminate extension as unprivileged sub',
item => $sub_ext_2,
expected_result => { code => 403 }
);
$sub_res->client($c_subadm_ext);
$sub_res->test_delete(
name => 'terminate extension as subadmin',
item => $sub_ext,
expected_result => { code => 204 }
);
$items = $num_res->test_get(
name => 'number assignment after ext delete',
item => $num_item_alias,
expected_links => [qw/ngcp:subscribers/],
expected_result => { code => 200 }
);
$item = pop @{ $items };
is($item->{subscriber_id}, $subadm_pilot->{id}, "subscribers - number subscriber after ext delete");
$test->inc_test_count;
# test deletion of own subscriber
$sub_res->test_delete(
name => 'terminate own subadmin as subadmin',
item => $subadm_ext,
expected_result => { code => 403, error_re => 'Cannot terminate own subscriber' }
);
# test deletion of pilot subscriber
$sub_res->test_delete(
name => 'terminate pilot subscriber as subadmin',
item => $subadm_pilot,
expected_result => { code => 403, error_re => 'Cannot terminate pilot subscriber' }
);
# can we (not) move number to foreign sub?
$num_res->test_put(
name => 'move number to foreign subscriber',
item => $num_item_alias,
data_replace => { field => 'subscriber_id', value => $ref->data('my_foreign_pilot')->{id}},
expected_result => { code => 422, error_re => "Invalid 'subscriber_id', does not exist" }
);
# check if we can access own customer but not foreign
$customer_res->client($c_subadm_ext);
$customer_res->test_get(
name => 'get own customer as privileged subscriber',
item => $customer,
expected_links => [],
expected_result => { 'code' => 200 },
);
$customer_res->test_get(
name => 'get foreign customer as privileged subscriber',
item => $ref->data('my_foreign_customer'),
expected_result => { 'code' => 403 }
);
}
# TODO: more tests for unprivileged subscriber!
$sub_res->push_created_item($subadm_pilot);
$sub_res->push_created_item($subadm_ext);
$customer_res->push_created_item($customer);
$sub_res->client($c);
$customer_res->client($c);
$test->done();