18
18
*/
19
19
package org .apache .gravitino .storage .relational .service ;
20
20
21
+ import com .google .common .base .Joiner ;
21
22
import com .google .common .base .Preconditions ;
22
23
import com .google .common .collect .Lists ;
23
24
import com .google .common .collect .Sets ;
24
25
import java .io .IOException ;
25
26
import java .util .Collections ;
27
+ import java .util .Comparator ;
28
+ import java .util .HashMap ;
26
29
import java .util .HashSet ;
27
30
import java .util .List ;
31
+ import java .util .Map ;
28
32
import java .util .Objects ;
29
33
import java .util .Set ;
30
34
import java .util .function .Function ;
38
42
import org .apache .gravitino .authorization .SecurableObject ;
39
43
import org .apache .gravitino .exceptions .NoSuchEntityException ;
40
44
import org .apache .gravitino .meta .RoleEntity ;
45
+ import org .apache .gravitino .storage .relational .mapper .CatalogMetaMapper ;
46
+ import org .apache .gravitino .storage .relational .mapper .FilesetMetaMapper ;
41
47
import org .apache .gravitino .storage .relational .mapper .GroupRoleRelMapper ;
42
48
import org .apache .gravitino .storage .relational .mapper .OwnerMetaMapper ;
43
49
import org .apache .gravitino .storage .relational .mapper .RoleMetaMapper ;
50
+ import org .apache .gravitino .storage .relational .mapper .SchemaMetaMapper ;
44
51
import org .apache .gravitino .storage .relational .mapper .SecurableObjectMapper ;
45
52
import org .apache .gravitino .storage .relational .mapper .UserRoleRelMapper ;
53
+ import org .apache .gravitino .storage .relational .po .CatalogPO ;
54
+ import org .apache .gravitino .storage .relational .po .FilesetPO ;
46
55
import org .apache .gravitino .storage .relational .po .RolePO ;
56
+ import org .apache .gravitino .storage .relational .po .SchemaPO ;
47
57
import org .apache .gravitino .storage .relational .po .SecurableObjectPO ;
48
58
import org .apache .gravitino .storage .relational .utils .ExceptionUtils ;
49
59
import org .apache .gravitino .storage .relational .utils .POConverters ;
54
64
55
65
/** The service class for role metadata. It provides the basic database operations for role. */
56
66
public class RoleMetaService {
67
+ private static final String DOT = "." ;
68
+ private static final Joiner DOT_JOINER = Joiner .on (DOT );
57
69
58
70
private static final Logger LOG = LoggerFactory .getLogger (RoleMetaService .class );
59
71
private static final RoleMetaService INSTANCE = new RoleMetaService ();
@@ -353,21 +365,58 @@ private static List<SecurableObject> listSecurableObjects(RolePO po) {
353
365
List <SecurableObjectPO > securableObjectPOs = listSecurableObjectsByRoleId (po .getRoleId ());
354
366
List <SecurableObject > securableObjects = Lists .newArrayList ();
355
367
356
- for (SecurableObjectPO securableObjectPO : securableObjectPOs ) {
357
- String fullName =
358
- MetadataObjectService .getMetadataObjectFullName (
359
- securableObjectPO .getType (), securableObjectPO .getMetadataObjectId ());
360
- if (fullName != null ) {
361
- securableObjects .add (
362
- POConverters .fromSecurableObjectPO (
363
- fullName , securableObjectPO , getType (securableObjectPO .getType ())));
364
- } else {
365
- LOG .warn (
366
- "The securable object {} {} may be deleted" ,
367
- securableObjectPO .getMetadataObjectId (),
368
- securableObjectPO .getType ());
369
- }
370
- }
368
+ securableObjectPOs .stream ()
369
+ .collect (Collectors .groupingBy (SecurableObjectPO ::getType ))
370
+ .forEach (
371
+ (type , objects ) -> {
372
+ // If the type is Fileset, use the batch retrieval interface;
373
+ // otherwise, use the single retrieval interface
374
+ if (type .equals (MetadataObject .Type .FILESET .name ())) {
375
+ List <Long > filesetIds =
376
+ objects .stream ()
377
+ .map (SecurableObjectPO ::getMetadataObjectId )
378
+ .collect (Collectors .toList ());
379
+
380
+ Map <Long , String > filesetIdAndNameMap = getFilesetObjectFullNames (filesetIds );
381
+
382
+ for (SecurableObjectPO securableObjectPO : objects ) {
383
+ String fullName =
384
+ filesetIdAndNameMap .get (securableObjectPO .getMetadataObjectId ());
385
+ if (fullName != null ) {
386
+ securableObjects .add (
387
+ POConverters .fromSecurableObjectPO (
388
+ fullName , securableObjectPO , getType (securableObjectPO .getType ())));
389
+ } else {
390
+ LOG .warn (
391
+ "The securable object {} {} may be deleted" ,
392
+ securableObjectPO .getMetadataObjectId (),
393
+ securableObjectPO .getType ());
394
+ }
395
+ }
396
+ } else {
397
+ // todo:to get other securable object fullNames using batch retrieving
398
+ for (SecurableObjectPO securableObjectPO : objects ) {
399
+ String fullName =
400
+ MetadataObjectService .getMetadataObjectFullName (
401
+ securableObjectPO .getType (), securableObjectPO .getMetadataObjectId ());
402
+ if (fullName != null ) {
403
+ securableObjects .add (
404
+ POConverters .fromSecurableObjectPO (
405
+ fullName , securableObjectPO , getType (securableObjectPO .getType ())));
406
+ } else {
407
+ LOG .warn (
408
+ "The securable object {} {} may be deleted" ,
409
+ securableObjectPO .getMetadataObjectId (),
410
+ securableObjectPO .getType ());
411
+ }
412
+ }
413
+ }
414
+ });
415
+
416
+ // To ensure that the order of the returned securable objects remains consistent,
417
+ // the securable objects are sorted by fullName here,
418
+ // since the order of securable objects after grouping by is different each time.
419
+ securableObjects .sort (Comparator .comparing (MetadataObject ::fullName ));
371
420
372
421
return securableObjects ;
373
422
}
@@ -394,4 +443,64 @@ private static MetadataObject.Type getType(String type) {
394
443
private static String getEntityType (SecurableObject securableObject ) {
395
444
return securableObject .type ().name ();
396
445
}
446
+
447
+ public static Map <Long , String > getFilesetObjectFullNames (List <Long > ids ) {
448
+ List <FilesetPO > filesetPOs =
449
+ SessionUtils .getWithoutCommit (
450
+ FilesetMetaMapper .class , mapper -> mapper .listFilesetPOsByFilesetIds (ids ));
451
+
452
+ if (filesetPOs == null || filesetPOs .isEmpty ()) {
453
+ return new HashMap <>();
454
+ }
455
+
456
+ List <Long > catalogIds =
457
+ filesetPOs .stream ().map (FilesetPO ::getCatalogId ).collect (Collectors .toList ());
458
+ List <Long > schemaIds =
459
+ filesetPOs .stream ().map (FilesetPO ::getSchemaId ).collect (Collectors .toList ());
460
+
461
+ Map <Long , String > catalogIdAndNameMap = getCatalogIdAndNameMap (catalogIds );
462
+ Map <Long , String > schemaIdAndNameMap = getSchemaIdAndNameMap (schemaIds );
463
+
464
+ HashMap <Long , String > filesetIdAndNameMap = new HashMap <>();
465
+
466
+ filesetPOs .forEach (
467
+ filesetPO -> {
468
+ // since the catalog or schema can be deleted, we need to check the null value,
469
+ // and when catalog or schema is deleted, we will set catalogName or schemaName to null
470
+ String catalogName = catalogIdAndNameMap .getOrDefault (filesetPO .getCatalogId (), null );
471
+ if (catalogName == null ) {
472
+ LOG .warn ("The catalog of fileset {} may be deleted" , filesetPO .getFilesetId ());
473
+ filesetIdAndNameMap .put (filesetPO .getFilesetId (), null );
474
+ return ;
475
+ }
476
+
477
+ String schemaName = schemaIdAndNameMap .getOrDefault (filesetPO .getSchemaId (), null );
478
+ if (schemaName == null ) {
479
+ LOG .warn ("The schema of fileset {} may be deleted" , filesetPO .getFilesetId ());
480
+ filesetIdAndNameMap .put (filesetPO .getFilesetId (), null );
481
+ return ;
482
+ }
483
+
484
+ String fullName = DOT_JOINER .join (catalogName , schemaName , filesetPO .getFilesetName ());
485
+ filesetIdAndNameMap .put (filesetPO .getFilesetId (), fullName );
486
+ });
487
+
488
+ return filesetIdAndNameMap ;
489
+ }
490
+
491
+ public static Map <Long , String > getSchemaIdAndNameMap (List <Long > schemaIds ) {
492
+ List <SchemaPO > schemaPOS =
493
+ SessionUtils .getWithoutCommit (
494
+ SchemaMetaMapper .class , mapper -> mapper .listSchemaPOsBySchemaIds (schemaIds ));
495
+ return schemaPOS .stream ()
496
+ .collect (Collectors .toMap (SchemaPO ::getSchemaId , SchemaPO ::getSchemaName ));
497
+ }
498
+
499
+ public static Map <Long , String > getCatalogIdAndNameMap (List <Long > catalogIds ) {
500
+ List <CatalogPO > catalogPOs =
501
+ SessionUtils .getWithoutCommit (
502
+ CatalogMetaMapper .class , mapper -> mapper .listCatalogPOsByCatalogIds (catalogIds ));
503
+ return catalogPOs .stream ()
504
+ .collect (Collectors .toMap (CatalogPO ::getCatalogId , CatalogPO ::getCatalogName ));
505
+ }
397
506
}
0 commit comments