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 fd051ec11a ISIS-3167: activates ManagedObject for VALUE
fd051ec11a is described below

commit fd051ec11a2899f3d6fd46bb68df2482bab8c68e
Author: Andi Huber <ahu...@apache.org>
AuthorDate: Tue Aug 30 13:32:18 2022 +0200

    ISIS-3167: activates ManagedObject for VALUE
    
    - purge ObjectSpecification mockery
---
 .../_testing/MetaModelContext_forTesting.java      |  43 +-
 .../isis/core/metamodel/commons/ClassUtil.java     |   4 +-
 ...ionOrAnyMatchingValueSemanticsFacetFactory.java |  48 ++-
 .../isis/core/metamodel/object/ManagedObject.java  |   4 +-
 .../core/metamodel/object/MmAssertionUtil.java     |   6 +-
 .../metamodel/object/_ManagedObjectSpecified.java  |  15 +-
 .../classsubstitutor/ClassSubstitutor.java         |   6 +-
 .../classsubstitutor/ClassSubstitutorRegistry.java |   3 +-
 .../core/metamodel/spec/ObjectSpecification.java   |  22 +-
 .../specloader/SpecificationLoaderDefault.java     |  17 +-
 .../specimpl/ObjectSpecificationAbstract.java      |   9 -
 .../apache/isis/core/metamodel/util/Facets.java    |  16 +-
 .../metamodel/facets/AbstractFacetFactoryTest.java |  16 -
 .../actions/ActionMethodsFacetFactoryTest.java     |  21 +-
 ...nnotationFacetFactoryTest_ActionInvocation.java |  36 +-
 .../CollectionFieldMethodsFacetFactoryTest.java    |  16 +-
 ...ollectionAnnotationFacetFactoryTest_typeOf.java |  22 -
 .../PropertyMethodsFacetFactoryTest.java           |  11 +-
 .../testspec/ObjectSpecificationStub.java          | 404 -------------------
 .../testdomain/interact/NewParameterModelTest.java |   1 +
 .../domainobjects/JsonValueEncoderTest.java        | 232 +++++++++++
 .../JsonValueEncoderTestAbstract.java              |  63 +++
 .../JsonValueEncoderTest_asAdapter.java            | 447 ---------------------
 .../JsonValueEncoderTest_asObject.java             |  64 ---
 24 files changed, 434 insertions(+), 1092 deletions(-)

diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/_testing/MetaModelContext_forTesting.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/_testing/MetaModelContext_forTesting.java
index 08eca038d5..b8864ec3ff 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/_testing/MetaModelContext_forTesting.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/_testing/MetaModelContext_forTesting.java
@@ -19,7 +19,6 @@
 package org.apache.isis.core.metamodel._testing;
 
 import java.util.ArrayList;
-import java.util.Collections;
 import java.util.List;
 import java.util.Map;
 import java.util.Optional;
@@ -30,6 +29,7 @@ import java.util.stream.Stream;
 import static java.util.Objects.requireNonNull;
 
 import org.springframework.core.env.AbstractEnvironment;
+import org.springframework.util.ClassUtils;
 
 import org.apache.isis.applib.services.factory.FactoryService;
 import org.apache.isis.applib.services.grid.GridLoaderService;
@@ -53,7 +53,6 @@ import 
org.apache.isis.applib.value.semantics.ValueSemanticsAbstract;
 import org.apache.isis.applib.value.semantics.ValueSemanticsProvider;
 import org.apache.isis.applib.value.semantics.ValueSemanticsResolver;
 import org.apache.isis.commons.collections.Can;
-import org.apache.isis.commons.internal.assertions._Assert;
 import org.apache.isis.commons.internal.base._Lazy;
 import org.apache.isis.commons.internal.base._NullSafe;
 import org.apache.isis.commons.internal.base._Strings;
@@ -69,13 +68,11 @@ import 
org.apache.isis.core.config.beans.IsisBeanTypeRegistry;
 import org.apache.isis.core.config.beans.IsisBeanTypeRegistryDefault;
 import org.apache.isis.core.config.environment.IsisSystemEnvironment;
 import org.apache.isis.core.config.progmodel.ProgrammingModelConstants;
+import org.apache.isis.core.metamodel.commons.ClassUtil;
 import org.apache.isis.core.metamodel.context.MetaModelContext;
 import org.apache.isis.core.metamodel.execution.MemberExecutorService;
 import org.apache.isis.core.metamodel.facets.object.icon.ObjectIconService;
-import org.apache.isis.core.metamodel.facets.object.title.TitleFacet;
-import 
org.apache.isis.core.metamodel.facets.object.title.parser.TitleFacetFromValueFacet;
-import org.apache.isis.core.metamodel.facets.object.value.ValueFacet;
-import 
org.apache.isis.core.metamodel.facets.object.value.vsp.ValueFacetUsingSemanticsProvider;
+import 
org.apache.isis.core.metamodel.facets.object.value.annotcfg.ValueFacetForValueAnnotationOrAnyMatchingValueSemanticsFacetFactory;
 import org.apache.isis.core.metamodel.object.ManagedObject;
 import org.apache.isis.core.metamodel.objectmanager.ObjectManager;
 import org.apache.isis.core.metamodel.objectmanager.ObjectManagerDefault;
@@ -84,6 +81,8 @@ import 
org.apache.isis.core.metamodel.progmodel.ProgrammingModel;
 import org.apache.isis.core.metamodel.progmodel.ProgrammingModelAbstract;
 import 
org.apache.isis.core.metamodel.progmodel.ProgrammingModelInitFilterDefault;
 import 
org.apache.isis.core.metamodel.progmodels.dflt.ProgrammingModelFacetsJava11;
+import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutorDefault;
+import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutorForCollections;
 import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutorRegistry;
 import org.apache.isis.core.metamodel.services.events.MetamodelEventService;
 import org.apache.isis.core.metamodel.services.grid.GridLoaderServiceDefault;
@@ -95,7 +94,6 @@ import 
org.apache.isis.core.metamodel.services.message.MessageServiceNoop;
 import org.apache.isis.core.metamodel.services.title.TitleServiceDefault;
 import org.apache.isis.core.metamodel.specloader.SpecificationLoader;
 import org.apache.isis.core.metamodel.specloader.SpecificationLoaderDefault;
-import 
org.apache.isis.core.metamodel.specloader.specimpl.ObjectSpecificationAbstract;
 import org.apache.isis.core.metamodel.valuesemantics.BigDecimalValueSemantics;
 import org.apache.isis.core.metamodel.valuesemantics.URLValueSemantics;
 import org.apache.isis.core.metamodel.valuesemantics.UUIDValueSemantics;
