From 1d5f3ce3165de7b5e0d3c9deabb86e774b91ef32 Mon Sep 17 00:00:00 2001 From: Oliver Gorwits Date: Sat, 24 Sep 2022 19:01:05 +0100 Subject: [PATCH] #929 implement first half of multi tenancy with tenant_databases setting --- lib/App/Netdisco/Configuration.pm | 31 +++++- lib/App/Netdisco/JobQueue/PostgreSQL.pm | 52 +++++----- lib/App/Netdisco/Transport/SNMP.pm | 2 +- lib/App/Netdisco/Util/Device.pm | 16 ++-- lib/App/Netdisco/Util/Graph.pm | 6 +- lib/App/Netdisco/Util/Nbtstat.pm | 4 +- lib/App/Netdisco/Util/Node.pm | 6 +- lib/App/Netdisco/Util/NodeMonitor.pm | 2 +- lib/App/Netdisco/Util/Port.pm | 2 +- lib/App/Netdisco/Util/PortMAC.pm | 2 +- lib/App/Netdisco/Util/Statistics.pm | 2 +- lib/App/Netdisco/Web.pm | 94 ++++++++++++++++++- lib/App/Netdisco/Web/API/Objects.pm | 14 +-- lib/App/Netdisco/Web/AdminTask.pm | 8 +- lib/App/Netdisco/Web/Device.pm | 4 +- .../Web/Plugin/AdminTask/DuplicateDevices.pm | 4 +- .../Web/Plugin/AdminTask/NodeMonitor.pm | 14 +-- .../Web/Plugin/AdminTask/OrphanedDevices.pm | 4 +- .../Web/Plugin/AdminTask/PollerPerformance.pm | 2 +- .../Web/Plugin/AdminTask/PseudoDevice.pm | 14 +-- .../Web/Plugin/AdminTask/SlowDevices.pm | 2 +- .../Web/Plugin/AdminTask/TimedOutDevices.pm | 4 +- .../Netdisco/Web/Plugin/AdminTask/Topology.pm | 12 +-- .../Plugin/AdminTask/UndiscoveredNeighbors.pm | 2 +- .../Netdisco/Web/Plugin/AdminTask/UserLog.pm | 10 +- .../Netdisco/Web/Plugin/AdminTask/Users.pm | 14 +-- .../Netdisco/Web/Plugin/Device/Addresses.pm | 2 +- lib/App/Netdisco/Web/Plugin/Device/Details.pm | 8 +- lib/App/Netdisco/Web/Plugin/Device/Modules.pm | 2 +- .../Netdisco/Web/Plugin/Device/Neighbors.pm | 14 +-- lib/App/Netdisco/Web/Plugin/Device/Ports.pm | 2 +- lib/App/Netdisco/Web/Plugin/Device/SNMP.pm | 22 ++--- lib/App/Netdisco/Web/Plugin/Device/Vlans.pm | 2 +- lib/App/Netdisco/Web/Plugin/Inventory.pm | 4 +- .../Web/Plugin/Report/ApChannelDist.pm | 2 +- .../Netdisco/Web/Plugin/Report/ApClients.pm | 2 +- .../Web/Plugin/Report/ApRadioChannelPower.pm | 4 +- .../Web/Plugin/Report/DeviceAddrNoDNS.pm | 2 +- .../Web/Plugin/Report/DeviceByLocation.pm | 2 +- .../Web/Plugin/Report/DeviceDnsMismatch.pm | 2 +- .../Web/Plugin/Report/DevicePoeStatus.pm | 4 +- .../Web/Plugin/Report/DuplexMismatch.pm | 2 +- .../Netdisco/Web/Plugin/Report/HalfDuplex.pm | 2 +- .../Web/Plugin/Report/InventoryByModelByOS.pm | 2 +- .../Netdisco/Web/Plugin/Report/IpInventory.pm | 8 +- .../Web/Plugin/Report/ModuleInventory.pm | 8 +- lib/App/Netdisco/Web/Plugin/Report/Netbios.pm | 4 +- .../Web/Plugin/Report/NodeMultiIPs.pm | 2 +- .../Netdisco/Web/Plugin/Report/NodeVendor.pm | 4 +- .../Web/Plugin/Report/NodesDiscovered.pm | 2 +- .../Web/Plugin/Report/PortAdminDown.pm | 2 +- .../Web/Plugin/Report/PortBlocking.pm | 2 +- lib/App/Netdisco/Web/Plugin/Report/PortLog.pm | 8 +- .../Web/Plugin/Report/PortMultiNodes.pm | 2 +- .../Netdisco/Web/Plugin/Report/PortSsid.pm | 2 +- .../Web/Plugin/Report/PortUtilization.pm | 4 +- .../Web/Plugin/Report/PortVLANMismatch.pm | 4 +- .../Web/Plugin/Report/SsidInventory.pm | 2 +- .../Web/Plugin/Report/SubnetUtilization.pm | 2 +- .../Web/Plugin/Report/VlanInventory.pm | 2 +- lib/App/Netdisco/Web/Plugin/Search/Device.pm | 4 +- lib/App/Netdisco/Web/Plugin/Search/Node.pm | 18 ++-- lib/App/Netdisco/Web/Plugin/Search/Port.pm | 4 +- lib/App/Netdisco/Web/Plugin/Search/VLAN.pm | 4 +- lib/App/Netdisco/Web/PortControl.pm | 4 +- lib/App/Netdisco/Web/Report.pm | 10 +- lib/App/Netdisco/Web/Search.pm | 2 +- lib/App/Netdisco/Web/Statistics.pm | 2 +- lib/App/Netdisco/Web/TypeAhead.pm | 8 +- share/config.yml | 1 + share/views/layouts/main.tt | 38 +++++++- 71 files changed, 355 insertions(+), 205 deletions(-) diff --git a/lib/App/Netdisco/Configuration.pm b/lib/App/Netdisco/Configuration.pm index dbe66b81..5f09fe42 100644 --- a/lib/App/Netdisco/Configuration.pm +++ b/lib/App/Netdisco/Configuration.pm @@ -63,11 +63,40 @@ if (ref {} eq ref setting('database')) { foreach my $c (@{setting('external_databases')}) { my $schema = delete $c->{tag} or next; - next if $schema eq 'netdisco'; + next if exists setting('plugins')->{DBIC}->{$schema}; setting('plugins')->{DBIC}->{$schema} = $c; setting('plugins')->{DBIC}->{$schema}->{schema_class} ||= 'App::Netdisco::GenericDB'; } + + foreach my $c (@{setting('tenant_databases')}) { + my $schema = $c->{tag} or next; + next if exists setting('plugins')->{DBIC}->{$schema}; + + my $name = $c->{name} || $c->{tag}; + my $host = $c->{host}; + my $user = $c->{user}; + my $pass = $c->{pass}; + + my $dsn = "dbi:Pg:dbname=${name}"; + $dsn .= ";host=${host}" if $host; + + setting('plugins')->{DBIC}->{$schema} = { + dsn => $dsn, + user => $user, + password => $pass, + options => { + AutoCommit => 1, + RaiseError => 1, + auto_savepoint => 1, + pg_enable_utf8 => 1, + }, + schema_class => 'App::Netdisco::DB', + }; + } + + # and support tenancies by setting what the default schema points to + setting('plugins')->{DBIC}->{'default'}->{'alias'} = 'netdisco'; } # always set this diff --git a/lib/App/Netdisco/JobQueue/PostgreSQL.pm b/lib/App/Netdisco/JobQueue/PostgreSQL.pm index c9f53311..a8c95b4b 100644 --- a/lib/App/Netdisco/JobQueue/PostgreSQL.pm +++ b/lib/App/Netdisco/JobQueue/PostgreSQL.pm @@ -58,8 +58,8 @@ sub _get_denied_actions { } sub jq_warm_thrusters { - my @devices = schema('netdisco')->resultset('Device')->all; - my $rs = schema('netdisco')->resultset('DeviceSkip'); + my @devices = schema(vars->{'tenant'})->resultset('Device')->all; + my $rs = schema(vars->{'tenant'})->resultset('DeviceSkip'); my %actionset = (); foreach my $d (@devices) { @@ -67,7 +67,7 @@ sub jq_warm_thrusters { $actionset{$d->ip} = \@badactions if scalar @badactions; } - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { $rs->search({ backend => setting('workers')->{'BACKEND'}, }, { for => 'update' }, )->update({ actionset => [] }); @@ -93,9 +93,9 @@ sub jq_warm_thrusters { # fix up the pseudo devices which need layer 3 # TODO remove this after next release - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { my @hosts = grep { defined } - map { schema('netdisco')->resultset('Device')->search_for_device($_->{only}) } + map { schema(vars->{'tenant'})->resultset('Device')->search_for_device($_->{only}) } grep { exists $_->{only} and ref '' eq ref $_->{only} } grep { exists $_->{driver} and $_->{driver} eq 'cli' } @{ setting('device_auth') }; @@ -109,10 +109,10 @@ sub jq_getsome { my $num_slots = shift; return () unless $num_slots and $num_slots > 0; - my $jobs = schema('netdisco')->resultset('Admin'); + my $jobs = schema(vars->{'tenant'})->resultset('Admin'); my @returned = (); - my $tasty = schema('netdisco')->resultset('Virtual::TastyJobs') + my $tasty = schema(vars->{'tenant'})->resultset('Virtual::TastyJobs') ->search(undef,{ bind => [ setting('workers')->{'BACKEND'}, setting('job_prio')->{'high'}, setting('workers')->{'BACKEND'}, setting('workers')->{'max_deferrals'}, @@ -127,7 +127,7 @@ sub jq_getsome { # and return false if it should have been skipped. my @badactions = _get_denied_actions($job->device); if (scalar @badactions) { - schema('netdisco')->resultset('DeviceSkip')->find_or_create({ + schema(vars->{'tenant'})->resultset('DeviceSkip')->find_or_create({ backend => setting('workers')->{'BACKEND'}, device => $job->device, },{ key => 'device_skip_pkey' })->add_to_actionset(@badactions); @@ -182,7 +182,7 @@ sub jq_getsome { sub jq_locked { my @returned = (); - my $rs = schema('netdisco')->resultset('Admin')->search({ + my $rs = schema(vars->{'tenant'})->resultset('Admin')->search({ status => ('queued-'. setting('workers')->{'BACKEND'}), started => \[q/> (now() - ?::interval)/, setting('jobs_stale_after')], }); @@ -196,7 +196,7 @@ sub jq_locked { sub jq_queued { my $job_type = shift; - return schema('netdisco')->resultset('Admin')->search({ + return schema(vars->{'tenant'})->resultset('Admin')->search({ device => { '!=' => undef}, action => $job_type, status => { -like => 'queued%' }, @@ -209,7 +209,7 @@ sub jq_lock { # lock db row and update to show job has been picked try { - my $updated = schema('netdisco')->resultset('Admin') + my $updated = schema(vars->{'tenant'})->resultset('Admin') ->search({ job => $job->id, status => 'queued' }, { for => 'update' }) ->update({ status => ('queued-'. setting('workers')->{'BACKEND'}), @@ -237,15 +237,15 @@ sub jq_defer { # behaviour seems reasonable, to me (or desirable, perhaps). try { - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { if ($job->device) { - schema('netdisco')->resultset('DeviceSkip')->find_or_create({ + schema(vars->{'tenant'})->resultset('DeviceSkip')->find_or_create({ backend => setting('workers')->{'BACKEND'}, device => $job->device, },{ key => 'device_skip_pkey' })->increment_deferrals; } # lock db row and update to show job is available - schema('netdisco')->resultset('Admin') + schema(vars->{'tenant'})->resultset('Admin') ->find($job->id, {for => 'update'}) ->update({ status => 'queued', started => undef }); }); @@ -269,14 +269,14 @@ sub jq_complete { # connection failures counter to forget about occasional connect glitches. try { - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { if ($job->device) { - schema('netdisco')->resultset('DeviceSkip')->find_or_create({ + schema(vars->{'tenant'})->resultset('DeviceSkip')->find_or_create({ backend => setting('workers')->{'BACKEND'}, device => $job->device, },{ key => 'device_skip_pkey' })->update({ deferrals => 0 }); } - schema('netdisco')->resultset('Admin') + schema(vars->{'tenant'})->resultset('Admin') ->find($job->id, {for => 'update'})->update({ status => $job->status, log => $job->log, @@ -297,7 +297,7 @@ sub jq_complete { } sub jq_log { - return schema('netdisco')->resultset('Admin')->search({ + return schema(vars->{'tenant'})->resultset('Admin')->search({ 'me.action' => { '-not_like' => 'hook::%' }, -or => [ { 'me.log' => undef }, @@ -312,7 +312,7 @@ sub jq_log { sub jq_userlog { my $user = shift; - return schema('netdisco')->resultset('Admin')->search({ + return schema(vars->{'tenant'})->resultset('Admin')->search({ username => $user, log => { '-not_like' => 'duplicate of %' }, finished => { '>' => \"(now() - interval '5 seconds')" }, @@ -328,8 +328,8 @@ sub jq_insert { my $happy = false; try { - schema('netdisco')->txn_do(sub { - schema('netdisco')->resultset('Admin')->populate([ + schema(vars->{'tenant'})->txn_do(sub { + schema(vars->{'tenant'})->resultset('Admin')->populate([ map {{ device => $_->{device}, device_key => $_->{device_key}, @@ -355,14 +355,14 @@ sub jq_delete { my $id = shift; if ($id) { - schema('netdisco')->txn_do(sub { - schema('netdisco')->resultset('Admin')->find($id)->delete(); + schema(vars->{'tenant'})->txn_do(sub { + schema(vars->{'tenant'})->resultset('Admin')->find($id)->delete(); }); } else { - schema('netdisco')->txn_do(sub { - schema('netdisco')->resultset('Admin')->delete(); - schema('netdisco')->resultset('DeviceSkip')->delete(); + schema(vars->{'tenant'})->txn_do(sub { + schema(vars->{'tenant'})->resultset('Admin')->delete(); + schema(vars->{'tenant'})->resultset('DeviceSkip')->delete(); }); } } diff --git a/lib/App/Netdisco/Transport/SNMP.pm b/lib/App/Netdisco/Transport/SNMP.pm index 8979bcce..2ad14ec1 100644 --- a/lib/App/Netdisco/Transport/SNMP.pm +++ b/lib/App/Netdisco/Transport/SNMP.pm @@ -97,7 +97,7 @@ sub test_connection { # avoid renumbering to localhost loopbacks return undef if $addr->addr eq '0.0.0.0' or check_acl_no($addr->addr, 'group:__LOOPBACK_ADDRESSES__'); - my $device = schema('netdisco')->resultset('Device') + my $device = schema(vars->{'tenant'})->resultset('Device') ->new_result({ ip => $addr->addr }) or return undef; my $readers = $class->instance->readers or return undef; return $readers->{$device->ip} if exists $readers->{$device->ip}; diff --git a/lib/App/Netdisco/Util/Device.pm b/lib/App/Netdisco/Util/Device.pm index 2a380a52..1489b633 100644 --- a/lib/App/Netdisco/Util/Device.pm +++ b/lib/App/Netdisco/Util/Device.pm @@ -57,12 +57,12 @@ sub get_device { # in case the management IP of one device is in use on another device, # we first try to get an exact match for the IP as mgmt interface. my $alias = - schema('netdisco')->resultset('DeviceIp')->find($ip, $ip) + schema(vars->{'tenant'})->resultset('DeviceIp')->find($ip, $ip) || - schema('netdisco')->resultset('DeviceIp')->search({alias => $ip})->first; + schema(vars->{'tenant'})->resultset('DeviceIp')->search({alias => $ip})->first; $ip = $alias->ip if defined $alias; - return schema('netdisco')->resultset('Device')->with_times + return schema(vars->{'tenant'})->resultset('Device')->with_times ->find_or_new({ip => $ip}); } @@ -82,12 +82,12 @@ sub delete_device { return 0 if not $device->in_storage; my $happy = 0; - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { # will delete everything related too... - schema('netdisco')->resultset('Device') + schema(vars->{'tenant'})->resultset('Device') ->search({ ip => $device->ip })->delete({archive_nodes => $archive}); - schema('netdisco')->resultset('UserLog')->create({ + schema(vars->{'tenant'})->resultset('UserLog')->create({ username => session('logged_in_user'), userip => scalar eval {request->remote_address}, event => (sprintf "Delete device %s", $device->ip), @@ -116,11 +116,11 @@ sub renumber_device { return 0 if not $device->in_storage; my $happy = 0; - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { $device->renumber($new_ip) or die "cannot renumber to: $new_ip"; # rollback - schema('netdisco')->resultset('UserLog')->create({ + schema(vars->{'tenant'})->resultset('UserLog')->create({ username => session('logged_in_user'), userip => scalar eval {request->remote_address}, event => (sprintf "Renumber device %s to %s", $ip, $new_ip), diff --git a/lib/App/Netdisco/Util/Graph.pm b/lib/App/Netdisco/Util/Graph.pm index 7c06cd8b..2e23ed3f 100644 --- a/lib/App/Netdisco/Util/Graph.pm +++ b/lib/App/Netdisco/Util/Graph.pm @@ -373,13 +373,13 @@ Nodes without topology information are not included. sub make_graph { my $G = Graph::Undirected->new(); - my $devices = schema('netdisco')->resultset('Device') + my $devices = schema(vars->{'tenant'})->resultset('Device') ->search({}, { columns => [qw/ip dns location /] }); - my $links = schema('netdisco')->resultset('DevicePort') + my $links = schema(vars->{'tenant'})->resultset('DevicePort') ->search({remote_ip => { -not => undef }}, { columns => [qw/ip remote_ip speed remote_type/]}); my %aliases = map {$_->alias => $_->ip} - schema('netdisco')->resultset('DeviceIp') + schema(vars->{'tenant'})->resultset('DeviceIp') ->search({}, { columns => [qw/ip alias/] })->all; my %devs = ( map {($_->ip => $_->dns)} $devices->all ); diff --git a/lib/App/Netdisco/Util/Nbtstat.pm b/lib/App/Netdisco/Util/Nbtstat.pm index 6ca6c93b..d44e16ab 100644 --- a/lib/App/Netdisco/Util/Nbtstat.pm +++ b/lib/App/Netdisco/Util/Nbtstat.pm @@ -120,7 +120,7 @@ sub _filter_nbname { unless ( check_mac( $mac, $ip ) ) { # Just assume it's the last MAC we saw this IP at. - my $node_ip = schema('netdisco')->resultset('NodeIp') + my $node_ip = schema(vars->{'tenant'})->resultset('NodeIp') ->single( { ip => $ip, -bool => 'active' } ); if ( !defined $node_ip ) { @@ -158,7 +158,7 @@ sub store_nbt { my ( $hash_ref, $now ) = @_; $now ||= 'now()'; - schema('netdisco')->resultset('NodeNbt')->update_or_create( + schema(vars->{'tenant'})->resultset('NodeNbt')->update_or_create( { mac => $hash_ref->{'mac'}, ip => $hash_ref->{'ip'}, nbname => $hash_ref->{'nbname'}, diff --git a/lib/App/Netdisco/Util/Node.pm b/lib/App/Netdisco/Util/Node.pm index f878c3da..c5ecb9de 100644 --- a/lib/App/Netdisco/Util/Node.pm +++ b/lib/App/Netdisco/Util/Node.pm @@ -175,13 +175,13 @@ sub store_arp { debug sprintf 'store_arp - mac %s ip %s', $mac->as_ieee, $ip; - schema('netdisco')->txn_do(sub { - my $current = schema('netdisco')->resultset('NodeIp') + schema(vars->{'tenant'})->txn_do(sub { + my $current = schema(vars->{'tenant'})->resultset('NodeIp') ->search( { ip => $ip, -bool => 'active'}, { columns => [qw/mac ip/] })->update({active => \'false'}); - schema('netdisco')->resultset('NodeIp') + schema(vars->{'tenant'})->resultset('NodeIp') ->update_or_create( { mac => $mac->as_ieee, diff --git a/lib/App/Netdisco/Util/NodeMonitor.pm b/lib/App/Netdisco/Util/NodeMonitor.pm index 5109bb17..cd99e361 100644 --- a/lib/App/Netdisco/Util/NodeMonitor.pm +++ b/lib/App/Netdisco/Util/NodeMonitor.pm @@ -29,7 +29,7 @@ sub _email { } sub monitor { - my $monitor = schema('netdisco')->resultset('Virtual::NodeMonitor'); + my $monitor = schema(vars->{'tenant'})->resultset('Virtual::NodeMonitor'); while (my $entry = $monitor->next) { my $body = <<"end_body"; diff --git a/lib/App/Netdisco/Util/Port.pm b/lib/App/Netdisco/Util/Port.pm index cc9ac979..85c33f3b 100644 --- a/lib/App/Netdisco/Util/Port.pm +++ b/lib/App/Netdisco/Util/Port.pm @@ -152,7 +152,7 @@ sub get_port { # accept either ip or dbic object $device = get_device($device); - my $port = schema('netdisco')->resultset('DevicePort') + my $port = schema(vars->{'tenant'})->resultset('DevicePort') ->find({ip => $device->ip, port => $portname}); return $port; diff --git a/lib/App/Netdisco/Util/PortMAC.pm b/lib/App/Netdisco/Util/PortMAC.pm index d3925938..af533b2e 100644 --- a/lib/App/Netdisco/Util/PortMAC.pm +++ b/lib/App/Netdisco/Util/PortMAC.pm @@ -36,7 +36,7 @@ sub get_port_macs { my $bindarray = [ { sqlt_datatype => "array" }, $fw_mac_list ]; my $macs - = schema('netdisco')->resultset('Virtual::PortMacs')->search({}, + = schema(vars->{'tenant'})->resultset('Virtual::PortMacs')->search({}, { bind => [$bindarray, $bindarray], select => [ 'mac', 'ip' ], group_by => [ 'mac', 'ip' ] } ); my $cursor = $macs->cursor; while ( my @vals = $cursor->next ) { diff --git a/lib/App/Netdisco/Util/Statistics.pm b/lib/App/Netdisco/Util/Statistics.pm index dd51d6be..87f7e958 100644 --- a/lib/App/Netdisco/Util/Statistics.pm +++ b/lib/App/Netdisco/Util/Statistics.pm @@ -31,7 +31,7 @@ figures. =cut sub update_stats { - my $schema = schema('netdisco'); + my $schema = schema(vars->{'tenant'}); eval { require SNMP::Info }; my $snmpinfo_ver = ($@ ? 'n/a' : $SNMP::Info::VERSION); my $postgres_ver = pretty_version($schema->storage->dbh->{pg_server_version}, 2); diff --git a/lib/App/Netdisco/Web.pm b/lib/App/Netdisco/Web.pm index 371e46bc..b5bff515 100644 --- a/lib/App/Netdisco/Web.pm +++ b/lib/App/Netdisco/Web.pm @@ -18,6 +18,7 @@ use Path::Class 'dir'; use Module::Load (); use Data::Visitor::Tiny; use Scalar::Util 'blessed'; +use Storable 'dclone'; use App::Netdisco::Util::Web qw/ interval_to_daterange @@ -27,8 +28,9 @@ use App::Netdisco::Util::Web qw/ /; BEGIN { - # https://github.com/PerlDancer/Dancer/issues/967 no warnings 'redefine'; + + # https://github.com/PerlDancer/Dancer/issues/967 *Dancer::_redirect = sub { my ($destination, $status) = @_; my $response = Dancer::SharedData->response; @@ -52,6 +54,49 @@ BEGIN { code => $status || 500)->render() )->throw; }; + + # to insert /t/$tenant if set + # which is fine for building links, but not fine for + # comparison to request->path, because when is_forward() the + # request->path is changed... + *Dancer::Request::uri_for = sub { + my ($self, $part, $params, $dont_escape) = @_; + my $uri = $self->base; + + if (vars->{'tenant'}) { + $part = '/t/'. vars->{'tenant'} . $part; + } + + # Make sure there's exactly one slash between the base and the new part + my $base = $uri->path; + $base =~ s|/$||; + $part =~ s|^/||; + $uri->path("$base/$part"); + + $uri->query_form($params) if $params; + + return $dont_escape ? uri_unescape($uri->canonical) : $uri->canonical; + }; + + # ...so here we are monkeypatching request->path as well + *Dancer::Request::path = sub { + die "path is accessor not mutator" if scalar @_ > 1; + my $self = shift; + $self->_build_path() unless $self->{path}; + + if (vars->{'tenant'} and $self->{path} !~ m{/t/}) { + my $path = $self->{path}; + my $base = setting('path'); + my $tenant = '/t/' . vars->{'tenant'}; + + $tenant = ($base . $tenant) if $base ne '/'; + $tenant .= '/' if $base eq '/'; + $path =~ s/^$base/$tenant/; + + return $path; + } + return $self->{path}; + }; } use App::Netdisco::Web::AuthN; @@ -140,6 +185,18 @@ hook after_error_render => sub { setting('layout' => 'main') }; for @port_columns; } +# build lookup for tenancies +{ + set('tenant_displaynames' => { + map { ( $_->{tag} => { displayname => $_->{displayname}, + path => config->{url_base}->with("/t/$_->{tag}")->path } ) } + @{ setting('tenant_databases') }, + { tag => 'netdisco', displayname => 'Default' } + }); + config->{'tenant_displaynames'}->{'netdisco'}->{'path'} + = URI::Based->new((config->{path} eq '/') ? '' : config->{path})->path; +} + hook 'before' => sub { my $key = request->path; if (param('tab') and ($key !~ m/ajax/)) { @@ -182,7 +239,9 @@ hook 'before_template' => sub { # allow portable static content $tokens->{uri_base} = request->base->path - if request->base->path ne '/'; + if request->base->path ne '/'; + $tokens->{uri_base} .= ('/t/'. vars->{'tenant'}) + if vars->{'tenant'}; # allow portable dynamic content $tokens->{uri_for} = sub { uri_for(@_)->path_query }; @@ -287,8 +346,23 @@ hook before_layout_render => sub { hook 'after' => sub { my $r = shift; # a Dancer::Response - if (request->path eq uri_for('/swagger.json')->path) { - $r->content( to_json( $r->content ) ); + if (request->path eq uri_for('/swagger.json')->path + and ref {} eq ref $r->content) { + my $spec = dclone $r->content; + + if (vars->{'tenant'}) { + my $base = setting('path'); + my $tenant = '/t/' . vars->{'tenant'}; + $tenant = ($base . $tenant) if $base ne '/'; + $tenant .= '/' if $base eq '/'; + + foreach my $path (sort keys %{ $spec->{paths} }) { + (my $newpath = $path) =~ s/^$base/$tenant/; + $spec->{paths}->{$newpath} = delete $spec->{paths}->{$path}; + } + } + + $r->content( to_json( $spec ) ); header('Content-Type' => 'application/json'); } @@ -364,6 +438,18 @@ hook 'after' => sub { } }; +# support for tenancies +any qr{^/t/(?[^/]+)/?$} => sub { + my $capture = captures; + var tenant => $capture->{'tenant'}; + forward '/'; +}; +any '/t/*/**' => sub { + my ($tenant, $path) = splat; + var tenant => $tenant; + forward (join '/', '', @$path, (request->path =~ m{/$} ? '' : ())); +}; + any qr{.*} => sub { var('notfound' => true); status 'not_found'; diff --git a/lib/App/Netdisco/Web/API/Objects.pm b/lib/App/Netdisco/Web/API/Objects.pm index 9b44ae42..2671b666 100644 --- a/lib/App/Netdisco/Web/API/Objects.pm +++ b/lib/App/Netdisco/Web/API/Objects.pm @@ -20,7 +20,7 @@ swagger_path { ], responses => { default => {} }, }, get '/api/v1/object/device/:ip' => require_role api => sub { - my $device = try { schema('netdisco')->resultset('Device') + my $device = try { schema(vars->{'tenant'})->resultset('Device') ->find( params->{ip} ) } or send_error('Bad Device', 404); return to_json $device->TO_JSON; }; @@ -39,7 +39,7 @@ foreach my $rel (qw/device_ips vlans ports modules port_vlans wireless_ports ssi ], responses => { default => {} }, }, get "/api/v1/object/device/:ip/$rel" => require_role api => sub { - my $rows = try { schema('netdisco')->resultset('Device') + my $rows = try { schema(vars->{'tenant'})->resultset('Device') ->find( params->{ip} )->$rel } or send_error('Bad Device', 404); return to_json [ map {$_->TO_JSON} $rows->all ]; }; @@ -65,7 +65,7 @@ foreach my $rel (qw/nodes active_nodes nodes_with_age active_nodes_with_age vlan responses => { default => {} }, }, get qr{/api/v1/object/device/(?[^/]+)/port/(?.+)/${rel}$} => require_role api => sub { my $params = captures; - my $rows = try { schema('netdisco')->resultset('DevicePort') + my $rows = try { schema(vars->{'tenant'})->resultset('DevicePort') ->find( $$params{port}, $$params{ip} )->$rel } or send_error('Bad Device or Port', 404); return to_json [ map {$_->TO_JSON} $rows->all ]; @@ -92,7 +92,7 @@ foreach my $rel (qw/power properties ssid wireless agg_master neighbor last_node responses => { default => {} }, }, get qr{/api/v1/object/device/(?[^/]+)/port/(?.+)/${rel}$} => require_role api => sub { my $params = captures; - my $row = try { schema('netdisco')->resultset('DevicePort') + my $row = try { schema(vars->{'tenant'})->resultset('DevicePort') ->find( $$params{port}, $$params{ip} )->$rel } or send_error('Bad Device or Port', 404); return to_json $row->TO_JSON; @@ -119,7 +119,7 @@ swagger_path { responses => { default => {} }, }, get qr{/api/v1/object/device/(?[^/]+)/port/(?.+)$} => require_role api => sub { my $params = captures; - my $port = try { schema('netdisco')->resultset('DevicePort') + my $port = try { schema(vars->{'tenant'})->resultset('DevicePort') ->find( $$params{port}, $$params{ip} ) } or send_error('Bad Device or Port', 404); return to_json $port->TO_JSON; @@ -145,7 +145,7 @@ swagger_path { responses => { default => {} }, }, get '/api/v1/object/device/:ip/nodes' => require_role api => sub { my $active = (params->{active_only} and ('true' eq params->{active_only})) ? 1 : 0; - my $rows = try { schema('netdisco')->resultset('Node') + my $rows = try { schema(vars->{'tenant'})->resultset('Node') ->search({ switch => params->{ip}, ($active ? (-bool => 'active') : ()) }) } or send_error('Bad Device', 404); return to_json [ map {$_->TO_JSON} $rows->all ]; @@ -172,7 +172,7 @@ swagger_path { responses => { default => {} }, }, get '/api/v1/object/vlan/:vlan/nodes' => require_role api => sub { my $active = (params->{active_only} and ('true' eq params->{active_only})) ? 1 : 0; - my $rows = try { schema('netdisco')->resultset('Node') + my $rows = try { schema(vars->{'tenant'})->resultset('Node') ->search({ vlan => params->{vlan}, ($active ? (-bool => 'active') : ()) }) } or send_error('Bad VLAN', 404); return to_json [ map {$_->TO_JSON} $rows->all ]; diff --git a/lib/App/Netdisco/Web/AdminTask.pm b/lib/App/Netdisco/Web/AdminTask.pm index 0df76cc1..9eb9322c 100644 --- a/lib/App/Netdisco/Web/AdminTask.pm +++ b/lib/App/Netdisco/Web/AdminTask.pm @@ -79,7 +79,7 @@ ajax "/ajax/control/admin/snapshot_req" => require_role admin => sub { if ! $device or $device->addr eq '0.0.0.0'; add_job('loadmibs') - if not schema('netdisco')->resultset('SNMPObject')->count(); + if not schema(vars->{'tenant'})->resultset('SNMPObject')->count(); # will store for download and for browsing add_job('snapshot', $device->addr, 'yes') or send_error('Bad device', 400); @@ -90,7 +90,7 @@ get "/ajax/content/admin/snapshot_get" => require_role admin => sub { send_error('Bad device', 400) if ! $device or $device->addr eq '0.0.0.0'; - my $content = schema('netdisco')->resultset('DeviceSnapshot')->find($device->addr)->cache; + my $content = schema(vars->{'tenant'})->resultset('DeviceSnapshot')->find($device->addr)->cache; send_file( \$content, content_type => 'text/plain', filename => ($device->addr .'-snapshot.txt') ); }; @@ -99,8 +99,8 @@ ajax "/ajax/control/admin/snapshot_del" => require_role setting('defanged_admin' send_error('Bad device', 400) if ! $device or $device->addr eq '0.0.0.0'; - schema('netdisco')->resultset('DeviceSnapshot')->find($device->addr)->delete; - schema('netdisco')->resultset('DeviceBrowser')->search({ip => $device->addr})->delete; + schema(vars->{'tenant'})->resultset('DeviceSnapshot')->find($device->addr)->delete; + schema(vars->{'tenant'})->resultset('DeviceBrowser')->search({ip => $device->addr})->delete; }; get '/admin/*' => require_role admin => sub { diff --git a/lib/App/Netdisco/Web/Device.pm b/lib/App/Netdisco/Web/Device.pm index 008c407f..7f39d4c9 100644 --- a/lib/App/Netdisco/Web/Device.pm +++ b/lib/App/Netdisco/Web/Device.pm @@ -63,7 +63,7 @@ hook 'before_template' => sub { get '/device' => require_login sub { my $q = param('q'); - my $devices = schema('netdisco')->resultset('Device'); + my $devices = schema(vars->{'tenant'})->resultset('Device'); # we are passed either dns or ip my $dev = $devices->search({ @@ -86,7 +86,7 @@ get '/device' => require_login sub { template 'device', { is_pseudo => $first->is_pseudo, display_name => ($others ? $first->ip : ($first->dns || $first->ip)), - lgroup_list => [ schema('netdisco')->resultset('Device')->get_distinct_col('location') ], + lgroup_list => [ schema(vars->{'tenant'})->resultset('Device')->get_distinct_col('location') ], hgroup_list => setting('host_group_displaynames'), device => params->{'tab'}, }, { layout => 'main' }; diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/DuplicateDevices.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/DuplicateDevices.pm index 5c808c47..608aaba9 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/DuplicateDevices.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/DuplicateDevices.pm @@ -13,8 +13,8 @@ register_admin_task({ }); ajax '/ajax/content/admin/duplicatedevices' => require_role admin => sub { - my @set = schema('netdisco')->resultset('Device')->search({ - serial => { '-in' => schema('netdisco')->resultset('Device')->search({ + my @set = schema(vars->{'tenant'})->resultset('Device')->search({ + serial => { '-in' => schema(vars->{'tenant'})->resultset('Device')->search({ '-and' => [serial => { '!=', undef }, serial => { '!=', '' }], }, { group_by => ['serial'], diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/NodeMonitor.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/NodeMonitor.pm index 98aa716b..fe8c4a10 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/NodeMonitor.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/NodeMonitor.pm @@ -24,8 +24,8 @@ sub _sanity_ok { ajax '/ajax/control/admin/nodemonitor/add' => require_role admin => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $monitor = schema('netdisco')->resultset('NodeMonitor') + schema(vars->{'tenant'})->txn_do(sub { + my $monitor = schema(vars->{'tenant'})->resultset('NodeMonitor') ->create({ mac => param('mac'), matchoui => (param('matchoui') ? \'true' : \'false'), @@ -39,8 +39,8 @@ ajax '/ajax/control/admin/nodemonitor/add' => require_role admin => sub { ajax '/ajax/control/admin/nodemonitor/del' => require_role admin => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - schema('netdisco')->resultset('NodeMonitor') + schema(vars->{'tenant'})->txn_do(sub { + schema(vars->{'tenant'})->resultset('NodeMonitor') ->find({mac => param('mac')})->delete; }); }; @@ -48,8 +48,8 @@ ajax '/ajax/control/admin/nodemonitor/del' => require_role admin => sub { ajax '/ajax/control/admin/nodemonitor/update' => require_role admin => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $monitor = schema('netdisco')->resultset('NodeMonitor') + schema(vars->{'tenant'})->txn_do(sub { + my $monitor = schema(vars->{'tenant'})->resultset('NodeMonitor') ->find({mac => param('mac')}); return unless $monitor; @@ -65,7 +65,7 @@ ajax '/ajax/control/admin/nodemonitor/update' => require_role admin => sub { }; ajax '/ajax/content/admin/nodemonitor' => require_role admin => sub { - my $set = schema('netdisco')->resultset('NodeMonitor') + my $set = schema(vars->{'tenant'})->resultset('NodeMonitor') ->search(undef, { order_by => [qw/active date mac/] }); content_type('text/html'); diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/OrphanedDevices.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/OrphanedDevices.pm index 949e7a38..5b107f72 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/OrphanedDevices.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/OrphanedDevices.pm @@ -17,11 +17,11 @@ register_admin_task( get '/ajax/content/admin/orphaned' => require_role admin => sub { - my @tree = schema('netdisco')->resultset('Virtual::UnDirEdgesAgg') + my @tree = schema(vars->{'tenant'})->resultset('Virtual::UnDirEdgesAgg') ->search( undef, { prefetch => 'device' } )->hri->all; my @orphans - = schema('netdisco')->resultset('Virtual::OrphanedDevices')->search() + = schema(vars->{'tenant'})->resultset('Virtual::OrphanedDevices')->search() ->order_by('ip')->hri->all; return unless ( scalar @tree || scalar @orphans ); diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/PollerPerformance.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/PollerPerformance.pm index f13472e5..754fb70c 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/PollerPerformance.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/PollerPerformance.pm @@ -13,7 +13,7 @@ register_admin_task({ }); ajax '/ajax/content/admin/performance' => require_role admin => sub { - my $set = schema('netdisco')->resultset('Virtual::PollerPerformance'); + my $set = schema(vars->{'tenant'})->resultset('Virtual::PollerPerformance'); content_type('text/html'); template 'ajax/admintask/performance.tt', { diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/PseudoDevice.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/PseudoDevice.pm index 8cfa1ae6..44a29800 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/PseudoDevice.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/PseudoDevice.pm @@ -32,8 +32,8 @@ sub _sanity_ok { ajax '/ajax/control/admin/pseudodevice/add' => require_role admin => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $device = schema('netdisco')->resultset('Device') + schema(vars->{'tenant'})->txn_do(sub { + my $device = schema(vars->{'tenant'})->resultset('Device') ->create({ ip => param('ip'), dns => (hostname_from_ip(param('ip')) || ''), @@ -55,7 +55,7 @@ ajax '/ajax/control/admin/pseudodevice/add' => require_role admin => sub { ]); # device_ip table is used to show whether topo is "broken" - schema('netdisco')->resultset('DeviceIp') + schema(vars->{'tenant'})->resultset('DeviceIp') ->create({ ip => param('ip'), alias => param('ip'), @@ -66,8 +66,8 @@ ajax '/ajax/control/admin/pseudodevice/add' => require_role admin => sub { ajax '/ajax/control/admin/pseudodevice/update' => require_role admin => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $device = schema('netdisco')->resultset('Device') + schema(vars->{'tenant'})->txn_do(sub { + my $device = schema(vars->{'tenant'})->resultset('Device') ->with_port_count->find({ip => param('ip')}); return unless $device; my $count = $device->port_count; @@ -87,7 +87,7 @@ ajax '/ajax/control/admin/pseudodevice/update' => require_role admin => sub { ->single({port => "Port${port}"})->delete; # clear outdated manual topology links - schema('netdisco')->resultset('Topology')->search({ + schema(vars->{'tenant'})->resultset('Topology')->search({ -or => [ { dev1 => $device->ip, port1 => "Port${port}" }, { dev2 => $device->ip, port2 => "Port${port}" }, @@ -106,7 +106,7 @@ ajax '/ajax/control/admin/pseudodevice/update' => require_role admin => sub { }; ajax '/ajax/content/admin/pseudodevice' => require_role admin => sub { - my $set = schema('netdisco')->resultset('Device') + my $set = schema(vars->{'tenant'})->resultset('Device') ->search( {-bool => 'is_pseudo'}, {order_by => { -desc => 'last_discover' }}, diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/SlowDevices.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/SlowDevices.pm index a15b88f5..e65242d2 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/SlowDevices.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/SlowDevices.pm @@ -13,7 +13,7 @@ register_admin_task({ }); ajax '/ajax/content/admin/slowdevices' => require_role admin => sub { - my $set = schema('netdisco')->resultset('Virtual::SlowDevices'); + my $set = schema(vars->{'tenant'})->resultset('Virtual::SlowDevices'); content_type('text/html'); template 'ajax/admintask/slowdevices.tt', { diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/TimedOutDevices.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/TimedOutDevices.pm index d382585e..f981deeb 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/TimedOutDevices.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/TimedOutDevices.pm @@ -17,13 +17,13 @@ ajax '/ajax/control/admin/timedoutdevices/del' => require_role admin => sub { send_error('Missing backend', 400) unless param('backend'); send_error('Missing device', 400) unless param('device'); - schema('netdisco')->resultset('DeviceSkip')->find_or_create({ + schema(vars->{'tenant'})->resultset('DeviceSkip')->find_or_create({ backend => param('backend'), device => param('device'), },{ key => 'device_skip_pkey' })->update({ deferrals => 0 }); }; ajax '/ajax/content/admin/timedoutdevices' => require_role admin => sub { - my @set = schema('netdisco')->resultset('DeviceSkip')->search({ + my @set = schema(vars->{'tenant'})->resultset('DeviceSkip')->search({ deferrals => { '>' => 0 } },{ rows => (setting('dns')->{max_outstanding} || 50), order_by => [{ -desc => 'deferrals' }, { -asc => [qw/device backend/] }] diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/Topology.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/Topology.pm index f4b0b7d7..b27e063f 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/Topology.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/Topology.pm @@ -35,7 +35,7 @@ sub _sanity_ok { ajax '/ajax/control/admin/topology/add' => require_any_role [qw(admin port_control)] => sub { send_error('Bad Request', 400) unless _sanity_ok(); - my $device = schema('netdisco')->resultset('Topology') + my $device = schema(vars->{'tenant'})->resultset('Topology') ->create({ dev1 => param('dev1'), port1 => param('port1'), @@ -46,7 +46,7 @@ ajax '/ajax/control/admin/topology/add' => require_any_role [qw(admin port_contr # re-set remote device details in affected ports # could fail for bad device or port names try { - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { # only work on root_ips my $left = get_device(param('dev1')); my $right = get_device(param('dev2')); @@ -84,8 +84,8 @@ ajax '/ajax/control/admin/topology/add' => require_any_role [qw(admin port_contr ajax '/ajax/control/admin/topology/del' => require_any_role [qw(admin port_control)] => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $device = schema('netdisco')->resultset('Topology') + schema(vars->{'tenant'})->txn_do(sub { + my $device = schema(vars->{'tenant'})->resultset('Topology') ->search({ dev1 => param('dev1'), port1 => param('port1'), @@ -97,7 +97,7 @@ ajax '/ajax/control/admin/topology/del' => require_any_role [qw(admin port_contr # re-set remote device details in affected ports # could fail for bad device or port names try { - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { # only work on root_ips my $left = get_device(param('dev1')); my $right = get_device(param('dev2')); @@ -133,7 +133,7 @@ ajax '/ajax/control/admin/topology/del' => require_any_role [qw(admin port_contr }; ajax '/ajax/content/admin/topology' => require_any_role [qw(admin port_control)] => sub { - my $set = schema('netdisco')->resultset('Topology') + my $set = schema(vars->{'tenant'})->resultset('Topology') ->search({},{order_by => [qw/dev1 dev2 port1/]}); content_type('text/html'); diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/UndiscoveredNeighbors.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/UndiscoveredNeighbors.pm index 8b1a27fb..dc6be02f 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/UndiscoveredNeighbors.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/UndiscoveredNeighbors.pm @@ -23,7 +23,7 @@ register_admin_task( get '/ajax/content/admin/undiscoveredneighbors' => require_role admin => sub { my @results - = schema('netdisco')->resultset('Virtual::UndiscoveredNeighbors')->hri->all; + = schema(vars->{'tenant'})->resultset('Virtual::UndiscoveredNeighbors')->hri->all; return unless scalar @results; if ( request->is_ajax ) { diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/UserLog.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/UserLog.pm index acde13c2..8e815213 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/UserLog.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/UserLog.pm @@ -18,7 +18,7 @@ ajax '/ajax/control/admin/userlog/data' => require_role admin => sub { send_error( 'Missing parameter', 400 ) unless ( param('draw') && param('draw') =~ /\d+/ ); - my $rs = schema('netdisco')->resultset('UserLog'); + my $rs = schema(vars->{'tenant'})->resultset('UserLog'); my $exp_params = expand_hash( scalar params ); @@ -41,18 +41,18 @@ ajax '/ajax/control/admin/userlog/data' => require_role admin => sub { ajax '/ajax/control/admin/userlog/del' => require_role admin => sub { send_error( 'Missing entry', 400 ) unless param('entry'); - schema('netdisco')->txn_do( + schema(vars->{'tenant'})->txn_do( sub { - my $device = schema('netdisco')->resultset('UserLog') + my $device = schema(vars->{'tenant'})->resultset('UserLog') ->search( { entry => param('entry') } )->delete; } ); }; ajax '/ajax/control/admin/userlog/delall' => require_role admin => sub { - schema('netdisco')->txn_do( + schema(vars->{'tenant'})->txn_do( sub { - my $device = schema('netdisco')->resultset('UserLog')->delete; + my $device = schema(vars->{'tenant'})->resultset('UserLog')->delete; } ); }; diff --git a/lib/App/Netdisco/Web/Plugin/AdminTask/Users.pm b/lib/App/Netdisco/Web/Plugin/AdminTask/Users.pm index 458ecd90..711e78e8 100644 --- a/lib/App/Netdisco/Web/Plugin/AdminTask/Users.pm +++ b/lib/App/Netdisco/Web/Plugin/AdminTask/Users.pm @@ -34,8 +34,8 @@ sub _make_password { ajax '/ajax/control/admin/users/add' => require_role setting('defanged_admin') => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $user = schema('netdisco')->resultset('User') + schema(vars->{'tenant'})->txn_do(sub { + my $user = schema(vars->{'tenant'})->resultset('User') ->create({ username => param('username'), password => _make_password(param('password')), @@ -53,8 +53,8 @@ ajax '/ajax/control/admin/users/add' => require_role setting('defanged_admin') = ajax '/ajax/control/admin/users/del' => require_role setting('defanged_admin') => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - schema('netdisco')->resultset('User') + schema(vars->{'tenant'})->txn_do(sub { + schema(vars->{'tenant'})->resultset('User') ->find({username => param('username')})->delete; }); }; @@ -62,8 +62,8 @@ ajax '/ajax/control/admin/users/del' => require_role setting('defanged_admin') = ajax '/ajax/control/admin/users/update' => require_role setting('defanged_admin') => sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $user = schema('netdisco')->resultset('User') + schema(vars->{'tenant'})->txn_do(sub { + my $user = schema(vars->{'tenant'})->resultset('User') ->find({username => param('username')}); return unless $user; @@ -83,7 +83,7 @@ ajax '/ajax/control/admin/users/update' => require_role setting('defanged_admin' }; get '/ajax/content/admin/users' => require_role admin => sub { - my @results = schema('netdisco')->resultset('User') + my @results = schema(vars->{'tenant'})->resultset('User') ->search(undef, { '+columns' => { created => \"to_char(creation, 'YYYY-MM-DD HH24:MI')", diff --git a/lib/App/Netdisco/Web/Plugin/Device/Addresses.pm b/lib/App/Netdisco/Web/Plugin/Device/Addresses.pm index 76a1c8b9..08dcf4c1 100644 --- a/lib/App/Netdisco/Web/Plugin/Device/Addresses.pm +++ b/lib/App/Netdisco/Web/Plugin/Device/Addresses.pm @@ -13,7 +13,7 @@ get '/ajax/content/device/addresses' => require_login sub { my $q = param('q'); my $device - = schema('netdisco')->resultset('Device')->search_for_device($q) + = schema(vars->{'tenant'})->resultset('Device')->search_for_device($q) or send_error( 'Bad device', 400 ); my @results = $device->device_ips diff --git a/lib/App/Netdisco/Web/Plugin/Device/Details.pm b/lib/App/Netdisco/Web/Plugin/Device/Details.pm index 93f86494..5ddbfdac 100644 --- a/lib/App/Netdisco/Web/Plugin/Device/Details.pm +++ b/lib/App/Netdisco/Web/Plugin/Device/Details.pm @@ -12,11 +12,11 @@ register_device_tab({ tag => 'details', label => 'Details' }); # device details table ajax '/ajax/content/device/details' => require_login sub { my $q = param('q'); - my $device = schema('netdisco')->resultset('Device') + my $device = schema(vars->{'tenant'})->resultset('Device') ->search_for_device($q) or send_error('Bad device', 400); my @results - = schema('netdisco')->resultset('Device') + = schema(vars->{'tenant'})->resultset('Device') ->search({ 'me.ip' => $device->ip }, { '+select' => ['snapshot.ip'], @@ -27,11 +27,11 @@ ajax '/ajax/content/device/details' => require_login sub { ->hri->all; my @power - = schema('netdisco')->resultset('DevicePower') + = schema(vars->{'tenant'})->resultset('DevicePower') ->search( { 'me.ip' => $device->ip } )->with_poestats->hri->all; my @interfaces - = schema('netdisco')->resultset('Device') + = schema(vars->{'tenant'})->resultset('Device') ->find($device->ip) ->device_ips->hri->all; diff --git a/lib/App/Netdisco/Web/Plugin/Device/Modules.pm b/lib/App/Netdisco/Web/Plugin/Device/Modules.pm index 241aab54..fe2b144b 100644 --- a/lib/App/Netdisco/Web/Plugin/Device/Modules.pm +++ b/lib/App/Netdisco/Web/Plugin/Device/Modules.pm @@ -13,7 +13,7 @@ register_device_tab({ tag => 'modules', label => 'Modules' }); ajax '/ajax/content/device/modules' => require_login sub { my $q = param('q'); - my $device = schema('netdisco')->resultset('Device') + my $device = schema(vars->{'tenant'})->resultset('Device') ->search_for_device($q) or send_error('Bad device', 400); my @set = $device->modules->search({}, {order_by => { -asc => [qw/parent class pos index/] }}); diff --git a/lib/App/Netdisco/Web/Plugin/Device/Neighbors.pm b/lib/App/Netdisco/Web/Plugin/Device/Neighbors.pm index 7a29f00e..f926ce77 100644 --- a/lib/App/Netdisco/Web/Plugin/Device/Neighbors.pm +++ b/lib/App/Netdisco/Web/Plugin/Device/Neighbors.pm @@ -19,7 +19,7 @@ ajax '/ajax/content/device/netmap' => require_login sub { ajax '/ajax/data/device/netmappositions' => require_login sub { my $q = param('q'); - my $qdev = schema('netdisco')->resultset('Device') + my $qdev = schema(vars->{'tenant'})->resultset('Device') ->search_for_device($q) or send_error('Bad device', 400); my $p = param('positions') or send_error('Missing positions', 400); @@ -55,7 +55,7 @@ ajax '/ajax/data/device/netmappositions' => require_login sub { } return unless scalar keys %clean; - my $posrow = schema('netdisco')->resultset('NetmapPositions')->find({ + my $posrow = schema(vars->{'tenant'})->resultset('NetmapPositions')->find({ device => (($mapshow eq 'neighbors') ? $qdev->ip : undef), host_groups => \[ '= ?', [host_groups => [sort @hgrplist]] ], locations => \[ '= ?', [locations => [sort @lgrplist]] ], @@ -66,7 +66,7 @@ ajax '/ajax/data/device/netmappositions' => require_login sub { $posrow->update({ positions => to_json(\%clean) }); } else { - schema('netdisco')->resultset('NetmapPositions')->create({ + schema(vars->{'tenant'})->resultset('NetmapPositions')->create({ device => (($mapshow eq 'neighbors') ? $qdev->ip : undef), host_groups => [sort @hgrplist], locations => [sort @lgrplist], @@ -136,7 +136,7 @@ sub make_link_infostring { ajax '/ajax/data/device/netmap' => require_login sub { my $q = param('q'); - my $qdev = schema('netdisco')->resultset('Device') + my $qdev = schema(vars->{'tenant'})->resultset('Device') ->search_for_device($q) or send_error('Bad device', 400); my $vlan = param('vlan'); @@ -168,7 +168,7 @@ ajax '/ajax/data/device/netmap' => require_login sub { # LINKS my %seen_link = (); - my $links = schema('netdisco')->resultset('Virtual::DeviceLinks')->search({ + my $links = schema(vars->{'tenant'})->resultset('Virtual::DeviceLinks')->search({ ($mapshow eq 'neighbors' ? ( -or => [ { left_ip => $qdev->ip }, { right_ip => $qdev->ip }, @@ -195,7 +195,7 @@ ajax '/ajax/data/device/netmap' => require_login sub { # DEVICES (NODES) - my $posrow = schema('netdisco')->resultset('NetmapPositions')->find({ + my $posrow = schema(vars->{'tenant'})->resultset('NetmapPositions')->find({ device => (($mapshow eq 'neighbors') ? $qdev->ip : undef), host_groups => \[ '= ?', [host_groups => [sort @hgrplist]] ], locations => \[ '= ?', [locations => [sort @lgrplist]] ], @@ -203,7 +203,7 @@ ajax '/ajax/data/device/netmap' => require_login sub { }); my $pos_for = from_json( $posrow ? $posrow->positions : '{}' ); - my $devices = schema('netdisco')->resultset('Device')->search({}, { + my $devices = schema(vars->{'tenant'})->resultset('Device')->search({}, { '+select' => [\'floor(log(throughput.total))'], '+as' => ['log'], join => 'throughput', distinct => 1, })->with_times; diff --git a/lib/App/Netdisco/Web/Plugin/Device/Ports.pm b/lib/App/Netdisco/Web/Plugin/Device/Ports.pm index 1eb2b4da..4a3b0179 100644 --- a/lib/App/Netdisco/Web/Plugin/Device/Ports.pm +++ b/lib/App/Netdisco/Web/Plugin/Device/Ports.pm @@ -18,7 +18,7 @@ get '/ajax/content/device/ports' => require_login sub { $prefer = '' unless defined $prefer and $prefer =~ m/^(?:port|name|vlan)$/; - my $device = schema('netdisco')->resultset('Device') + my $device = schema(vars->{'tenant'})->resultset('Device') ->search_for_device($q) or send_error('Bad device', 400); my $set = $device->ports->with_properties; diff --git a/lib/App/Netdisco/Web/Plugin/Device/SNMP.pm b/lib/App/Netdisco/Web/Plugin/Device/SNMP.pm index decff052..ecadf304 100644 --- a/lib/App/Netdisco/Web/Plugin/Device/SNMP.pm +++ b/lib/App/Netdisco/Web/Plugin/Device/SNMP.pm @@ -15,10 +15,10 @@ use Module::Load (); use Try::Tiny; register_device_tab({ tag => 'snmp', label => 'SNMP', - render_if => sub { schema('netdisco')->resultset('DeviceBrowser')->count() } }); + render_if => sub { schema(vars->{'tenant'})->resultset('DeviceBrowser')->count() } }); get '/ajax/content/device/snmp' => require_login sub { - my $device = try { schema('netdisco')->resultset('Device') + my $device = try { schema(vars->{'tenant'})->resultset('Device') ->search_for_device( param('q') ) } or send_error('Bad Device', 404); @@ -27,7 +27,7 @@ get '/ajax/content/device/snmp' => require_login sub { }; ajax '/ajax/data/device/:ip/snmptree/:base' => require_login sub { - my $device = try { schema('netdisco')->resultset('Device') + my $device = try { schema(vars->{'tenant'})->resultset('Device') ->find( param('ip') ) } or send_error('Bad Device', 404); @@ -41,14 +41,14 @@ ajax '/ajax/data/device/:ip/snmptree/:base' => require_login sub { children => \0, state => { disabled => \1 }, icon => 'icon-search', - }] unless schema('netdisco')->resultset('DeviceSnapshot')->find($device->ip); + }] unless schema(vars->{'tenant'})->resultset('DeviceSnapshot')->find($device->ip); return to_json [{ text => 'No MIB data. Please run `~/bin/netdisco-do loadmibs`.', children => \0, state => { disabled => \1 }, icon => 'icon-search', - }] unless schema('netdisco')->resultset('SNMPObject')->count(); + }] unless schema(vars->{'tenant'})->resultset('SNMPObject')->count(); my $items = _get_snmp_data($device->ip, $base); to_json $items; @@ -61,7 +61,7 @@ ajax '/ajax/data/snmp/typeahead' => require_login sub { my $deviceonly = param('deviceonly'); my $table = ($deviceonly ? 'DeviceBrowser' : 'SNMPObject'); - my @found = schema('netdisco')->resultset($table) + my @found = schema(vars->{'tenant'})->resultset($table) ->search({ -or => [ oid => $term, oid => { -like => ($term .'.%') }, leaf => { -ilike => ('%'. $term .'%') } ], @@ -80,14 +80,14 @@ ajax '/ajax/data/snmp/nodesearch' => require_login sub { my $found = undef; if ($partial) { - $found = schema('netdisco')->resultset('SNMPObject') + $found = schema(vars->{'tenant'})->resultset('SNMPObject') ->search({ -or => [ oid => $to_match, oid => { -like => ($to_match .'.%') }, leaf => { -ilike => ($to_match .'%') } ] }, { rows => 1, order_by => 'oid_parts' })->first; } else { - $found = schema('netdisco')->resultset('SNMPObject') + $found = schema(vars->{'tenant'})->resultset('SNMPObject') ->search({ -or => [ oid => $to_match, leaf => $to_match ] }, { rows => 1, order_by => 'oid_parts' })->first; @@ -108,14 +108,14 @@ ajax '/ajax/data/snmp/nodesearch' => require_login sub { }; ajax '/ajax/content/device/:ip/snmpnode/:oid' => require_login sub { - my $device = try { schema('netdisco')->resultset('Device') + my $device = try { schema(vars->{'tenant'})->resultset('Device') ->find( param('ip') ) } or send_error('Bad Device', 404); my $oid = param('oid'); $oid =~ m/^\.1(\.\d+)*$/ or send_error('Bad OID', 404); - my $object = schema('netdisco')->resultset('DeviceBrowser') + my $object = schema(vars->{'tenant'})->resultset('DeviceBrowser') ->with_snmp_object($device->ip)->find({ 'snmp_object.oid' => $oid }) or send_error('Bad OID', 404); @@ -138,7 +138,7 @@ sub _get_snmp_data { my @parts = grep {length} split m/\./, $base; my %meta = map { ('.'. join '.', @{$_->{oid_parts}}) => $_ } - schema('netdisco')->resultset('Virtual::FilteredSNMPObject') + schema(vars->{'tenant'})->resultset('Virtual::FilteredSNMPObject') ->search({}, { bind => [ $ip, (scalar @parts + 1), diff --git a/lib/App/Netdisco/Web/Plugin/Device/Vlans.pm b/lib/App/Netdisco/Web/Plugin/Device/Vlans.pm index 827f469c..7ae64987 100644 --- a/lib/App/Netdisco/Web/Plugin/Device/Vlans.pm +++ b/lib/App/Netdisco/Web/Plugin/Device/Vlans.pm @@ -15,7 +15,7 @@ register_device_tab({ tag => 'vlans', label => 'VLANs', provides_csv => 1 }); get '/ajax/content/device/vlans' => require_login sub { my $q = param('q'); - my $device = schema('netdisco')->resultset('Device') + my $device = schema(vars->{'tenant'})->resultset('Device') ->search_for_device($q) or send_error('Bad device', 400); my @results = $device->vlans->search( { vlan => { '>' => 0 } }, { order_by => 'vlan' } )->hri->all; diff --git a/lib/App/Netdisco/Web/Plugin/Inventory.pm b/lib/App/Netdisco/Web/Plugin/Inventory.pm index 0146323e..71dc40e3 100644 --- a/lib/App/Netdisco/Web/Plugin/Inventory.pm +++ b/lib/App/Netdisco/Web/Plugin/Inventory.pm @@ -13,8 +13,8 @@ register_navbar_item({ }); get '/inventory' => require_login sub { - my $platforms = schema('netdisco')->resultset('Device')->get_platforms(); - my $releases = schema('netdisco')->resultset('Device')->get_releases(); + my $platforms = schema(vars->{'tenant'})->resultset('Device')->get_platforms(); + my $releases = schema(vars->{'tenant'})->resultset('Device')->get_releases(); my %release_map = ( map { (join '', map {sprintf '%05s', $_} split m/(\D)/, ($_->{os_ver} || '')) => $_ } diff --git a/lib/App/Netdisco/Web/Plugin/Report/ApChannelDist.pm b/lib/App/Netdisco/Web/Plugin/Report/ApChannelDist.pm index 90823281..054f33b7 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/ApChannelDist.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/ApChannelDist.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/apchanneldist' => require_login sub { - my @results = schema('netdisco')->resultset('DevicePortWireless')->search( + my @results = schema(vars->{'tenant'})->resultset('DevicePortWireless')->search( { channel => { '!=', '0' } }, { select => [ 'channel', { count => 'channel' } ], as => [qw/ channel ch_count /], diff --git a/lib/App/Netdisco/Web/Plugin/Report/ApClients.pm b/lib/App/Netdisco/Web/Plugin/Report/ApClients.pm index 33e256a4..ff1ff6fb 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/ApClients.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/ApClients.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/apclients' => require_login sub { - my @results = schema('netdisco')->resultset('Device')->search( + my @results = schema(vars->{'tenant'})->resultset('Device')->search( { 'nodes.time_last' => { '>=', \'me.last_macsuck' } }, { select => [ 'ip', 'dns', 'name', 'model', 'location' ], join => { 'ports' => { 'ssid' => 'nodes' } }, diff --git a/lib/App/Netdisco/Web/Plugin/Report/ApRadioChannelPower.pm b/lib/App/Netdisco/Web/Plugin/Report/ApRadioChannelPower.pm index 54ec63be..2c86a2c7 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/ApRadioChannelPower.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/ApRadioChannelPower.pm @@ -20,7 +20,7 @@ get '/ajax/content/report/apradiochannelpower/data' => require_login sub { send_error( 'Missing parameter', 400 ) unless ( param('draw') && param('draw') =~ /\d+/ ); - my $rs = schema('netdisco')->resultset('Virtual::ApRadioChannelPower'); + my $rs = schema(vars->{'tenant'})->resultset('Virtual::ApRadioChannelPower'); my $exp_params = expand_hash( scalar params ); my $recordsTotal = $rs->count; my @data = $rs->get_datatables_data($exp_params)->hri->all; @@ -43,7 +43,7 @@ get '/ajax/content/report/apradiochannelpower' => require_login sub { } else { my @results - = schema('netdisco')->resultset('Virtual::ApRadioChannelPower') + = schema(vars->{'tenant'})->resultset('Virtual::ApRadioChannelPower') ->hri->all; return unless scalar @results; diff --git a/lib/App/Netdisco/Web/Plugin/Report/DeviceAddrNoDNS.pm b/lib/App/Netdisco/Web/Plugin/Report/DeviceAddrNoDNS.pm index ae0c1fc1..16aa99f5 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/DeviceAddrNoDNS.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/DeviceAddrNoDNS.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/deviceaddrnodns' => require_login sub { - my @results = schema('netdisco')->resultset('Device')->search( + my @results = schema(vars->{'tenant'})->resultset('Device')->search( { 'device_ips.dns' => undef }, { select => [ 'ip', 'dns', 'name', 'location', 'contact' ], join => [qw/device_ips/], diff --git a/lib/App/Netdisco/Web/Plugin/Report/DeviceByLocation.pm b/lib/App/Netdisco/Web/Plugin/Report/DeviceByLocation.pm index 233b647e..32980adb 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/DeviceByLocation.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/DeviceByLocation.pm @@ -17,7 +17,7 @@ register_report( get '/ajax/content/report/devicebylocation' => require_login sub { my @results - = schema('netdisco')->resultset('Device') + = schema(vars->{'tenant'})->resultset('Device') ->columns( [qw/ ip dns name location vendor model /] ) ->order_by( [qw/ location name ip vendor model /] )->hri->all; diff --git a/lib/App/Netdisco/Web/Plugin/Report/DeviceDnsMismatch.pm b/lib/App/Netdisco/Web/Plugin/Report/DeviceDnsMismatch.pm index e8a1ef3c..600d2ca1 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/DeviceDnsMismatch.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/DeviceDnsMismatch.pm @@ -20,7 +20,7 @@ get '/ajax/content/report/devicednsmismatch' => require_login sub { (my $suffix = '***:'. setting('domain_suffix')) =~ s|\Q(?^\Eu?|(?|g; my @results - = schema('netdisco')->resultset('Virtual::DeviceDnsMismatch') + = schema(vars->{'tenant'})->resultset('Virtual::DeviceDnsMismatch') ->search( undef, { bind => [ $suffix, $suffix ] } ) ->columns( [qw/ ip dns name location contact /] )->hri->all; diff --git a/lib/App/Netdisco/Web/Plugin/Report/DevicePoeStatus.pm b/lib/App/Netdisco/Web/Plugin/Report/DevicePoeStatus.pm index b5617d49..1af62cb9 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/DevicePoeStatus.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/DevicePoeStatus.pm @@ -20,7 +20,7 @@ get '/ajax/content/report/devicepoestatus/data' => require_login sub { send_error( 'Missing parameter', 400 ) unless ( param('draw') && param('draw') =~ /\d+/ ); - my $rs = schema('netdisco')->resultset('Virtual::DevicePoeStatus'); + my $rs = schema(vars->{'tenant'})->resultset('Virtual::DevicePoeStatus'); my $exp_params = expand_hash( scalar params ); my $recordsTotal = $rs->count; @@ -44,7 +44,7 @@ get '/ajax/content/report/devicepoestatus' => require_login sub { } else { my @results - = schema('netdisco')->resultset('Virtual::DevicePoeStatus') + = schema(vars->{'tenant'})->resultset('Virtual::DevicePoeStatus') ->hri->all; return unless scalar @results; diff --git a/lib/App/Netdisco/Web/Plugin/Report/DuplexMismatch.pm b/lib/App/Netdisco/Web/Plugin/Report/DuplexMismatch.pm index ab978a7c..94e6bfa6 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/DuplexMismatch.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/DuplexMismatch.pm @@ -17,7 +17,7 @@ register_report( get '/ajax/content/report/duplexmismatch' => require_login sub { my @results - = schema('netdisco')->resultset('Virtual::DuplexMismatch')->hri->all; + = schema(vars->{'tenant'})->resultset('Virtual::DuplexMismatch')->hri->all; return unless scalar @results; diff --git a/lib/App/Netdisco/Web/Plugin/Report/HalfDuplex.pm b/lib/App/Netdisco/Web/Plugin/Report/HalfDuplex.pm index d6a65162..d84ba589 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/HalfDuplex.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/HalfDuplex.pm @@ -17,7 +17,7 @@ register_report( get '/ajax/content/report/halfduplex' => require_login sub { my @results - = schema('netdisco')->resultset('DevicePort') + = schema(vars->{'tenant'})->resultset('DevicePort') ->columns( [qw/ ip port name duplex /] )->search( { up => 'up', duplex => { '-ilike' => 'half' } }, { '+columns' => [qw/ device.dns device.name /], diff --git a/lib/App/Netdisco/Web/Plugin/Report/InventoryByModelByOS.pm b/lib/App/Netdisco/Web/Plugin/Report/InventoryByModelByOS.pm index b5015647..856d13ce 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/InventoryByModelByOS.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/InventoryByModelByOS.pm @@ -15,7 +15,7 @@ register_report( ); get '/ajax/content/report/inventorybymodelbyos' => require_login sub { - my @results = schema('netdisco')->resultset('Device')->search(undef, { + my @results = schema(vars->{'tenant'})->resultset('Device')->search(undef, { columns => [qw/vendor model os os_ver/], select => [ { count => 'os_ver' } ], as => [qw/ os_ver_count /], diff --git a/lib/App/Netdisco/Web/Plugin/Report/IpInventory.pm b/lib/App/Netdisco/Web/Plugin/Report/IpInventory.pm index 809d2f0c..d074d5a0 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/IpInventory.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/IpInventory.pm @@ -66,7 +66,7 @@ get '/ajax/content/report/ipinventory' => require_login sub { # server-side to provide user feedback $limit = 8192 if $limit > 8192; - my $rs1 = schema('netdisco')->resultset('DeviceIp')->search( + my $rs1 = schema(vars->{'tenant'})->resultset('DeviceIp')->search( undef, { join => ['device', 'device_port'], select => [ @@ -86,7 +86,7 @@ get '/ajax/content/report/ipinventory' => require_login sub { } )->hri; - my $rs2 = schema('netdisco')->resultset('NodeIp')->search( + my $rs2 = schema(vars->{'tenant'})->resultset('NodeIp')->search( undef, { join => ['oui', 'netbios'], columns => [qw( ip mac time_first time_last dns active)], @@ -99,7 +99,7 @@ get '/ajax/content/report/ipinventory' => require_login sub { } )->hri; - my $rs3 = schema('netdisco')->resultset('NodeNbt')->search( + my $rs3 = schema(vars->{'tenant'})->resultset('NodeNbt')->search( undef, { join => ['oui'], columns => [qw( ip mac time_first time_last )], @@ -120,7 +120,7 @@ get '/ajax/content/report/ipinventory' => require_login sub { if ( $never ) { $subnet = NetAddr::IP::Lite->new('0.0.0.0/32') if ($subnet->bits ne 32); - my $rs4 = schema('netdisco')->resultset('Virtual::CidrIps')->search( + my $rs4 = schema(vars->{'tenant'})->resultset('Virtual::CidrIps')->search( undef, { bind => [ $subnet->cidr ], columns => [qw( ip mac time_first time_last dns active node age vendor nbname )], diff --git a/lib/App/Netdisco/Web/Plugin/Report/ModuleInventory.pm b/lib/App/Netdisco/Web/Plugin/Report/ModuleInventory.pm index 221b8f3f..7205f391 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/ModuleInventory.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/ModuleInventory.pm @@ -41,11 +41,11 @@ get '/ajax/content/report/moduleinventory/data' => require_login sub { send_error( 'Missing parameter', 400 ) unless ( param('draw') && param('draw') =~ /\d+/ ); - my $rs = schema('netdisco')->resultset('DeviceModule'); + my $rs = schema(vars->{'tenant'})->resultset('DeviceModule'); $rs = $rs->search( { -bool => 'fru' } ) if param('fruonly'); if ( param('device') ) { - my @ips = schema('netdisco')->resultset('Device') + my @ips = schema(vars->{'tenant'})->resultset('Device') ->search_fuzzy( param('device') )->get_column('ip')->all; params->{'ips'} = \@ips; @@ -87,14 +87,14 @@ get '/ajax/content/report/moduleinventory' => require_login sub { my $has_opt = List::MoreUtils::any { param($_) } qw/device description name type model serial class/; - my $rs = schema('netdisco')->resultset('DeviceModule'); + my $rs = schema(vars->{'tenant'})->resultset('DeviceModule'); $rs = $rs->search( { -bool => 'fru' } ) if param('fruonly'); my @results; if ( $has_opt && !request->is_ajax ) { if ( param('device') ) { - my @ips = schema('netdisco')->resultset('Device') + my @ips = schema(vars->{'tenant'})->resultset('Device') ->search_fuzzy( param('device') )->get_column('ip')->all; params->{'ips'} = \@ips; diff --git a/lib/App/Netdisco/Web/Plugin/Report/Netbios.pm b/lib/App/Netdisco/Web/Plugin/Report/Netbios.pm index 83f0ea25..873c11f8 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/Netbios.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/Netbios.pm @@ -41,7 +41,7 @@ get '/ajax/content/report/netbios/data' => require_login sub { my $domain = param('domain'); - my $rs = schema('netdisco')->resultset('NodeNbt'); + my $rs = schema(vars->{'tenant'})->resultset('NodeNbt'); my $search = $domain eq 'blank' ? '' : $domain; $rs = $rs->search( { domain => $search } ) @@ -69,7 +69,7 @@ get '/ajax/content/report/netbios' => require_login sub { my $domain = param('domain'); - my $rs = schema('netdisco')->resultset('NodeNbt'); + my $rs = schema(vars->{'tenant'})->resultset('NodeNbt'); my @results; if ( defined $domain && !request->is_ajax ) { diff --git a/lib/App/Netdisco/Web/Plugin/Report/NodeMultiIPs.pm b/lib/App/Netdisco/Web/Plugin/Report/NodeMultiIPs.pm index 30303f70..3c9fdfd9 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/NodeMultiIPs.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/NodeMultiIPs.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/nodemultiips' => require_login sub { - my @results = schema('netdisco')->resultset('Node')->search( + my @results = schema(vars->{'tenant'})->resultset('Node')->search( {}, { select => [ 'mac', 'switch', 'port' ], join => [qw/device ips oui/], diff --git a/lib/App/Netdisco/Web/Plugin/Report/NodeVendor.pm b/lib/App/Netdisco/Web/Plugin/Report/NodeVendor.pm index 480fcb93..9fefec88 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/NodeVendor.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/NodeVendor.pm @@ -42,7 +42,7 @@ get '/ajax/content/report/nodevendor/data' => require_login sub { my $vendor = param('vendor'); - my $rs = schema('netdisco')->resultset('Node'); + my $rs = schema(vars->{'tenant'})->resultset('Node'); my $match = $vendor eq 'blank' ? undef : $vendor; @@ -78,7 +78,7 @@ get '/ajax/content/report/nodevendor' => require_login sub { my $vendor = param('vendor'); - my $rs = schema('netdisco')->resultset('Node'); + my $rs = schema(vars->{'tenant'})->resultset('Node'); my @results; if ( defined $vendor && !request->is_ajax ) { diff --git a/lib/App/Netdisco/Web/Plugin/Report/NodesDiscovered.pm b/lib/App/Netdisco/Web/Plugin/Report/NodesDiscovered.pm index a55178e0..bce349df 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/NodesDiscovered.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/NodesDiscovered.pm @@ -42,7 +42,7 @@ register_report( get '/ajax/content/report/nodesdiscovered' => require_login sub { my $op = param('matchall') ? '-and' : '-or'; - my @results = schema('netdisco')->resultset('Virtual::NodesDiscovered') + my @results = schema(vars->{'tenant'})->resultset('Virtual::NodesDiscovered') ->search({ $op => [ (param('aps') ? diff --git a/lib/App/Netdisco/Web/Plugin/Report/PortAdminDown.pm b/lib/App/Netdisco/Web/Plugin/Report/PortAdminDown.pm index a1dfdb14..50d39709 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/PortAdminDown.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/PortAdminDown.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/portadmindown' => require_login sub { - my @results = schema('netdisco')->resultset('Device')->search( + my @results = schema(vars->{'tenant'})->resultset('Device')->search( { 'up_admin' => 'down' }, { select => [ 'ip', 'dns', 'name' ], join => [ 'ports' ], diff --git a/lib/App/Netdisco/Web/Plugin/Report/PortBlocking.pm b/lib/App/Netdisco/Web/Plugin/Report/PortBlocking.pm index 8cef49a9..85ef562e 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/PortBlocking.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/PortBlocking.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/portblocking' => require_login sub { - my @results = schema('netdisco')->resultset('Device')->search( + my @results = schema(vars->{'tenant'})->resultset('Device')->search( { 'stp' => [ 'blocking', 'broken' ], 'up' => { '!=', 'down' } }, { select => [ 'ip', 'dns', 'name' ], join => ['ports'], diff --git a/lib/App/Netdisco/Web/Plugin/Report/PortLog.pm b/lib/App/Netdisco/Web/Plugin/Report/PortLog.pm index 5d3e7409..d80048da 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/PortLog.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/PortLog.pm @@ -26,8 +26,8 @@ sub _sanity_ok { ajax '/ajax/control/report/portlog/add' => require_login sub { send_error('Bad Request', 400) unless _sanity_ok(); - schema('netdisco')->txn_do(sub { - my $user = schema('netdisco')->resultset('DevicePortLog') + schema(vars->{'tenant'})->txn_do(sub { + my $user = schema(vars->{'tenant'})->resultset('DevicePortLog') ->create({ ip => param('ip'), port => param('port'), @@ -45,11 +45,11 @@ ajax '/ajax/content/report/portlog' => require_login sub { my $port = param('f'); send_error('Bad Request', 400) unless $device and $port; - $device = schema('netdisco')->resultset('Device') + $device = schema(vars->{'tenant'})->resultset('Device') ->search_for_device($device); return unless $device; - my $set = schema('netdisco')->resultset('DevicePortLog')->search({ + my $set = schema(vars->{'tenant'})->resultset('DevicePortLog')->search({ ip => $device->ip, port => $port, }, { diff --git a/lib/App/Netdisco/Web/Plugin/Report/PortMultiNodes.pm b/lib/App/Netdisco/Web/Plugin/Report/PortMultiNodes.pm index 2b4790d0..e35c2bf9 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/PortMultiNodes.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/PortMultiNodes.pm @@ -22,7 +22,7 @@ register_report( ); get '/ajax/content/report/portmultinodes' => require_login sub { - my @results = schema('netdisco')->resultset('Device')->search( + my @results = schema(vars->{'tenant'})->resultset('Device')->search( { 'ports.remote_ip' => undef, (param('vlan') ? ('ports.vlan' => param('vlan'), 'nodes.vlan' => param('vlan')) : ()), diff --git a/lib/App/Netdisco/Web/Plugin/Report/PortSsid.pm b/lib/App/Netdisco/Web/Plugin/Report/PortSsid.pm index f0970ca6..a850017a 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/PortSsid.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/PortSsid.pm @@ -46,7 +46,7 @@ get '/ajax/content/report/portssid' => require_login sub { my $ssid = param('ssid'); - my $rs = schema('netdisco')->resultset('DevicePortSsid'); + my $rs = schema(vars->{'tenant'})->resultset('DevicePortSsid'); if ( defined $ssid ) { diff --git a/lib/App/Netdisco/Web/Plugin/Report/PortUtilization.pm b/lib/App/Netdisco/Web/Plugin/Report/PortUtilization.pm index 5cbed3e9..d08bda85 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/PortUtilization.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/PortUtilization.pm @@ -28,11 +28,11 @@ register_report( ); get '/ajax/content/report/portutilization' => require_login sub { - return unless schema('netdisco')->resultset('Device')->count; + return unless schema(vars->{'tenant'})->resultset('Device')->count; my $age_num = param('age_num') || 3; my $age_unit = param('age_unit') || 'months'; - my @results = schema('netdisco')->resultset('Virtual::PortUtilization') + my @results = schema(vars->{'tenant'})->resultset('Virtual::PortUtilization') ->search(undef, { bind => [ "$age_num $age_unit", "$age_num $age_unit", "$age_num $age_unit" ] })->hri->all; if (request->is_ajax) { diff --git a/lib/App/Netdisco/Web/Plugin/Report/PortVLANMismatch.pm b/lib/App/Netdisco/Web/Plugin/Report/PortVLANMismatch.pm index 369a8746..366cb6c4 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/PortVLANMismatch.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/PortVLANMismatch.pm @@ -17,8 +17,8 @@ register_report( ); get '/ajax/content/report/portvlanmismatch' => require_login sub { - return unless schema('netdisco')->resultset('Device')->count; - my @results = schema('netdisco') + return unless schema(vars->{'tenant'})->resultset('Device')->count; + my @results = schema(vars->{'tenant'}) ->resultset('Virtual::PortVLANMismatch')->search({},{ bind => [ setting('sidebar_defaults')->{'device_ports'}->{'p_hide1002'}->{'default'} ? (1002, 1003, 1004, 1005) : (0, 0, 0, 0) ], diff --git a/lib/App/Netdisco/Web/Plugin/Report/SsidInventory.pm b/lib/App/Netdisco/Web/Plugin/Report/SsidInventory.pm index 9a7844b3..619fc456 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/SsidInventory.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/SsidInventory.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/ssidinventory' => require_login sub { - my @results = schema('netdisco')->resultset('DevicePortSsid') + my @results = schema(vars->{'tenant'})->resultset('DevicePortSsid') ->get_ssids->hri->all; return unless scalar @results; diff --git a/lib/App/Netdisco/Web/Plugin/Report/SubnetUtilization.pm b/lib/App/Netdisco/Web/Plugin/Report/SubnetUtilization.pm index c4351a03..b2087bc0 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/SubnetUtilization.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/SubnetUtilization.pm @@ -40,7 +40,7 @@ get '/ajax/content/report/subnets' => require_login sub { $start = $start . ' 00:00:00'; $end = $end . ' 23:59:59'; - my @results = schema('netdisco')->resultset('Virtual::SubnetUtilization') + my @results = schema(vars->{'tenant'})->resultset('Virtual::SubnetUtilization') ->search(undef,{ bind => [ $subnet, $start, $end, $start, $subnet, $start, $start ], })->hri->all; diff --git a/lib/App/Netdisco/Web/Plugin/Report/VlanInventory.pm b/lib/App/Netdisco/Web/Plugin/Report/VlanInventory.pm index 389b74d0..9f56dcaa 100644 --- a/lib/App/Netdisco/Web/Plugin/Report/VlanInventory.pm +++ b/lib/App/Netdisco/Web/Plugin/Report/VlanInventory.pm @@ -16,7 +16,7 @@ register_report( ); get '/ajax/content/report/vlaninventory' => require_login sub { - my @results = schema('netdisco')->resultset('DeviceVlan')->search( + my @results = schema(vars->{'tenant'})->resultset('DeviceVlan')->search( { 'me.description' => { '!=', 'NULL' }, 'me.vlan' => { '>' => 0 }, 'ports.vlan' => { '>' => 0 }, diff --git a/lib/App/Netdisco/Web/Plugin/Search/Device.pm b/lib/App/Netdisco/Web/Plugin/Search/Device.pm index 5b59ed32..9299aae6 100644 --- a/lib/App/Netdisco/Web/Plugin/Search/Device.pm +++ b/lib/App/Netdisco/Web/Plugin/Search/Device.pm @@ -72,10 +72,10 @@ get '/ajax/content/search/device' => require_login sub { my $see_all = param('seeallcolumns'); if ($see_all) { - $rs_columns = schema('netdisco')->resultset('Device'); + $rs_columns = schema(vars->{'tenant'})->resultset('Device'); } else { - $rs_columns = schema('netdisco')->resultset('Device')->columns( + $rs_columns = schema(vars->{'tenant'})->resultset('Device')->columns( [ "ip", "dns", "name", "location", "model", "os_ver", "serial", "chassis_id" ] diff --git a/lib/App/Netdisco/Web/Plugin/Search/Node.pm b/lib/App/Netdisco/Web/Plugin/Search/Node.pm index ea589099..f548d120 100644 --- a/lib/App/Netdisco/Web/Plugin/Search/Node.pm +++ b/lib/App/Netdisco/Web/Plugin/Search/Node.pm @@ -131,7 +131,7 @@ get '/ajax/content/search/node' => require_login sub { ($using_wildcards ? \['me.mac::text ILIKE ?', $likeval] : ((!defined $mac or $mac->errstr) ? \'0=1' : ('me.mac' => $mac->as_ieee)) ); - my $sightings = schema('netdisco')->resultset('Node') + my $sightings = schema(vars->{'tenant'})->resultset('Node') ->search({-and => [@where_mac, @active, @times]}, { order_by => {'-desc' => 'time_last'}, '+columns' => [ @@ -143,7 +143,7 @@ get '/ajax/content/search/node' => require_login sub { join => 'device', }); - my $ips = schema('netdisco')->resultset('NodeIp') + my $ips = schema(vars->{'tenant'})->resultset('NodeIp') ->search({-and => [@where_mac, @active, @times]}, { order_by => {'-desc' => 'time_last'}, '+columns' => [ @@ -155,7 +155,7 @@ get '/ajax/content/search/node' => require_login sub { join => 'oui' }); - my $netbios = schema('netdisco')->resultset('NodeNbt') + my $netbios = schema(vars->{'tenant'})->resultset('NodeNbt') ->search({-and => [@where_mac, @active, @times]}, { order_by => {'-desc' => 'time_last'}, '+columns' => [ @@ -167,7 +167,7 @@ get '/ajax/content/search/node' => require_login sub { join => 'oui' }); - my $wireless = schema('netdisco')->resultset('NodeWireless')->search( + my $wireless = schema(vars->{'tenant'})->resultset('NodeWireless')->search( { -and => [@where_mac, @wifitimes] }, { order_by => { '-desc' => 'time_last' }, '+columns' => [ @@ -180,7 +180,7 @@ get '/ajax/content/search/node' => require_login sub { } ); - my $rs_dp = schema('netdisco')->resultset('DevicePort'); + my $rs_dp = schema(vars->{'tenant'})->resultset('DevicePort'); if ($sightings->has_rows or $ips->has_rows or $netbios->has_rows) { my $ports = param('deviceports') ? $rs_dp->search({ -and => [@where_mac] }, { order_by => { '-desc' => 'creation' }}) : undef; @@ -208,7 +208,7 @@ get '/ajax/content/search/node' => require_login sub { } } - my $set = schema('netdisco')->resultset('NodeNbt') + my $set = schema(vars->{'tenant'})->resultset('NodeNbt') ->search_by_name({nbname => $likeval, @active, @times}); unless ( $set->has_rows ) { @@ -216,11 +216,11 @@ get '/ajax/content/search/node' => require_login sub { and my $ip = NetAddr::IP::Lite->new($node)) { # search_by_ip() will extract cidr notation if necessary - $set = schema('netdisco')->resultset('NodeIp') + $set = schema(vars->{'tenant'})->resultset('NodeIp') ->search_by_ip({ip => $ip, @active, @times}); } else { - $set = schema('netdisco')->resultset('NodeIp') + $set = schema(vars->{'tenant'})->resultset('NodeIp') ->search_by_dns({ ($using_wildcards ? (dns => $likeval) : (dns => "${likeval}.\%", @@ -233,7 +233,7 @@ get '/ajax/content/search/node' => require_login sub { # we'll try the OUI company name as a fallback if (param('show_vendor') and not $set->has_rows) { - $set = schema('netdisco')->resultset('NodeIp') + $set = schema(vars->{'tenant'})->resultset('NodeIp') ->with_times ->search( {'oui.company' => { -ilike => ''.sql_match($node)}, @times}, diff --git a/lib/App/Netdisco/Web/Plugin/Search/Port.pm b/lib/App/Netdisco/Web/Plugin/Search/Port.pm index 1c945b87..2a7b29e4 100644 --- a/lib/App/Netdisco/Web/Plugin/Search/Port.pm +++ b/lib/App/Netdisco/Web/Plugin/Search/Port.pm @@ -45,7 +45,7 @@ get '/ajax/content/search/port' => require_login sub { my $rs; if ($q =~ m/^[0-9]+$/ and $q < 4096) { - $rs = schema('netdisco')->resultset('DevicePort') + $rs = schema(vars->{'tenant'})->resultset('DevicePort') ->columns( [qw/ ip port name up up_admin speed /] )->search({ "port_vlans.vlan" => $q, ( param('uplink') ? () : (-or => [ @@ -70,7 +70,7 @@ get '/ajax/content/search/port' => require_login sub { and (($mac->as_ieee eq '00:00:00:00:00:00') or ($mac->as_ieee !~ m/$RE{net}{MAC}/))); - $rs = schema('netdisco')->resultset('DevicePort') + $rs = schema(vars->{'tenant'})->resultset('DevicePort') ->columns( [qw/ ip port name up up_admin speed /] ) ->search({ -and => [ diff --git a/lib/App/Netdisco/Web/Plugin/Search/VLAN.pm b/lib/App/Netdisco/Web/Plugin/Search/VLAN.pm index 3bd47476..d089edcd 100644 --- a/lib/App/Netdisco/Web/Plugin/Search/VLAN.pm +++ b/lib/App/Netdisco/Web/Plugin/Search/VLAN.pm @@ -27,11 +27,11 @@ get '/ajax/content/search/vlan' => require_login sub { my $rs; if ( $q =~ m/^\d+$/ ) { - $rs = schema('netdisco')->resultset('Device') + $rs = schema(vars->{'tenant'})->resultset('Device') ->carrying_vlan( { vlan => $q } ); } else { - $rs = schema('netdisco')->resultset('Device') + $rs = schema(vars->{'tenant'})->resultset('Device') ->carrying_vlan_name( { name => $q } ); } diff --git a/lib/App/Netdisco/Web/PortControl.pm b/lib/App/Netdisco/Web/PortControl.pm index eff24f47..9c3c6686 100644 --- a/lib/App/Netdisco/Web/PortControl.pm +++ b/lib/App/Netdisco/Web/PortControl.pm @@ -29,13 +29,13 @@ ajax '/ajax/portcontrol' => require_any_role [qw(admin port_control)] => sub { ? (param('action') ."-other") : param('value')); - schema('netdisco')->txn_do(sub { + schema(vars->{'tenant'})->txn_do(sub { if (param('port')) { my $act = "$action $subaction"; $act =~ s/-other$//; $act =~ s/^portcontrol/port/; - schema('netdisco')->resultset('DevicePortLog')->create({ + schema(vars->{'tenant'})->resultset('DevicePortLog')->create({ ip => param('device'), port => param('port'), action => $act, diff --git a/lib/App/Netdisco/Web/Report.pm b/lib/App/Netdisco/Web/Report.pm index 77fbeacc..53694206 100644 --- a/lib/App/Netdisco/Web/Report.pm +++ b/lib/App/Netdisco/Web/Report.pm @@ -11,24 +11,24 @@ get '/report/*' => require_login sub { my ( $domain_list, $class_list, $ssid_list, $type_list, $vendor_list ); if ( $tag eq 'netbios' ) { - $domain_list = [ schema('netdisco')->resultset('NodeNbt') + $domain_list = [ schema(vars->{'tenant'})->resultset('NodeNbt') ->get_distinct_col('domain') ]; } elsif ( $tag eq 'moduleinventory' ) { - $class_list = [ schema('netdisco')->resultset('DeviceModule') + $class_list = [ schema(vars->{'tenant'})->resultset('DeviceModule') ->get_distinct_col('class') ]; } elsif ( $tag eq 'portssid' ) { - $ssid_list = [ schema('netdisco')->resultset('DevicePortSsid') + $ssid_list = [ schema(vars->{'tenant'})->resultset('DevicePortSsid') ->get_distinct_col('ssid') ]; } elsif ( $tag eq 'nodesdiscovered' ) { - $type_list = [ schema('netdisco')->resultset('DevicePort') + $type_list = [ schema(vars->{'tenant'})->resultset('DevicePort') ->get_distinct_col('remote_type') ]; } elsif ( $tag eq 'nodevendor' ) { $vendor_list = [ - schema('netdisco')->resultset('Node')->search( + schema(vars->{'tenant'})->resultset('Node')->search( {}, { join => 'oui', columns => ['oui.abbrev'], diff --git a/lib/App/Netdisco/Web/Search.pm b/lib/App/Netdisco/Web/Search.pm index 0affb993..eacd638d 100644 --- a/lib/App/Netdisco/Web/Search.pm +++ b/lib/App/Netdisco/Web/Search.pm @@ -24,7 +24,7 @@ hook 'before_template' => sub { get '/search' => require_login sub { my $q = param('q'); - my $s = schema('netdisco'); + my $s = schema(vars->{'tenant'}); if (not param('tab')) { if (not $q) { diff --git a/lib/App/Netdisco/Web/Statistics.pm b/lib/App/Netdisco/Web/Statistics.pm index 9c523a68..3f1b4ccb 100644 --- a/lib/App/Netdisco/Web/Statistics.pm +++ b/lib/App/Netdisco/Web/Statistics.pm @@ -6,7 +6,7 @@ use Dancer::Plugin::Auth::Extensible; get '/ajax/content/statistics' => require_login sub { - my $stats = schema('netdisco')->resultset('Statistics') + my $stats = schema(vars->{'tenant'})->resultset('Statistics') ->search(undef, { order_by => { -desc => 'day' }, rows => 1 }); $stats = ($stats->count ? $stats->first : undef); diff --git a/lib/App/Netdisco/Web/TypeAhead.pm b/lib/App/Netdisco/Web/TypeAhead.pm index 40c7da62..98817f9d 100644 --- a/lib/App/Netdisco/Web/TypeAhead.pm +++ b/lib/App/Netdisco/Web/TypeAhead.pm @@ -11,7 +11,7 @@ ajax '/ajax/data/devicename/typeahead' => require_login sub { return '[]' unless setting('navbar_autocomplete'); my $q = param('query') || param('term'); - my $set = schema('netdisco')->resultset('Device')->search_fuzzy($q); + my $set = schema(vars->{'tenant'})->resultset('Device')->search_fuzzy($q); content_type 'application/json'; to_json [map {$_->dns || $_->name || $_->ip} $set->all]; @@ -19,7 +19,7 @@ ajax '/ajax/data/devicename/typeahead' => require_login sub { ajax '/ajax/data/deviceip/typeahead' => require_login sub { my $q = param('query') || param('term'); - my $set = schema('netdisco')->resultset('Device')->search_fuzzy($q); + my $set = schema(vars->{'tenant'})->resultset('Device')->search_fuzzy($q); my @data = (); while (my $d = $set->next) { @@ -40,7 +40,7 @@ ajax '/ajax/data/port/typeahead' => require_login sub { my $port = param('port1') || param('port2'); send_error('Missing device', 400) unless $dev; - my $device = schema('netdisco')->resultset('Device') + my $device = schema(vars->{'tenant'})->resultset('Device') ->find({ip => $dev}); send_error('Bad device', 400) unless $device; @@ -60,7 +60,7 @@ ajax '/ajax/data/port/typeahead' => require_login sub { ajax '/ajax/data/subnet/typeahead' => require_login sub { my $q = param('query') || param('term'); $q = "$q\%" if $q !~ m/\%/; - my $nets = schema('netdisco')->resultset('Subnet')->search( + my $nets = schema(vars->{'tenant'})->resultset('Subnet')->search( { 'me.net::text' => { '-ilike' => $q }}, { columns => ['net'], order_by => 'net' } ); diff --git a/share/config.yml b/share/config.yml index 773755c7..c889dfe8 100644 --- a/share/config.yml +++ b/share/config.yml @@ -17,6 +17,7 @@ include_paths: [] template_paths: [] site_local_files: false external_databases: [] +tenant_databases: [] # ------------ # WEB FRONTEND diff --git a/share/views/layouts/main.tt b/share/views/layouts/main.tt index 221346b4..2f404305 100644 --- a/share/views/layouts/main.tt +++ b/share/views/layouts/main.tt @@ -76,7 +76,7 @@