MT#4289 contracts: filter by product and separate terminate

Only show reseller and peering contracts in the
Contracts controller. Also remove the generic create
in favour of the peering/create and reseller/create.

Customer controller now has its own terminate routine to be really
independent from the Contract controller.

Now we can expose the Contract controller in the menu.
agranig/rest
Gerhard Jungwirth 13 years ago committed by Andreas Granig
parent 35c82cca7f
commit e184e00f86

@ -11,7 +11,7 @@ use NGCP::Panel::Utils::Contract;
use NGCP::Panel::Utils::Subscriber;
use NGCP::Panel::Utils::DateTime;
sub auto :Does(ACL) :ACLDetachTo('/denied_page') :AllowedRole(admin) :AllowedRole(reseller) {
sub auto :Does(ACL) :ACLDetachTo('/denied_page') :AllowedRole(admin) {
my ($self, $c) = @_;
$c->log->debug(__PACKAGE__ . '::auto');
NGCP::Panel::Utils::Navigation::check_redirect_chain(c => $c);
@ -24,7 +24,6 @@ sub contract_list :Chained('/') :PathPart('contract') :CaptureArgs(0) {
$c->stash->{contract_dt_columns} = NGCP::Panel::Utils::Datatables::set_columns($c, [
{ name => "id", search => 1, title => "#" },
{ name => "external_id", search => 1, title => "External #" },
{ name => "contact.reseller.name", search => 1, title => "Reseller" },
{ name => "contact.email", search => 1, title => "Contact Email" },
{ name => "billing_mappings.product.name", search => 1, title => "Product" },
{ name => "billing_mappings.billing_profile.name", search => 1, title => "Billing Profile" },
@ -40,10 +39,17 @@ sub contract_list :Chained('/') :PathPart('contract') :CaptureArgs(0) {
join => 'contact',
});
}
$rs = $rs->search({
'-or' => [
'product.class' => 'pstnpeering',
'product.class' => 'sippeering',
'product.class' => 'reseller',
],
}, {
'join' => {'billing_mappings' => 'product'},
});
$c->stash(contract_select_rs => $rs);
$c->stash(page_title => "Contract",
page_title_plural => "Contracts");
$c->stash(ajax_uri => $c->uri_for_action("/contract/ajax"));
$c->stash(template => 'contract/list.tt');
}
@ -52,72 +58,6 @@ sub root :Chained('contract_list') :PathPart('') :Args(0) {
my ($self, $c) = @_;
}
sub create :Chained('contract_list') :PathPart('create') :Args(0) {
my ($self, $c) = @_;
my $posted = ($c->request->method eq 'POST');
my $params = {};
$params = $params->merge($c->session->{created_objects});
my $form;
$form = NGCP::Panel::Form::Contract::Basic->new;
$form->process(
posted => $posted,
params => $c->request->params,
item => $params
);
NGCP::Panel::Utils::Navigation::check_form_buttons(
c => $c,
form => $form,
fields => {'contact.create' => $c->uri_for('/contact/create'),
'billing_profile.create' => $c->uri_for('/billing/create')},
back_uri => $c->req->uri,
);
if($posted && $form->validated) {
try {
my $schema = $c->model('DB');
$schema->txn_do(sub {
$form->params->{contact_id} = $form->params->{contact}{id};
delete $form->params->{contract};
my $bprof_id = $form->params->{billing_profile}{id};
delete $form->params->{billing_profile};
$form->{create_timestamp} = $form->{modify_timestamp} = NGCP::Panel::Utils::DateTime::current_local;
my $contract = $schema->resultset('contracts')->create($form->params);
my $billing_profile = $schema->resultset('billing_profiles')->find($bprof_id);
$contract->billing_mappings->create({
billing_profile_id => $bprof_id,
});
NGCP::Panel::Utils::Contract::create_contract_balance(
c => $c,
profile => $billing_profile,
contract => $contract,
);
delete $c->session->{created_objects}->{contact};
delete $c->session->{created_objects}->{billing_profile};
$c->session->{created_objects}->{contract} = { id => $contract->id };
my $contract_id = $contract->id;
$c->flash(messages => [{type => 'success', text => "Contract #$contract_id successfully created!"}]);
});
} catch($e) {
NGCP::Panel::Utils::Message->error(
c => $c,
error => $e,
desc => "Failed to create contract.",
);
}
NGCP::Panel::Utils::Navigation::back_or($c, $c->uri_for('/contract'));
}
$c->stash(create_flag => 1);
$c->stash(form => $form);
}
sub create_without_reseller :Chained('contract_list') :PathPart('create/noreseller') :Args(0) {
my ($self, $c) = @_;
$self->create($c, 1);
}
sub base :Chained('contract_list') :PathPart('') :CaptureArgs(1) {
my ($self, $c, $contract_id) = @_;
@ -144,8 +84,6 @@ sub base :Chained('contract_list') :PathPart('') :CaptureArgs(1) {
$billing_mapping->product->handle ne 'SIP_PEERING' &&
$billing_mapping->product->handle ne 'PSTN_PEERING')) {
$c->stash(page_title => "Customer",
page_title_plural => "Customers");
}
$c->stash(contract => {$res->get_inflated_columns});
@ -227,8 +165,7 @@ sub edit :Chained('base') :PathPart('edit') :Args(0) {
delete $c->session->{created_objects}->{contact};
delete $c->session->{created_objects}->{billing_profile};
});
my $page_title = $c->stash->{page_title};
$c->flash(messages => [{type => 'success', text => "$page_title successfully changed!"}]);
$c->flash(messages => [{type => 'success', text => "Contract successfully changed!"}]);
} catch($e) {
NGCP::Panel::Utils::Message->error(
c => $c,
@ -262,8 +199,7 @@ sub terminate :Chained('base') :PathPart('terminate') :Args(0) {
contract => $contract,
);
}
my $page_title = $c->stash->{page_title};
$c->flash(messages => [{type => 'success', text => "$page_title successfully terminated"}]);
$c->flash(messages => [{type => 'success', text => "Contract successfully terminated"}]);
} catch ($e) {
NGCP::Panel::Utils::Message->error(
c => $c,
@ -460,7 +396,8 @@ sub reseller_create :Chained('reseller_list') :PathPart('create') :Args(0) {
$c->session->{created_objects}->{contract} = { id => $contract->id };
delete $c->session->{created_objects}->{contact};
delete $c->session->{created_objects}->{billing_profile};
$c->flash(messages => [{type => 'success', text => 'Contract successfully created'}]);
my $contract_id = $contract->id;
$c->flash(messages => [{type => 'success', text => "Contract #$contract_id successfully created"}]);
});
} catch($e) {
NGCP::Panel::Utils::Message->error(

@ -380,6 +380,36 @@ sub edit :Chained('base') :PathPart('edit') :Args(0) {
$c->stash(form => $form);
}
sub terminate :Chained('base') :PathPart('terminate') :Args(0) {
my ($self, $c) = @_;
my $contract = $c->stash->{contract};
if ($contract->id == 1) {
$c->flash(messages => [{type => 'error', text => 'Cannot terminate contract with the id 1'}]);
NGCP::Panel::Utils::Navigation::back_or($c, $c->uri_for('/contract'));
}
try {
my $old_status = $contract->status;
$contract->update({ status => 'terminated' });
# if status changed, populate it down the chain
if($contract->status ne $old_status) {
NGCP::Panel::Utils::Contract::recursively_lock_contract(
c => $c,
contract => $contract,
);
}
$c->flash(messages => [{type => 'success', text => "Customer successfully terminated"}]);
} catch ($e) {
NGCP::Panel::Utils::Message->error(
c => $c,
error => $e,
desc => "Failed to terminate contract.",
);
};
NGCP::Panel::Utils::Navigation::back_or($c, $c->uri_for('/contract'));
}
sub details :Chained('base') :PathPart('details') :Args(0) {
my ($self, $c) = @_;

@ -1,8 +1,8 @@
[% site_config.title = page_title_plural -%]
[% site_config.title = "Contracts" -%]
[%
helper.name = page_title;
helper.name = "Contract";
IF edit_flag;
helper.name = page_title _ " #" _ contract.id;
helper.name = "Contract #" _ contract.id;
END;
helper.data = contracts;
helper.messages = messages;
@ -20,7 +20,8 @@
{ name = 'Edit', uri = "/contract/'+full.id+'/edit", class = 'btn-small btn-primary', icon = 'icon-edit' },
];
helper.top_buttons = [
{ name = 'Create Contract', uri = c.uri_for('/contract/create'), icon = 'icon-star' },
{ name = 'Create Peering Contract', uri = c.uri_for_action('/contract/peering_create'), icon = 'icon-star' },
{ name = 'Create Reseller Contract', uri = c.uri_for_action('/contract/reseller_create'), icon = 'icon-star' },
];
END;

@ -15,7 +15,7 @@
UNLESS c.user.read_only;
helper.dt_buttons = [
{ name = 'Edit', uri = "/customer/'+full.id+'/edit", class = 'btn-small btn-primary', icon = 'icon-edit' },
{ name = 'Terminate', uri = "/contract/'+full.id+'/terminate", class = 'btn-small btn-secondary', icon = 'icon-remove' },
{ name = 'Terminate', uri = "/customer/'+full.id+'/terminate", class = 'btn-small btn-secondary', icon = 'icon-remove' },
{ name = 'Details', uri = "/customer/'+full.id+'/details", class = 'btn-small btn-tertiary', icon = 'icon-list' },
];
helper.top_buttons = [

@ -160,7 +160,7 @@ $(document).ready(function() {
<span class="pull-left" style="margin:0 5px 0 5px;">
[% IF button.accordion_button == 1 && loop.count == 1 -%]
<a class="btn btn-primary btn-large" href="[% button.uri %]" style="margin-left:25px;"><i class="[% button.icon %]"></i> [% button.name %]</a>
[% ELSIF loop.count == 1-%]
[% ELSE -%]
<a class="btn btn-primary btn-large" href="[% button.uri %]"><i class="[% button.icon %]"></i> [% button.name %]</a>
[% END -%]
</span>

@ -200,7 +200,7 @@
UNLESS c.user.read_only;
helper.dt_buttons = [
{ name = 'Edit', uri = "/contract/'+full.id+'/edit", class = 'btn-small btn-primary', icon = 'icon-edit' },
{ name = 'Terminate', uri = "/contract/'+full.id+'/terminate", class = 'btn-small btn-secondary', icon = 'icon-remove' },
{ name = 'Terminate', uri = "/customer/'+full.id+'/terminate", class = 'btn-small btn-secondary', icon = 'icon-remove' },
{ name = 'Details', uri = "/customer/'+full.id+'/details", class = 'btn-small btn-tertiary', icon = 'icon-list' },
];
ELSE;

@ -8,6 +8,7 @@
<li><a href="[% c.uri_for('/administrator') %]">Administrators</a></li>
<li><a href="[% c.uri_for('/reseller') %]">Resellers</a></li>
<li><a href="[% c.uri_for('/customer') %]">Customers</a></li>
<li><a href="[% c.uri_for('/contract') %]">Reseller and Peering Contracts</a></li>
<li><a href="[% c.uri_for('/contact') %]">Contacts</a></li>
<li><a href="[% c.uri_for('/domain') %]">Domains</a></li>
<li><a href="[% c.uri_for('/subscriber') %]">Subscribers</a></li>

Loading…
Cancel
Save