package RWDE::SearchClient::Indexable; use strict; use warnings; use Error qw(:try); use RWDE::Exceptions; use RWDE::Search; =pod =head2 add_to_index Add the content defined in my derived to the remote searchable index =cut sub add_to_index { my ($self, $params) = @_; $self->_check_index(); my $index_path; if (defined($$params{index_path})) { $index_path = $$params{index_path}; } else { $index_path = $self->get_index_path(); } my $index_data; # This try block exists because errors/exceptions are behaving VERY strange here. # Try using an error statement in this method! try { $index_data = $self->get_index_hash(); } catch Error with { my $ex = shift; $self->syslog_msg('info', "$ex"); $self->syslog_msg('info', "You likely have attempted to add an invalid class term to a class index."); $ex->throw(); }; RWDE::Search->index_document( { index_fields => $self->get_index_fields(), index_path => $index_path, index_data => $index_data } ); return (); } sub optimize_index { my ($self, $params) = @_; # dynamically require the object type we are going to try and use my $term = RWDE::AbstractFactory->instantiate({ class => $self }); $term->_check_index(); my $index_path; if (defined($$params{index_path})) { $index_path = $$params{index_path}; } else { $index_path = $term->get_index_path(); } RWDE::Search->optimize_index( { index_path => $index_path, index_fields => $term->get_index_fields(), } ); return (); } # Delete the defined index_item from the remote searchable index. sub delete_from_index { my ($self, $params) = @_; $self->_check_index(); throw RWDE::DataNotFoundException({ info => "Item to delete from search index was not specified." }) unless defined $$params{item_id}; my $index_path; if (defined($$params{index_path})) { $index_path = $$params{index_path}; } else { $index_path = $self->get_index_path(); } RWDE::Search->delete_document( { index_path => $index_path, index_fields => $self->get_index_fields(), item_id => $$params{item_id} # "primary key" to delete from the search index } ); return (); } # search for content in the index sub search_index { my ($self, $params) = @_; # create the object type we are going to use to # get the static data through polymorphism my $term = RWDE::AbstractFactory->instantiate({ class => $self }); $term->_check_index(); throw RWDE::DataNotFoundException({ info => "No items matched your query" }) unless defined $$params{query} || defined $$params{query_text}; my ($docs, $total) = @{RWDE::Search->search_index( { maxreturn => $$params{maxreturn}, startidx => $$params{startidx}, query => $$params{query}, query_text => $$params{query_text}, category => $$params{category}, index_path => $$params{index_path}, index_fields => $term->get_index_fields() } )}; unless (ref $docs eq 'ARRAY') { throw RWDE::DataBadException({ info => "Searching is temporarily unavailable, please try again later." }); } throw RWDE::DataNotFoundException({ info => "No items matched your query" }) unless (scalar @{$docs} > 0); return ($docs, $total); } =pod =head2 get_index_hash Return back the hash defined by the object as targets for indexing specified in an object for indexing as . =cut sub get_index_hash { my ($self, $params) = @_; my $field_values; foreach my $key (keys %{ $self->get_index_fields() }) { $$field_values{$key} = $self->$key; } return $field_values; } sub get_index_fields { my ($self, $number) = @_; $self->check_object(); return $self->{_index_fields}; } #Determine if a class supports indexing or not. Private method. sub _check_index { my ($self, $params) = @_; my $class = ref $self || $self; if (not defined $self->get_index_fields()) { throw RWDE::DevelException({ info => "Class $class doesn't support indexing" }); } return (); } sub get_index_table { my ($self, $number) = @_; return $self->{_table}; } sub get_index_divide { my ($self, $number) = @_; return $self->{_index_divide}; } 1;