Merge pull request #236 from apache/bugfix/235-Misleading-error-message-when-JCas-type-is-not-registered

Issue #235: Misleading error message when JCas type is not registered
diff --git a/uimaj-core/src/main/java/org/apache/uima/cas/CASRuntimeException.java b/uimaj-core/src/main/java/org/apache/uima/cas/CASRuntimeException.java
index 643ce8c..47e4282 100644
--- a/uimaj-core/src/main/java/org/apache/uima/cas/CASRuntimeException.java
+++ b/uimaj-core/src/main/java/org/apache/uima/cas/CASRuntimeException.java
@@ -121,12 +121,19 @@
    * supertypes "{3}".
    */
   public static final String JCAS_MISMATCH_SUPERTYPE = "JCAS_MISMATCH_SUPERTYPE";
+
   /**
    * JCas type "{0}" used in Java code, but was not declared in the XML type descriptor.
    */
   public static final String JCAS_TYPE_NOT_IN_CAS = "JCAS_TYPE_NOT_IN_CAS";
 
   /**
+   * JCas type "{0}" defined in CAS type system and used in Java code, but was not registered in
+   * JCasRegistry.
+   */
+  public static final String JCAS_TYPE_NOT_IN_CAS_REGISTRY = "JCAS_TYPE_NOT_IN_CAS_REGISTRY";
+
+  /**
    * CAS type system type "{0}" defines field "{1}" with range "{2}", but JCas class has range
    * "{3}".
    */
diff --git a/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java b/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java
index 1bea514..2c31e9b 100644
--- a/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java
+++ b/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java
@@ -2736,7 +2736,7 @@
               "Missing UIMA type, JCas Class name: %s, index: %d, jcasRegisteredTypes size: %d%n",
               className, typeindex, jcasRegisteredTypes.size());
       dumpTypeSystem();
-      throw new CASRuntimeException(CASRuntimeException.JCAS_TYPE_NOT_IN_CAS, className);
+      throw new CASRuntimeException(CASRuntimeException.JCAS_TYPE_NOT_IN_CAS_REGISTRY, className);
     } else {
       throw new CASRuntimeException(CASRuntimeException.JCAS_UNKNOWN_TYPE_NOT_IN_CAS);
     }
diff --git a/uimaj-core/src/main/java/org/apache/uima/pear/util/FileUtil.java b/uimaj-core/src/main/java/org/apache/uima/pear/util/FileUtil.java
index ae18a1a..50a8ff9 100644
--- a/uimaj-core/src/main/java/org/apache/uima/pear/util/FileUtil.java
+++ b/uimaj-core/src/main/java/org/apache/uima/pear/util/FileUtil.java
@@ -145,9 +145,8 @@
       boolean extAccepted = true;
       if (_dirPath != null) {
         String parentDir = file.getParent();
-        dirAccepted = parentDir != null
-                && parentDir.replace(WINDOWS_SEPARATOR_CHAR, UNIX_SEPARATOR_CHAR)
-                        .startsWith(_dirPath);
+        dirAccepted = parentDir != null && parentDir
+                .replace(WINDOWS_SEPARATOR_CHAR, UNIX_SEPARATOR_CHAR).startsWith(_dirPath);
       }
       if (_fileExt != null) {
         extAccepted = file.getPath().toLowerCase().endsWith(_fileExt);
@@ -789,9 +788,8 @@
       File file = new File(targetDir, jarEntry.getName());
 
       if (!normalizeToUnix(file.getCanonicalPath()).startsWith(prefix)) {
-        throw new IOException(
-                "Can only write within target folder [" + targetDir.getAbsolutePath()
-                        + "]. Please validate ZIP contents.");
+        throw new IOException("Can only write within target folder [" + targetDir.getAbsolutePath()
+                + "]. Please validate ZIP contents.");
       }
 
       File dir = file.getParentFile();
diff --git a/uimaj-core/src/main/resources/org/apache/uima/UIMAException_Messages.properties b/uimaj-core/src/main/resources/org/apache/uima/UIMAException_Messages.properties
index 1898db0..71df49e 100644
--- a/uimaj-core/src/main/resources/org/apache/uima/UIMAException_Messages.properties
+++ b/uimaj-core/src/main/resources/org/apache/uima/UIMAException_Messages.properties
@@ -557,6 +557,7 @@
 JCAS_MISSING_FIELD_ACCESSOR = JCas Class "{0}" is missing required field accessor, or access not permitted, for field "{1}" during {2} operation.
 JCAS_CAS_MISMATCH = CAS type system doesn''t match JCas Type definition for type "{0}".
 JCAS_TYPE_NOT_IN_CAS = JCas type "{0}" used in Java code,  but was not declared in the XML type descriptor.
+JCAS_TYPE_NOT_IN_CAS_REGISTRY = JCas type "{0}" defined in CAS type system and used in Java code, but was not registered in JCasRegistry.
 JCAS_UNKNOWN_TYPE_NOT_IN_CAS = Unknown JCas type used in Java code but was not declared or imported in the XML descriptor for this component.
 JCAS_FIELD_MISSING_IN_TYPE_SYSTEM = JCAS class "{0}" defines a UIMA field "{1}" but the UIMA type doesn''t define that field.
 JCAS_FIELD_ADJ_OFFSET_CHANGED = In JCAS class "{0}", UIMA field "{1}" was set up when this class was previously loaded and initialized, to have an adjusted offset of "{2}" but now the feature has a different adjusted offset of "{3}"; this may be due to something else other than type system commit actions loading and initializing the JCas class, or to having a different non-compatible type system for this class, trying to use a common JCas cover class, which is not supported. 
diff --git a/uimaj-core/src/test/java/org/apache/uima/jcas/test/JCasTest.java b/uimaj-core/src/test/java/org/apache/uima/jcas/test/JCasTest.java
index 78fe7de..359c51c 100644
--- a/uimaj-core/src/test/java/org/apache/uima/jcas/test/JCasTest.java
+++ b/uimaj-core/src/test/java/org/apache/uima/jcas/test/JCasTest.java
@@ -19,10 +19,13 @@
 
 package org.apache.uima.jcas.test;
 
+import static org.apache.uima.util.CasCreationUtils.createCas;
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
+import static org.assertj.core.api.InstanceOfAssertFactories.throwable;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
-import static org.junit.Assert.fail;
 
 import java.util.Arrays;
 import java.util.Iterator;
@@ -70,7 +73,6 @@
 import org.apache.uima.jcas.tcas.Annotation;
 import org.apache.uima.resource.metadata.impl.TypeSystemDescription_impl;
 import org.apache.uima.test.junit_extension.JUnitExtension;
-import org.apache.uima.util.CasCreationUtils;
 import org.assertj.core.api.Assertions;
 import org.junit.jupiter.api.AfterEach;
 import org.junit.jupiter.api.BeforeEach;
@@ -126,8 +128,9 @@
       // initializing JCas type: aa.Root, feature: testMissingImport\n")) {
       // assertTrue(false);
       // }
-    } else
+    } else {
       assertTrue(false);
+    }
   }
 
   public void checkExpectedBadCASError(Exception e1, String err) {
@@ -139,8 +142,9 @@
       if (!(e.getMessageKey().equals(err))) {
         assertTrue(false);
       }
-    } else
+    } else {
       assertTrue(false);
+    }
   }
 
   @AfterEach
