This is an automated email from the ASF dual-hosted git repository.

ahuber pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/isis.git


The following commit(s) were added to refs/heads/master by this push:
     new 393d2a5a2b ISIS-3049: fully implement FacetHolderLayered
393d2a5a2b is described below

commit 393d2a5a2b5942dc41e6bfba2aec77df15809031
Author: Andi Huber <ahu...@apache.org>
AuthorDate: Tue Jun 28 22:08:33 2022 +0200

    ISIS-3049: fully implement FacetHolderLayered
    
    - provides a merged view of the local and the shared list of facets
---
 .../metamodel/facetapi/FacetHolderAbstract.java    | 16 +++---
 .../metamodel/facetapi/FacetHolderLayered.java     | 57 ++++++++++++++++++----
 .../isis/core/metamodel/facetapi/FacetRanking.java |  7 +++
 3 files changed, 64 insertions(+), 16 deletions(-)

diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderAbstract.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderAbstract.java
index e53864592f..432e9ecf3e 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderAbstract.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderAbstract.java
@@ -70,14 +70,14 @@ implements FacetHolder {
     private final Object $lock = new Object();
 
     @Override
-    public boolean containsFacet(final Class<? extends Facet> facetType) {
+    public final boolean containsFacet(final Class<? extends Facet> facetType) 
{
         synchronized($lock) {
             return snapshot.get().containsKey(facetType);
         }
     }
 
     @Override
-    public void addFacet(final @NonNull Facet facet) {
+    public final void addFacet(final @NonNull Facet facet) {
         synchronized($lock) {
 
             val ranking = rankingByType.computeIfAbsent(facet.facetType(), 
FacetRanking::new);
@@ -88,15 +88,17 @@ implements FacetHolder {
         }
     }
 
+    //TODO should be made final - however, overridden by 
ObjectSpecificationAbstract,
+    // which potentially leads to inconsistent behavior with facet and 
facet-ranking streaming
     @Override
-    public <T extends Facet> T getFacet(final Class<T> facetType) {
+    public /*final*/ <T extends Facet> T getFacet(final Class<T> facetType) {
         synchronized($lock) {
             return uncheckedCast(snapshot.get().get(facetType));
         }
     }
 
     @Override
-    public Stream<Facet> streamFacets() {
+    public final Stream<Facet> streamFacets() {
         synchronized($lock) {
             // consumers should play nice and don't take too long (as we have 
a lock)
             return snapshot.get().values().stream();
@@ -104,7 +106,7 @@ implements FacetHolder {
     }
 
     @Override
-    public int getFacetCount() {
+    public final int getFacetCount() {
         synchronized($lock) {
             return snapshot.get().size();
         }
@@ -113,12 +115,12 @@ implements FacetHolder {
     // -- VALIDATION SUPPORT
 
     @Override
-    public Stream<FacetRanking> streamFacetRankings() {
+    public final Stream<FacetRanking> streamFacetRankings() {
         return rankingByType.values().stream();
     }
 
     @Override
-    public Optional<FacetRanking> getFacetRanking(final Class<? extends Facet> 
facetType) {
+    public final Optional<FacetRanking> getFacetRanking(final Class<? extends 
Facet> facetType) {
         return Optional.ofNullable(rankingByType.get(facetType));
     }
 
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderLayered.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderLayered.java
index ba0cee8a4c..4549df9b94 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderLayered.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetHolderLayered.java
@@ -18,11 +18,13 @@
  */
 package org.apache.isis.core.metamodel.facetapi;
 
+import java.util.HashSet;
 import java.util.Optional;
 import java.util.stream.Stream;
 
 import org.apache.isis.applib.Identifier;
 import org.apache.isis.applib.services.i18n.TranslationContext;
+import org.apache.isis.commons.internal.base._NullSafe;
 import org.apache.isis.core.metamodel.context.MetaModelContext;
 import org.apache.isis.core.metamodel.facets.FacetedMethod;
 
@@ -87,7 +89,7 @@ implements FacetHolder {
             return shared.getFacetCount();
         }
         // cannot simply add up shared and local
-        return (int)streamFacets().count();
+        return (int)streamPopulatedFacetTypes().count();
     }
 
     @Override
@@ -110,9 +112,11 @@ implements FacetHolder {
         if(localFacet.semanticEquals(sharedFacet)) {
             return localFacet; // arbitrarily picking one
         }
-        return localFacet; // have the local win, this is safe for layout.xml 
stuff, but not for future use-cases
+        // semantic conflict
+        // have the local win, this is safe for layout.xml stuff, but probably 
not for future use-cases
+        return localFacet;
 
-//        // semantic conflict (unfortunately semanticEquals() is not always 
implemented yet)
+//        unfortunately semanticEquals() is not always implemented yet, 
otherwise we could throw ...
 //        throw _Exceptions.illegalState("conflicting facet semantics between 
shared %s and local %s",
 //                FacetUtil.toString(sharedFacet),
 //                FacetUtil.toString(localFacet));
@@ -126,20 +130,55 @@ implements FacetHolder {
 
     @Override
     public Stream<Facet> streamFacets() {
-        //FIXME[ISIS-3049] concat with local
-        return shared.streamFacets();
+        // optimization, not strictly required
+        if(local.getFacetCount()==0) {
+            return shared.streamFacets();
+        }
+        return streamPopulatedFacetTypes()
+                .<Facet>map(facetType->getFacet(facetType))
+                .filter(_NullSafe::isPresent);
     }
 
     @Override
     public Stream<FacetRanking> streamFacetRankings() {
-        //FIXME[ISIS-3049] concat with local
-        return shared.streamFacetRankings();
+        // optimization, not strictly required
+        if(local.getFacetCount()==0) {
+            return shared.streamFacetRankings();
+        }
+        return streamPopulatedFacetTypes()
+                .map(facetType->getFacetRanking(facetType).orElseThrow());
     }
 
     @Override
     public Optional<FacetRanking> getFacetRanking(final Class<? extends Facet> 
facetType) {
-        //FIXME[ISIS-3049] concat with local
-        return shared.getFacetRanking(facetType);
+        val localFacetRanking = local.getFacetRanking(facetType);
+        val sharedFacetRanking = shared.getFacetRanking(facetType);
+
+        if(localFacetRanking.isEmpty()) {
+            return sharedFacetRanking;
+        }
+        if(sharedFacetRanking.isEmpty()) {
+            return localFacetRanking;
+        }
+
+        val combinedFacetRanking = new FacetRanking(facetType);
+        // arbitrarily picking order: shared first and local last, such that 
if in conflict local wins
+        combinedFacetRanking.addAll(sharedFacetRanking.get());
+        combinedFacetRanking.addAll(localFacetRanking.get());
+
+        return Optional.of(combinedFacetRanking);
+    }
+
+    // -- HELPER
+
+    private Stream<Class<? extends Facet>> streamPopulatedFacetTypes() {
+        val facetTypes = new HashSet<Class<? extends Facet>>();
+        Stream.concat(
+                shared.streamFacets(),
+                local.streamFacets())
+        .map(Facet::facetType)
+        .forEach(facetTypes::add);
+        return facetTypes.stream();
     }
 
 }
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetRanking.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetRanking.java
index b3bdf31ce6..cc0d8b8e92 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetRanking.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facetapi/FacetRanking.java
@@ -121,6 +121,11 @@ public final class FacetRanking {
         return changesTopRank;
     }
 
+    public void addAll(final @NonNull FacetRanking facetRanking) {
+        facetRanking.facetsByPrecedence.asNavigableMapElseFail()
+            .forEach((k, facets)->facets.forEach(this::add));
+    }
+
     /**
      * Optionally returns the winning facet, considering the event facet (if 
any) and the top rank,
      * based on whether there was any added that has given facetType.
@@ -279,4 +284,6 @@ public final class FacetRanking {
     }
 
 
+
+
 }

Reply via email to