implement device search!
This commit is contained in:
		| @@ -82,6 +82,7 @@ __PACKAGE__->set_primary_key("ip"); | ||||
| # Created by DBIx::Class::Schema::Loader v0.07015 @ 2012-01-07 14:20:02 | ||||
| # DO NOT MODIFY THIS OR ANYTHING ABOVE! md5sum:671/XuuvsO2aMB1+IRWFjg | ||||
|  | ||||
| __PACKAGE__->has_many( device_ips => 'Netdisco::DB::Result::DeviceIp', 'ip' ); | ||||
| __PACKAGE__->has_many( vlans => 'Netdisco::DB::Result::DeviceVlan', 'ip' ); | ||||
| __PACKAGE__->has_many( ports => 'Netdisco::DB::Result::DevicePort', 'ip' ); | ||||
| __PACKAGE__->has_many( | ||||
|   | ||||
| @@ -34,6 +34,6 @@ __PACKAGE__->set_primary_key("ip", "alias"); | ||||
| # Created by DBIx::Class::Schema::Loader v0.07015 @ 2012-01-07 14:20:02 | ||||
| # DO NOT MODIFY THIS OR ANYTHING ABOVE! md5sum:/ugGtBSGyrJ7s6yqJ9bclQ | ||||
|  | ||||
| __PACKAGE__->belongs_to( device => 'Netdisco::DB::Result::Device', 'ip' ); | ||||
|  | ||||
| # You can replace this text with custom code or comments, and it will be preserved on regeneration | ||||
| 1; | ||||
|   | ||||
| @@ -1,6 +1,97 @@ | ||||
| package Netdisco::DB::ResultSet::Device; | ||||
| use base 'DBIx::Class::ResultSet'; | ||||
|  | ||||
| use NetAddr::IP::Lite ':lower'; | ||||
|  | ||||
| # finds distinct values of a col for use in form selections | ||||
| sub get_distinct { | ||||
|   my ($set, $col) = @_; | ||||
|   return $set unless $col; | ||||
|  | ||||
|   return $set->search({}, | ||||
|     { | ||||
|       columns => [$col], | ||||
|       order_by => $col, | ||||
|       distinct => 1 | ||||
|     } | ||||
|   )->get_column($col)->all; | ||||
| } | ||||
|  | ||||
| sub by_field { | ||||
|     my ($set, $p) = @_; | ||||
|     return $set unless ref {} eq ref $p; | ||||
|     my $op = $p->{matchall} ? '-and' : '-or'; | ||||
|  | ||||
|     # this is a bit of a dreadful hack to catch junk entry | ||||
|     # whilst avoiding returning all devices in the DB | ||||
|     my $ip = ($p->{ip} ? | ||||
|       (NetAddr::IP::Lite->new($p->{ip}) || NetAddr::IP::Lite->new('255.255.255.255')) | ||||
|       : undef); | ||||
|  | ||||
|     return $set->search( | ||||
|       { | ||||
|         $op => [ | ||||
|           ($p->{name} ? ('me.name' => | ||||
|             { '-ilike' => "\%$p->{name}\%" }) : ()), | ||||
|           ($p->{location} ? ('me.location' => | ||||
|             { '-ilike' => "\%$p->{location}\%" }) : ()), | ||||
|           ($p->{description} ? ('me.description' => | ||||
|             { '-ilike' => "\%$p->{description}\%" }) : ()), | ||||
|           ($p->{model} ? ('me.model' => | ||||
|             { '-in' => $p->{model} }) : ()), | ||||
|           ($p->{os_ver} ? ('me.os_ver' => | ||||
|             { '-in' => $p->{os_ver} }) : ()), | ||||
|           ($p->{vendor} ? ('me.vendor' => | ||||
|             { '-in' => $p->{vendor} }) : ()), | ||||
|           ($p->{dns} ? ( | ||||
|           -or => [ | ||||
|             'me.dns'      => { '-ilike' => "\%$p->{dns}\%" }, | ||||
|             'device_ips.dns' => { '-ilike' => "\%$p->{dns}\%" }, | ||||
|           ]) : ()), | ||||
|           ($ip ? ( | ||||
|           -or => [ | ||||
|             'me.ip'  => { '<<=' => $ip->cidr }, | ||||
|             'device_ips.alias' => { '<<=' => $ip->cidr }, | ||||
|           ]) : ()), | ||||
|         ], | ||||
|       }, | ||||
|       { | ||||
|         join => 'device_ips', | ||||
|         group_by => 'me.ip', | ||||
|       } | ||||
|     ); | ||||
| } | ||||
|  | ||||
| sub by_any { | ||||
|     my ($set, $q) = @_; | ||||
|     return $set unless $q; | ||||
|     $q = "\%$q\%" if $q !~ m/\%/; | ||||
|  | ||||
|     return $set->search( | ||||
|       { | ||||
|         -or => [ | ||||
|           'me.contact'  => { '-ilike' => $q }, | ||||
|           'me.serial'   => { '-ilike' => $q }, | ||||
|           'me.location' => { '-ilike' => $q }, | ||||
|           'me.name'     => { '-ilike' => $q }, | ||||
|           'me.description' => { '-ilike' => $q }, | ||||
|           -or => [ | ||||
|             'me.dns'      => { '-ilike' => $q }, | ||||
|             'device_ips.dns' => { '-ilike' => $q }, | ||||
|           ], | ||||
|           -or => [ | ||||
|             'me.ip::text'  => { '-ilike' => $q }, | ||||
|             'device_ips.alias::text' => { '-ilike' => $q }, | ||||
|           ], | ||||
|         ], | ||||
|       }, | ||||
|       { | ||||
|         join => 'device_ips', | ||||
|         group_by => 'me.ip', | ||||
|       } | ||||
|     ); | ||||
| } | ||||
|  | ||||
| sub carrying_vlan { | ||||
|     my ($set, $vlan) = @_; | ||||
|     return $set unless $vlan and $vlan =~ m/^\d+$/; | ||||
| @@ -19,5 +110,4 @@ sub carrying_vlan { | ||||
|     ); | ||||
| } | ||||
|  | ||||
|  | ||||
| 1; | ||||
|   | ||||
| @@ -26,6 +26,7 @@ sub by_mac { | ||||
| sub by_name { | ||||
|     my ($set, $name) = @_; | ||||
|     return $set unless $name; | ||||
|     $name = "\%$name\%" if $name !~ m/\%/; | ||||
|  | ||||
|     return $set->search( | ||||
|       { | ||||
|   | ||||
| @@ -8,6 +8,7 @@ use Digest::MD5 (); | ||||
| use Socket6 (); # to ensure dependency is met | ||||
| use NetAddr::IP::Lite ':lower'; | ||||
| use Net::MAC (); | ||||
| use List::MoreUtils (); | ||||
|  | ||||
| hook 'before' => sub { | ||||
|     if (! session('user') && request->path !~ m{^/login}) { | ||||
| @@ -20,20 +21,50 @@ hook 'before' => sub { | ||||
|     if (not param('tab') or param('tab') ne 'node') { | ||||
|         params->{'stamps'} = 'checked'; | ||||
|     } | ||||
|     if (not param('tab') or param('tab') ne 'device') { | ||||
|         params->{'matchall'} = 'matchall'; | ||||
|     } | ||||
|  | ||||
|     # set up query string defaults for templates | ||||
|     # set up query string defaults, | ||||
|     # only for templates which link to themselves (node) | ||||
|     var('query_defaults' => { map { ($_ => "tab=$_") } qw/node/ }); | ||||
|     var('query_defaults')->{node} .= "\&$_=". (param($_) || '') | ||||
|       for qw/stamps vendor archived partial/; | ||||
|  | ||||
|     # set up property lists for device search | ||||
|     var('model_list' => [ | ||||
|       schema('netdisco')->resultset('Device')->get_distinct('model') | ||||
|     ]); | ||||
|     var('os_ver_list' => [ | ||||
|       schema('netdisco')->resultset('Device')->get_distinct('os_ver') | ||||
|     ]); | ||||
|     var('vendor_list' => [ | ||||
|       schema('netdisco')->resultset('Device')->get_distinct('vendor') | ||||
|     ]); | ||||
| }; | ||||
|  | ||||
| get '/' => sub { | ||||
|     template 'index'; | ||||
| }; | ||||
| # device with various properties or a default match-all | ||||
| ajax '/ajax/content/search/device' => sub { | ||||
|     my $has_opt = List::MoreUtils::any {param($_)} | ||||
|       qw/name location dns ip description model os_ver vendor/; | ||||
|     my $set; | ||||
|  | ||||
|     if ($has_opt) { | ||||
|       $set = schema('netdisco')->resultset('Device')->by_field(scalar params); | ||||
|       return unless $set->count; | ||||
|     } | ||||
|     else { | ||||
|       my $q = param('q'); | ||||
|       return unless $q; | ||||
|  | ||||
|       $set = schema('netdisco')->resultset('Device')->by_any($q); | ||||
|       return unless $set->count; | ||||
|     } | ||||
|  | ||||
| ajax '/ajax/content/search/:thing' => sub { | ||||
|     content_type('text/html'); | ||||
|     return '<p>Hello '. param('thing') .'.</p>'; | ||||
|     template 'ajax/device.tt', { | ||||
|       results => $set, | ||||
|     }, { layout => undef }; | ||||
| }; | ||||
|  | ||||
| # nodes matching the param as an IP or DNS hostname or MAC | ||||
| @@ -111,6 +142,10 @@ ajax '/ajax/content/search/port' => sub { | ||||
|     }, { layout => undef }; | ||||
| }; | ||||
|  | ||||
| get '/' => sub { | ||||
|     template 'index'; | ||||
| }; | ||||
|  | ||||
| get '/search' => sub { | ||||
|     my $q = param('q'); | ||||
|     if ($q and not param('tab')) { | ||||
|   | ||||
		Reference in New Issue
	
	Block a user