@@ -998,22 +1002,22 @@
   @Test
   public void testUndefinedType() throws Exception {
     // create jcas with no type system
-    JCas localJcas = CasCreationUtils.createCas(new TypeSystemDescription_impl(), null, null)
-            .getJCas();
+    JCas localJcas = createCas(new TypeSystemDescription_impl(), null, null).getJCas();
     localJcas.setDocumentText("This is a test.");
-    try {
-      // this should throw an exception
-      localJcas.getCasType(Sentence.type);
-      fail();
-    } catch (CASRuntimeException e) {
-      assertEquals(CASRuntimeException.JCAS_TYPE_NOT_IN_CAS, e.getMessageKey());
-    }
+
+    assertThatExceptionOfType(CASRuntimeException.class) //
+            .isThrownBy(() -> localJcas.getCasType(Sentence.type)) //
+            .asInstanceOf(throwable(CASRuntimeException.class)) //
+            .extracting(CASRuntimeException::getMessageKey) //
+            .isEqualTo(CASRuntimeException.JCAS_TYPE_NOT_IN_CAS_REGISTRY);
+
     // check that this does not leave JCAS in an inconsistent state
     // (a check for bug UIMA-738)
     Iterator<Annotation> iter = localJcas.getAnnotationIndex().iterator();
-    assertTrue(iter.hasNext());
-    Annotation annot = iter.next();
-    assertEquals("This is a test.", annot.getCoveredText());
+    assertThat(iter).hasNext();
+    assertThat(iter.next()) //
+            .extracting(Annotation::getCoveredText) //
+            .isEqualTo("This is a test.");
   }
 
   /*
diff --git a/uimaj-core/src/test/java/org/apache/uima/pear/util/PearInstallationVerificationTest.java b/uimaj-core/src/test/java/org/apache/uima/pear/util/PearInstallationVerificationTest.java
index 1b331e3..3be9193 100644
--- a/uimaj-core/src/test/java/org/apache/uima/pear/util/PearInstallationVerificationTest.java
+++ b/uimaj-core/src/test/java/org/apache/uima/pear/util/PearInstallationVerificationTest.java
@@ -42,28 +42,25 @@
  */
 public class PearInstallationVerificationTest {
   @Test
-  public void testAePearVerification(@TempDir
-  File temp) throws Exception {
+  public void testAePearVerification(@TempDir File temp) throws Exception {
     assertThatPearInstalls(getFile("pearTests/analysisEngine.pear"), temp);
   }
 
   @Test
-  public void testCcPearVerification(@TempDir
-  File temp) throws Exception {
+  public void testCcPearVerification(@TempDir File temp) throws Exception {
     assertThatPearInstalls(getFile("pearTests/casConsumer.pear"), temp);
   }
 
   @Test
-  public void testTsPearVerification(@TempDir
-  File temp) throws Exception {
+  public void testTsPearVerification(@TempDir File temp) throws Exception {
     assertThatPearInstalls(getFile("pearTests/typeSystem.pear"), temp);
   }
 
   // TODO: create testcases for ci, cr, cpe pear packages
 
   @Test
-  public void thatSpecialXmlCharactersInTargetPathDoNotBreakInstallation(@TempDir
-  File temp) throws Exception {
+  public void thatSpecialXmlCharactersInTargetPathDoNotBreakInstallation(@TempDir File temp)
+          throws Exception {
     File folder = new File(temp, "!'&");
     folder.mkdirs();
     assertThatPearInstalls(getFile("pearTests/analysisEngine.pear"),