' | grep '\([^<]*\)<\/td>/\1/' | grep -v Total > /tmp/$$.values
paste /tmp/$$.headers /tmp/$$.values | tail +2 | awk -v FS='\t' '{printf("%-20s %s\n",$1,$2)}'
rm /tmp/$$.headers /tmp/$$.values
else
- echo "xpath is not installed. Jacoco coverage summary will not be produced here...";
+ echo "Jacoco coverage summary was not found.";
fi
+echo "-----------------------------"
+echo
-if which html2text > /dev/null 2>&1; then
- echo "Untested classes, per Jacoco:"
- echo "-----------------------------"
- for i in target/site/jacoco/*/index.html; do
- html2text -width 500 -nobs $i | sed '1,/^Total/d;' | grep -v Created | sed 's/ \+/ /g' | sed 's/ [[:digit:]]$//' | grep -v 0$ | cut -d' ' -f1;
- done;
- echo
-else
- echo "html2text is not installed. Untested classes from Jacoco will not be printed here...";
-fi
+echo "Untested classes, per Jacoco for module: ${project.artifactId}"
+echo "-----------------------------"
+# Parse Jacoco XML reports directly to find classes with 0% coverage
+sed 's//&\n/g;s/<\/class>/&\n/g' target/site/jacoco/jacoco.xml | grep -v 'counter type="CLASS" missed="0"' | sed 's/>.*//;s/.*\///;s/".*//'
+echo "-----------------------------"
+echo
]]>
diff --git a/qqq-backend-module-filesystem/pom.xml b/qqq-backend-module-filesystem/pom.xml
index c389a018..ec34d48e 100644
--- a/qqq-backend-module-filesystem/pom.xml
+++ b/qqq-backend-module-filesystem/pom.xml
@@ -55,11 +55,6 @@
sshd-sftp
2.14.0
-
- org.apache.sshd
- sshd-sftp
- 2.14.0
-
cloud.localstack
diff --git a/qqq-middleware-javalin/pom.xml b/qqq-middleware-javalin/pom.xml
index 3cfe058d..1099db78 100644
--- a/qqq-middleware-javalin/pom.xml
+++ b/qqq-middleware-javalin/pom.xml
@@ -122,6 +122,18 @@
src/main/java
+
+ org.apache.maven.plugins
+ maven-surefire-plugin
+ 3.5.3
+
+
+
+ ${project.basedir}/src/test/resources/static-site.jar
+
+
+
+
org.apache.maven.plugins
maven-compiler-plugin
diff --git a/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/backend/javalin/QJavalinImplementation.java b/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/backend/javalin/QJavalinImplementation.java
index 0213141b..ad6ccb23 100644
--- a/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/backend/javalin/QJavalinImplementation.java
+++ b/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/backend/javalin/QJavalinImplementation.java
@@ -1932,6 +1932,7 @@ public class QJavalinImplementation
{
String searchTerm = context.queryParam("searchTerm");
String ids = context.queryParam("ids");
+ String labels = context.queryParam("labels");
SearchPossibleValueSourceInput input = new SearchPossibleValueSourceInput();
setupSession(context, input);
@@ -1945,6 +1946,11 @@ public class QJavalinImplementation
List idList = new ArrayList<>(Arrays.asList(ids.split(",")));
input.setIdList(idList);
}
+ else if(StringUtils.hasContent(labels))
+ {
+ List labelList = new ArrayList<>(Arrays.asList(labels.split(",")));
+ input.setLabelList(labelList);
+ }
SearchPossibleValueSourceOutput output = new SearchPossibleValueSourceAction().execute(input);
diff --git a/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/middleware/javalin/routeproviders/SimpleFileSystemDirectoryRouter.java b/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/middleware/javalin/routeproviders/SimpleFileSystemDirectoryRouter.java
index c6504be1..e30c94a9 100644
--- a/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/middleware/javalin/routeproviders/SimpleFileSystemDirectoryRouter.java
+++ b/qqq-middleware-javalin/src/main/java/com/kingsrook/qqq/middleware/javalin/routeproviders/SimpleFileSystemDirectoryRouter.java
@@ -49,16 +49,14 @@ import static com.kingsrook.qqq.backend.core.logging.LogUtils.logPair;
public class SimpleFileSystemDirectoryRouter implements QJavalinRouteProviderInterface
{
private static final QLogger LOG = QLogger.getLogger(SimpleFileSystemDirectoryRouter.class);
+ public static boolean loadStaticFilesFromJar = false;
+
private final String hostedPath;
private final String fileSystemPath;
-
private QCodeReference routeAuthenticator;
-
private QInstance qInstance;
-
-
/*******************************************************************************
** Constructor
**
@@ -67,6 +65,24 @@ public class SimpleFileSystemDirectoryRouter implements QJavalinRouteProviderInt
{
this.hostedPath = hostedPath;
this.fileSystemPath = fileSystemPath;
+
+ ///////////////////////////////////////////////////////////////////////////////////////////////////////
+ // read the property to see if we should load static files from the jar file or from the file system //
+ // Javan only supports loading via one method per path, so its a choice of one or the other... //
+ ///////////////////////////////////////////////////////////////////////////////////////////////////////
+ try
+ {
+ String propertyName = "qqq.javalin.enableStaticFilesFromJar"; // TODO: make a more general way to handle properties like this system-wide via a central config class
+ String propertyValue = System.getProperty(propertyName, "");
+ if(propertyValue.equals("true"))
+ {
+ loadStaticFilesFromJar = true;
+ }
+ }
+ catch(Exception e)
+ {
+ e.printStackTrace();
+ }
}
@@ -98,25 +114,41 @@ public class SimpleFileSystemDirectoryRouter implements QJavalinRouteProviderInt
***************************************************************************/
private void handleJavalinStaticFileConfig(StaticFileConfig staticFileConfig)
{
- URL resource = getClass().getClassLoader().getResource(fileSystemPath);
- if(resource == null)
- {
- String message = "Could not find file system path: " + fileSystemPath;
- if(fileSystemPath.startsWith("/") && getClass().getClassLoader().getResource(fileSystemPath.replaceFirst("^/+", "")) != null)
- {
- message += ". For non-absolute paths, do not prefix with a leading slash.";
- }
- throw new RuntimeException(message);
- }
if(!hostedPath.startsWith("/"))
{
LOG.warn("hostedPath [" + hostedPath + "] should probably start with a leading slash...");
}
- staticFileConfig.directory = resource.getFile();
- staticFileConfig.hostedPath = hostedPath;
- staticFileConfig.location = Location.EXTERNAL;
+ /// /////////////////////////////////////////////////////////////////////////////////////
+ // Handle loading static files from the jar OR the filesystem based on system property //
+ /// /////////////////////////////////////////////////////////////////////////////////////
+ if(SimpleFileSystemDirectoryRouter.loadStaticFilesFromJar)
+ {
+ staticFileConfig.directory = fileSystemPath;
+ staticFileConfig.hostedPath = hostedPath;
+ staticFileConfig.location = Location.CLASSPATH;
+ LOG.info("Static File Config : hostedPath [" + hostedPath + "] : directory [" + staticFileConfig.directory + "] : location [CLASSPATH]");
+ }
+ else
+ {
+ URL resource = getClass().getClassLoader().getResource(fileSystemPath);
+ if(resource == null)
+ {
+ String message = "Could not find file system path: " + fileSystemPath;
+ if(fileSystemPath.startsWith("/") && getClass().getClassLoader().getResource(fileSystemPath.replaceFirst("^/+", "")) != null)
+ {
+ message += ". For non-absolute paths, do not prefix with a leading slash.";
+ }
+ throw new RuntimeException(message);
+ }
+
+ staticFileConfig.directory = resource.getFile();
+ staticFileConfig.hostedPath = hostedPath;
+ staticFileConfig.location = Location.EXTERNAL;
+ LOG.info("Static File Config : hostedPath [" + hostedPath + "] : directory [" + staticFileConfig.directory + "] : location [EXTERNAL]");
+ }
+
}
diff --git a/qqq-middleware-javalin/src/test/java/com/kingsrook/qqq/middleware/javalin/QApplicationJavalinServerTest.java b/qqq-middleware-javalin/src/test/java/com/kingsrook/qqq/middleware/javalin/QApplicationJavalinServerTest.java
index a6bf4085..a9524022 100644
--- a/qqq-middleware-javalin/src/test/java/com/kingsrook/qqq/middleware/javalin/QApplicationJavalinServerTest.java
+++ b/qqq-middleware-javalin/src/test/java/com/kingsrook/qqq/middleware/javalin/QApplicationJavalinServerTest.java
@@ -29,6 +29,7 @@ import com.kingsrook.qqq.backend.core.exceptions.QException;
import com.kingsrook.qqq.backend.core.instances.AbstractQQQApplication;
import com.kingsrook.qqq.backend.core.model.metadata.QInstance;
import com.kingsrook.qqq.backend.javalin.TestUtils;
+import com.kingsrook.qqq.middleware.javalin.routeproviders.SimpleFileSystemDirectoryRouter;
import com.kingsrook.qqq.middleware.javalin.specs.v1.MiddlewareVersionV1;
import io.javalin.http.HttpStatus;
import kong.unirest.HttpResponse;
@@ -52,6 +53,16 @@ class QApplicationJavalinServerTest
+ /***************************************************************************
+ **
+ ***************************************************************************/
+ private static AbstractQQQApplication getQqqApplication()
+ {
+ return new TestApplication();
+ }
+
+
+
/*******************************************************************************
**
*******************************************************************************/
@@ -60,6 +71,7 @@ class QApplicationJavalinServerTest
{
javalinServer.stop();
TestApplication.callCount = 0;
+ System.clearProperty("qqq.javalin.enableStaticFilesFromJar");
}
@@ -196,6 +208,48 @@ class QApplicationJavalinServerTest
+ /*******************************************************************************
+ **
+ *******************************************************************************/
+ @Test
+ void testStaticRouterFilesFromExternal() throws Exception
+ {
+ System.setProperty("qqq.javalin.enableStaticFilesFromJar", "false");
+
+ javalinServer = new QApplicationJavalinServer(getQqqApplication())
+ .withServeFrontendMaterialDashboard(false)
+ .withPort(PORT);
+ javalinServer.start();
+
+ Unirest.config().setDefaultResponseEncoding("UTF-8");
+ HttpResponse response = Unirest.get("http://localhost:" + PORT + "/statically-served/foo.html").asString();
+ assertEquals("Foo? Bar!", response.getBody());
+ }
+
+
+
+ /*******************************************************************************
+ **
+ *******************************************************************************/
+ @Test
+ void testStaticRouterFilesFromClasspath() throws Exception
+ {
+ System.setProperty("qqq.javalin.enableStaticFilesFromJar", "true");
+
+ javalinServer = new QApplicationJavalinServer(new QApplicationJavalinServerTest.TestApplication())
+ .withServeFrontendMaterialDashboard(false)
+ .withPort(PORT)
+ .withAdditionalRouteProvider(new SimpleFileSystemDirectoryRouter("/statically-served-from-jar", "static-site-from-jar/"));
+
+ javalinServer.start();
+
+ Unirest.config().setDefaultResponseEncoding("UTF-8");
+ HttpResponse response = Unirest.get("http://localhost:" + PORT + "/statically-served-from-jar/foo-in-jar.html").asString();
+ assertEquals("Foo in a Jar!\n", response.getBody());
+ }
+
+
+
/*******************************************************************************
**
*******************************************************************************/
@@ -296,16 +350,6 @@ class QApplicationJavalinServerTest
- /***************************************************************************
- **
- ***************************************************************************/
- private static AbstractQQQApplication getQqqApplication()
- {
- return new TestApplication();
- }
-
-
-
/***************************************************************************
**
***************************************************************************/
diff --git a/qqq-middleware-javalin/src/test/resources/static-site.jar b/qqq-middleware-javalin/src/test/resources/static-site.jar
new file mode 100644
index 00000000..f5e203e4
Binary files /dev/null and b/qqq-middleware-javalin/src/test/resources/static-site.jar differ
|