@@ -47,6 +47,12 @@ const TIMED_OPS = Object.freeze({
47
47
DELETE_MULTIPLE_OBJECTS : 'delete_multiple_objects'
48
48
} ) ;
49
49
50
+ /**
51
+ * @typedef {{
52
+ * is_finished?: Boolean | Undefined,
53
+ * expire?: { is_finished?: Boolean | Undefined, key_marker?: String | Undefined, candidates_file_offset?: number | undefined}
54
+ * noncurrent?: { is_finished?: Boolean | Undefined, key_marker_versioned?: String | Undefined, version_id_marker?: String | Undefined }}} RuleState
55
+ */
50
56
51
57
class NCLifecycle {
52
58
constructor ( config_fs , options = { } ) {
@@ -265,7 +271,7 @@ class NCLifecycle {
265
271
if ( candidates . delete_candidates ?. length > 0 ) {
266
272
const expiration = lifecycle_rule . expiration ? this . _get_expiration_time ( lifecycle_rule . expiration ) : 0 ;
267
273
const filter_func = this . _build_lifecycle_filter ( { filter : lifecycle_rule . filter , expiration} ) ;
268
-
274
+ dbg . log0 ( 'process_rule: calling delete_multiple_objects, num of objects to be deleted' , candidates . delete_candidates . length ) ;
269
275
const delete_res = await this . _call_op_and_update_status ( {
270
276
bucket_name,
271
277
rule_id,
@@ -282,6 +288,7 @@ class NCLifecycle {
282
288
}
283
289
284
290
if ( candidates . abort_mpu_candidates ?. length > 0 ) {
291
+ dbg . log0 ( 'process_rule: calling delete_multiple_objects, num of mpu to be aborted' , candidates . delete_candidates . length ) ;
285
292
await this . _call_op_and_update_status ( {
286
293
bucket_name,
287
294
rule_id,
@@ -465,7 +472,7 @@ class NCLifecycle {
465
472
* @returns {Promise<Object[]> }
466
473
*/
467
474
async get_candidates_by_expiration_rule_posix ( lifecycle_rule , bucket_json , object_sdk ) {
468
- const rule_state = this . lifecycle_run_status . buckets_statuses [ bucket_json . name ] . rules_statuses [ lifecycle_rule . id ] . state . expire ;
475
+ const rule_state = this . _get_rule_state ( bucket_json , lifecycle_rule ) . expire ;
469
476
if ( rule_state . is_finished ) return [ ] ;
470
477
const expiration = this . _get_expiration_time ( lifecycle_rule . expiration ) ;
471
478
if ( expiration < 0 ) return [ ] ;
@@ -520,7 +527,7 @@ class NCLifecycle {
520
527
* @returns {Promise<Object[]> }
521
528
*/
522
529
async get_candidates_by_expiration_delete_marker_rule ( lifecycle_rule , bucket_json , object_sdk , { versions_list} ) {
523
- const rule_state = this . lifecycle_run_status . buckets_statuses [ bucket_json . name ] . rules_statuses [ lifecycle_rule . id ] . state . noncurrent ;
530
+ const rule_state = this . _get_rule_state ( bucket_json , lifecycle_rule ) . noncurrent ;
524
531
if ( rule_state . is_finished ) return [ ] ;
525
532
if ( ! versions_list ) {
526
533
versions_list = await this . load_versions_list ( object_sdk , lifecycle_rule , bucket_json , rule_state ) ;
@@ -619,7 +626,7 @@ class NCLifecycle {
619
626
* @returns {Promise<Object[]> }
620
627
*/
621
628
async get_candidates_by_noncurrent_version_expiration_rule ( lifecycle_rule , bucket_json , object_sdk , { versions_list} ) {
622
- const rule_state = this . lifecycle_run_status . buckets_statuses [ bucket_json . name ] . rules_statuses [ lifecycle_rule . id ] . state . noncurrent ;
629
+ const rule_state = this . _get_rule_state ( bucket_json , lifecycle_rule ) . noncurrent ;
623
630
if ( rule_state . is_finished ) return [ ] ;
624
631
625
632
if ( ! versions_list ) {
@@ -965,19 +972,22 @@ class NCLifecycle {
965
972
*/
966
973
init_rule_status ( bucket_name , rule_id ) {
967
974
this . lifecycle_run_status . buckets_statuses [ bucket_name ] . rules_statuses [ rule_id ] ??= { } ;
968
- this . lifecycle_run_status . buckets_statuses [ bucket_name ] . rules_statuses [ rule_id ] . state ??= { expire : { } , noncurrent : { } } ;
975
+ this . lifecycle_run_status . buckets_statuses [ bucket_name ] . rules_statuses [ rule_id ] . state ??= { expire : { } , noncurrent : { } } ;
969
976
this . lifecycle_run_status . buckets_statuses [ bucket_name ] . rules_statuses [ rule_id ] . rule_process_times = { } ;
970
977
this . lifecycle_run_status . buckets_statuses [ bucket_name ] . rules_statuses [ rule_id ] . rule_stats ??= { } ;
971
978
return this . lifecycle_run_status . buckets_statuses [ bucket_name ] . rules_statuses [ rule_id ] ;
972
979
}
973
980
974
981
/**
975
- * updates the rule state if all actions finished
982
+ * update_rule_status_is_finished updates the rule state if all actions finished
983
+ * notice that expire and noncurrent properties are initiated in init_rule_status()
984
+ * therefore they should not be undefined
976
985
* @param {string } bucket_name
977
986
* @param {string } rule_id
987
+ * @returns {Void }
978
988
*/
979
989
update_rule_status_is_finished ( bucket_name , rule_id ) {
980
- const rule_state = this . lifecycle_run_status . buckets_statuses [ bucket_name ] . rules_statuses [ rule_id ] . state ;
990
+ const rule_state = this . _get_rule_state ( { name : bucket_name } , { id : rule_id } ) ;
981
991
rule_state . is_finished = ( rule_state . expire . is_finished === undefined || rule_state . expire . is_finished === true ) &&
982
992
( rule_state . noncurrent . is_finished === undefined || rule_state . noncurrent . is_finished === true ) ;
983
993
}
@@ -1011,18 +1021,20 @@ class NCLifecycle {
1011
1021
* _set_rule_state sets the current rule state on the lifecycle run status
1012
1022
* @param {Object } bucket_json
1013
1023
* @param {* } lifecycle_rule
1014
- * @param {{is_finished?: Boolean | Undefined, candidates_file_offset?: number | undefined} } rule_state
1024
+ * @param {RuleState } rule_state
1015
1025
* @returns {Void }
1016
1026
*/
1017
1027
_set_rule_state ( bucket_json , lifecycle_rule , rule_state ) {
1018
- this . lifecycle_run_status . buckets_statuses [ bucket_json . name ] . rules_statuses [ lifecycle_rule . id ] . state = rule_state ;
1028
+ const existing_state = this . _get_rule_state ( bucket_json , lifecycle_rule ) ;
1029
+ const new_state = { ...existing_state , ...rule_state } ;
1030
+ this . lifecycle_run_status . buckets_statuses [ bucket_json . name ] . rules_statuses [ lifecycle_rule . id ] . state = new_state ;
1019
1031
}
1020
1032
1021
1033
/**
1022
1034
* _get_rule_state gets the current rule state on the lifecycle run status
1023
1035
* @param {Object } bucket_json
1024
1036
* @param {* } lifecycle_rule
1025
- * @returns {{is_finished?: Boolean | Undefined, candidates_file_offset?: number | undefined} } rule_state
1037
+ * @returns {RuleState }
1026
1038
*/
1027
1039
_get_rule_state ( bucket_json , lifecycle_rule ) {
1028
1040
return this . lifecycle_run_status . buckets_statuses [ bucket_json . name ] . rules_statuses [ lifecycle_rule . id ] . state ;
@@ -1164,6 +1176,7 @@ class NCLifecycle {
1164
1176
for ( const bucket_name of bucket_names ) {
1165
1177
const bucket_json = await this . config_fs . get_bucket_by_name ( bucket_name , config_fs_options ) ;
1166
1178
const bucket_mount_point = this . find_mount_point_by_bucket_path ( mount_point_to_policy_map , bucket_json . path ) ;
1179
+ if ( ! bucket_json . lifecycle_configuration_rules ?. length ) continue ;
1167
1180
for ( const lifecycle_rule of bucket_json . lifecycle_configuration_rules ) {
1168
1181
// currently we support expiration (current version) only
1169
1182
if ( lifecycle_rule . expiration ) {
@@ -1377,22 +1390,28 @@ class NCLifecycle {
1377
1390
* 1.2.2. parse the key from the candidate line
1378
1391
* 1.2.3. push the key to the candidates array
1379
1392
* 2. if candidates file does not exist, we return without error because it's valid that no candidates found
1393
+ * GAP - when supporting noncurrent rule, we should update the state type to noncurrent based on the candidates file path
1380
1394
* @param {Object } bucket_json
1381
1395
* @param {* } lifecycle_rule
1382
1396
* @param {String } rule_candidates_path
1383
1397
* @returns {Promise<Object[]> } parsed_candidates_array
1384
1398
*/
1385
1399
async parse_candidates_from_gpfs_ilm_policy ( bucket_json , lifecycle_rule , rule_candidates_path ) {
1386
1400
let reader ;
1401
+ const state_type = 'expire' ;
1402
+ const rule_state = this . _get_rule_state ( bucket_json , lifecycle_rule ) ?. [ state_type ] ;
1403
+ dbg . log2 ( `parse_candidates_from_gpfs_ilm_policy rule_state=${ rule_state } state_type=${ state_type } , currently on gpfs ilm flow - we support only expiration rule` ) ;
1404
+ if ( rule_state ?. is_finished ) return [ ] ;
1405
+ const finished_state = { [ state_type ] : { is_finished : true , candidates_file_offset : undefined } } ;
1406
+
1387
1407
try {
1388
- const rule_state = this . _get_rule_state ( bucket_json , lifecycle_rule ) ;
1389
1408
dbg . log2 ( `parse_candidates_from_gpfs_ilm_policy bucket_name=${ bucket_json . name } , rule_id ${ lifecycle_rule . id } , existing rule_state=${ util . inspect ( rule_state ) } ` ) ;
1390
-
1391
1409
const parsed_candidates_array = [ ] ;
1392
1410
reader = new NewlineReader ( this . non_gpfs_fs_context , rule_candidates_path , { lock : 'SHARED' , read_file_offset : rule_state ?. candidates_file_offset || 0 } ) ;
1411
+
1393
1412
const [ count , is_finished ] = await reader . forEachFilePathEntry ( async entry => {
1394
1413
if ( parsed_candidates_array . length >= config . NC_LIFECYCLE_LIST_BATCH_SIZE ) return false ;
1395
- const cur_rule_state = { is_finished : false , candidates_file_offset : reader . next_line_file_offset } ;
1414
+ const cur_rule_state = { [ state_type ] : { is_finished : false , candidates_file_offset : reader . next_line_file_offset } } ;
1396
1415
this . _set_rule_state ( bucket_json , lifecycle_rule , cur_rule_state ) ;
1397
1416
const key = this . _parse_key_from_line ( entry , bucket_json ) ;
1398
1417
// TODO - need to add etag, size, version_id
@@ -1402,14 +1421,14 @@ class NCLifecycle {
1402
1421
} ) ;
1403
1422
1404
1423
if ( is_finished ) {
1405
- this . _set_rule_state ( bucket_json , lifecycle_rule , { is_finished : true , candidates_file_offset : undefined } ) ;
1424
+ this . _set_rule_state ( bucket_json , lifecycle_rule , finished_state ) ;
1406
1425
}
1407
1426
dbg . log2 ( `parse_candidates_from_gpfs_ilm_policy: parsed_candidates_array ${ util . inspect ( parsed_candidates_array ) } , rule_state=${ util . inspect ( rule_state ) } , count=${ count } is_finished=${ is_finished } ` ) ;
1408
1427
return parsed_candidates_array ;
1409
1428
} catch ( err ) {
1410
1429
if ( err . code === 'ENOENT' ) {
1411
1430
dbg . log2 ( `parse_candidates_from_gpfs_ilm_policy ilm_candidates_file_exists does not exist, no candidates to delete` ) ;
1412
- this . _set_rule_state ( bucket_json , lifecycle_rule , { is_finished : true , candidates_file_offset : undefined } ) ;
1431
+ this . _set_rule_state ( bucket_json , lifecycle_rule , finished_state ) ;
1413
1432
return ;
1414
1433
}
1415
1434
dbg . error ( 'parse_candidates_from_gpfs_ilm_policy: error' , err ) ;
0 commit comments