@@ -134,7 +132,12 @@ implements MetaModelContext {
     private IsisConfiguration configuration = newIsisConfiguration();
 
     @Builder.Default
-    private ClassSubstitutorRegistry classSubstitutorRegistry = new 
ClassSubstitutorRegistry(Collections.emptyList());
+    private ClassSubstitutorRegistry classSubstitutorRegistry =
+        new ClassSubstitutorRegistry(List.of(
+                //new ClassSubstitutorForDomainObjects(),
+                new ClassSubstitutorForCollections(),
+                new ClassSubstitutorDefault()
+                ));
 
     private ObjectManager objectManager;
 
@@ -353,6 +356,7 @@ implements MetaModelContext {
             val programmingModel = requireNonNull(getProgrammingModel());
             val isisBeanTypeClassifier = 
requireNonNull(getIsisBeanTypeClassifier());
             val isisBeanTypeRegistry = 
requireNonNull(getIsisBeanTypeRegistry());
+            val classSubstitutorRegistry = 
requireNonNull(getClassSubstitutorRegistry());
 
             specificationLoader = SpecificationLoaderDefault.getInstance(
                     configuration,
@@ -360,7 +364,8 @@ implements MetaModelContext {
                     serviceRegistry,
                     programmingModel,
                     isisBeanTypeClassifier,
-                    isisBeanTypeRegistry);
+                    isisBeanTypeRegistry,
+                    classSubstitutorRegistry);
 
         }
         return specificationLoader;
@@ -535,18 +540,16 @@ implements MetaModelContext {
     public <T> MetaModelContext_forTesting withValueSemantics(final 
ValueSemanticsAbstract<T> valueSemantics) {
         val valueClass = valueSemantics.getCorrespondingClass();
         val valueSpec = getSpecificationLoader().loadSpecification(valueClass);
-        final ValueFacet<T> valueFacet = ValueFacetUsingSemanticsProvider
-                .create(valueClass, Can.of(valueSemantics), valueSpec);
-        valueSpec.addFacet(valueFacet);
-        valueSpec.addFacet(TitleFacetFromValueFacet.create(valueFacet, 
valueSpec));
-
-        ((ObjectSpecificationAbstract)valueSpec).invalidateCachedFacets(); // 
optimization stuff
-
-        _Assert.assertTrue(valueSpec.valueFacet().isPresent());
-        
_Assert.assertTrue(valueSpec.lookupNonFallbackFacet(TitleFacet.class).isPresent());
-
+        ValueFacetForValueAnnotationOrAnyMatchingValueSemanticsFacetFactory
+            .installValueFacet(valueClass, Can.of(valueSemantics), valueSpec);
+
+        if(ClassUtils.isPrimitiveWrapper(valueClass)) {
+            val primitiveType = 
ClassUtil.unboxPrimitiveIfNecessary(valueClass);
+            val primitiveTypeSpec = 
getSpecificationLoader().loadSpecification(primitiveType);
+            ValueFacetForValueAnnotationOrAnyMatchingValueSemanticsFacetFactory
+            .installValueFacet(valueClass, Can.of(valueSemantics), 
primitiveTypeSpec);
+        }
         return this;
     }
 
-
 }
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/commons/ClassUtil.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/commons/ClassUtil.java
index 65db6d0311..4a2bb3e9e2 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/commons/ClassUtil.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/commons/ClassUtil.java
@@ -69,7 +69,7 @@ public final class ClassUtil {
             double.class, Double.class,
             void.class, Void.class);
 
-    final Map<Class<?>, Class<?>> primitiveByNameWrapper = Map.of(
+    final Map<Class<?>, Class<?>> primitiveByWrapper = Map.of(
             Boolean.class, boolean.class,
             Byte.class, byte.class,
             Character.class, char.class,
@@ -93,7 +93,7 @@ public final class ClassUtil {
         val firstPass = clazz.isPrimitive()
                 || !clazz.getPackageName().equals("java.lang")
                 ? clazz
-                : primitiveByNameWrapper.get(clazz);
+                : primitiveByWrapper.get(clazz); //null-able
         return firstPass!=null
                 ? firstPass
                 : clazz;
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facets/object/value/annotcfg/ValueFacetForValueAnnotationOrAnyMatchingValueSemanticsFacetFactory.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facets/object/value/annotcfg/ValueFacetForValueAnnotationOrAnyMatchingValueSemanticsFacetFactory.java
index 8392da1ffd..21e7b7adb0 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facets/object/value/annotcfg/ValueFacetForValueAnnotationOrAnyMatchingValueSemanticsFacetFactory.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/facets/object/value/annotcfg/ValueFacetForValueAnnotationOrAnyMatchingValueSemanticsFacetFactory.java
@@ -25,9 +25,11 @@ import org.apache.isis.applib.annotation.Value;
 import org.apache.isis.applib.id.LogicalType;
 import org.apache.isis.applib.value.semantics.ValueSemanticsProvider;
 import org.apache.isis.applib.value.semantics.ValueSemanticsResolver;
+import org.apache.isis.commons.collections.Can;
+import org.apache.isis.commons.internal.assertions._Assert;
 import org.apache.isis.commons.internal.base._Casts;
 import org.apache.isis.core.metamodel.context.MetaModelContext;
-import org.apache.isis.core.metamodel.facetapi.FacetHolder;
+import org.apache.isis.core.metamodel.facetapi.FacetUtil;
 import org.apache.isis.core.metamodel.facetapi.FeatureType;
 import org.apache.isis.core.metamodel.facets.FacetFactoryAbstract;
 import org.apache.isis.core.metamodel.facets.object.defaults.DefaultedFacet;
@@ -42,7 +44,9 @@ import 
org.apache.isis.core.metamodel.facets.object.value.MaxLengthFacetFromValu
 import 
org.apache.isis.core.metamodel.facets.object.value.TypicalLengthFacetFromValueFacet;
 import org.apache.isis.core.metamodel.facets.object.value.ValueFacet;
 import 
org.apache.isis.core.metamodel.facets.object.value.vsp.ValueFacetUsingSemanticsProvider;
+import org.apache.isis.core.metamodel.spec.ObjectSpecification;
 import 
org.apache.isis.core.metamodel.specloader.specimpl.ObjectSpecificationAbstract;
+import org.apache.isis.core.metamodel.util.Facets;
 
 import lombok.AccessLevel;
 import lombok.Getter;
@@ -89,11 +93,9 @@ extends FacetFactoryAbstract {
         val logicalType = LogicalType.infer(valueClass);
         val identifier = Identifier.classIdentifier(logicalType);
 
-        addAllFacetsForValueSemantics(identifier, valueClass, facetHolder, 
valueIfAny);
-
-        // optimization
-        _Casts.castTo(ObjectSpecificationAbstract.class, facetHolder)
-        .ifPresent(ObjectSpecificationAbstract::invalidateCachedFacets);
+        _Casts.castTo(ObjectSpecification.class, facetHolder)
+        .ifPresent(valueSpec->
+            addAllFacetsForValueSemantics(identifier, valueClass, valueSpec, 
valueIfAny));
     }
 
     // -- HELPER
@@ -101,7 +103,7 @@ extends FacetFactoryAbstract {
     private <T> Optional<ValueFacet<T>> addAllFacetsForValueSemantics(
             final Identifier identifier,
             final Class<T> valueClass,
-            final FacetHolder holder,
+            final ObjectSpecification valueSpec,
             final Optional<Value> valueIfAny) {
 
         val semanticsProviders = 
getValueSemanticsResolver().selectValueSemantics(identifier, valueClass);
@@ -118,21 +120,35 @@ extends FacetFactoryAbstract {
             log.debug("found {} ValueSemanticsProvider(s) for value type {}", 
semanticsProviders.size(), valueClass);
         }
 
-        val valueFacet = ValueFacetUsingSemanticsProvider.create(valueClass, 
semanticsProviders, holder);
+        val valueFacet = installValueFacet(valueClass, semanticsProviders, 
valueSpec);
+        return Optional.of(valueFacet);
+    }
+
+    // JUnit support
+    public static <T> ValueFacet<T> installValueFacet(
+            final Class<T> valueClass,
+            final Can<ValueSemanticsProvider<T>> valueSemanticsProviders,
+            final ObjectSpecification valueSpec) {
 
-        addFacet(valueFacet);
-        addFacet(new ImmutableFacetViaValueSemantics(holder));
-        addFacet(TitleFacetFromValueFacet.create(valueFacet, holder));
+        final ValueFacet<T> valueFacet = ValueFacetUsingSemanticsProvider
+                .create(valueClass, valueSemanticsProviders, valueSpec);
 
-        addFacetIfPresent(TypicalLengthFacetFromValueFacet.create(valueFacet, 
holder));
-        addFacetIfPresent(MaxLengthFacetFromValueFacet.create(valueFacet, 
holder));
-        addFacetIfPresent(DefaultedFacetFromValueFacet.create(valueFacet, 
holder));
+        valueSpec.addFacet(valueFacet);
+        valueSpec.addFacet(new ImmutableFacetViaValueSemantics(valueSpec));
+        valueSpec.addFacet(TitleFacetFromValueFacet.create(valueFacet, 
valueSpec));
 
-        return Optional.of(valueFacet);
-    }
+        
FacetUtil.addFacetIfPresent(TypicalLengthFacetFromValueFacet.create(valueFacet, 
valueSpec));
+        
FacetUtil.addFacetIfPresent(MaxLengthFacetFromValueFacet.create(valueFacet, 
valueSpec));
+        
FacetUtil.addFacetIfPresent(DefaultedFacetFromValueFacet.create(valueFacet, 
valueSpec));
 
+        ((ObjectSpecificationAbstract)valueSpec).invalidateCachedFacets(); // 
optimization stuff
 
+        _Assert.assertTrue(valueSpec.valueFacet().isPresent());
+        
_Assert.assertTrue(valueSpec.lookupNonFallbackFacet(TitleFacet.class).isPresent());
+        _Assert.assertNotNull(Facets.valueSerializerElseFail(valueSpec, 
valueSpec.getCorrespondingClass()));
 
+        return valueFacet;
+    }
 
     // -- DEPENDENCIES
 
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/ManagedObject.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/ManagedObject.java
index 7851dd2569..4ba7466d57 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/ManagedObject.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/ManagedObject.java
@@ -434,8 +434,8 @@ public interface ManagedObject extends HasMetaModelContext {
             final @NonNull ObjectSpecification spec,
             final @Nullable Object pojo) {
         return pojo != null
-                ? new _ManagedObjectWithEagerSpec(spec, pojo) //FIXME
-                //new _ManagedObjectValue(spec, pojo)
+                //? new _ManagedObjectWithEagerSpec(spec, pojo) //FIXME
+                ? new _ManagedObjectValue(spec, pojo)
                 : empty(spec);
     }
     /**
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/MmAssertionUtil.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/MmAssertionUtil.java
index eee5b2f32f..654b3c805b 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/MmAssertionUtil.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/MmAssertionUtil.java
@@ -25,6 +25,7 @@ import org.springframework.util.ClassUtils;
 
 import org.apache.isis.commons.internal.assertions._Assert;
 import org.apache.isis.commons.internal.exceptions._Exceptions;
+import org.apache.isis.core.metamodel.commons.ClassUtil;
 import org.apache.isis.core.metamodel.spec.ObjectSpecification;
 
 import lombok.NonNull;
@@ -41,7 +42,10 @@ public class MmAssertionUtil {
                 || requiredSpec==null) {
             return;
         }
-        val actualSpec = 
requiredSpec.getSpecificationLoader().specForType(pojo.getClass()).orElse(null);
+        val actualType = requiredSpec.isPrimitive()
+                ? ClassUtil.unboxPrimitiveIfNecessary(pojo.getClass())
+                : pojo.getClass();
+        val actualSpec = 
requiredSpec.getSpecificationLoader().specForType(actualType).orElse(null);
         _Assert.assertEquals(requiredSpec, actualSpec, ()->
             String.format("pojo's actual ObjectSpecification %s "
                     + "does not exaclty match %s%n", actualSpec, 
requiredSpec));
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/_ManagedObjectSpecified.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/_ManagedObjectSpecified.java
index 2071aad5ce..4894928b96 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/_ManagedObjectSpecified.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/object/_ManagedObjectSpecified.java
@@ -27,11 +27,14 @@ import 
org.apache.isis.commons.internal.exceptions._Exceptions;
 import org.apache.isis.core.metamodel.context.MetaModelContext;
 import org.apache.isis.core.metamodel.spec.ObjectSpecification;
 
+import lombok.AccessLevel;
 import lombok.Getter;
 import lombok.NonNull;
+import lombok.RequiredArgsConstructor;
 import lombok.val;
 import lombok.experimental.Accessors;
 
+@RequiredArgsConstructor(access = AccessLevel.PROTECTED)
 abstract class _ManagedObjectSpecified
 implements ManagedObject {
 
@@ -41,13 +44,6 @@ implements ManagedObject {
     @Getter(onMethod_ = {@Override}) @Accessors(makeFinal = true)
     private final @NonNull ObjectSpecification specification;
 
-    protected _ManagedObjectSpecified(
-            final @NonNull Specialization specialization,
-            final @NonNull ObjectSpecification specification) {
-        this.specialization = specialization;
-        this.specification = specification;
-    }
-
     @Override
     public final MetaModelContext getMetaModelContext() {
         return getSpecification().getMetaModelContext();
@@ -62,7 +58,10 @@ implements ManagedObject {
     public final <T> T assertCompliance(final @NonNull T pojo) {
         MmAssertionUtil.assertPojoNotWrapped(pojo);
         if(specification.isAbstract()) {
-            
_Assert.assertFalse(specialization.getTypePolicy().isExactTypeRequired());
+            
_Assert.assertFalse(specialization.getTypePolicy().isExactTypeRequired(),
+                    ()->String.format("Specialization %s does not allow 
abstract type %s",
+                            specialization,
+                            specification));
         }
         if(specialization.getTypePolicy().isExactTypeRequired()) {
             MmAssertionUtil.assertExactType(specification, pojo);
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutor.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutor.java
index 2257909ad2..3e557caa69 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutor.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutor.java
@@ -79,7 +79,7 @@ public interface ClassSubstitutor {
             return NEVER_INTROSPECT_CLASS;
         }
 
-        public static Substitution replaceWith(@lombok.NonNull 
@org.springframework.lang.NonNull Class<?> cls) {
+        public static Substitution replaceWith(final @NonNull Class<?> cls) {
             return of(Type.REPLACE_WITH_OTHER_CLASS, cls);
         }
 
@@ -116,7 +116,7 @@ public interface ClassSubstitutor {
         // -- OPERATOR
 
         @Override
-        public Class<?> apply(Class<?> cls) {
+        public Class<?> apply(final Class<?> cls) {
             if(isNeverIntrospect()) {
                 return null;
             }
@@ -132,7 +132,7 @@ public interface ClassSubstitutor {
      * @return (non-null) Substitution for given {@code cls}
      * @since 2.0
      */
-    Substitution getSubstitution(@lombok.NonNull 
@org.springframework.lang.NonNull Class<?> cls);
+    Substitution getSubstitution(@NonNull Class<?> cls);
 
 
 }
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutorRegistry.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutorRegistry.java
index 3d0fd6e9c5..30465702f7 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutorRegistry.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/services/classsubstitutor/ClassSubstitutorRegistry.java
@@ -46,14 +46,13 @@ import lombok.extern.log4j.Log4j2;
 public class ClassSubstitutorRegistry {
 
     private final List<ClassSubstitutor> classSubstitutors;
+    private final Map<Class<?>, Substitution> cache = 
_Maps.newConcurrentHashMap();
 
     @Inject
     public ClassSubstitutorRegistry(final List<ClassSubstitutor> 
classSubstitutors) {
         this.classSubstitutors = classSubstitutors;
     }
 
-    private final Map<Class<?>, Substitution> cache = 
_Maps.newConcurrentHashMap();
-
     /**
      * @param originalClass
      * @return (non-null) the aggregated Substitution that applies to given 
originalClass
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/spec/ObjectSpecification.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/spec/ObjectSpecification.java
index 976b36f4b5..f0a755a073 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/spec/ObjectSpecification.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/spec/ObjectSpecification.java
@@ -412,8 +412,26 @@ extends
         return getBeanSort().isMixin();
     }
 
-    //TODO this predicate can now be answered by getBeanSort().isAbstract(), 
we can retire any old logic
-    boolean isAbstract();
+    /**
+     * Whether {@link #getCorrespondingClass()} is {@link Void} or void.
+     */
+    default boolean isVoid() {
+        return getCorrespondingClass()==void.class
+                || getCorrespondingClass()==Void.class;
+    }
+
+    /**
+     * Whether {@link #getCorrespondingClass()} is a primitive type,
+     * but not {@link Void} or void.
+     */
+    default boolean isPrimitive() {
+        return !isVoid()
+                && getCorrespondingClass().isPrimitive();
+    }
+
+    default boolean isAbstract() {
+        return getBeanSort().isAbstract();
+    }
 
     default boolean isEntity() {
         return getBeanSort().isEntity()
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/SpecificationLoaderDefault.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/SpecificationLoaderDefault.java
index 66afd57dfa..9ada3880b1 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/SpecificationLoaderDefault.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/SpecificationLoaderDefault.java
@@ -71,8 +71,6 @@ import 
org.apache.isis.core.metamodel.progmodel.ProgrammingModelService;
 import 
org.apache.isis.core.metamodel.progmodels.dflt.ProgrammingModelFacetsJava11;
 import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutor;
 import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutor.Substitution;
-import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutorDefault;
-import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutorForCollections;
 import 
org.apache.isis.core.metamodel.services.classsubstitutor.ClassSubstitutorRegistry;
 import org.apache.isis.core.metamodel.spec.ObjectSpecification;
 import org.apache.isis.core.metamodel.specloader.facetprocessor.FacetProcessor;
@@ -184,17 +182,14 @@ public class SpecificationLoaderDefault implements 
SpecificationLoader {
             final ServiceRegistry serviceRegistry,
             final ProgrammingModel programmingModel,
             final IsisBeanTypeClassifier isisBeanTypeClassifier,
-            final IsisBeanTypeRegistry isisBeanTypeRegistry) {
+            final IsisBeanTypeRegistry isisBeanTypeRegistry,
+            final ClassSubstitutorRegistry classSubstitutorRegistry) {
 
         val instance = new SpecificationLoaderDefault(
                 programmingModel, isisConfiguration, isisSystemEnvironment,
                 serviceRegistry, isisBeanTypeClassifier, isisBeanTypeRegistry,
                 ()->new ValueSemanticsResolverDefault(List.of(), null),
-                new ClassSubstitutorRegistry(List.of(
-                        //new ClassSubstitutorForDomainObjects(),
-                        new ClassSubstitutorForCollections(),
-                        new ClassSubstitutorDefault()
-                        )));
+                classSubstitutorRegistry);
 
         instance.metaModelContext = 
serviceRegistry.lookupServiceElseFail(MetaModelContext.class);
         instance.facetProcessor = new FacetProcessor(programmingModel, 
instance.metaModelContext);
@@ -243,11 +238,11 @@ public class SpecificationLoaderDefault implements 
SpecificationLoader {
             .concat(
                 
isisBeanTypeRegistry.getDiscoveredValueTypes().keySet().stream(),
                 valueSemanticsResolver.get().streamClassesWithValueSemantics())
-            .forEach(valueType -> {
-                val valueSpec = loadSpecification(valueType, 
IntrospectionState.NOT_INTROSPECTED);
+            .forEach(valueClass -> {
+                val valueSpec = loadSpecification(valueClass, 
IntrospectionState.NOT_INTROSPECTED);
                 if(valueSpec!=null) {
                     knownSpecs.add(valueSpec);
-                    valueTypeSpecs.put(valueType, valueSpec);
+                    valueTypeSpecs.put(valueClass, valueSpec);
                 }
             });
 
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/specimpl/ObjectSpecificationAbstract.java
 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/specimpl/ObjectSpecificationAbstract.java
index c0fbc1d6f8..bc0767a990 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/specimpl/ObjectSpecificationAbstract.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/specloader/specimpl/ObjectSpecificationAbstract.java
@@ -47,7 +47,6 @@ import org.apache.isis.commons.internal.collections._Sets;
 import org.apache.isis.commons.internal.collections._Streams;
 import org.apache.isis.commons.internal.exceptions._Exceptions;
 import org.apache.isis.core.config.beans.IsisBeanTypeRegistry;
-import org.apache.isis.core.metamodel.commons.ClassExtensions;
 import org.apache.isis.core.metamodel.consent.Consent;
 import org.apache.isis.core.metamodel.consent.InteractionInitiatedBy;
 import org.apache.isis.core.metamodel.consent.InteractionResult;
@@ -176,7 +175,6 @@ implements ObjectSpecification {
     private final Class<?> correspondingClass;
     private final String fullName;
     private final String shortName;
-    private final boolean isAbstract;
 
     private final LogicalType logicalType;
 
@@ -209,8 +207,6 @@ implements ObjectSpecification {
         this.shortName = shortName;
         this.beanSort = beanSort;
 
-        this.isAbstract = ClassExtensions.isAbstract(introspectedClass);
-
         this.facetProcessor = facetProcessor;
         this.postProcessor = postProcessor;
     }
@@ -617,11 +613,6 @@ implements ObjectSpecification {
         return directSubclasses.hasSubclasses();
     }
 
-    @Override
-    public final boolean isAbstract() {
-        return isAbstract;
-    }
-
     // -- ASSOCIATIONS
 
     @Override
diff --git 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/util/Facets.java 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/util/Facets.java
index 3b2a7e4a3a..a11dae3ce3 100644
--- 
a/core/metamodel/src/main/java/org/apache/isis/core/metamodel/util/Facets.java
+++ 
b/core/metamodel/src/main/java/org/apache/isis/core/metamodel/util/Facets.java
@@ -24,6 +24,7 @@ import java.util.function.Predicate;
 import java.util.stream.Stream;
 
 import org.springframework.lang.Nullable;
+import org.springframework.util.ClassUtils;
 
 import org.apache.isis.applib.annotation.BookmarkPolicy;
 import org.apache.isis.applib.annotation.DomainServiceLayout.MenuBar;
@@ -404,7 +405,7 @@ public final class Facets {
             final ObjectSpecification objectSpec,
             final Class<X> requiredType) {
         return objectSpec.valueFacet()
-        
.filter(valueFacet->requiredType.isAssignableFrom(valueFacet.getValueClass()))
+        .filter(typeGuard(requiredType))
         .flatMap(ValueFacet::selectDefaultSemantics)
         .map(_Casts::uncheckedCast);
     }
@@ -414,7 +415,7 @@ public final class Facets {
             final ObjectSpecification objectSpec,
             final Class<X> requiredType) {
         return objectSpec.valueFacet()
-        
.filter(valueFacet->requiredType.isAssignableFrom(valueFacet.getValueClass()))
+        .filter(typeGuard(requiredType))
         .map(valueFacet->(ValueSerializer<X>)valueFacet);
     }
 
@@ -427,4 +428,15 @@ public final class Facets {
                 objectSpec.getCorrespondingClass().getName()));
     }
 
+    // -- HELPER
+
+    @SuppressWarnings("rawtypes")
+    private Predicate<? super ValueFacet> typeGuard(
+            final Class<?> requiredType) {
+        return valueFacet->
+            ClassUtils.resolvePrimitiveIfNecessary(requiredType)
+            .isAssignableFrom(
+                    
ClassUtils.resolvePrimitiveIfNecessary(valueFacet.getValueClass()));
+    }
+
 }
diff --git 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/AbstractFacetFactoryTest.java
 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/AbstractFacetFactoryTest.java
index b72301b44b..a18facd2be 100644
--- 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/AbstractFacetFactoryTest.java
+++ 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/AbstractFacetFactoryTest.java
@@ -41,8 +41,6 @@ import 
org.apache.isis.core.metamodel.facets.FacetFactory.ProcessMethodContext;
 import 
org.apache.isis.core.metamodel.facets.actions.layout.ActionLayoutFacetFactory;
 import 
org.apache.isis.core.metamodel.facets.collections.layout.CollectionLayoutFacetFactory;
 import 
org.apache.isis.core.metamodel.facets.properties.propertylayout.PropertyLayoutFacetFactory;
-import org.apache.isis.core.metamodel.spec.ObjectSpecification;
-import org.apache.isis.core.metamodel.specloader.SpecificationLoader;
 import org.apache.isis.core.security.authentication.InteractionContextFactory;
 
 import junit.framework.TestCase;
@@ -68,7 +66,6 @@ public abstract class AbstractFacetFactoryTest extends 
TestCase {
     protected TranslationService mockTranslationService;
     protected InteractionProvider mockInteractionProvider;
     protected final InteractionContext iaContext = 
InteractionContextFactory.testing();
-    protected SpecificationLoader mockSpecificationLoader;
     protected MethodRemover_forTesting methodRemover;
 
     protected FacetHolder facetHolder;
@@ -88,10 +85,7 @@ public abstract class AbstractFacetFactoryTest extends 
TestCase {
 
         mockTranslationService = context.mock(TranslationService.class);
 
-        mockSpecificationLoader = context.mock(SpecificationLoader.class);
-
         metaModelContext = MetaModelContext_forTesting.builder()
-                .specificationLoader(mockSpecificationLoader)
                 .translationService(mockTranslationService)
                 .interactionProvider(mockInteractionProvider)
                 .build();
@@ -113,18 +107,8 @@ public abstract class AbstractFacetFactoryTest extends 
TestCase {
                 );
     }
 
-
-
-    protected void 
allowing_specificationLoader_loadSpecification_any_willReturn(final 
ObjectSpecification objectSpecification) {
-        context.checking(new Expectations() {{
-            
allowing(mockSpecificationLoader).loadSpecification(with(any(Class.class)));
-            will(returnValue(objectSpecification));
-        }});
-    }
-
     @Override
     protected void tearDown() throws Exception {
-        mockSpecificationLoader = null;
         methodRemover = null;
         facetedMethod = null;
         super.tearDown();
diff --git 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/ActionMethodsFacetFactoryTest.java
 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/ActionMethodsFacetFactoryTest.java
index 7816e0b4bb..25110b3047 100644
--- 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/ActionMethodsFacetFactoryTest.java
+++ 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/ActionMethodsFacetFactoryTest.java
@@ -46,13 +46,13 @@ import 
org.apache.isis.core.metamodel.facets.param.defaults.ActionParameterDefau
 import 
org.apache.isis.core.metamodel.facets.param.defaults.methodnum.ActionParameterDefaultsFacetViaMethod;
 import 
org.apache.isis.core.metamodel.facets.param.defaults.methodnum.ActionParameterDefaultsFacetViaMethodFactory;
 import org.apache.isis.core.metamodel.spec.ObjectSpecification;
-import org.apache.isis.core.metamodel.testspec.ObjectSpecificationStub;
 
 import lombok.val;
 
 public class ActionMethodsFacetFactoryTest extends AbstractFacetFactoryTest {
 
-    private JUnitRuleMockery2 context = 
JUnitRuleMockery2.createFor(JUnitRuleMockery2.Mode.INTERFACES_AND_CLASSES);
+    private JUnitRuleMockery2 context =
+            
JUnitRuleMockery2.createFor(JUnitRuleMockery2.Mode.INTERFACES_AND_CLASSES);
 
     private ObjectSpecification voidSpec;
 //    private final ObjectSpecification stringSpec = new 
ObjectSpecificationStub("java.lang.String");
@@ -65,7 +65,8 @@ public class ActionMethodsFacetFactoryTest extends 
AbstractFacetFactoryTest {
 
         super.setUp();
 
-        voidSpec = new ObjectSpecificationStub(metaModelContext, void.class);
+        val specLoader = metaModelContext.getSpecificationLoader();
+        voidSpec = specLoader.loadSpecification(void.class);
 
         context.checking(new Expectations() {{
 
@@ -103,9 +104,6 @@ public class ActionMethodsFacetFactoryTest extends 
AbstractFacetFactoryTest {
     public void testInstallsValidateMethodNoArgsFacetAndRemovesMethod() {
         val facetFactory = new 
ActionValidationFacetViaMethodFactory(metaModelContext);
 
-        // mockSpecificationLoader.setLoadSpecificationStringReturn(voidSpec);
-        
allowing_specificationLoader_loadSpecification_any_willReturn(this.voidSpec);
-
         @SuppressWarnings("unused")
         class Customer {
 
@@ -134,9 +132,6 @@ public class ActionMethodsFacetFactoryTest extends 
AbstractFacetFactoryTest {
     public void testInstallsValidateMethodSomeArgsFacetAndRemovesMethod() {
         val facetFactory = new 
ActionValidationFacetViaMethodFactory(metaModelContext);
 
-        // mockSpecificationLoader.setLoadSpecificationStringReturn(voidSpec);
-        
allowing_specificationLoader_loadSpecification_any_willReturn(this.voidSpec);
-
         class Customer {
             @SuppressWarnings("unused")
             public void someAction(final int x, final int y) {
@@ -165,8 +160,6 @@ public class ActionMethodsFacetFactoryTest extends 
AbstractFacetFactoryTest {
     public void testInstallsParameterDefaultsMethodAndRemovesMethod() {
         val facetFactory = new 
ActionParameterDefaultsFacetViaMethodFactory(metaModelContext);
 
-        
allowing_specificationLoader_loadSpecification_any_willReturn(this.voidSpec);
-
         class Customer {
             @SuppressWarnings("unused")
             public void someAction(final int x, final long y) {
@@ -214,9 +207,6 @@ public class ActionMethodsFacetFactoryTest extends 
AbstractFacetFactoryTest {
     public void testInstallsParameterChoicesMethodAndRemovesMethod() {
         val facetFactory = new 
ActionParameterChoicesFacetViaMethodFactory(metaModelContext);
 
-        // mockSpecificationLoader.setLoadSpecificationStringReturn(voidSpec);
-        
allowing_specificationLoader_loadSpecification_any_willReturn(this.voidSpec);
-
         class Customer {
             @SuppressWarnings("unused")
             public void someAction(final int x, final long y, final long z) {
@@ -279,9 +269,6 @@ public class ActionMethodsFacetFactoryTest extends 
AbstractFacetFactoryTest {
     public void testInstallsParameterAutoCompleteMethodAndRemovesMethod() {
         val facetFactory = new 
ActionParameterAutoCompleteFacetViaMethodFactory(metaModelContext);
 
-        // mockSpecificationLoader.setLoadSpecificationStringReturn(voidSpec);
-        
allowing_specificationLoader_loadSpecification_any_willReturn(this.voidSpec);
-
         class Customer {
             @SuppressWarnings("unused")
             public void someAction(final int x, final long y) {
diff --git 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/action/ActionAnnotationFacetFactoryTest_ActionInvocation.java
 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/action/ActionAnnotationFacetFactoryTest_ActionInvocation.java
index 5c81339757..ea8495b228 100644
--- 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/action/ActionAnnotationFacetFactoryTest_ActionInvocation.java
+++ 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/actions/action/ActionAnnotationFacetFactoryTest_ActionInvocation.java
@@ -35,7 +35,6 @@ import 
org.apache.isis.core.metamodel.facets.param.choices.ActionParameterChoice
 import 
org.apache.isis.core.metamodel.facets.param.choices.methodnum.ActionParameterChoicesFacetViaMethod;
 import 
org.apache.isis.core.metamodel.facets.param.choices.methodnum.ActionParameterChoicesFacetViaMethodFactory;
 import org.apache.isis.core.metamodel.spec.ObjectSpecification;
-import org.apache.isis.core.metamodel.testspec.ObjectSpecificationStub;
 
 import lombok.val;
 
@@ -60,15 +59,14 @@ extends AbstractFacetFactoryTest {
         super.setUp();
         this.facetFactory =  new 
ActionAnnotationFacetFactory(metaModelContext);
 
-        voidSpec = new ObjectSpecificationStub(metaModelContext, void.class);
-        stringSpec = new ObjectSpecificationStub(metaModelContext, 
java.lang.String.class);
-        customerSpec = new ObjectSpecificationStub(metaModelContext, 
Customer.class);
+        val specLoader = metaModelContext.getSpecificationLoader();
+        voidSpec = specLoader.loadSpecification(void.class);
+        stringSpec = specLoader.loadSpecification(java.lang.String.class);
+        customerSpec = specLoader.loadSpecification(Customer.class);
     }
 
     public void testActionInvocationFacetIsInstalledAndMethodRemoved() {
 
-        
allowing_specificationLoader_loadSpecification_any_willReturn(voidSpec);
-
         class Customer {
             public void someAction() {
             }
@@ -89,8 +87,6 @@ extends AbstractFacetFactoryTest {
 
     public void testActionReturnTypeWhenVoid() {
 
-        
allowing_specificationLoader_loadSpecification_any_willReturn(voidSpec);
-
         class Customer {
             public void someAction() {
             }
@@ -107,8 +103,6 @@ extends AbstractFacetFactoryTest {
 
     public void testActionReturnTypeWhenNotVoid() {
 
-        
allowing_specificationLoader_loadSpecification_any_willReturn(stringSpec);
-
         class Customer {
             public String someAction() {
                 return null;
@@ -126,27 +120,29 @@ extends AbstractFacetFactoryTest {
 
     public void testActionOnType() {
 
-        
allowing_specificationLoader_loadSpecification_any_willReturn(customerSpec);
-
-        class Customer {
+        class LocalCustomer {
             public String someAction() {
                 return null;
             }
         }
-        final Method actionMethod = findMethod(Customer.class, "someAction");
+
+        val customerSpec = 
metaModelContext.getSpecificationLoader().loadSpecification(LocalCustomer.class);
+
+        final Method actionMethod = findMethod(LocalCustomer.class, 
"someAction");
 
         processInvocation(facetFactory, ProcessMethodContext
-                .forTesting(Customer.class, null, actionMethod, methodRemover, 
facetedMethod));
+                .forTesting(LocalCustomer.class, null, actionMethod, 
methodRemover, facetedMethod));
 
         final Facet facet = 
facetedMethod.getFacet(ActionInvocationFacet.class);
-        final ActionInvocationFacetForDomainEventAbstract 
actionInvocationFacetViaMethod = (ActionInvocationFacetForDomainEventAbstract) 
facet;
-        assertEquals(customerSpec, 
actionInvocationFacetViaMethod.getDeclaringType());
+        final ActionInvocationFacetForDomainEventAbstract 
actionInvocationFacetViaMethod =
+                (ActionInvocationFacetForDomainEventAbstract) facet;
+        assertEquals(
+                customerSpec,
+                actionInvocationFacetViaMethod.getDeclaringType());
     }
 
     public void testActionsPickedUpFromSuperclass() {
 
-        
allowing_specificationLoader_loadSpecification_any_willReturn(voidSpec);
-
         class Customer {
             public void someAction(final int x, final long y) {
             }
@@ -169,8 +165,6 @@ extends AbstractFacetFactoryTest {
 
     public void testActionsPickedUpFromSuperclassButHelpersFromSubClass() {
 
-        
allowing_specificationLoader_loadSpecification_any_willReturn(voidSpec);
-
         val facetFactoryForChoices = new 
ActionParameterChoicesFacetViaMethodFactory(metaModelContext);
         val facetFactoryForDisable = new 
DisableForContextFacetViaMethodFactory(metaModelContext);
 
diff --git 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/CollectionFieldMethodsFacetFactoryTest.java
 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/CollectionFieldMethodsFacetFactoryTest.java
index 8cef5dd85f..332aa6ede1 100644
--- 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/CollectionFieldMethodsFacetFactoryTest.java
+++ 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/CollectionFieldMethodsFacetFactoryTest.java
@@ -23,33 +23,21 @@ import java.util.Collection;
 import java.util.List;
 import java.util.Set;
 
-import org.junit.Rule;
-
-import org.apache.isis.core.internaltestsupport.jmocking.JUnitRuleMockery2;
-import 
org.apache.isis.core.internaltestsupport.jmocking.JUnitRuleMockery2.Mode;
 import org.apache.isis.core.metamodel.facetapi.Facet;
 import org.apache.isis.core.metamodel.facets.AbstractFacetFactoryTest;
 import org.apache.isis.core.metamodel.facets.FacetFactory.ProcessMethodContext;
 import 
org.apache.isis.core.metamodel.facets.collections.accessor.CollectionAccessorFacetViaAccessor;
 import 
org.apache.isis.core.metamodel.facets.collections.accessor.CollectionAccessorFacetViaAccessorFactory;
 import 
org.apache.isis.core.metamodel.facets.propcoll.accessor.PropertyOrCollectionAccessorFacet;
-import org.apache.isis.core.metamodel.spec.ObjectSpecification;
 
 import lombok.val;
 
-public class CollectionFieldMethodsFacetFactoryTest extends 
AbstractFacetFactoryTest {
-
-    @Rule
-    public JUnitRuleMockery2 context = 
JUnitRuleMockery2.createFor(Mode.INTERFACES_AND_CLASSES);
-
-    private ObjectSpecification mockSpecification;
+public class CollectionFieldMethodsFacetFactoryTest
+extends AbstractFacetFactoryTest {
 
     @Override
     public void setUp() throws Exception {
         super.setUp();
-
-        // expecting
-        
allowing_specificationLoader_loadSpecification_any_willReturn(mockSpecification);
     }
 
     public void 
testPropertyAccessorFacetIsInstalledForJavaUtilCollectionAndMethodRemoved() {
diff --git 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/collection/CollectionAnnotationFacetFactoryTest_typeOf.java
 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/collection/CollectionAnnotationFacetFactoryTest_typeOf.java
index e7417f94b4..3eff6c4ad8 100644
--- 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/collection/CollectionAnnotationFacetFactoryTest_typeOf.java
+++ 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/collections/collection/CollectionAnnotationFacetFactoryTest_typeOf.java
@@ -21,16 +21,12 @@ package 
org.apache.isis.core.metamodel.facets.collections.collection;
 import java.lang.reflect.Method;
 import java.util.Collection;
 
-import org.jmock.Expectations;
-import org.jmock.auto.Mock;
-
 import org.apache.isis.core.metamodel.facetapi.Facet;
 import org.apache.isis.core.metamodel.facets.AbstractFacetFactoryTest;
 import org.apache.isis.core.metamodel.facets.FacetFactory.ProcessMethodContext;
 import org.apache.isis.core.metamodel.facets.actcoll.typeof.TypeOfFacet;
 import 
org.apache.isis.core.metamodel.facets.actcoll.typeof.TypeOfFacetFromArray;
 import 
org.apache.isis.core.metamodel.facets.actcoll.typeof.TypeOfFacetFromGenerics;
-import org.apache.isis.core.metamodel.spec.ObjectSpecification;
 
 public class CollectionAnnotationFacetFactoryTest_typeOf
 extends AbstractFacetFactoryTest {
@@ -61,11 +57,6 @@ extends AbstractFacetFactoryTest {
         }
         final Method actionMethod = findMethod(Customer.class, "someAction");
 
-        context.checking(new Expectations() {{
-            
allowing(mockSpecificationLoader).loadSpecification(Customer.class);
-            will(returnValue(mockCustomerSpec));
-        }});
-
         facetFactory.process(ProcessMethodContext
                 .forTesting(Customer.class, null, actionMethod, methodRemover, 
facetedMethod));
 
@@ -87,11 +78,6 @@ extends AbstractFacetFactoryTest {
             }
         }
 
-        context.checking(new Expectations() {{
-            
allowing(mockSpecificationLoader).loadSpecification(Customer.class);
-            will(returnValue(mockCustomerSpec));
-        }});
-
         final Method collectionAccessorMethod = findMethod(Customer.class, 
"getOrders");
 
         facetFactory.process(ProcessMethodContext
@@ -105,9 +91,6 @@ extends AbstractFacetFactoryTest {
 
     }
 
-    @Mock
-    ObjectSpecification mockCustomerSpec;
-
     public void testTypeOfFacetIsInferredForCollectionFromOrderArray() {
         class Order {
         }
@@ -119,11 +102,6 @@ extends AbstractFacetFactoryTest {
         }
         final Method collectionAccessorMethod = findMethod(Customer.class, 
"getOrders");
 
-        context.checking(new Expectations() {{
-            
allowing(mockSpecificationLoader).loadSpecification(Customer.class);
-            will(returnValue(mockCustomerSpec));
-        }});
-
         facetFactory.process(ProcessMethodContext
                 .forTesting(Customer.class, null, collectionAccessorMethod, 
methodRemover, facetedMethod));
 
diff --git 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/properties/PropertyMethodsFacetFactoryTest.java
 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/properties/PropertyMethodsFacetFactoryTest.java
index 51f8eece8e..e74edba3b2 100644
--- 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/properties/PropertyMethodsFacetFactoryTest.java
+++ 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/facets/properties/PropertyMethodsFacetFactoryTest.java
@@ -20,8 +20,6 @@ package org.apache.isis.core.metamodel.facets.properties;
 
 import java.lang.reflect.Method;
 
-import org.jmock.auto.Mock;
-
 import org.apache.isis.core.metamodel.facetapi.Facet;
 import org.apache.isis.core.metamodel.facetapi.FeatureType;
 import org.apache.isis.core.metamodel.facets.AbstractFacetFactoryTest;
@@ -55,20 +53,15 @@ import 
org.apache.isis.core.metamodel.facets.properties.update.modify.PropertySe
 import 
org.apache.isis.core.metamodel.facets.properties.validating.PropertyValidateFacet;
 import 
org.apache.isis.core.metamodel.facets.properties.validating.method.PropertyValidateFacetViaMethod;
 import 
org.apache.isis.core.metamodel.facets.properties.validating.method.PropertyValidateFacetViaMethodFactory;
-import org.apache.isis.core.metamodel.spec.ObjectSpecification;
 
 import lombok.val;
 
-public class PropertyMethodsFacetFactoryTest extends AbstractFacetFactoryTest {
-
-    @Mock private ObjectSpecification mockSpecification;
+public class PropertyMethodsFacetFactoryTest
+extends AbstractFacetFactoryTest {
 
     @Override
     public void setUp() throws Exception {
         super.setUp();
-
-        // expecting
-        
allowing_specificationLoader_loadSpecification_any_willReturn(mockSpecification);
     }
 
     public void testPropertyAccessorFacetIsInstalledAndMethodRemoved() {
diff --git 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/testspec/ObjectSpecificationStub.java
 
b/core/metamodel/src/test/java/org/apache/isis/core/metamodel/testspec/ObjectSpecificationStub.java
deleted file mode 100644
index 82b71b2d85..0000000000
--- 
a/core/metamodel/src/test/java/org/apache/isis/core/metamodel/testspec/ObjectSpecificationStub.java
+++ /dev/null
@@ -1,404 +0,0 @@
-/*
- *  Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *        http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- */
-package org.apache.isis.core.metamodel.testspec;
-
-import java.lang.reflect.Method;
-import java.util.List;
-import java.util.Optional;
-import java.util.function.Consumer;
-import java.util.stream.Stream;
-
-import org.apache.isis.applib.Identifier;
-import org.apache.isis.applib.annotation.Where;
-import org.apache.isis.applib.id.LogicalType;
-import org.apache.isis.applib.services.metamodel.BeanSort;
-import org.apache.isis.commons.collections.Can;
-import org.apache.isis.commons.collections.ImmutableEnumSet;
-import org.apache.isis.commons.internal.base._Casts;
-import org.apache.isis.commons.internal.collections._Lists;
-import org.apache.isis.core.metamodel.consent.Consent;
-import org.apache.isis.core.metamodel.consent.InteractionInitiatedBy;
-import org.apache.isis.core.metamodel.consent.InteractionResult;
-import org.apache.isis.core.metamodel.context.MetaModelContext;
-import org.apache.isis.core.metamodel.facetapi.FacetHolder;
-import org.apache.isis.core.metamodel.facetapi.FeatureType;
-import org.apache.isis.core.metamodel.facets.WhereValueFacet;
-import org.apache.isis.core.metamodel.facets.all.hide.HiddenFacet;
-import 
org.apache.isis.core.metamodel.facets.members.cssclassfa.CssClassFaFactory;
-import org.apache.isis.core.metamodel.facets.object.icon.ObjectIcon;
-import org.apache.isis.core.metamodel.facets.object.immutable.ImmutableFacet;
-import org.apache.isis.core.metamodel.facets.object.title.TitleRenderRequest;
-import org.apache.isis.core.metamodel.facets.object.value.ValueFacet;
-import org.apache.isis.core.metamodel.interactions.ObjectTitleContext;
-import org.apache.isis.core.metamodel.interactions.ObjectValidityContext;
-import org.apache.isis.core.metamodel.object.ManagedObject;
-import org.apache.isis.core.metamodel.spec.ActionScope;
-import org.apache.isis.core.metamodel.spec.ObjectSpecification;
-import org.apache.isis.core.metamodel.spec.feature.MixedIn;
-import org.apache.isis.core.metamodel.spec.feature.ObjectAction;
-import org.apache.isis.core.metamodel.spec.feature.ObjectAssociation;
-import org.apache.isis.core.metamodel.spec.feature.ObjectMember;
-import org.apache.isis.core.metamodel.spec.feature.OneToOneAssociation;
-import org.apache.isis.core.metamodel.specloader.specimpl.IntrospectionState;
-
-import lombok.Getter;
-import lombok.val;
-
-public class ObjectSpecificationStub
-implements ObjectSpecification {
-
-    private ObjectAction action;
-    public List<ObjectAssociation> fields = _Lists.newArrayList();
-    private String title;
-    /**
-     * lazily derived, see {@link #getLogicalType()}
-     */
-    private final LogicalType logicalType;
-
-    private ObjectSpecification elementSpecification;
-    private final Class<?> correspondingClass;
-    private final String name;
-
-    @Getter(onMethod_ = {@Override}) private FacetHolder facetHolder;
-
-    @Override
-    public Optional<? extends ObjectMember> getMember(final String memberId) {
-        val objectAction = getAction(memberId);
-        if(objectAction.isPresent()) {
-            return objectAction;
-        }
-        val association = getAssociation(memberId);
-        if(association.isPresent()) {
-            return association;
-        }
-        return Optional.empty();
-    }
-
-    @Override
-    public boolean isInjectable() {
-        // XXX not implemented
-        return false;
-    }
-
-    @Override
-    public Class<?> getCorrespondingClass() {
-        return correspondingClass;
-    }
-
-    public ObjectSpecificationStub(final MetaModelContext mmc, final Class<?> 
correspondingClass) {
-        this.facetHolder = FacetHolder.simple(mmc, null);
-        this.correspondingClass = correspondingClass;
-        this.logicalType = LogicalType.infer(correspondingClass);
-        this.title = "";
-        this.name = correspondingClass.getCanonicalName();
-    }
-
-    @Override
-    public FeatureType getFeatureType() {
-        return FeatureType.OBJECT;
-    }
-
-    @Override
-    protected Object clone() throws CloneNotSupportedException {
-        return super.clone();
-    }
-
-    @Override
-    public boolean isAbstract() {
-        return false;
-    }
-
-    @Override
-    public Optional<ObjectAssociation> getDeclaredAssociation(final String 
name, final MixedIn mixedIn) {
-        for (int i = 0; i < fields.size(); i++) {
-            if (fields.get(i).getId().equals(name)) {
-                return Optional.ofNullable(fields.get(i));
-            }
-        }
-        return Optional.empty();
-    }
-
-    @Override
-    public Stream<ObjectAssociation> streamDeclaredAssociations(final MixedIn 
mixedIn) {
-        return fields.stream();
-    }
-
-    @Override
-    public String getFullIdentifier() {
-        return name;
-    }
-
-    @Override
-    public LogicalType getLogicalType() {
-        return logicalType;
-    }
-
-    @Override
-    public Can<LogicalType> getAliases() {
-        return Can.empty();
-    }
-
-    @Override
-    public String getIconName(final ManagedObject reference) {
-        return null;
-    }
-
-    @Override
-    public ObjectIcon getIcon(final ManagedObject object) {
-        return null;
-    }
-
-    @Override
-    public Object getNavigableParent(final Object object) {
-        return null;
-    }
-
-    @Override
-    public String getCssClass(final ManagedObject reference) {
-        return null;
-    }
-
-    private Optional<ObjectAction> lookupObjectAction(final String name) {
-        if (action != null && action.getId().equals(name)) {
-            return Optional.of(action);
-        }
-        return Optional.empty();
-    }
-
-    @Override
-    public Optional<ObjectAction> getDeclaredAction(
-            final String id, final ImmutableEnumSet<ActionScope> scopes, final 
MixedIn mixedIn) {
-        val nameParmsIdentityString = id.substring(0, id.indexOf('('));
-        val action = lookupObjectAction(nameParmsIdentityString);
-
-        if(scopes==null) {
-            return action;
-        }
-
-        if (action.isPresent()
-                && scopes.contains(action.get().getScope())) {
-            return action;
-        }
-        return Optional.empty();
-
-    }
-
-    @Override
-    public String getPluralName() {
-        return null;
-    }
-
-    @Override
-    public String getShortIdentifier() {
-        return name.substring(name.lastIndexOf('.') + 1);
-    }
-
-    @Override
-    public String getSingularName() {
-        return name + " (singular)";
-    }
-
-    @Override
-    public String getDescription() {
-        return getSingularName();
-    }
-
-    @Override
-    public String getHelp() {
-        return null;
-    }
-
-    @Override
-    public String getTitle(final TitleRenderRequest titleRenderRequest) {
-        return title;
-    }
-
-    @Override
-    public boolean hasSubclasses() {
-        return false;
-    }
-
-    @Override
-    public Can<ObjectSpecification> interfaces() {
-        return Can.empty();
-    }
-
-    @Override
-    public boolean isOfType(final ObjectSpecification cls) {
-        return cls == this;
-    }
-
-    @Override
-    public boolean isParented() {
-        return false;
-    }
-
-    @Override
-    public Can<ObjectSpecification> subclasses(final Depth depth) {
-        return Can.empty();
-    }
-
-    @Override
-    public ObjectSpecification superclass() {
-        return null;
-    }
-
-    @Override
-    public Consent isValid(final ManagedObject targetAdapter, final 
InteractionInitiatedBy interactionInitiatedBy) {
-        return null;
-    }
-
-    @Override
-    public Identifier getFeatureIdentifier() {
-        return 
Identifier.classIdentifier(LogicalType.fqcn(correspondingClass));
-    }
-
-    @Override
-    public boolean isHidden() {
-        return false;
-    }
-
-    @Override
-    public boolean isImmutable() {
-        return containsFacet(ImmutableFacet.class);
-    }
-
-    @Override
-    public ObjectValidityContext createValidityInteractionContext(
-            final ManagedObject targetAdapter, final InteractionInitiatedBy 
interactionInitiatedBy) {
-        return null;
-    }
-
-    @Override
-    public ObjectTitleContext createTitleInteractionContext(
-            final ManagedObject targetObjectAdapter, final 
InteractionInitiatedBy invocationMethod) {
-        return null;
-    }
-
-    @Override
-    public InteractionResult isValidResult(final ManagedObject targetAdapter, 
final InteractionInitiatedBy interactionInitiatedBy) {
-        return null;
-    }
-
-
-    // /////////////////////////////////////////////////////////////
-    // introspection
-    // /////////////////////////////////////////////////////////////
-
-    @Override
-    public Stream<ObjectAction> streamDeclaredActions(final MixedIn 
contributed) {
-        return null;
-    }
-
-    @Override
-    public Stream<ObjectAction> streamDeclaredActions(final 
ImmutableEnumSet<ActionScope> types, final MixedIn contributed) {
-        return null;
-    }
-
-    // /////////////////////////////////////////////////////////
-    // view models and wizards
-    // /////////////////////////////////////////////////////////
-
-    @Override
-    public String toString() {
-        return getFullIdentifier();
-    }
-
-    @Override
-    public Optional<ObjectSpecification> getElementSpecification() {
-        return Optional.ofNullable(elementSpecification);
-    }
-
-    @Override
-    public BeanSort getBeanSort() {
-        return BeanSort.UNKNOWN; // [2158] not implemented yet
-    }
-
-    @Override
-    public void introspectUpTo(final IntrospectionState upTo) {
-        // [2158] not implemented yet
-    }
-
-    @Override
-    public Optional<? extends ObjectMember> getMember(final Method method) {
-        return Optional.empty();
-    }
-
-    @Override
-    public Optional<ObjectAction> getAction(
-            final String id, final ImmutableEnumSet<ActionScope> scopes, final 
MixedIn mixedIn) {
-        // poorly implemented, inheritance not supported
-        return getDeclaredAction(id, scopes, mixedIn);
-    }
-
-    @Override
-    public Stream<ObjectAction> streamActions(
-            final ImmutableEnumSet<ActionScope> types,
-            final MixedIn contributed,
-            final Consumer<ObjectAction> onActionOverloaded) {
-        // poorly implemented, inheritance not supported
-        return streamDeclaredActions(contributed);
-    }
-
-    @Override
-    public Optional<ObjectAssociation> getAssociation(final String id, final 
MixedIn mixedIn) {
-        // poorly implemented, inheritance not supported
-        return getDeclaredAssociation(id, mixedIn);
-    }
-
-    @Override
-    public Stream<ObjectAssociation> streamAssociations(final MixedIn 
contributed) {
-        // poorly implemented, inheritance not supported
-        return streamDeclaredAssociations(contributed);
-    }
-
-    @Override
-    public Stream<ObjectAction> streamRuntimeActions(final MixedIn mixedIn) {
-        val actionScopes = 
ActionScope.forEnvironment(getMetaModelContext().getSystemEnvironment());
-        return streamActions(actionScopes, mixedIn);
-    }
-
-    @Override
-    public Optional<CssClassFaFactory> getCssClassFaFactory() {
-        return Optional.empty();
-    }
-
-    @Override
-    public Stream<OneToOneAssociation> streamPropertiesForColumnRendering(
-            final Identifier memberIdentifier,
-            final ManagedObject parentObject) {
-
-        val whereContext = memberIdentifier.getType().isAction()
-                ? Where.STANDALONE_TABLES
-                : Where.PARENTED_TABLES;
-
-        return streamProperties(MixedIn.INCLUDED)
-                .filter(property->property.streamFacets()
-                        .filter(facet -> facet instanceof HiddenFacet)
-                        .map(WhereValueFacet.class::cast)
-                        .map(WhereValueFacet::where)
-                        .noneMatch(where -> where.includes(whereContext)));
-    }
-
-    @Override
-    public Optional<ValueFacet> valueFacet() {
-        return _Casts.uncheckedCast(lookupFacet(ValueFacet.class));
-    }
-
-}
diff --git 
a/regressiontests/stable-interact/src/test/java/org/apache/isis/testdomain/interact/NewParameterModelTest.java
 
b/regressiontests/stable-interact/src/test/java/org/apache/isis/testdomain/interact/NewParameterModelTest.java
index b78c22368f..a0790f446a 100644
--- 
a/regressiontests/stable-interact/src/test/java/org/apache/isis/testdomain/interact/NewParameterModelTest.java
+++ 
b/regressiontests/stable-interact/src/test/java/org/apache/isis/testdomain/interact/NewParameterModelTest.java
@@ -137,6 +137,7 @@ class NewParameterModelTest extends InteractionTestAbstract 
{
         pendingArgs.setParamValues(params);
 
         val resultOrVeto = actionInteraction.invokeWith(pendingArgs);
+
         assertTrue(resultOrVeto.isSuccess());
 
         assertEquals(5, (int)resultOrVeto.getSuccessElseFail().getPojo());
diff --git 
a/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest.java
 
b/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest.java
new file mode 100644
index 0000000000..b5b9cf3a8d
--- /dev/null
+++ 
b/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest.java
@@ -0,0 +1,232 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *        http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ */
+package org.apache.isis.viewer.restfulobjects.rendering.domainobjects;
+
+import java.math.BigDecimal;
+import java.math.BigInteger;
+
+import com.fasterxml.jackson.databind.node.BigIntegerNode;
+import com.fasterxml.jackson.databind.node.BooleanNode;
+import com.fasterxml.jackson.databind.node.DecimalNode;
+import com.fasterxml.jackson.databind.node.DoubleNode;
+import com.fasterxml.jackson.databind.node.IntNode;
+import com.fasterxml.jackson.databind.node.LongNode;
+import com.fasterxml.jackson.databind.node.TextNode;
+
+import org.hamcrest.Matchers;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+import org.junit.jupiter.params.ParameterizedTest;
+import org.junit.jupiter.params.provider.ValueSource;
+
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.is;
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.assertSame;
+import static org.junit.jupiter.api.Assertions.assertThrows;
+
+import org.apache.isis.viewer.restfulobjects.applib.JsonRepresentation;
+
+import lombok.val;
+
+class JsonValueEncoderTest
+extends JsonValueEncoderTestAbstract {
+
+    @BeforeEach
+    void setup() {
+        super.setUp();
+    }
+
+    @Test
+    void whenManagedObjectIsNull() {
+        assertThrows(RuntimeException.class, ()->{
+            jsonValueEncoder.asObject(null, null);
+        });
+    }
+
+    @Test
+    void whenSpecIsNull() throws Exception {
+        val representation = new 
JsonRepresentation(TextNode.valueOf("aString"));
+        assertThrows(IllegalArgumentException.class, ()->{
+            jsonValueEncoder.asAdapter(null, representation, null);
+        });
+    }
+
+    @Test
+    void whenReprIsNull() throws Exception {
+        val spec = specFor(Object.class);
+        assertThat(jsonValueEncoder.asAdapter(spec, null, null), 
is(Matchers.nullValue()));
+    }
+
+    @Test
+    void whenReprIsAnArray() throws Exception {
+        val spec = specFor(Integer.class); // arbitrary value class, pick any
+        assertThrows(IllegalArgumentException.class, ()->{
+            jsonValueEncoder.asAdapter(spec, JsonRepresentation.newArray(), 
null);
+        });
+    }
+
+    @Test
+    void whenReprIsAMap() throws Exception {
+        val spec = specFor(Integer.class); // arbitrary value class, pick any
+        assertThrows(IllegalArgumentException.class, ()->{
+            assertNull(jsonValueEncoder.asAdapter(spec, 
JsonRepresentation.newMap(), null));
+        });
+    }
+
+    @Test
+    void whenSpecDoesNotHaveAnEncodableFacet() throws Exception {
+        val representation = new 
JsonRepresentation(TextNode.valueOf("aString"));
+        val spec = specFor(Object.class); // arbitrary non-value class, pick 
any
+        assertThrows(IllegalArgumentException.class, ()->{
+            assertNull(jsonValueEncoder.asAdapter(spec, representation, null));
+        });
+    }
+
+    @ParameterizedTest
+    @ValueSource(classes = {
+            boolean.class, Boolean.class,
+            long.class, Long.class,
+            int.class, Integer.class,
+            short.class, Short.class,
+            byte.class, Byte.class,
+            char.class, Character.class,
+            double.class, Double.class,
+            float.class, Float.class,
+            BigInteger.class, BigDecimal.class,})
+    void whenObjectSpecIsIncompatibleWithRepr(final Class<?> 
correspondingClass) {
+        // given
+        val spec = specFor(correspondingClass);
+
+        // when repr is 'string'
+        assertThrows(IllegalArgumentException.class, ()->{
+            val representation = new 
JsonRepresentation(TextNode.valueOf("aString"));
+            jsonValueEncoder.asAdapter(spec, representation, null);
+        });
+
+        // when repr is 'map'
+        assertThrows(IllegalArgumentException.class, ()->{
+            val representation = JsonRepresentation.newMap("foo", "bar");
+            jsonValueEncoder.asAdapter(spec, representation, null);
+        });
+    }
+
+    @ParameterizedTest
+    @ValueSource(classes = {boolean.class, Boolean.class})
+    void whenReprIsBoolean(final Class<?> correspondingClass) {
+        // given
+        final boolean value = true;
+        val representation = new 
JsonRepresentation(BooleanNode.valueOf(value));
+        val spec = specFor(boolean.class);
+
+        // when
+        val adapter = jsonValueEncoder.asAdapter(spec, representation, null);
+
+        // then
+        assertSame(spec, adapter.getSpecification());
+    }
+
+    @ParameterizedTest
+    @ValueSource(classes = {int.class, Integer.class})
+    void whenReprIsInteger(final Class<?> correspondingClass) {
+        // given
+        val spec = specFor(correspondingClass);
+        final int value = 123;
+        val representation = new JsonRepresentation(IntNode.valueOf(value));
+
+        // when
+        val adapter = jsonValueEncoder.asAdapter(spec, representation, null);
+
+        // then
+        assertSame(spec, adapter.getSpecification());
+    }
+
+    @ParameterizedTest
+    @ValueSource(classes = {long.class, Long.class})
+    void whenReprIsLong(final Class<?> correspondingClass) {
+        // given
+        val spec = specFor(correspondingClass);
+        final long value = 1234567890L;
+        val representation = new JsonRepresentation(LongNode.valueOf(value));
+
+        // when
+        val adapter = jsonValueEncoder.asAdapter(spec, representation, null);
+
+        // then
+        assertSame(spec, adapter.getSpecification());
+    }
+
+    @ParameterizedTest
+    @ValueSource(classes = {double.class, Double.class})
+    void whenReprIsDouble(final Class<?> correspondingClass) {
+        // given
+        val spec = specFor(correspondingClass);
+        final double value = 123.45;
+        val representation = new JsonRepresentation(DoubleNode.valueOf(value));
+
+        // when
+        val adapter = jsonValueEncoder.asAdapter(spec, representation, null);
+
+        // then
+        assertSame(spec, adapter.getSpecification());
+    }
+
+    @Test
+    void whenReprIsBigInteger() throws Exception {
+        // given
+        val spec = specFor(BigInteger.class);
+        final BigInteger value = BigInteger.valueOf(123);
+        val representation = new 
JsonRepresentation(BigIntegerNode.valueOf(value));
+
+        // when
+        val adapter = jsonValueEncoder.asAdapter(spec, representation, null);
+
+        // then
+        assertSame(spec, adapter.getSpecification());
+    }
+
+    @Test
+    void whenReprIsBigDecimal() throws Exception {
+        // given
+        val spec = specFor(BigDecimal.class);
+        final BigDecimal value = new BigDecimal("123234234.45612312343535");
+        val representation = new 
JsonRepresentation(DecimalNode.valueOf(value));
+
+        // when
+        val adapter = jsonValueEncoder.asAdapter(spec, representation, null);
+
+        // then
+        assertSame(spec, adapter.getSpecification());
+    }
+
+
+    @Test
+    void whenReprIsString() throws Exception {
+        // given
+        val spec = specFor(String.class);
+        val representation = new 
JsonRepresentation(TextNode.valueOf("aString"));
+
+        // when
+        val adapter = jsonValueEncoder.asAdapter(spec, representation, null);
+
+        // then
+        assertSame(spec, adapter.getSpecification());
+    }
+
+}
diff --git 
a/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTestAbstract.java
 
b/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTestAbstract.java
new file mode 100644
index 0000000000..55c36078f8
--- /dev/null
+++ 
b/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTestAbstract.java
@@ -0,0 +1,63 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *        http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ */
+package org.apache.isis.viewer.restfulobjects.rendering.domainobjects;
+
+import org.apache.isis.core.metamodel._testing.MetaModelContext_forTesting;
+import org.apache.isis.core.metamodel.context.MetaModelContext;
+import org.apache.isis.core.metamodel.spec.ObjectSpecification;
+import org.apache.isis.core.metamodel.valuesemantics.BigDecimalValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.BigIntegerValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.BooleanValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.ByteValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.DoubleValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.FloatValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.IntValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.LongValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.ShortValueSemantics;
+import org.apache.isis.core.metamodel.valuesemantics.StringValueSemantics;
+import 
org.apache.isis.viewer.restfulobjects.rendering.service.valuerender.JsonValueEncoderServiceDefault;
+
+abstract class JsonValueEncoderTestAbstract {
+
+    protected MetaModelContext mmc;
+    protected JsonValueEncoderServiceDefault jsonValueEncoder;
+
+    protected void setUp() {
+        mmc = MetaModelContext_forTesting.builder()
+                .build()
+                .withValueSemantics(new StringValueSemantics())
+                .withValueSemantics(new BooleanValueSemantics())
+                .withValueSemantics(new BigDecimalValueSemantics())
+                .withValueSemantics(new BigIntegerValueSemantics())
+                .withValueSemantics(new LongValueSemantics())
+                .withValueSemantics(new IntValueSemantics())
+                .withValueSemantics(new ShortValueSemantics())
+                .withValueSemantics(new ByteValueSemantics())
+                .withValueSemantics(new DoubleValueSemantics())
+                .withValueSemantics(new FloatValueSemantics())
+                ;
+
+        jsonValueEncoder = 
JsonValueEncoderServiceDefault.forTesting(mmc.getSpecificationLoader());
+    }
+
+    protected ObjectSpecification specFor(final Class<?> cls) {
+        return mmc.getSpecificationLoader().specForTypeElseFail(cls);
+    }
+
+}
diff --git 
a/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest_asAdapter.java
 
b/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest_asAdapter.java
deleted file mode 100644
index 6606a23eab..0000000000
--- 
a/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest_asAdapter.java
+++ /dev/null
@@ -1,447 +0,0 @@
-/*
- *  Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *        http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- */
-package org.apache.isis.viewer.restfulobjects.rendering.domainobjects;
-
-import java.math.BigDecimal;
-import java.math.BigInteger;
-import java.util.Optional;
-
-import com.fasterxml.jackson.databind.node.BigIntegerNode;
-import com.fasterxml.jackson.databind.node.BooleanNode;
-import com.fasterxml.jackson.databind.node.DecimalNode;
-import com.fasterxml.jackson.databind.node.DoubleNode;
-import com.fasterxml.jackson.databind.node.IntNode;
-import com.fasterxml.jackson.databind.node.LongNode;
-import com.fasterxml.jackson.databind.node.TextNode;
-
-import org.hamcrest.Matchers;
-import org.jmock.Expectations;
-import org.jmock.auto.Mock;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.hamcrest.Matchers.is;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertSame;
-
-import org.apache.isis.applib.exceptions.recoverable.TextEntryParseException;
-import org.apache.isis.applib.id.LogicalType;
-import org.apache.isis.core.internaltestsupport.jmocking.JUnitRuleMockery2;
-import org.apache.isis.core.metamodel.facetapi.Facet;
-import org.apache.isis.core.metamodel.facets.object.value.ValueFacet;
-import 
org.apache.isis.core.metamodel.facets.object.value.ValueSerializer.Format;
-import org.apache.isis.core.metamodel.object.ManagedObject;
-import org.apache.isis.core.metamodel.spec.ObjectSpecification;
-import org.apache.isis.core.metamodel.specloader.SpecificationLoader;
-import org.apache.isis.viewer.restfulobjects.applib.JsonRepresentation;
-import 
org.apache.isis.viewer.restfulobjects.rendering.service.valuerender.JsonValueEncoderService;
-import 
org.apache.isis.viewer.restfulobjects.rendering.service.valuerender.JsonValueEncoderServiceDefault;
-
-import lombok.val;
-
-public class JsonValueEncoderTest_asAdapter {
-
-    @Rule public JUnitRuleMockery2 context =
-            
JUnitRuleMockery2.createFor(JUnitRuleMockery2.Mode.INTERFACES_AND_CLASSES);
-
-    @Mock private ObjectSpecification mockObjectSpec;
-    @Mock private ValueFacet mockValueFacet;
-    @Mock private ManagedObject mockObjectAdapter;
-    @Mock private SpecificationLoader specLoader;
-
-    private JsonRepresentation representation;
-    private JsonValueEncoderService jsonValueEncoder;
-
-    @Before
-    public void setUp() throws Exception {
-
-        jsonValueEncoder = 
JsonValueEncoderServiceDefault.forTesting(specLoader);
-
-        representation = new JsonRepresentation(TextNode.valueOf("aString"));
-    }
-
-    @After
-    public void tearDown() throws Exception {
-
-    }
-
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenSpecIsNull() throws Exception {
-        jsonValueEncoder.asAdapter(null, representation, null);
-    }
-
-    @Test
-    public void whenReprIsNull() throws Exception {
-        assertThat(jsonValueEncoder.asAdapter(mockObjectSpec, null, null), 
is(Matchers.nullValue()));
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenReprIsAnArray() throws Exception {
-        allowingObjectSpecHas(ValueFacet.class, mockValueFacet);
-        jsonValueEncoder.asAdapter(mockObjectSpec, 
JsonRepresentation.newArray(), null);
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenReprIsAMap() throws Exception {
-        allowingObjectSpecHas(ValueFacet.class, mockValueFacet);
-        assertNull(jsonValueEncoder.asAdapter(mockObjectSpec, 
JsonRepresentation.newMap(), null));
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenSpecDoesNotHaveAnEncodableFacet() throws Exception {
-        allowingObjectSpecHas(ValueFacet.class, null);
-
-        assertNull(jsonValueEncoder.asAdapter(mockObjectSpec, representation, 
null));
-    }
-
-    @Test
-    public void whenReprIsBooleanPrimitive() throws Exception {
-        whenReprIsBoolean(boolean.class);
-    }
-
-    @Test
-    public void whenReprIsBooleanWrapper() throws Exception {
-        whenReprIsBoolean(Boolean.class);
-    }
-
-    private void whenReprIsBoolean(final Class<?> correspondingClass) {
-        // given
-        allowingObjectSpecHasValue(correspondingClass);
-        
allowingObjectSpecCorrespondingClassAndObjectTypeIs(correspondingClass);
-        final boolean value = true;
-        representation = new JsonRepresentation(BooleanNode.valueOf(value));
-        context.checking(new Expectations() {
-            {
-                allowing(specLoader).specForType(((Object)value).getClass());
-                will(returnValue(Optional.of(mockObjectSpec)));
-            }
-        });
-
-        // when
-        val adapter = jsonValueEncoder.asAdapter(mockObjectSpec, 
representation, null);
-
-        // then
-        assertSame(mockObjectSpec, adapter.getSpecification());
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenObjectSpecIsBooleanButReprIsNot() throws Exception {
-        // given
-        allowingObjectSpecHasValue(boolean.class);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(boolean.class);
-
-        context.checking(new Expectations() {
-            {
-                allowing(mockValueFacet).fromEncodedString(Format.JSON, 
"aString");
-                will(throwException(new TextEntryParseException("'aString' 
cannot be parsed as a boolean value")));
-            }
-        });
-
-        // when
-        jsonValueEncoder.asAdapter(mockObjectSpec, representation, null);
-    }
-
-    @Test
-    public void whenReprIsIntegerPrimitive() throws Exception {
-        whenReprIsInteger(int.class);
-    }
-
-    @Test
-    public void whenReprIsIntegerWrapper() throws Exception {
-        whenReprIsInteger(Integer.class);
-    }
-
-    private void whenReprIsInteger(final Class<?> correspondingClass) {
-        // given
-        allowingObjectSpecHasValue(correspondingClass);
-        
allowingObjectSpecCorrespondingClassAndObjectTypeIs(correspondingClass);
-        final int value = 123;
-        representation = new JsonRepresentation(IntNode.valueOf(value));
-        context.checking(new Expectations() {
-            {
-                allowing(specLoader).specForType(((Object)value).getClass());
-                will(returnValue(Optional.of(mockObjectSpec)));
-            }
-        });
-
-        // when
-        val adapter = jsonValueEncoder.asAdapter(mockObjectSpec, 
representation, null);
-
-        // then
-        assertSame(mockObjectSpec, adapter.getSpecification());
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenObjectSpecIsIntegerButReprIsNot() throws Exception {
-        // given
-        allowingObjectSpecHas(ValueFacet.class, mockValueFacet);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(int.class);
-
-        representation = JsonRepresentation.newMap("foo", "bar");
-
-        // when
-        jsonValueEncoder.asAdapter(mockObjectSpec, representation, null);
-    }
-
-    @Test
-    public void whenReprIsLongPrimitive() throws Exception {
-        whenReprIsLong(long.class);
-    }
-
-    @Test
-    public void whenReprIsLongWrapper() throws Exception {
-        whenReprIsLong(Long.class);
-    }
-
-    private void whenReprIsLong(final Class<?> correspondingClass) {
-        // given
-        allowingObjectSpecHasValue(correspondingClass);
-        
allowingObjectSpecCorrespondingClassAndObjectTypeIs(correspondingClass);
-        final long value = 1234567890L;
-        representation = new JsonRepresentation(LongNode.valueOf(value));
-        context.checking(new Expectations() {
-            {
-                allowing(specLoader).specForType(((Object)value).getClass());
-                will(returnValue(Optional.of(mockObjectSpec)));
-            }
-        });
-
-        // when
-        val adapter = jsonValueEncoder.asAdapter(mockObjectSpec, 
representation, null);
-
-        // then
-        assertSame(mockObjectSpec, adapter.getSpecification());
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenObjectSpecIsLongButReprIsNot() throws Exception {
-        // given
-        allowingObjectSpecHasValue(long.class);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(long.class);
-
-        context.checking(new Expectations() {
-            {
-                allowing(mockValueFacet).fromEncodedString(Format.JSON, 
"aString");
-                will(throwException(new TextEntryParseException("'aString' 
cannot be parsed as a long value")));
-            }
-        });
-
-        // when
-        jsonValueEncoder.asAdapter(mockObjectSpec, representation, null);
-    }
-
-    @Test
-    public void whenReprIsDoublePrimitive() throws Exception {
-        whenReprIsDouble(double.class);
-    }
-
-    @Test
-    public void whenReprIsDoubleWrapper() throws Exception {
-        whenReprIsDouble(Double.class);
-    }
-
-    private void whenReprIsDouble(final Class<?> correspondingClass) {
-        // given
-        allowingObjectSpecHasValue(correspondingClass);
-        
allowingObjectSpecCorrespondingClassAndObjectTypeIs(correspondingClass);
-        final double value = 123.45;
-        representation = new JsonRepresentation(DoubleNode.valueOf(value));
-        context.checking(new Expectations() {
-            {
-                allowing(specLoader).specForType(((Object)value).getClass());
-                will(returnValue(Optional.of(mockObjectSpec)));
-            }
-        });
-
-        // when
-        val adapter = jsonValueEncoder.asAdapter(mockObjectSpec, 
representation, null);
-
-        // then
-        assertSame(mockObjectSpec, adapter.getSpecification());
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenObjectSpecIsDoubleButReprIsNot() throws Exception {
-        // given
-        allowingObjectSpecHas(ValueFacet.class, mockValueFacet);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(double.class);
-
-        representation = JsonRepresentation.newMap("foo", "bar");
-
-        // when
-        jsonValueEncoder.asAdapter(mockObjectSpec, representation, null);
-    }
-
-    @Test
-    public void whenReprIsBigInteger() throws Exception {
-        // given
-        allowingObjectSpecHasValue(BigInteger.class);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(BigInteger.class);
-        final BigInteger value = BigInteger.valueOf(123);
-        representation = new JsonRepresentation(BigIntegerNode.valueOf(value));
-        context.checking(new Expectations() {
-            {
-                allowing(specLoader).specForType(value.getClass());
-                will(returnValue(Optional.of(mockObjectSpec)));
-            }
-        });
-
-        // when
-        val adapter = jsonValueEncoder.asAdapter(mockObjectSpec, 
representation, null);
-
-        // then
-        assertSame(mockObjectSpec, adapter.getSpecification());
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenObjectSpecIsBigIntegerButReprIsNot() throws Exception {
-        // given
-        allowingObjectSpecHas(ValueFacet.class, mockValueFacet);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(BigInteger.class);
-
-        representation = JsonRepresentation.newMap("foo", "bar");
-
-        // when
-        jsonValueEncoder.asAdapter(mockObjectSpec, representation, null);
-    }
-
-    @Test
-    public void whenReprIsBigDecimal() throws Exception {
-        // given
-        allowingObjectSpecHasValue(BigDecimal.class);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(BigDecimal.class);
-        final BigDecimal value = new BigDecimal("123234234.45612312343535");
-        representation = new JsonRepresentation(DecimalNode.valueOf(value));
-        context.checking(new Expectations() {
-            {
-                allowing(specLoader).specForType(value.getClass());
-                will(returnValue(Optional.of(mockObjectSpec)));
-
-            }
-        });
-
-        // when
-        val adapter = jsonValueEncoder.asAdapter(mockObjectSpec, 
representation, null);
-
-        // then
-        assertSame(mockObjectSpec, adapter.getSpecification());
-    }
-
-    @Test(expected = IllegalArgumentException.class)
-    public void whenObjectSpecIsBigDecimalButReprIsNot() throws Exception {
-        // given
-        allowingObjectSpecHas(ValueFacet.class, mockValueFacet);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(BigDecimal.class);
-
-        representation = JsonRepresentation.newMap("foo", "bar");
-
-        // when
-        jsonValueEncoder.asAdapter(mockObjectSpec, representation, null);
-    }
-
-    @Test
-    public void whenReprIsString() throws Exception {
-        // given
-        allowingObjectSpecHasValue(String.class);
-        allowingObjectSpecCorrespondingClassAndObjectTypeIs(String.class);
-        representation = new JsonRepresentation(TextNode.valueOf("aString"));
-
-        context.checking(new Expectations() {
-            {
-                allowing(specLoader).specForType(String.class);
-                will(returnValue(Optional.of(mockObjectSpec)));
-            }
-        });
-
-        // when
-        val adapter = jsonValueEncoder.asAdapter(mockObjectSpec, 
representation, null);
-
-        // then
-        assertSame(mockObjectSpec, adapter.getSpecification());
-    }
-
-
-
-    private void allowingObjectSpecHasValue(final Class<?> valueClass) {
-        context.checking(new Expectations() {
-            {
-
-                allowing(mockObjectSpec).isValue();
-                will(returnValue(true));
-
-                allowing(mockObjectSpec).isAbstract();
-                will(returnValue(false));
-
-                allowing(mockObjectSpec).valueFacet();
-                will(returnValue(Optional.of(mockValueFacet)));
-
-                allowing(mockObjectSpec).getFacet(ValueFacet.class);
-                will(returnValue(mockValueFacet));
-
-                allowing(mockObjectSpec).lookupFacet(ValueFacet.class);
-                will(returnValue(Optional.of(mockValueFacet)));
-
-                allowing(mockValueFacet).getValueClass();
-                will(returnValue(valueClass));
-
-                allowing(mockObjectSpec).isNonScalar();
-                will(returnValue(true));
-
-            }
-        });
-    }
-
-    private <T extends Facet> void allowingObjectSpecHas(final Class<T> 
facetClass, final T facet) {
-        context.checking(new Expectations() {
-            {
-
-                allowing(mockObjectSpec).valueFacet();
-                will(returnValue(Optional.ofNullable(facet)));
-
-                allowing(mockObjectSpec).getFacet(facetClass);
-                will(returnValue(facet));
-
-                allowing(mockObjectSpec).lookupFacet(facetClass);
-                will(returnValue(Optional.ofNullable(facet)));
-
-                allowing(mockObjectSpec).getCorrespondingClass();
-                will(returnValue(mockObjectSpec.getClass())); // used only for 
illegal argument exception message
-
-            }
-        });
-    }
-
-    private void allowingObjectSpecCorrespondingClassAndObjectTypeIs(final 
Class<?> result) {
-        context.checking(new Expectations() {
-            {
-                allowing(mockObjectSpec).getCorrespondingClass();
-                will(returnValue(result));
-
-                allowing(mockObjectSpec).getLogicalType();
-                will(returnValue(LogicalType.fqcn(result)));
-
-            }
-        });
-    }
-
-}
diff --git 
a/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest_asObject.java
 
b/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest_asObject.java
deleted file mode 100644
index 3f7b6b5434..0000000000
--- 
a/viewers/restfulobjects/rendering/src/test/java/org/apache/isis/viewer/restfulobjects/rendering/domainobjects/JsonValueEncoderTest_asObject.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- *  Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *        http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- */
-package org.apache.isis.viewer.restfulobjects.rendering.domainobjects;
-
-import org.jmock.Expectations;
-import org.jmock.auto.Mock;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-
-import org.apache.isis.core.internaltestsupport.jmocking.JUnitRuleMockery2;
-import org.apache.isis.core.metamodel.object.ManagedObject;
-import org.apache.isis.core.metamodel.spec.ObjectSpecification;
-import org.apache.isis.core.metamodel.specloader.SpecificationLoader;
-import 
org.apache.isis.viewer.restfulobjects.rendering.service.valuerender.JsonValueEncoderService;
-import 
org.apache.isis.viewer.restfulobjects.rendering.service.valuerender.JsonValueEncoderServiceDefault;
-
-public class JsonValueEncoderTest_asObject {
-
-    @Rule public JUnitRuleMockery2 context =
-            
JUnitRuleMockery2.createFor(JUnitRuleMockery2.Mode.INTERFACES_AND_CLASSES);
-
-    @Mock private ObjectSpecification mockObjectSpec;
-    @Mock private ManagedObject mockObjectAdapter;
-    @Mock private SpecificationLoader specLoader;
-
-    private JsonValueEncoderService jsonValueEncoder;
-
-    @Before
-    public void setUp() throws Exception {
-
-        context.checking(new Expectations() {
-            {
-                allowing(mockObjectAdapter).getSpecification();
-                will(returnValue(mockObjectSpec));
-            }
-        });
-
-        jsonValueEncoder = 
JsonValueEncoderServiceDefault.forTesting(specLoader);
-
-    }
-
-    @Test(expected = Exception.class)
-    public void whenAdapterIsNull() throws Exception {
-        jsonValueEncoder.asObject(null, null);
-    }
-
-}

Reply via email to