| line | stmt | bran | cond | sub | pod | time | code | 
| 1 |  |  |  |  |  |  | package Elastic::Model::Index; | 
| 2 |  |  |  |  |  |  | $Elastic::Model::Index::VERSION = '0.51'; | 
| 3 | 23 |  |  | 23 |  | 183 | use Carp; | 
|  | 23 |  |  |  |  | 57 |  | 
|  | 23 |  |  |  |  | 2002 |  | 
| 4 | 23 |  |  | 23 |  | 128 | use Moose; | 
|  | 23 |  |  |  |  | 29 |  | 
|  | 23 |  |  |  |  | 189 |  | 
| 5 |  |  |  |  |  |  | with 'Elastic::Model::Role::Index'; | 
| 6 |  |  |  |  |  |  |  | 
| 7 | 23 |  |  | 23 |  | 134280 | use namespace::autoclean; | 
|  | 23 |  |  |  |  | 52 |  | 
|  | 23 |  |  |  |  | 320 |  | 
| 8 |  |  |  |  |  |  |  | 
| 9 | 23 |  |  | 23 |  | 2106 | no Moose; | 
|  | 23 |  |  |  |  | 40 |  | 
|  | 23 |  |  |  |  | 178 |  | 
| 10 |  |  |  |  |  |  |  | 
| 11 |  |  |  |  |  |  |  | 
| 12 |  |  |  |  |  |  | sub create { | 
| 13 |  |  |  |  |  |  |  | 
| 14 | 0 |  |  | 0 | 1 |  | my $self   = shift; | 
| 15 | 0 |  |  |  |  |  | my $params = $self->index_config(@_); | 
| 16 | 0 |  |  |  |  |  | $self->model->store->create_index(%$params); | 
| 17 | 0 |  |  |  |  |  | return $self; | 
| 18 |  |  |  |  |  |  | } | 
| 19 |  |  |  |  |  |  |  | 
| 20 |  |  |  |  |  |  |  | 
| 21 |  |  |  |  |  |  | sub reindex { | 
| 22 |  |  |  |  |  |  |  | 
| 23 | 0 |  |  | 0 | 1 |  | my $self   = shift; | 
| 24 | 0 | 0 |  |  |  |  | my $domain = shift | 
| 25 |  |  |  |  |  |  | or croak "No (domain) passed to reindex()"; | 
| 26 |  |  |  |  |  |  |  | 
| 27 | 0 |  |  |  |  |  | my %args       = ( repoint_uids => 1, @_ ); | 
| 28 | 0 |  |  |  |  |  | my $verbose    = !$args{quiet}; | 
| 29 | 0 |  | 0 |  |  |  | my $scan       = $args{scan} || '2m'; | 
| 30 | 0 |  | 0 |  |  |  | my $size       = $args{size} || 1000; | 
| 31 | 0 |  | 0 |  |  |  | my $bulk_size  = $args{bulk_size} || $size; | 
| 32 | 0 |  |  |  |  |  | my $dest_index = $self->name; | 
| 33 | 0 |  |  |  |  |  | my $model      = $self->model; | 
| 34 | 0 |  | 0 | 0 |  |  | my $transform  = $args{transform} || sub {@_}; | 
|  | 0 |  |  |  |  |  |  | 
| 35 |  |  |  |  |  |  |  | 
| 36 | 0 | 0 |  |  |  |  | printf "Reindexing domain ($domain) to index ($dest_index)\n" if $verbose; | 
| 37 |  |  |  |  |  |  |  | 
| 38 | 0 | 0 |  |  |  |  | if ( $self->exists ) { | 
| 39 | 0 | 0 |  |  |  |  | print "Index ($dest_index) already exists.\n" if $verbose; | 
| 40 |  |  |  |  |  |  | } | 
| 41 |  |  |  |  |  |  | else { | 
| 42 | 0 | 0 |  |  |  |  | print "Creating index ($dest_index)\n" if $verbose; | 
| 43 | 0 |  |  |  |  |  | $self->create(); | 
| 44 |  |  |  |  |  |  | } | 
| 45 |  |  |  |  |  |  |  | 
| 46 |  |  |  |  |  |  |  | 
| 47 |  |  |  |  |  |  |  | 
| 48 | 0 |  |  |  |  |  | my %uids; | 
| 49 |  |  |  |  |  |  | my $doc_updater = sub { | 
| 50 | 0 |  |  | 0 |  |  | my ($doc) = $transform->(@_); | 
| 51 | 0 |  |  |  |  |  | $uids{ $doc->{_index} }{ $doc->{_type} }{ $doc->{_id} } = 1; | 
| 52 | 0 |  |  |  |  |  | $doc->{_index} = $dest_index; | 
| 53 | 0 |  |  |  |  |  | return $doc; | 
| 54 | 0 |  |  |  |  |  | }; | 
| 55 |  |  |  |  |  |  |  | 
| 56 |  |  |  |  |  |  |  | 
| 57 | 0 |  |  |  |  |  | my $old = $model->domain($domain)->namespace->alias($domain); | 
| 58 | 0 |  |  |  |  |  | my %map | 
| 59 | 0 |  |  |  |  |  | = map { $_ => 1 } $old->is_alias | 
| 60 | 0 | 0 |  |  |  |  | ? keys %{ $old->aliased_to } | 
| 61 |  |  |  |  |  |  | : ($domain); | 
| 62 |  |  |  |  |  |  |  | 
| 63 |  |  |  |  |  |  | my $uid_updater = sub { | 
| 64 | 0 |  |  | 0 |  |  | my $uid = shift; | 
| 65 | 0 | 0 |  |  |  |  | $uid->{index} = $dest_index | 
| 66 |  |  |  |  |  |  | if $map{ $uid->{index} }; | 
| 67 | 0 |  |  |  |  |  | }; | 
| 68 |  |  |  |  |  |  |  | 
| 69 | 0 |  |  |  |  |  | my $updater = $self->doc_updater( $doc_updater, $uid_updater ); | 
| 70 |  |  |  |  |  |  |  | 
| 71 | 0 |  |  |  |  |  | my $source = $model->view->domain($domain)->size($size)->scan($scan); | 
| 72 |  |  |  |  |  |  | $model->store->reindex( | 
| 73 | 0 |  |  | 0 |  |  | source      => sub { $source->shift_element }, | 
| 74 | 0 |  |  |  |  |  | verbose     => $verbose, | 
| 75 |  |  |  |  |  |  | transform   => $updater, | 
| 76 |  |  |  |  |  |  | bulk_size   => $bulk_size, | 
| 77 |  |  |  |  |  |  | on_conflict => $args{on_conflict}, | 
| 78 |  |  |  |  |  |  | on_error    => $args{on_error}, | 
| 79 |  |  |  |  |  |  | ); | 
| 80 |  |  |  |  |  |  |  | 
| 81 | 0 | 0 |  |  |  |  | return 1 unless $args{repoint_uids}; | 
| 82 |  |  |  |  |  |  |  | 
| 83 | 0 |  |  |  |  |  | $self->repoint_uids( | 
| 84 |  |  |  |  |  |  | uids        => \%uids, | 
| 85 |  |  |  |  |  |  | verbose     => $verbose, | 
| 86 |  |  |  |  |  |  | exclude     => [ keys %map ], | 
| 87 |  |  |  |  |  |  | size        => $size, | 
| 88 |  |  |  |  |  |  | bulk_size   => $bulk_size, | 
| 89 |  |  |  |  |  |  | scan        => $scan, | 
| 90 |  |  |  |  |  |  | on_conflict => $args{uid_on_conflict}, | 
| 91 |  |  |  |  |  |  | on_error    => $args{uid_on_error}, | 
| 92 |  |  |  |  |  |  | ); | 
| 93 |  |  |  |  |  |  | } | 
| 94 |  |  |  |  |  |  |  | 
| 95 |  |  |  |  |  |  |  | 
| 96 |  |  |  |  |  |  | sub repoint_uids { | 
| 97 |  |  |  |  |  |  |  | 
| 98 | 0 |  |  | 0 | 1 |  | my ( $self, %args ) = @_; | 
| 99 |  |  |  |  |  |  |  | 
| 100 | 0 |  |  |  |  |  | my $verbose    = $args{verbose}; | 
| 101 | 0 |  | 0 |  |  |  | my $scan       = $args{scan} || '2m'; | 
| 102 | 0 |  | 0 |  |  |  | my $size       = $args{size} || 1000; | 
| 103 | 0 |  | 0 |  |  |  | my $bulk_size  = $args{bulk_size} || $size; | 
| 104 | 0 |  |  |  |  |  | my $model      = $self->model; | 
| 105 | 0 |  |  |  |  |  | my $index_name = $self->name; | 
| 106 | 0 |  | 0 |  |  |  | my $uids       = $args{uids} || {}; | 
| 107 |  |  |  |  |  |  |  | 
| 108 | 0 | 0 |  |  |  |  | unless (%$uids) { | 
| 109 | 0 | 0 |  |  |  |  | print "No UIDs to repoint\n" if $verbose; | 
| 110 | 0 |  |  |  |  |  | return 1; | 
| 111 |  |  |  |  |  |  | } | 
| 112 |  |  |  |  |  |  |  | 
| 113 | 0 | 0 |  |  |  |  | my %exclude = map { $_ => 1 } ( $index_name, @{ $args{exclude} || [] } ); | 
|  | 0 |  |  |  |  |  |  | 
|  | 0 |  |  |  |  |  |  | 
| 114 | 0 |  |  |  |  |  | my @indices = grep { not $exclude{$_} } $model->all_live_indices; | 
|  | 0 |  |  |  |  |  |  | 
| 115 |  |  |  |  |  |  |  | 
| 116 | 0 | 0 |  |  |  |  | unless (@indices) { | 
| 117 | 0 | 0 |  |  |  |  | print "No UIDs to repoint\n" if $verbose; | 
| 118 | 0 |  |  |  |  |  | return 1; | 
| 119 |  |  |  |  |  |  | } | 
| 120 |  |  |  |  |  |  |  | 
| 121 | 0 |  |  |  |  |  | my @uid_attrs = $self->_uid_attrs_for_indices(@indices); | 
| 122 | 0 | 0 |  |  |  |  | unless (@uid_attrs) { | 
| 123 | 0 | 0 |  |  |  |  | print "No UIDs to repoint\n" if $verbose; | 
| 124 | 0 |  |  |  |  |  | return 1; | 
| 125 |  |  |  |  |  |  | } | 
| 126 |  |  |  |  |  |  |  | 
| 127 | 0 |  |  |  |  |  | my $view = $model->view->domain( \@indices )->size($size); | 
| 128 |  |  |  |  |  |  |  | 
| 129 |  |  |  |  |  |  | my $doc_updater = sub { | 
| 130 | 0 |  |  | 0 |  |  | my $doc = shift; | 
| 131 | 0 |  |  |  |  |  | $doc->{_version}++; | 
| 132 | 0 |  |  |  |  |  | return $doc; | 
| 133 | 0 |  |  |  |  |  | }; | 
| 134 |  |  |  |  |  |  |  | 
| 135 | 0 |  |  |  |  |  | my %map; | 
| 136 |  |  |  |  |  |  | my $uid_updater = sub { | 
| 137 | 0 |  |  | 0 |  |  | my $uid = shift; | 
| 138 | 0 | 0 |  |  |  |  | return unless $uids->{ $uid->{index} }{ $uid->{type} }{ $uid->{id} }; | 
| 139 | 0 |  |  |  |  |  | $uid->{index} = $index_name; | 
| 140 | 0 |  |  |  |  |  | }; | 
| 141 |  |  |  |  |  |  |  | 
| 142 | 0 |  |  |  |  |  | my $updater = $self->doc_updater( $doc_updater, $uid_updater ); | 
| 143 |  |  |  |  |  |  |  | 
| 144 | 0 |  |  |  |  |  | for my $index ( keys %$uids ) { | 
| 145 | 0 |  |  |  |  |  | my $types = $uids->{$index}; | 
| 146 | 0 |  |  |  |  |  | for my $type ( keys %$types ) { | 
| 147 | 0 |  |  |  |  |  | my @ids = keys %{ $types->{$type} }; | 
|  | 0 |  |  |  |  |  |  | 
| 148 |  |  |  |  |  |  |  | 
| 149 | 0 | 0 |  |  |  |  | printf( "Repointing %d UIDs from %s/%s\n", | 
| 150 |  |  |  |  |  |  | 0 + @ids, $index, $type ) | 
| 151 |  |  |  |  |  |  | if $verbose; | 
| 152 |  |  |  |  |  |  |  | 
| 153 | 0 |  |  |  |  |  | while (@ids) { | 
| 154 |  |  |  |  |  |  |  | 
| 155 | 0 |  |  |  |  |  | my $clauses | 
| 156 |  |  |  |  |  |  | = $self->_build_uid_clauses( \@uid_attrs, $index, $type, | 
| 157 |  |  |  |  |  |  | [ splice @ids, 0, $size ] ); | 
| 158 |  |  |  |  |  |  |  | 
| 159 | 0 |  |  |  |  |  | my $source = $view->filter( or => $clauses )->scan($scan); | 
| 160 |  |  |  |  |  |  | $model->store->reindex( | 
| 161 |  |  |  |  |  |  | source => sub { | 
| 162 | 0 |  |  | 0 |  |  | $source->shift_element; | 
| 163 |  |  |  |  |  |  | }, | 
| 164 | 0 |  |  |  |  |  | bulk_size   => $bulk_size, | 
| 165 |  |  |  |  |  |  | quiet       => 1, | 
| 166 |  |  |  |  |  |  | transform   => $updater, | 
| 167 |  |  |  |  |  |  | on_conflict => $args{on_conflict}, | 
| 168 |  |  |  |  |  |  | on_error    => $args{on_error}, | 
| 169 |  |  |  |  |  |  | ); | 
| 170 |  |  |  |  |  |  | } | 
| 171 | 0 | 0 |  |  |  |  | print "\n" if $verbose; | 
| 172 |  |  |  |  |  |  | } | 
| 173 |  |  |  |  |  |  | } | 
| 174 |  |  |  |  |  |  |  | 
| 175 | 0 | 0 |  |  |  |  | print "\nDone\n" if $verbose; | 
| 176 | 0 |  |  |  |  |  | return 1; | 
| 177 |  |  |  |  |  |  | } | 
| 178 |  |  |  |  |  |  |  | 
| 179 |  |  |  |  |  |  |  | 
| 180 |  |  |  |  |  |  | sub _uid_attrs_for_indices { | 
| 181 |  |  |  |  |  |  |  | 
| 182 | 0 |  |  | 0 |  |  | my $self    = shift; | 
| 183 | 0 |  |  |  |  |  | my @indices = @_; | 
| 184 | 0 |  |  |  |  |  | my $mapping = $self->model->store->get_mapping( index => \@indices ); | 
| 185 | 0 |  |  |  |  |  | my %attrs   = map { $_ => 1 } | 
|  | 0 |  |  |  |  |  |  | 
| 186 | 0 |  |  |  |  |  | map { _find_uid_attrs( $_->{properties} ) } | 
| 187 | 0 |  |  |  |  |  | map { values %{ $_->{mappings} } } values %$mapping; | 
|  | 0 |  |  |  |  |  |  | 
| 188 | 0 |  |  |  |  |  | return keys %attrs; | 
| 189 |  |  |  |  |  |  |  | 
| 190 |  |  |  |  |  |  | } | 
| 191 |  |  |  |  |  |  |  | 
| 192 |  |  |  |  |  |  |  | 
| 193 |  |  |  |  |  |  | sub _find_uid_attrs { | 
| 194 |  |  |  |  |  |  |  | 
| 195 | 0 |  |  | 0 |  |  | my ( $mapping, $level ) = @_; | 
| 196 |  |  |  |  |  |  |  | 
| 197 | 0 |  |  |  |  |  | my @attrs; | 
| 198 | 0 | 0 |  |  |  |  | $level = '' unless $level; | 
| 199 |  |  |  |  |  |  |  | 
| 200 | 0 |  |  |  |  |  | keys %$mapping; | 
| 201 | 0 |  |  |  |  |  | while ( my ( $k, $v ) = each %$mapping ) { | 
| 202 | 0 | 0 |  |  |  |  | next unless $v->{properties}; | 
| 203 | 0 | 0 |  |  |  |  | my $attr = $level ? "$level.$k" : $k; | 
| 204 |  |  |  |  |  |  |  | 
| 205 | 0 | 0 | 0 |  |  |  | if ( $k eq 'uid' and $v->{properties} and $v->{properties}{index} ) { | 
|  |  |  | 0 |  |  |  |  | 
| 206 | 0 |  |  |  |  |  | push @attrs, $attr; | 
| 207 | 0 |  |  |  |  |  | next; | 
| 208 |  |  |  |  |  |  | } | 
| 209 | 0 |  | 0 |  |  |  | push @attrs, _find_uid_attrs( $v->{properties} || {}, $attr ); | 
| 210 |  |  |  |  |  |  | } | 
| 211 | 0 |  |  |  |  |  | return @attrs; | 
| 212 |  |  |  |  |  |  | } | 
| 213 |  |  |  |  |  |  |  | 
| 214 |  |  |  |  |  |  |  | 
| 215 |  |  |  |  |  |  | sub _build_uid_clauses { | 
| 216 |  |  |  |  |  |  |  | 
| 217 | 0 |  |  | 0 |  |  | my ( $self, $uid_attrs, $index, $type, $ids ) = @_; | 
| 218 | 0 |  |  |  |  |  | my @clauses; | 
| 219 | 0 |  |  |  |  |  | for my $id (@$ids) { | 
| 220 | 0 |  |  |  |  |  | push @clauses, map { | 
| 221 | 0 |  |  |  |  |  | +{  and => [ | 
| 222 |  |  |  |  |  |  | { term => { "$_.index" => $index } }, | 
| 223 |  |  |  |  |  |  | { term => { "$_.type"  => $type } }, | 
| 224 |  |  |  |  |  |  | { term => { "$_.id"    => $id } } | 
| 225 |  |  |  |  |  |  | ] | 
| 226 |  |  |  |  |  |  | } | 
| 227 |  |  |  |  |  |  | } @$uid_attrs; | 
| 228 |  |  |  |  |  |  | } | 
| 229 | 0 |  |  |  |  |  | return \@clauses; | 
| 230 |  |  |  |  |  |  | } | 
| 231 |  |  |  |  |  |  |  | 
| 232 |  |  |  |  |  |  |  | 
| 233 |  |  |  |  |  |  | sub doc_updater { | 
| 234 |  |  |  |  |  |  |  | 
| 235 | 0 |  |  | 0 | 1 |  | my ( $self, $doc_updater, $uid_updater ) = @_; | 
| 236 |  |  |  |  |  |  | return sub { | 
| 237 | 0 |  |  | 0 |  |  | my $doc   = $doc_updater->(@_); | 
| 238 | 0 |  |  |  |  |  | my @stack = values %{ $doc->{_source} }; | 
|  | 0 |  |  |  |  |  |  | 
| 239 |  |  |  |  |  |  |  | 
| 240 | 0 |  |  |  |  |  | while ( my $val = shift @stack ) { | 
| 241 | 0 | 0 |  |  |  |  | unless ( ref $val eq 'HASH' ) { | 
| 242 | 0 | 0 |  |  |  |  | push @stack, @$val if ref $val eq 'ARRAY'; | 
| 243 | 0 |  |  |  |  |  | next; | 
| 244 |  |  |  |  |  |  | } | 
| 245 | 0 |  |  |  |  |  | my $uid = $val->{uid}; | 
| 246 | 0 | 0 | 0 |  |  |  | if (    $uid | 
|  |  |  | 0 |  |  |  |  | 
|  |  |  | 0 |  |  |  |  | 
| 247 |  |  |  |  |  |  | and ref $uid eq 'HASH' | 
| 248 |  |  |  |  |  |  | and $uid->{index} | 
| 249 |  |  |  |  |  |  | and $uid->{type} ) | 
| 250 |  |  |  |  |  |  | { | 
| 251 | 0 |  |  |  |  |  | $uid_updater->($uid); | 
| 252 |  |  |  |  |  |  | } | 
| 253 |  |  |  |  |  |  | else { | 
| 254 | 0 |  |  |  |  |  | push @stack, values %$val; | 
| 255 |  |  |  |  |  |  | } | 
| 256 |  |  |  |  |  |  | } | 
| 257 | 0 |  |  |  |  |  | return $doc; | 
| 258 | 0 |  |  |  |  |  | }; | 
| 259 |  |  |  |  |  |  | } | 
| 260 |  |  |  |  |  |  |  | 
| 261 |  |  |  |  |  |  | __PACKAGE__->meta->make_immutable; | 
| 262 |  |  |  |  |  |  |  | 
| 263 |  |  |  |  |  |  | 1; | 
| 264 |  |  |  |  |  |  |  | 
| 265 |  |  |  |  |  |  | =pod | 
| 266 |  |  |  |  |  |  |  | 
| 267 |  |  |  |  |  |  | =encoding UTF-8 | 
| 268 |  |  |  |  |  |  |  | 
| 269 |  |  |  |  |  |  | =head1 NAME | 
| 270 |  |  |  |  |  |  |  | 
| 271 |  |  |  |  |  |  | Elastic::Model::Index - Create and administer indices in Elasticsearch | 
| 272 |  |  |  |  |  |  |  | 
| 273 |  |  |  |  |  |  | =head1 VERSION | 
| 274 |  |  |  |  |  |  |  | 
| 275 |  |  |  |  |  |  | version 0.51 | 
| 276 |  |  |  |  |  |  |  | 
| 277 |  |  |  |  |  |  | =head1 SYNOPSIS | 
| 278 |  |  |  |  |  |  |  | 
| 279 |  |  |  |  |  |  | $index = $model->namespace('myapp')->index; | 
| 280 |  |  |  |  |  |  | $index = $model->namespace('myapp')->index('index_name'); | 
| 281 |  |  |  |  |  |  |  | 
| 282 |  |  |  |  |  |  | $index->create( settings => \%settings ); | 
| 283 |  |  |  |  |  |  |  | 
| 284 |  |  |  |  |  |  | $index->reindex( 'old_index' ); | 
| 285 |  |  |  |  |  |  |  | 
| 286 |  |  |  |  |  |  | See also L<Elastic::Model::Role::Index/SYNOPSIS>. | 
| 287 |  |  |  |  |  |  |  | 
| 288 |  |  |  |  |  |  | =head1 DESCRIPTION | 
| 289 |  |  |  |  |  |  |  | 
| 290 |  |  |  |  |  |  | L<Elastic::Model::Index> objects are used to create and administer indices | 
| 291 |  |  |  |  |  |  | in an Elasticsearch cluster. | 
| 292 |  |  |  |  |  |  |  | 
| 293 |  |  |  |  |  |  | See L<Elastic::Model::Role::Index> for more about usage. | 
| 294 |  |  |  |  |  |  | See L<Elastic::Manual::Scaling> for more about how indices can be used in your | 
| 295 |  |  |  |  |  |  | application. | 
| 296 |  |  |  |  |  |  |  | 
| 297 |  |  |  |  |  |  | =head1 METHODS | 
| 298 |  |  |  |  |  |  |  | 
| 299 |  |  |  |  |  |  | =head2 create() | 
| 300 |  |  |  |  |  |  |  | 
| 301 |  |  |  |  |  |  | $index = $index->create(); | 
| 302 |  |  |  |  |  |  | $index = $index->create( settings => \%settings, types => \@types ); | 
| 303 |  |  |  |  |  |  |  | 
| 304 |  |  |  |  |  |  | Creates an index called L<name|Elastic::Role::Model::Index/name> (which | 
| 305 |  |  |  |  |  |  | defaults to C<< $namespace->name >>). | 
| 306 |  |  |  |  |  |  |  | 
| 307 |  |  |  |  |  |  | The L<type mapping|Elastic::Manual::Terminology/Mapping> is automatically | 
| 308 |  |  |  |  |  |  | generated from the attributes of your doc classes listed in the | 
| 309 |  |  |  |  |  |  | L<namespace|Elastic::Model::Namespace>.  Similarly, any | 
| 310 |  |  |  |  |  |  | L<custom analyzers|Elastic::Model/"Custom analyzers"> required | 
| 311 |  |  |  |  |  |  | by your classes are added to the index | 
| 312 |  |  |  |  |  |  | L<\%settings|http://www.elasticsearch.org/guide/en/elasticsearch/reference/current/indices-update-settings.html> | 
| 313 |  |  |  |  |  |  | that you pass in: | 
| 314 |  |  |  |  |  |  |  | 
| 315 |  |  |  |  |  |  | $index->create( settings => {number_of_shards => 1} ); | 
| 316 |  |  |  |  |  |  |  | 
| 317 |  |  |  |  |  |  | To create an index with a sub-set of the types known to the | 
| 318 |  |  |  |  |  |  | L<namespace|Elastic::Model::Namespace>, pass in a list of C<@types>. | 
| 319 |  |  |  |  |  |  |  | 
| 320 |  |  |  |  |  |  | $index->create( types => ['user','post' ]); | 
| 321 |  |  |  |  |  |  |  | 
| 322 |  |  |  |  |  |  | =head2 reindex() | 
| 323 |  |  |  |  |  |  |  | 
| 324 |  |  |  |  |  |  | # reindex $domain_name to $index->name | 
| 325 |  |  |  |  |  |  | $index->reindex( $domain_name ); | 
| 326 |  |  |  |  |  |  |  | 
| 327 |  |  |  |  |  |  | # more options | 
| 328 |  |  |  |  |  |  | $index->reindex( | 
| 329 |  |  |  |  |  |  | $domain, | 
| 330 |  |  |  |  |  |  |  | 
| 331 |  |  |  |  |  |  | repoint_uids    => 1, | 
| 332 |  |  |  |  |  |  | size            => 1000, | 
| 333 |  |  |  |  |  |  | bulk_size       => 1000, | 
| 334 |  |  |  |  |  |  | scan            => '2m', | 
| 335 |  |  |  |  |  |  | quiet           => 0, | 
| 336 |  |  |  |  |  |  |  | 
| 337 |  |  |  |  |  |  | transform       => sub {...}, | 
| 338 |  |  |  |  |  |  |  | 
| 339 |  |  |  |  |  |  | on_conflict     => sub {...} | 'IGNORE' | 
| 340 |  |  |  |  |  |  | on_error        => sub {...} | 'IGNORE' | 
| 341 |  |  |  |  |  |  | uid_on_conflict => sub {...} | 'IGNORE' | 
| 342 |  |  |  |  |  |  | uid_on_error    => sub {...} | 'IGNORE' | 
| 343 |  |  |  |  |  |  | ); | 
| 344 |  |  |  |  |  |  |  | 
| 345 |  |  |  |  |  |  | While you can add to the L<mapping|Elastic::Manual::Terminology/Mapping> of | 
| 346 |  |  |  |  |  |  | an index, you can't change what is already there. Especially during development, | 
| 347 |  |  |  |  |  |  | you will need to reindex your data to a new index. | 
| 348 |  |  |  |  |  |  |  | 
| 349 |  |  |  |  |  |  | L</reindex()> reindexes your data from L<domain|Elastic::Manual::Terminology/Domain> | 
| 350 |  |  |  |  |  |  | C<$domain_name> into an index called C<< $index->name >>. The new index is | 
| 351 |  |  |  |  |  |  | created if it doesn't already exist. | 
| 352 |  |  |  |  |  |  |  | 
| 353 |  |  |  |  |  |  | See L<Elastic::Manual::Reindex> for more about reindexing strategies. The | 
| 354 |  |  |  |  |  |  | documentation below explains what each parameter does: | 
| 355 |  |  |  |  |  |  |  | 
| 356 |  |  |  |  |  |  | =over | 
| 357 |  |  |  |  |  |  |  | 
| 358 |  |  |  |  |  |  | =item size | 
| 359 |  |  |  |  |  |  |  | 
| 360 |  |  |  |  |  |  | The C<size> parameter defaults to 1,000 and controls how many documents | 
| 361 |  |  |  |  |  |  | are pulled from C<$domain> in each request.  See L<Elastic::Model::View/size>. | 
| 362 |  |  |  |  |  |  |  | 
| 363 |  |  |  |  |  |  | B<Note:> documents are pulled from the C<domain>/C<view> using | 
| 364 |  |  |  |  |  |  | L<Elastic::Model::View/scan()>, which can pull a maximum of | 
| 365 |  |  |  |  |  |  | L<size|Elastic::Model::View/size> C<* number_of_primary_shards> in a single | 
| 366 |  |  |  |  |  |  | request.  If you have large docs or underpowered servers, you may want to | 
| 367 |  |  |  |  |  |  | change the C<size> parameter. | 
| 368 |  |  |  |  |  |  |  | 
| 369 |  |  |  |  |  |  | =item bulk_size | 
| 370 |  |  |  |  |  |  |  | 
| 371 |  |  |  |  |  |  | The C<bulk_size> parameter defaults to C<size> and controls how many documents | 
| 372 |  |  |  |  |  |  | are indexed into the new domain in a single bulk-indexing request. | 
| 373 |  |  |  |  |  |  |  | 
| 374 |  |  |  |  |  |  | =item scan | 
| 375 |  |  |  |  |  |  |  | 
| 376 |  |  |  |  |  |  | C<scan> is the same as L<Elastic::Model::View/scan> - it controls how long | 
| 377 |  |  |  |  |  |  | Elasticsearch should keep the "scroll" live between requests.  Defaults to | 
| 378 |  |  |  |  |  |  | '2m'.  Increase this if the reindexing process is slow and you get | 
| 379 |  |  |  |  |  |  | scroll timeouts. | 
| 380 |  |  |  |  |  |  |  | 
| 381 |  |  |  |  |  |  | =item repoint_uids | 
| 382 |  |  |  |  |  |  |  | 
| 383 |  |  |  |  |  |  | If true (the default), L</repoint_uids()> will be called automatically to | 
| 384 |  |  |  |  |  |  | update any L<UIDs|Elastic::Model::UID> (which point at the old index) in | 
| 385 |  |  |  |  |  |  | indices other than the ones currently being reindexed. | 
| 386 |  |  |  |  |  |  |  | 
| 387 |  |  |  |  |  |  | =item transform | 
| 388 |  |  |  |  |  |  |  | 
| 389 |  |  |  |  |  |  | If you need to change the structure/data of your doc while reindexing, you | 
| 390 |  |  |  |  |  |  | can pass a C<transform> coderef.  This will be called before any changes | 
| 391 |  |  |  |  |  |  | have been made to the doc, and should return the new doc. For instance, | 
| 392 |  |  |  |  |  |  | to convert the single-value C<tag> field to an array of C<tags>: | 
| 393 |  |  |  |  |  |  |  | 
| 394 |  |  |  |  |  |  | $index->reindex( | 
| 395 |  |  |  |  |  |  | 'new_index', | 
| 396 |  |  |  |  |  |  | 'transform' => sub { | 
| 397 |  |  |  |  |  |  | my $doc = shift; | 
| 398 |  |  |  |  |  |  | $doc->{_source}{tags} = [ delete $doc->{_source}{tag} ]; | 
| 399 |  |  |  |  |  |  | return $doc | 
| 400 |  |  |  |  |  |  | } | 
| 401 |  |  |  |  |  |  | ); | 
| 402 |  |  |  |  |  |  |  | 
| 403 |  |  |  |  |  |  | =item on_conflict / on_error | 
| 404 |  |  |  |  |  |  |  | 
| 405 |  |  |  |  |  |  | If you are indexing to the new index at the same time as you | 
| 406 |  |  |  |  |  |  | are reindexing, you may get document conflicts.  You can handle the conflicts | 
| 407 |  |  |  |  |  |  | with a coderef callback, or ignore them by by setting C<on_conflict> to | 
| 408 |  |  |  |  |  |  | C<'IGNORE'>: | 
| 409 |  |  |  |  |  |  |  | 
| 410 |  |  |  |  |  |  | $index->reindex( 'myapp_v2', on_conflict => 'IGNORE' ); | 
| 411 |  |  |  |  |  |  |  | 
| 412 |  |  |  |  |  |  | Similarly, you can pass an C<on_error> handler which will handle other errors, | 
| 413 |  |  |  |  |  |  | or all errors if no C<on_conflict> handler is defined. | 
| 414 |  |  |  |  |  |  |  | 
| 415 |  |  |  |  |  |  | See L<Search::Elasticsearch::Bulk/Using-callbacks> for more. | 
| 416 |  |  |  |  |  |  |  | 
| 417 |  |  |  |  |  |  | =item uid_on_conflict / uid_on_error | 
| 418 |  |  |  |  |  |  |  | 
| 419 |  |  |  |  |  |  | These work in the same way as the C<on_conflict> or C<on_error> handlers, | 
| 420 |  |  |  |  |  |  | but are passed to L</repoint_uids()> if C<repoint_uids> is true. | 
| 421 |  |  |  |  |  |  |  | 
| 422 |  |  |  |  |  |  | =item quiet | 
| 423 |  |  |  |  |  |  |  | 
| 424 |  |  |  |  |  |  | By default, L</reindex()> prints out progress information.  To silence this, | 
| 425 |  |  |  |  |  |  | set C<quiet> to true: | 
| 426 |  |  |  |  |  |  |  | 
| 427 |  |  |  |  |  |  | $index->reindex( 'myapp_v2', quiet   => 1 ); | 
| 428 |  |  |  |  |  |  |  | 
| 429 |  |  |  |  |  |  | =back | 
| 430 |  |  |  |  |  |  |  | 
| 431 |  |  |  |  |  |  | =head2 repoint_uids() | 
| 432 |  |  |  |  |  |  |  | 
| 433 |  |  |  |  |  |  | $index->repoint_uids( | 
| 434 |  |  |  |  |  |  | uids        => [ ['myapp_v1','user',10],['myapp_v1','user',12]...], | 
| 435 |  |  |  |  |  |  | exclude     => ['myapp_v2'], | 
| 436 |  |  |  |  |  |  | scan        => '2m', | 
| 437 |  |  |  |  |  |  | size        => 1000, | 
| 438 |  |  |  |  |  |  | bulk_size   => 1000, | 
| 439 |  |  |  |  |  |  | quiet       => 0, | 
| 440 |  |  |  |  |  |  |  | 
| 441 |  |  |  |  |  |  | on_conflict => sub {...} | 'IGNORE' | 
| 442 |  |  |  |  |  |  | on_error    => sub {...} | 'IGNORE' | 
| 443 |  |  |  |  |  |  | ); | 
| 444 |  |  |  |  |  |  |  | 
| 445 |  |  |  |  |  |  | The purpose of L</repoint_uids()> is to update stale L<UID|Elastic::Model::UID> | 
| 446 |  |  |  |  |  |  | attributes to point to a new index. It is called automatically from | 
| 447 |  |  |  |  |  |  | L</reindex()>. | 
| 448 |  |  |  |  |  |  |  | 
| 449 |  |  |  |  |  |  | Parameters: | 
| 450 |  |  |  |  |  |  |  | 
| 451 |  |  |  |  |  |  | =over | 
| 452 |  |  |  |  |  |  |  | 
| 453 |  |  |  |  |  |  | =item uids | 
| 454 |  |  |  |  |  |  |  | 
| 455 |  |  |  |  |  |  | C<uids> is a hash ref the stale L<UIDs|Elastic::Model::UID> which should be | 
| 456 |  |  |  |  |  |  | updated. | 
| 457 |  |  |  |  |  |  |  | 
| 458 |  |  |  |  |  |  | For instance: you have reindexed C<myapp_v1> to C<myapp_v2>, but domain | 
| 459 |  |  |  |  |  |  | C<other> has documents with UIDs which point to C<myapp_v1>. You | 
| 460 |  |  |  |  |  |  | can updated these by passing a list of the old UIDs, as follows: | 
| 461 |  |  |  |  |  |  |  | 
| 462 |  |  |  |  |  |  | $index = $namespace->index('myapp_v2'); | 
| 463 |  |  |  |  |  |  | $index->repoint_uids( | 
| 464 |  |  |  |  |  |  | uids    => {                        # index | 
| 465 |  |  |  |  |  |  | myapp_v1 => {                   # type | 
| 466 |  |  |  |  |  |  | user => { | 
| 467 |  |  |  |  |  |  | 1 => 1,                 # ids | 
| 468 |  |  |  |  |  |  | 2 => 1, | 
| 469 |  |  |  |  |  |  | } | 
| 470 |  |  |  |  |  |  | } | 
| 471 |  |  |  |  |  |  | } | 
| 472 |  |  |  |  |  |  | ); | 
| 473 |  |  |  |  |  |  |  | 
| 474 |  |  |  |  |  |  | =item exclude | 
| 475 |  |  |  |  |  |  |  | 
| 476 |  |  |  |  |  |  | By default, all indices known to the L<model|Elastic::Model::Role::Model> are | 
| 477 |  |  |  |  |  |  | updated. You can exclude indices with: | 
| 478 |  |  |  |  |  |  |  | 
| 479 |  |  |  |  |  |  | $index->repoint_uids( | 
| 480 |  |  |  |  |  |  | uids    => \@uids, | 
| 481 |  |  |  |  |  |  | exclude => ['index_1', ...] | 
| 482 |  |  |  |  |  |  | ); | 
| 483 |  |  |  |  |  |  |  | 
| 484 |  |  |  |  |  |  | =item size | 
| 485 |  |  |  |  |  |  |  | 
| 486 |  |  |  |  |  |  | This is the same as the C<size> parameter to L</reindex()>. | 
| 487 |  |  |  |  |  |  |  | 
| 488 |  |  |  |  |  |  | =item bulk_size | 
| 489 |  |  |  |  |  |  |  | 
| 490 |  |  |  |  |  |  | This is the same as the C<bulk_size> parameter to L</reindex()>. | 
| 491 |  |  |  |  |  |  |  | 
| 492 |  |  |  |  |  |  | =item scan | 
| 493 |  |  |  |  |  |  |  | 
| 494 |  |  |  |  |  |  | This is the same as the C<scan> parameter to L</reindex()>. | 
| 495 |  |  |  |  |  |  |  | 
| 496 |  |  |  |  |  |  | =item quiet | 
| 497 |  |  |  |  |  |  |  | 
| 498 |  |  |  |  |  |  | This is the same as the C<quiet> parameter to L</reindex()>. | 
| 499 |  |  |  |  |  |  |  | 
| 500 |  |  |  |  |  |  | =item on_conflict / on_error | 
| 501 |  |  |  |  |  |  |  | 
| 502 |  |  |  |  |  |  | These are the same as the C<uid_on_conflict> and C<uid_on_error> handlers | 
| 503 |  |  |  |  |  |  | in L</reindex()>. | 
| 504 |  |  |  |  |  |  |  | 
| 505 |  |  |  |  |  |  | =back | 
| 506 |  |  |  |  |  |  |  | 
| 507 |  |  |  |  |  |  | =head2 doc_updater() | 
| 508 |  |  |  |  |  |  |  | 
| 509 |  |  |  |  |  |  | $coderef = $index->doc_updater( $doc_updater, $uid_updater ); | 
| 510 |  |  |  |  |  |  |  | 
| 511 |  |  |  |  |  |  | L</doc_updater()> is used by L</reindex()> and L</repoint_uids()> to update | 
| 512 |  |  |  |  |  |  | the top-level doc and any UID attributes with callbacks. | 
| 513 |  |  |  |  |  |  |  | 
| 514 |  |  |  |  |  |  | The C<$doc_updater> receives the C<$doc> as its only attribute, and should | 
| 515 |  |  |  |  |  |  | return the C<$doc> after making any changes: | 
| 516 |  |  |  |  |  |  |  | 
| 517 |  |  |  |  |  |  | $doc_updater = sub { | 
| 518 |  |  |  |  |  |  | my ($doc) = @_; | 
| 519 |  |  |  |  |  |  | $doc->{_index} = 'foo'; | 
| 520 |  |  |  |  |  |  | return $doc | 
| 521 |  |  |  |  |  |  | }; | 
| 522 |  |  |  |  |  |  |  | 
| 523 |  |  |  |  |  |  | The C<$uid_updater> receives the UID as its only attribute: | 
| 524 |  |  |  |  |  |  |  | 
| 525 |  |  |  |  |  |  | $uid_updater = sub { | 
| 526 |  |  |  |  |  |  | my ($uid) = @_; | 
| 527 |  |  |  |  |  |  | $uid->{index} = 'foo' | 
| 528 |  |  |  |  |  |  | }; | 
| 529 |  |  |  |  |  |  |  | 
| 530 |  |  |  |  |  |  | =head1 IMPORTED ATTRIBUTES | 
| 531 |  |  |  |  |  |  |  | 
| 532 |  |  |  |  |  |  | Attributes imported from L<Elastic::Model::Role::Index> | 
| 533 |  |  |  |  |  |  |  | 
| 534 |  |  |  |  |  |  | =head2 L<namespace|Elastic::Model::Role::Index/namespace> | 
| 535 |  |  |  |  |  |  |  | 
| 536 |  |  |  |  |  |  | =head2 L<name|Elastic::Model::Role::Index/name> | 
| 537 |  |  |  |  |  |  |  | 
| 538 |  |  |  |  |  |  | =head1 IMPORTED METHODS | 
| 539 |  |  |  |  |  |  |  | 
| 540 |  |  |  |  |  |  | Methods imported from L<Elastic::Model::Role::Index> | 
| 541 |  |  |  |  |  |  |  | 
| 542 |  |  |  |  |  |  | =head2 L<close()|Elastic::Model::Role::Index/close()> | 
| 543 |  |  |  |  |  |  |  | 
| 544 |  |  |  |  |  |  | =head2 L<open()|Elastic::Model::Role::Index/open()> | 
| 545 |  |  |  |  |  |  |  | 
| 546 |  |  |  |  |  |  | =head2 L<refresh()|Elastic::Model::Role::Index/refresh()> | 
| 547 |  |  |  |  |  |  |  | 
| 548 |  |  |  |  |  |  | =head2 L<delete()|Elastic::Model::Role::Index/delete()> | 
| 549 |  |  |  |  |  |  |  | 
| 550 |  |  |  |  |  |  | =head2 L<update_analyzers()|Elastic::Model::Role::Index/update_analyzers()> | 
| 551 |  |  |  |  |  |  |  | 
| 552 |  |  |  |  |  |  | =head2 L<update_settings()|Elastic::Model::Role::Index/update_settings()> | 
| 553 |  |  |  |  |  |  |  | 
| 554 |  |  |  |  |  |  | =head2 L<delete_mapping()|Elastic::Model::Role::Index/delete_mapping()> | 
| 555 |  |  |  |  |  |  |  | 
| 556 |  |  |  |  |  |  | =head2 L<is_alias()|Elastic::Model::Role::Index/is_alias()> | 
| 557 |  |  |  |  |  |  |  | 
| 558 |  |  |  |  |  |  | =head2 L<is_index()|Elastic::Model::Role::Index/is_index()> | 
| 559 |  |  |  |  |  |  |  | 
| 560 |  |  |  |  |  |  | =head1 SEE ALSO | 
| 561 |  |  |  |  |  |  |  | 
| 562 |  |  |  |  |  |  | =over | 
| 563 |  |  |  |  |  |  |  | 
| 564 |  |  |  |  |  |  | =item * | 
| 565 |  |  |  |  |  |  |  | 
| 566 |  |  |  |  |  |  | L<Elastic::Model::Role::Index> | 
| 567 |  |  |  |  |  |  |  | 
| 568 |  |  |  |  |  |  | =item * | 
| 569 |  |  |  |  |  |  |  | 
| 570 |  |  |  |  |  |  | L<Elastic::Model::Alias> | 
| 571 |  |  |  |  |  |  |  | 
| 572 |  |  |  |  |  |  | =item * | 
| 573 |  |  |  |  |  |  |  | 
| 574 |  |  |  |  |  |  | L<Elastic::Model::Namespace> | 
| 575 |  |  |  |  |  |  |  | 
| 576 |  |  |  |  |  |  | =item * | 
| 577 |  |  |  |  |  |  |  | 
| 578 |  |  |  |  |  |  | L<Elastic::Manual::Scaling> | 
| 579 |  |  |  |  |  |  |  | 
| 580 |  |  |  |  |  |  | =back | 
| 581 |  |  |  |  |  |  |  | 
| 582 |  |  |  |  |  |  | =head1 AUTHOR | 
| 583 |  |  |  |  |  |  |  | 
| 584 |  |  |  |  |  |  | Clinton Gormley <drtech@cpan.org> | 
| 585 |  |  |  |  |  |  |  | 
| 586 |  |  |  |  |  |  | =head1 COPYRIGHT AND LICENSE | 
| 587 |  |  |  |  |  |  |  | 
| 588 |  |  |  |  |  |  | This software is copyright (c) 2015 by Clinton Gormley. | 
| 589 |  |  |  |  |  |  |  | 
| 590 |  |  |  |  |  |  | This is free software; you can redistribute it and/or modify it under | 
| 591 |  |  |  |  |  |  | the same terms as the Perl 5 programming language system itself. | 
| 592 |  |  |  |  |  |  |  | 
| 593 |  |  |  |  |  |  | =cut | 
| 594 |  |  |  |  |  |  |  | 
| 595 |  |  |  |  |  |  | __END__ | 
| 596 |  |  |  |  |  |  |  | 
| 597 |  |  |  |  |  |  | # ABSTRACT: Create and administer indices in Elasticsearch | 
| 598 |  |  |  |  |  |  |  | 
| 599 |  |  |  |  |  |  |  |