45
45
import org .elasticsearch .common .xcontent .XContentType ;
46
46
import org .elasticsearch .common .xcontent .json .JsonXContent ;
47
47
import org .elasticsearch .gateway .GatewayService ;
48
+ import org .elasticsearch .index .Index ;
48
49
import org .elasticsearch .index .IndexNotFoundException ;
49
50
import org .elasticsearch .index .mapper .MapperService ;
51
+ import org .elasticsearch .indices .IndexClosedException ;
50
52
import org .elasticsearch .rest .RestStatus ;
51
53
import org .elasticsearch .xpack .core .security .index .RestrictedIndicesNames ;
52
54
import org .elasticsearch .xpack .core .template .TemplateUtils ;
@@ -173,9 +175,11 @@ public ElasticsearchException getUnavailableReason() {
173
175
throw new IllegalStateException ("caller must make sure to use a frozen state and check indexAvailable" );
174
176
}
175
177
176
- if (localState .indexExists ()) {
178
+ if (localState .indexState == IndexMetaData .State .CLOSE ) {
179
+ return new IndexClosedException (new Index (localState .concreteIndexName , ClusterState .UNKNOWN_UUID ));
180
+ } else if (localState .indexExists ()) {
177
181
return new UnavailableShardsException (null ,
178
- "at least one primary shard for the index [" + localState .concreteIndexName + "] is unavailable" );
182
+ "at least one primary shard for the index [" + localState .concreteIndexName + "] is unavailable" );
179
183
} else {
180
184
return new IndexNotFoundException (localState .concreteIndexName );
181
185
}
@@ -206,11 +210,24 @@ public void clusterChanged(ClusterChangedEvent event) {
206
210
final boolean indexAvailable = checkIndexAvailable (event .state ());
207
211
final boolean mappingIsUpToDate = indexMetaData == null || checkIndexMappingUpToDate (event .state ());
208
212
final Version mappingVersion = oldestIndexMappingVersion (event .state ());
209
- final ClusterHealthStatus indexStatus = indexMetaData == null ? null :
210
- new ClusterIndexHealth (indexMetaData , event .state ().getRoutingTable ().index (indexMetaData .getIndex ())).getStatus ();
211
213
final String concreteIndexName = indexMetaData == null ? internalIndexName : indexMetaData .getIndex ().getName ();
214
+ final ClusterHealthStatus indexHealth ;
215
+ final IndexMetaData .State indexState ;
216
+ if (indexMetaData == null ) {
217
+ // Index does not exist
218
+ indexState = null ;
219
+ indexHealth = null ;
220
+ } else if (indexMetaData .getState () == IndexMetaData .State .CLOSE ) {
221
+ indexState = IndexMetaData .State .CLOSE ;
222
+ indexHealth = null ;
223
+ logger .warn ("Index [{}] is closed. This is likely to prevent security from functioning correctly" , concreteIndexName );
224
+ } else {
225
+ indexState = IndexMetaData .State .OPEN ;
226
+ final IndexRoutingTable routingTable = event .state ().getRoutingTable ().index (indexMetaData .getIndex ());
227
+ indexHealth = new ClusterIndexHealth (indexMetaData , routingTable ).getStatus ();
228
+ }
212
229
final State newState = new State (creationTime , isIndexUpToDate , indexAvailable , mappingIsUpToDate , mappingVersion ,
213
- concreteIndexName , indexStatus );
230
+ concreteIndexName , indexHealth , indexState );
214
231
this .indexState = newState ;
215
232
216
233
if (newState .equals (previousState ) == false ) {
@@ -221,23 +238,21 @@ public void clusterChanged(ClusterChangedEvent event) {
221
238
}
222
239
223
240
private boolean checkIndexAvailable (ClusterState state ) {
224
- final IndexRoutingTable routingTable = getIndexRoutingTable (state );
225
- if (routingTable != null && routingTable .allPrimaryShardsActive ()) {
226
- return true ;
227
- }
228
- logger .debug ("Index [{}] is not yet active" , aliasName );
229
- return false ;
230
- }
231
-
232
- /**
233
- * Returns the routing-table for this index, or <code>null</code> if the index does not exist.
234
- */
235
- private IndexRoutingTable getIndexRoutingTable (ClusterState clusterState ) {
236
- IndexMetaData metaData = resolveConcreteIndex (aliasName , clusterState .metaData ());
241
+ IndexMetaData metaData = resolveConcreteIndex (aliasName , state .metaData ());
237
242
if (metaData == null ) {
238
- return null ;
243
+ logger .debug ("Index [{}] is not available - no metadata" , aliasName );
244
+ return false ;
245
+ }
246
+ if (metaData .getState () == IndexMetaData .State .CLOSE ) {
247
+ logger .warn ("Index [{}] is closed" , aliasName );
248
+ return false ;
249
+ }
250
+ final IndexRoutingTable routingTable = state .routingTable ().index (metaData .getIndex ());
251
+ if (routingTable == null || routingTable .allPrimaryShardsActive () == false ) {
252
+ logger .debug ("Index [{}] is not yet active" , aliasName );
253
+ return false ;
239
254
} else {
240
- return clusterState . routingTable (). index ( metaData . getIndex ()) ;
255
+ return true ;
241
256
}
242
257
}
243
258
@@ -402,15 +417,15 @@ public void onFailure(Exception e) {
402
417
* Return true if the state moves from an unhealthy ("RED") index state to a healthy ("non-RED") state.
403
418
*/
404
419
public static boolean isMoveFromRedToNonRed (State previousState , State currentState ) {
405
- return (previousState .indexStatus == null || previousState .indexStatus == ClusterHealthStatus .RED )
406
- && currentState .indexStatus != null && currentState .indexStatus != ClusterHealthStatus .RED ;
420
+ return (previousState .indexHealth == null || previousState .indexHealth == ClusterHealthStatus .RED )
421
+ && currentState .indexHealth != null && currentState .indexHealth != ClusterHealthStatus .RED ;
407
422
}
408
423
409
424
/**
410
425
* Return true if the state moves from the index existing to the index not existing.
411
426
*/
412
427
public static boolean isIndexDeleted (State previousState , State currentState ) {
413
- return previousState .indexStatus != null && currentState .indexStatus == null ;
428
+ return previousState .indexHealth != null && currentState .indexHealth == null ;
414
429
}
415
430
416
431
private static byte [] readTemplateAsBytes (String templateName ) {
@@ -440,24 +455,27 @@ private static Tuple<String, Settings> parseMappingAndSettingsFromTemplateBytes(
440
455
* State of the security index.
441
456
*/
442
457
public static class State {
443
- public static final State UNRECOVERED_STATE = new State (null , false , false , false , null , null , null );
458
+ public static final State UNRECOVERED_STATE = new State (null , false , false , false , null , null , null , null );
444
459
public final Instant creationTime ;
445
460
public final boolean isIndexUpToDate ;
446
461
public final boolean indexAvailable ;
447
462
public final boolean mappingUpToDate ;
448
463
public final Version mappingVersion ;
449
464
public final String concreteIndexName ;
450
- public final ClusterHealthStatus indexStatus ;
465
+ public final ClusterHealthStatus indexHealth ;
466
+ public final IndexMetaData .State indexState ;
451
467
452
468
public State (Instant creationTime , boolean isIndexUpToDate , boolean indexAvailable ,
453
- boolean mappingUpToDate , Version mappingVersion , String concreteIndexName , ClusterHealthStatus indexStatus ) {
469
+ boolean mappingUpToDate , Version mappingVersion , String concreteIndexName , ClusterHealthStatus indexHealth ,
470
+ IndexMetaData .State indexState ) {
454
471
this .creationTime = creationTime ;
455
472
this .isIndexUpToDate = isIndexUpToDate ;
456
473
this .indexAvailable = indexAvailable ;
457
474
this .mappingUpToDate = mappingUpToDate ;
458
475
this .mappingVersion = mappingVersion ;
459
476
this .concreteIndexName = concreteIndexName ;
460
- this .indexStatus = indexStatus ;
477
+ this .indexHealth = indexHealth ;
478
+ this .indexState = indexState ;
461
479
}
462
480
463
481
@ Override
@@ -471,7 +489,8 @@ public boolean equals(Object o) {
471
489
mappingUpToDate == state .mappingUpToDate &&
472
490
Objects .equals (mappingVersion , state .mappingVersion ) &&
473
491
Objects .equals (concreteIndexName , state .concreteIndexName ) &&
474
- indexStatus == state .indexStatus ;
492
+ indexHealth == state .indexHealth &&
493
+ indexState == state .indexState ;
475
494
}
476
495
477
496
public boolean indexExists () {
@@ -481,7 +500,7 @@ public boolean indexExists() {
481
500
@ Override
482
501
public int hashCode () {
483
502
return Objects .hash (creationTime , isIndexUpToDate , indexAvailable , mappingUpToDate , mappingVersion , concreteIndexName ,
484
- indexStatus );
503
+ indexHealth );
485
504
}
486
505
}
487
506
}
0 commit comments