From e90ba9d5177b404be4c37bd5165a97b408eb194f Mon Sep 17 00:00:00 2001 From: Kirill Solomko Date: Sun, 15 Jan 2023 18:14:27 +0100 Subject: [PATCH] MT#56208 allow subscriber role access to cf sets * subscriber role can now GET call forward sets that does not belong to the user but used in call forwards assigned to the user * the user can only GET the sets but cannot update/delete them (403 Forbidden is raised in case of attempt) Change-Id: I391b802d962f4bbeae991e3046ac3f132a19edb6 --- .../Panel/Controller/API/CFBNumberSetsItem.pm | 8 +++++++ .../Controller/API/CFDestinationSetsItem.pm | 4 +++- .../Panel/Controller/API/CFSourceSetsItem.pm | 2 ++ .../Panel/Controller/API/CFTimeSetsItem.pm | 2 ++ lib/NGCP/Panel/Role/API/CFBNumberSets.pm | 20 ++++++++++++++++- lib/NGCP/Panel/Role/API/CFDestinationSets.pm | 22 +++++++++++++++++-- lib/NGCP/Panel/Role/API/CFSourceSets.pm | 20 ++++++++++++++++- lib/NGCP/Panel/Role/API/CFTimeSets.pm | 20 ++++++++++++++++- 8 files changed, 92 insertions(+), 6 deletions(-) diff --git a/lib/NGCP/Panel/Controller/API/CFBNumberSetsItem.pm b/lib/NGCP/Panel/Controller/API/CFBNumberSetsItem.pm index 19e237f1bc..53ccb876ab 100644 --- a/lib/NGCP/Panel/Controller/API/CFBNumberSetsItem.pm +++ b/lib/NGCP/Panel/Controller/API/CFBNumberSetsItem.pm @@ -37,6 +37,14 @@ sub get_journal_methods{ return [qw/handle_item_base_journal handle_journals_get handle_journalsitem_get handle_journals_options handle_journalsitem_options handle_journals_head handle_journalsitem_head/]; } +sub delete_item { + my ($self, $c, $item) = @_; + + return unless $self->check_subscriber_can_update_item($c, $item); + + return $self->SUPER::delete_item($c, $item); +} + 1; # vim: set tabstop=4 expandtab: diff --git a/lib/NGCP/Panel/Controller/API/CFDestinationSetsItem.pm b/lib/NGCP/Panel/Controller/API/CFDestinationSetsItem.pm index d335386166..4d5e9fdd71 100644 --- a/lib/NGCP/Panel/Controller/API/CFDestinationSetsItem.pm +++ b/lib/NGCP/Panel/Controller/API/CFDestinationSetsItem.pm @@ -138,7 +138,9 @@ sub DELETE :Allow { { my $dset = $self->item_by_id($c, $id); last unless $self->resource_exists($c, destinationset => $dset); - + + last unless $self->check_subscriber_can_update_item($c, $dset); + last unless $self->add_delete_journal_item_hal($c,sub { my $self = shift; my ($c) = @_; diff --git a/lib/NGCP/Panel/Controller/API/CFSourceSetsItem.pm b/lib/NGCP/Panel/Controller/API/CFSourceSetsItem.pm index 3750666e46..7c01c6fec3 100644 --- a/lib/NGCP/Panel/Controller/API/CFSourceSetsItem.pm +++ b/lib/NGCP/Panel/Controller/API/CFSourceSetsItem.pm @@ -139,6 +139,8 @@ sub DELETE :Allow { my $sset = $self->item_by_id($c, $id); last unless $self->resource_exists($c, sourceset => $sset); + return unless $self->check_subscriber_can_update_item($c, $sset); + last unless $self->add_delete_journal_item_hal($c,sub { my $self = shift; my ($c) = @_; diff --git a/lib/NGCP/Panel/Controller/API/CFTimeSetsItem.pm b/lib/NGCP/Panel/Controller/API/CFTimeSetsItem.pm index 07a87d3a7e..665de8d1ad 100644 --- a/lib/NGCP/Panel/Controller/API/CFTimeSetsItem.pm +++ b/lib/NGCP/Panel/Controller/API/CFTimeSetsItem.pm @@ -138,6 +138,8 @@ sub DELETE :Allow { { my $tset = $self->item_by_id($c, $id); last unless $self->resource_exists($c, timeset => $tset); + + return unless $self->check_subscriber_can_update_item($c, $tset); last unless $self->add_delete_journal_item_hal($c,sub { my $self = shift; diff --git a/lib/NGCP/Panel/Role/API/CFBNumberSets.pm b/lib/NGCP/Panel/Role/API/CFBNumberSets.pm index a1fadc497c..bba5e13b80 100644 --- a/lib/NGCP/Panel/Role/API/CFBNumberSets.pm +++ b/lib/NGCP/Panel/Role/API/CFBNumberSets.pm @@ -58,7 +58,12 @@ sub _item_rs { }); } elsif ($c->user->roles eq "subscriber") { $item_rs = $c->model('DB')->resultset('voip_cf_bnumber_sets')->search_rs({ - 'subscriber_id' => $c->user->id, + '-or' => [ + 'me.subscriber_id' => $c->user->id, + 'voip_cf_mappings.subscriber_id' => $c->user->id, + ] + },{ + join => 'voip_cf_mappings', }); } @@ -121,12 +126,25 @@ sub check_resource { return 1; # all good } +sub check_subscriber_can_update_item { + my ($self, $c, $item) = @_; + + if ($c->user->roles eq 'subscriber' && $c->user->id != $item->subscriber_id) { + $self->error($c, HTTP_FORBIDDEN, "This bnumber set does not belong to the user"); + return; + } + + return 1; +} + sub update_item { my ($self, $c, $item, $old_resource, $resource, $form) = @_; delete $resource->{id}; my $schema = $c->model('DB'); + return unless $self->check_subscriber_can_update_item($c, $item); + return unless $self->validate_form( c => $c, form => $form, diff --git a/lib/NGCP/Panel/Role/API/CFDestinationSets.pm b/lib/NGCP/Panel/Role/API/CFDestinationSets.pm index a4bb86ea50..c51478861c 100644 --- a/lib/NGCP/Panel/Role/API/CFDestinationSets.pm +++ b/lib/NGCP/Panel/Role/API/CFDestinationSets.pm @@ -101,7 +101,12 @@ sub _item_rs { }); } elsif ($c->user->roles eq "subscriber") { $item_rs = $c->model('DB')->resultset('voip_cf_destination_sets')->search_rs({ - 'subscriber_id' => $c->user->id, + '-or' => [ + 'me.subscriber_id' => $c->user->id, + 'voip_cf_mappings.subscriber_id' => $c->user->id, + ] + },{ + join => 'voip_cf_mappings', }); } @@ -115,22 +120,35 @@ sub item_by_id { return $item_rs->find($id); } +sub check_subscriber_can_update_item { + my ($self, $c, $item) = @_; + + if ($c->user->roles eq 'subscriber' && $c->user->id != $item->subscriber_id) { + $self->error($c, HTTP_FORBIDDEN, "This destination set does not belong to the user"); + return; + } + + return 1; +} + sub update_item { my ($self, $c, $item, $old_resource, $resource, $form) = @_; delete $resource->{id}; my $schema = $c->model('DB'); + return unless $self->check_subscriber_can_update_item($c, $item); + return unless $self->validate_form( c => $c, form => $form, resource => $resource, ); + if($c->user->roles eq "subscriberadmin" || $c->user->roles eq "subscriber") { $resource->{subscriber_id} = $c->user->voip_subscriber->id; } - if (! exists $resource->{destinations} ) { $resource->{destinations} = []; } diff --git a/lib/NGCP/Panel/Role/API/CFSourceSets.pm b/lib/NGCP/Panel/Role/API/CFSourceSets.pm index c41a40b3dc..9146965f3c 100644 --- a/lib/NGCP/Panel/Role/API/CFSourceSets.pm +++ b/lib/NGCP/Panel/Role/API/CFSourceSets.pm @@ -92,7 +92,12 @@ sub _item_rs { }); } elsif ($c->user->roles eq "subscriber") { $item_rs = $c->model('DB')->resultset('voip_cf_source_sets')->search_rs({ - 'subscriber_id' => $c->user->id, + '-or' => [ + 'me.subscriber_id' => $c->user->id, + 'voip_cf_mappings.subscriber_id' => $c->user->id, + ] + },{ + join => 'voip_cf_mappings', }); } @@ -106,12 +111,25 @@ sub item_by_id { return $item_rs->find($id); } +sub check_subscriber_can_update_item { + my ($self, $c, $item) = @_; + + if ($c->user->roles eq 'subscriber' && $c->user->id != $item->subscriber_id) { + $self->error($c, HTTP_FORBIDDEN, "This source set does not belong to the user"); + return; + } + + return 1; +} + sub update_item { my ($self, $c, $item, $old_resource, $resource, $form) = @_; delete $resource->{id}; my $schema = $c->model('DB'); + return unless $self->check_subscriber_can_update_item($c, $item); + return unless $self->validate_form( c => $c, form => $form, diff --git a/lib/NGCP/Panel/Role/API/CFTimeSets.pm b/lib/NGCP/Panel/Role/API/CFTimeSets.pm index 393751a19a..0c24415539 100644 --- a/lib/NGCP/Panel/Role/API/CFTimeSets.pm +++ b/lib/NGCP/Panel/Role/API/CFTimeSets.pm @@ -369,7 +369,12 @@ sub _item_rs { }); } elsif ($c->user->roles eq "subscriber") { $item_rs = $c->model('DB')->resultset('voip_cf_time_sets')->search_rs({ - 'subscriber_id' => $c->user->id, + '-or' => [ + 'me.subscriber_id' => $c->user->id, + 'voip_cf_mappings.subscriber_id' => $c->user->id, + ] + },{ + join => 'voip_cf_mappings', }); } @@ -383,12 +388,25 @@ sub item_by_id { return $item_rs->find($id); } +sub check_subscriber_can_update_item { + my ($self, $c, $item) = @_; + + if ($c->user->roles eq 'subscriber' && $c->user->id != $item->subscriber_id) { + $self->error($c, HTTP_FORBIDDEN, "This time set does not belong to the user"); + return; + } + + return 1; +} + sub update_item { my ($self, $c, $item, $old_resource, $resource, $form) = @_; delete $resource->{id}; my $schema = $c->model('DB'); + return unless $self->check_subscriber_can_update_item($c, $item); + return unless $self->validate_form( c => $c, form => $form,