From 12a691d8ce6754c17c782f1e85dddc3af6f54c4b Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 13 Aug 2021 17:08:53 +0200 Subject: [PATCH 001/105] Fix error with URLs in JEE servers --- frameworks/Kotlin/hexagon/build.gradle | 8 ++++---- frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt | 3 ++- .../Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt | 1 + 3 files changed, 7 insertions(+), 5 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index eeedb367dcf..71fce93860d 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,13 +4,13 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.3.20/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.0/gradle" - hexagonVersion = "1.3.20" - hikariVersion = "4.0.3" // TODO Check with 3.4.5, 4.0.3 or 5.0.0 + hexagonVersion = "1.4.0" + hikariVersion = "5.0.0" jettyVersion = "10.0.6" postgresqlVersion = "42.2.23" - cache2kVersion = "2.0.0.Final" + cache2kVersion = "2.2.1.Final" jacksonBlackbirdVersion = "2.12.4" } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 9ad9ea60fc4..8df102971de 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -6,6 +6,7 @@ import com.hexagonkt.serialization.Json import com.hexagonkt.serialization.toFieldsMap import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort +import java.net.URL import java.util.concurrent.ThreadLocalRandom class Controller(private val settings: Settings) { @@ -42,7 +43,7 @@ class Controller(private val settings: Settings) { val context = mapOf("fortunes" to sortedFortunes) response.contentType = "text/html;charset=utf-8" - ok(templateAdapter.render("fortunes.$templateKind.html", context)) + ok(templateAdapter.render(URL("classpath:fortunes.$templateKind.html"), context)) } private fun Call.dbQuery(store: BenchmarkStore) { diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index dfdf941d3cd..b2114fdf3ff 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -10,6 +10,7 @@ import javax.servlet.annotation.WebListener @WebListener class WebListenerServer(settings: Settings = Settings()) : ServletServer(Controller(settings).router) { init { + ClasspathHandler.registerHandler() Json.mapper.registerModule(BlackbirdModule()) SerializationManager.mapper = JacksonMapper SerializationManager.formats = linkedSetOf(Json) From 5242fd2c83badadb827a8db1c48143d11f6f11d9 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 13 Aug 2021 17:33:48 +0200 Subject: [PATCH 002/105] Clean up --- frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt | 2 -- 1 file changed, 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index b2114fdf3ff..174f5417267 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -15,6 +15,4 @@ import javax.servlet.annotation.WebListener SerializationManager.mapper = JacksonMapper SerializationManager.formats = linkedSetOf(Json) } - - val webRouter = super.router } \ No newline at end of file From 1ca6c4c0c4902ab812aab7995e87afc4e9a46cc9 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 13 Aug 2021 17:58:39 +0200 Subject: [PATCH 003/105] Avoid classpath URLs --- frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt | 8 +++++++- .../Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt | 1 - 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 8df102971de..e6f5107d987 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -1,5 +1,6 @@ package com.hexagonkt +import com.hexagonkt.helpers.require import com.hexagonkt.http.server.Call import com.hexagonkt.http.server.Router import com.hexagonkt.serialization.Json @@ -11,6 +12,11 @@ import java.util.concurrent.ThreadLocalRandom class Controller(private val settings: Settings) { + private val classLoader = Thread.currentThread().contextClassLoader + private val templates: Map = mapOf( + "pebble" to (classLoader.getResource("classpath:fortunes.pebble.html") ?: error("Template not found")) + ) + internal val router: Router by lazy { Router { before { @@ -43,7 +49,7 @@ class Controller(private val settings: Settings) { val context = mapOf("fortunes" to sortedFortunes) response.contentType = "text/html;charset=utf-8" - ok(templateAdapter.render(URL("classpath:fortunes.$templateKind.html"), context)) + ok(templateAdapter.render(templates.require(templateKind), context)) } private fun Call.dbQuery(store: BenchmarkStore) { diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index 174f5417267..488388534d3 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -10,7 +10,6 @@ import javax.servlet.annotation.WebListener @WebListener class WebListenerServer(settings: Settings = Settings()) : ServletServer(Controller(settings).router) { init { - ClasspathHandler.registerHandler() Json.mapper.registerModule(BlackbirdModule()) SerializationManager.mapper = JacksonMapper SerializationManager.formats = linkedSetOf(Json) From 6f5641bb2bd9244ae13fa6104041c04395401b95 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 13 Aug 2021 18:16:39 +0200 Subject: [PATCH 004/105] Fix template loading error --- frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index e6f5107d987..8e6d39ed8cb 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -14,7 +14,7 @@ class Controller(private val settings: Settings) { private val classLoader = Thread.currentThread().contextClassLoader private val templates: Map = mapOf( - "pebble" to (classLoader.getResource("classpath:fortunes.pebble.html") ?: error("Template not found")) + "pebble" to (classLoader.getResource("fortunes.pebble.html") ?: error("Template not found")) ) internal val router: Router by lazy { From 5fa3b6232b3e1510c6d9972290dca1bc11250a06 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 13 Aug 2021 18:28:49 +0200 Subject: [PATCH 005/105] Fix template loading error --- frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 8e6d39ed8cb..2e2fb70ba0f 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -12,9 +12,9 @@ import java.util.concurrent.ThreadLocalRandom class Controller(private val settings: Settings) { - private val classLoader = Thread.currentThread().contextClassLoader + private val classLoader = ClassLoader.getSystemClassLoader() private val templates: Map = mapOf( - "pebble" to (classLoader.getResource("fortunes.pebble.html") ?: error("Template not found")) + "pebble" to (classLoader.getResource("/fortunes.pebble.html") ?: error("Template not found")) ) internal val router: Router by lazy { From 6f8264fe4025c5af599350f93b34a04317bbe61e Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 13 Aug 2021 18:47:03 +0200 Subject: [PATCH 006/105] Chores --- frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 2e2fb70ba0f..ae49e8e5c54 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -14,7 +14,7 @@ class Controller(private val settings: Settings) { private val classLoader = ClassLoader.getSystemClassLoader() private val templates: Map = mapOf( - "pebble" to (classLoader.getResource("/fortunes.pebble.html") ?: error("Template not found")) + "pebble" to (classLoader.getResource("fortunes.pebble.html") ?: error("Template not found")) ) internal val router: Router by lazy { From c3941d1c8ebcaf2577768bd81ef55d139d6219f8 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 13 Aug 2021 19:11:46 +0200 Subject: [PATCH 007/105] Fix template loading error --- .../Kotlin/hexagon/hexagon-resin-mongodb.dockerfile | 1 + .../hexagon/hexagon-resin-postgresql.dockerfile | 1 + .../Kotlin/hexagon/src/main/kotlin/Controller.kt | 11 +++++++++-- 3 files changed, 11 insertions(+), 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile b/frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile index 9884c856d38..69ebbd5ecfa 100644 --- a/frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile @@ -21,5 +21,6 @@ WORKDIR /resin RUN curl -sL $RESIN | tar xz --strip-components=1 RUN rm -rf webapps/* COPY --from=gradle_build /hexagon/build/libs/ROOT.war webapps/ROOT.war +COPY src/main/resources/fortunes.pebble.html fortunes.pebble.html EXPOSE 9090 CMD ["java", "-jar", "lib/resin.jar", "console"] diff --git a/frameworks/Kotlin/hexagon/hexagon-resin-postgresql.dockerfile b/frameworks/Kotlin/hexagon/hexagon-resin-postgresql.dockerfile index 87c1fec3f51..4c88f47740f 100644 --- a/frameworks/Kotlin/hexagon/hexagon-resin-postgresql.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-resin-postgresql.dockerfile @@ -21,5 +21,6 @@ WORKDIR /resin RUN curl -sL $RESIN | tar xz --strip-components=1 RUN rm -rf webapps/* COPY --from=gradle_build /hexagon/build/libs/ROOT.war webapps/ROOT.war +COPY src/main/resources/fortunes.pebble.html fortunes.pebble.html EXPOSE 8080 CMD ["java", "-jar", "lib/resin.jar", "console"] diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index ae49e8e5c54..62f010c2eb2 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -12,9 +12,8 @@ import java.util.concurrent.ThreadLocalRandom class Controller(private val settings: Settings) { - private val classLoader = ClassLoader.getSystemClassLoader() private val templates: Map = mapOf( - "pebble" to (classLoader.getResource("fortunes.pebble.html") ?: error("Template not found")) + "pebble" to (urlOrNull("classpath:fortunes.pebble.html") ?: URL("file:/resin/fortunes.pebble.html")) ) internal val router: Router by lazy { @@ -84,4 +83,12 @@ class Controller(private val settings: Settings) { private fun randomWorld(): Int = ThreadLocalRandom.current().nextInt(settings.worldRows) + 1 + + private fun urlOrNull(path: String): URL? = + try { + URL(path) + } + catch (e: Exception) { + null + } } \ No newline at end of file From 4fe8ef6b71db0853018718b2270f185e0dffecad Mon Sep 17 00:00:00 2001 From: jaguililla Date: Tue, 24 Aug 2021 19:01:21 +0200 Subject: [PATCH 008/105] Delete MongoDB DB support Storage support in Hexagon will be moved outside the Toolkit, and so, it will be left outside the benchmark. --- frameworks/Kotlin/hexagon/README.md | 5 +- .../Kotlin/hexagon/benchmark_config.json | 48 +--------------- frameworks/Kotlin/hexagon/build.gradle | 5 +- frameworks/Kotlin/hexagon/config.toml | 38 +------------ .../hexagon-jetty-postgresql.dockerfile | 25 -------- .../hexagon/hexagon-resin-mongodb.dockerfile | 26 --------- ...ql.dockerfile => hexagon-resin.dockerfile} | 2 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 6 +- .../hexagon/src/main/kotlin/Benchmark.kt | 6 +- .../kotlin/store/BenchmarkMongoDbStore.kt | 57 ------------------- 10 files changed, 10 insertions(+), 208 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon-jetty-postgresql.dockerfile delete mode 100644 frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile rename frameworks/Kotlin/hexagon/{hexagon-resin-postgresql.dockerfile => hexagon-resin.dockerfile} (93%) delete mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkMongoDbStore.kt diff --git a/frameworks/Kotlin/hexagon/README.md b/frameworks/Kotlin/hexagon/README.md index 004f35927b4..54c66442a82 100644 --- a/frameworks/Kotlin/hexagon/README.md +++ b/frameworks/Kotlin/hexagon/README.md @@ -18,10 +18,7 @@ You can run tests against any running server passing the `verify.endpoint` proje ## Test URLs -In URLs replace `${DB_ENGINE}` with one of: - -* mongodb -* postgresql +In URLs replace `${DB_ENGINE}` with: `postgresql` and `${TEMPLATE_ENGINE}` with: `pebble` diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 424fcbb5e8a..7bca1a660ad 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -3,52 +3,6 @@ "tests": [ { "default": { - "json_url": "/json", - "db_url": "/mongodb/db", - "query_url": "/mongodb/query?queries=", - "fortune_url": "/mongodb/pebble/fortunes", - "update_url": "/mongodb/update?queries=", - "cached_query_url": "/mongodb/cached?count=", - "plaintext_url": "/plaintext", - "port": 9090, - "approach": "Realistic", - "classification": "Micro", - "database": "mongodb", - "framework": "Hexagon", - "language": "Kotlin", - "orm": "Raw", - "platform": "Servlet", - "webserver": "None", - "os": "Linux", - "database_os": "Linux", - "display_name": "Hexagon Jetty MongoDB", - "notes": "http://hexagonkt.com", - "versus": "servlet" - }, - "resin-mongodb": { - "json_url": "/json", - "db_url": "/mongodb/db", - "query_url": "/mongodb/query?queries=", - "fortune_url": "/mongodb/pebble/fortunes", - "update_url": "/mongodb/update?queries=", - "cached_query_url": "/mongodb/cached?count=", - "plaintext_url": "/plaintext", - "port": 8080, - "approach": "Realistic", - "classification": "Micro", - "database": "mongodb", - "framework": "Hexagon", - "language": "Kotlin", - "orm": "Raw", - "platform": "Servlet", - "webserver": "None", - "os": "Linux", - "database_os": "Linux", - "display_name": "Hexagon Resin MongoDB", - "notes": "http://hexagonkt.com", - "versus": "servlet" - }, - "jetty-postgresql": { "json_url": "/json", "db_url": "/postgresql/db", "query_url": "/postgresql/query?queries=", @@ -71,7 +25,7 @@ "notes": "http://hexagonkt.com", "versus": "servlet" }, - "resin-postgresql": { + "resin": { "json_url": "/json", "db_url": "/postgresql/db", "query_url": "/postgresql/query?queries=", diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 71fce93860d..ae2ce077696 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,9 +4,9 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.0/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.1/gradle" - hexagonVersion = "1.4.0" + hexagonVersion = "1.4.1" hikariVersion = "5.0.0" jettyVersion = "10.0.6" postgresqlVersion = "42.2.23" @@ -32,7 +32,6 @@ war { installDist.dependsOn("war") dependencies { - implementation("com.hexagonkt:store_mongodb:$hexagonVersion") implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index c83738043be..c688baad5a8 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -4,24 +4,6 @@ name = "hexagon" [main] urls.plaintext = "/plaintext" urls.json = "/json" -urls.db = "/mongodb/db" -urls.query = "/mongodb/query?queries=" -urls.update = "/mongodb/update?queries=" -urls.fortune = "/mongodb/pebble/fortunes" -urls.cached_query = "/mongodb/cached?count=" -approach = "Realistic" -classification = "Micro" -database = "mongodb" -database_os = "Linux" -os = "Linux" -orm = "Raw" -platform = "Servlet" -webserver = "None" -versus = "servlet" - -[resin-postgresql] -urls.plaintext = "/plaintext" -urls.json = "/json" urls.db = "/postgresql/db" urls.query = "/postgresql/query?queries=" urls.update = "/postgresql/update?queries=" @@ -37,7 +19,7 @@ platform = "Servlet" webserver = "None" versus = "servlet" -[jetty-postgresql] +[resin] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/postgresql/db" @@ -54,21 +36,3 @@ orm = "Raw" platform = "Servlet" webserver = "None" versus = "servlet" - -[resin-mongodb] -urls.plaintext = "/plaintext" -urls.json = "/json" -urls.db = "/mongodb/db" -urls.query = "/mongodb/query?queries=" -urls.update = "/mongodb/update?queries=" -urls.fortune = "/mongodb/pebble/fortunes" -urls.cached_query = "/mongodb/cached?count=" -approach = "Realistic" -classification = "Micro" -database = "mongodb" -database_os = "Linux" -os = "Linux" -orm = "Raw" -platform = "Servlet" -webserver = "None" -versus = "servlet" diff --git a/frameworks/Kotlin/hexagon/hexagon-jetty-postgresql.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jetty-postgresql.dockerfile deleted file mode 100644 index 08611f3b42d..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-jetty-postgresql.dockerfile +++ /dev/null @@ -1,25 +0,0 @@ -# -# BUILD -# -FROM gradle:7.1-jdk11 AS gradle_build -USER root -WORKDIR /hexagon - -COPY src src -COPY build.gradle build.gradle -RUN gradle --quiet --exclude-task test - -# -# RUNTIME -# -FROM adoptopenjdk:11-jre-hotspot-bionic -ENV DBSTORE postgresql -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE jetty -ENV PROJECT hexagon - -COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT - -EXPOSE 9090 - -ENTRYPOINT /opt/$PROJECT/bin/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile b/frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile deleted file mode 100644 index 69ebbd5ecfa..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-resin-mongodb.dockerfile +++ /dev/null @@ -1,26 +0,0 @@ -# -# BUILD -# -FROM gradle:7.1-jdk11 AS gradle_build -USER root -WORKDIR /hexagon - -COPY src src -COPY build.gradle build.gradle -RUN gradle --quiet --exclude-task test - -# -# RUNTIME -# -FROM adoptopenjdk:11-jre-hotspot-bionic -ENV DBSTORE mongodb -ENV MONGODB_DB_HOST tfb-database -ENV RESIN http://caucho.com/download/resin-4.0.65.tar.gz - -WORKDIR /resin -RUN curl -sL $RESIN | tar xz --strip-components=1 -RUN rm -rf webapps/* -COPY --from=gradle_build /hexagon/build/libs/ROOT.war webapps/ROOT.war -COPY src/main/resources/fortunes.pebble.html fortunes.pebble.html -EXPOSE 9090 -CMD ["java", "-jar", "lib/resin.jar", "console"] diff --git a/frameworks/Kotlin/hexagon/hexagon-resin-postgresql.dockerfile b/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile similarity index 93% rename from frameworks/Kotlin/hexagon/hexagon-resin-postgresql.dockerfile rename to frameworks/Kotlin/hexagon/hexagon-resin.dockerfile index 4c88f47740f..7ad188cd213 100644 --- a/frameworks/Kotlin/hexagon/hexagon-resin-postgresql.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.1-jdk11 AS gradle_build +FROM gradle:7.2-jdk11 AS gradle_build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index a846802eb3b..ad0603eb837 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.1-jdk11 AS gradle_build +FROM gradle:7.2-jdk11 AS gradle_build USER root WORKDIR /hexagon @@ -13,8 +13,8 @@ RUN gradle --quiet --exclude-task test # RUNTIME # FROM adoptopenjdk:11-jre-hotspot-bionic -ENV DBSTORE mongodb -ENV MONGODB_DB_HOST tfb-database +ENV DBSTORE postgresql +ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE jetty ENV PROJECT hexagon diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index e60779051f1..8ee2a680413 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -6,7 +6,6 @@ import com.hexagonkt.http.server.ServerPort import com.hexagonkt.http.server.ServerSettings import com.hexagonkt.http.server.jetty.JettyServletAdapter import com.hexagonkt.serialization.* -import com.hexagonkt.store.BenchmarkMongoDbStore import com.hexagonkt.store.BenchmarkSqlStore import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort @@ -14,10 +13,7 @@ import com.hexagonkt.templates.pebble.PebbleAdapter import java.net.InetAddress internal val benchmarkStores: Map by lazy { - mapOf( - "mongodb" to BenchmarkMongoDbStore("mongodb"), - "postgresql" to BenchmarkSqlStore("postgresql") - ) + mapOf("postgresql" to BenchmarkSqlStore("postgresql")) } internal val benchmarkTemplateEngines: Map by lazy { diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkMongoDbStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkMongoDbStore.kt deleted file mode 100644 index eb0ce04612e..00000000000 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkMongoDbStore.kt +++ /dev/null @@ -1,57 +0,0 @@ -package com.hexagonkt.store - -import com.hexagonkt.CachedWorld -import com.hexagonkt.Fortune -import com.hexagonkt.Settings -import com.hexagonkt.World -import com.hexagonkt.helpers.Jvm -import com.hexagonkt.helpers.fail -import com.hexagonkt.store.mongodb.MongoDbStore -import org.cache2k.Cache - -internal class BenchmarkMongoDbStore(engine: String, private val settings: Settings = Settings()) - : BenchmarkStore(settings) { - - data class MongoDbWorld(val _id: Int, val id: Int, val randomNumber: Int) - data class MongoDbFortune(val _id: Int, val message: String) - - private val dbHost: String by lazy { Jvm.systemSetting("${engine.uppercase()}_DB_HOST") ?: "localhost" } - - private val dbUrl: String by lazy { "mongodb://$dbHost/${settings.databaseName}" } - - private val worldRepository: MongoDbStore by lazy { - MongoDbStore(MongoDbWorld::class, MongoDbWorld::_id, dbUrl, settings.worldName) - } - - private val fortuneRepository by lazy { - MongoDbStore(MongoDbFortune::class, MongoDbFortune::_id, dbUrl, settings.fortuneName) - } - - override fun findAllFortunes(): List = fortuneRepository.findAll().map { Fortune(it._id, it.message) } - - override fun findWorlds(ids: List): List = - ids.mapNotNull { worldRepository.findOne(it) }.map { World(it.id, it.randomNumber) } - - override fun replaceWorlds(worlds: List) { - worlds.forEach { - val world = worldRepository.findOne(it.id) ?: fail - val worldCopy = world.copy(randomNumber = it.randomNumber) - worldRepository.replaceOne(worldCopy) - } - } - - override fun initWorldsCache(cache: Cache) { - worldRepository.findAll().forEach { - cache.put(it.id, CachedWorld(it.id, it.randomNumber)) - } - } - - override fun loadCachedWorld(id: Int): CachedWorld = - worldRepository.findOne(id) - ?.let { world -> CachedWorld(world.id, world.randomNumber) } - ?: error("World not found: $id") - - override fun close() { - /* Not needed */ - } -} \ No newline at end of file From 55852f184390c8b7019cc0ac215b061090e7b631 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Tue, 24 Aug 2021 19:36:22 +0200 Subject: [PATCH 009/105] Fix runtime problem --- frameworks/Kotlin/hexagon/build.gradle | 1 + frameworks/Kotlin/hexagon/hexagon-resin.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 2 +- 3 files changed, 3 insertions(+), 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index ae2ce077696..ef7e121a996 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -32,6 +32,7 @@ war { installDist.dependsOn("war") dependencies { + implementation("org.jetbrains.kotlin:kotlin-reflect:1.5.21") // TODO Remove on 1.4.2 implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") diff --git a/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile b/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile index 7ad188cd213..3bc3ddb7838 100644 --- a/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile @@ -7,7 +7,7 @@ WORKDIR /hexagon COPY src src COPY build.gradle build.gradle -RUN gradle --quiet --exclude-task test +RUN gradle --quiet # # RUNTIME diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index ad0603eb837..f40c3b93d3d 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -7,7 +7,7 @@ WORKDIR /hexagon COPY src src COPY build.gradle build.gradle -RUN gradle --quiet --exclude-task test +RUN gradle --quiet # # RUNTIME From 0046df55ebd80b8990cc9c0c8dbd6a7418ed6ed7 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Tue, 24 Aug 2021 22:25:48 +0200 Subject: [PATCH 010/105] Update Hexagon version --- frameworks/Kotlin/hexagon/build.gradle | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index ef7e121a996..70718db9f04 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,9 +4,9 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.1/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.2/gradle" - hexagonVersion = "1.4.1" + hexagonVersion = "1.4.2" hikariVersion = "5.0.0" jettyVersion = "10.0.6" postgresqlVersion = "42.2.23" @@ -32,7 +32,6 @@ war { installDist.dependsOn("war") dependencies { - implementation("org.jetbrains.kotlin:kotlin-reflect:1.5.21") // TODO Remove on 1.4.2 implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") From 010d153ae8ceb037c48785020c161bb8fccadc19 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 25 Aug 2021 21:27:48 +0200 Subject: [PATCH 011/105] Make Jackson Blackbird module optional --- frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index 8ee2a680413..7a851fd0174 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -36,7 +36,8 @@ internal val benchmarkServer: Server by lazy { } fun main() { - Json.mapper.registerModule(BlackbirdModule()) + if (System.getenv().containsKey("ENABLE_BLACKBIRD")) + Json.mapper.registerModule(BlackbirdModule()) SerializationManager.mapper = JacksonMapper SerializationManager.formats = linkedSetOf(Json) From dc625615d783f6e8519ad68c9762e42d9b6c0b20 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 13 Oct 2021 21:24:21 +0200 Subject: [PATCH 012/105] Add variation with Blackbird module enabled --- .../Kotlin/hexagon/benchmark_config.json | 23 ++++++++++++++++ frameworks/Kotlin/hexagon/config.toml | 18 +++++++++++++ .../hexagon/hexagon-blackbird.dockerfile | 26 +++++++++++++++++++ 3 files changed, 67 insertions(+) create mode 100644 frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 7bca1a660ad..44da569131b 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -25,6 +25,29 @@ "notes": "http://hexagonkt.com", "versus": "servlet" }, + "blackbird": { + "json_url": "/json", + "db_url": "/postgresql/db", + "query_url": "/postgresql/query?queries=", + "fortune_url": "/postgresql/pebble/fortunes", + "update_url": "/postgresql/update?queries=", + "cached_query_url": "/postgresql/cached?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Servlet", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Jetty PostgreSQL", + "notes": "http://hexagonkt.com", + "versus": "servlet" + }, "resin": { "json_url": "/json", "db_url": "/postgresql/db", diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index c688baad5a8..dfbcd24f032 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -19,6 +19,24 @@ platform = "Servlet" webserver = "None" versus = "servlet" +[blackbird] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/postgresql/db" +urls.query = "/postgresql/query?queries=" +urls.update = "/postgresql/update?queries=" +urls.fortune = "/postgresql/pebble/fortunes" +urls.cached_query = "/postgresql/cached?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Servlet" +webserver = "None" +versus = "servlet" + [resin] urls.plaintext = "/plaintext" urls.json = "/json" diff --git a/frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile b/frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile new file mode 100644 index 00000000000..07d9771d2e0 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile @@ -0,0 +1,26 @@ +# +# BUILD +# +FROM gradle:7.2-jdk11 AS gradle_build +USER root +WORKDIR /hexagon + +COPY src src +COPY build.gradle build.gradle +RUN gradle --quiet + +# +# RUNTIME +# +FROM adoptopenjdk:11-jre-hotspot-bionic +ENV DBSTORE postgresql +ENV POSTGRESQL_DB_HOST tfb-database +ENV WEBENGINE jetty +ENV PROJECT hexagon +ENV ENABLE_BLACKBIRD true + +COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT + +EXPOSE 9090 + +ENTRYPOINT /opt/$PROJECT/bin/$PROJECT From 349756851dfc0b992846b8ea82f89754d754dc4d Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 13 Oct 2021 21:25:08 +0200 Subject: [PATCH 013/105] Upgrade Hexagon version --- frameworks/Kotlin/hexagon/build.gradle | 12 ++++++------ .../Kotlin/hexagon/src/main/kotlin/Benchmark.kt | 3 ++- 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 70718db9f04..64e344c8d71 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,17 +1,17 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.5.21" + id "org.jetbrains.kotlin.jvm" version "1.5.31" } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.2/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.7/gradle" - hexagonVersion = "1.4.2" + hexagonVersion = "1.4.7" hikariVersion = "5.0.0" - jettyVersion = "10.0.6" - postgresqlVersion = "42.2.23" + jettyVersion = "10.0.7" + postgresqlVersion = "42.2.24" cache2kVersion = "2.2.1.Final" - jacksonBlackbirdVersion = "2.12.4" + jacksonBlackbirdVersion = "2.13.0" } apply(from: "$gradleScripts/kotlin.gradle") diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index 7a851fd0174..bfa87425fe1 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -1,6 +1,7 @@ package com.hexagonkt import com.fasterxml.jackson.module.blackbird.BlackbirdModule +import com.hexagonkt.helpers.Jvm import com.hexagonkt.http.server.Server import com.hexagonkt.http.server.ServerPort import com.hexagonkt.http.server.ServerSettings @@ -36,7 +37,7 @@ internal val benchmarkServer: Server by lazy { } fun main() { - if (System.getenv().containsKey("ENABLE_BLACKBIRD")) + if (Jvm.systemFlag("ENABLE_BLACKBIRD")) Json.mapper.registerModule(BlackbirdModule()) SerializationManager.mapper = JacksonMapper SerializationManager.formats = linkedSetOf(Json) From 8a565d196bf565857556e03fecff52a94b5cceef Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 23 Dec 2021 08:36:56 +0100 Subject: [PATCH 014/105] Enable blackbird Jackson module by default --- .../Kotlin/hexagon/benchmark_config.json | 23 ---------------- frameworks/Kotlin/hexagon/config.toml | 18 ------------- .../hexagon/hexagon-blackbird.dockerfile | 26 ------------------- frameworks/Kotlin/hexagon/hexagon.dockerfile | 3 ++- 4 files changed, 2 insertions(+), 68 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 44da569131b..7bca1a660ad 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -25,29 +25,6 @@ "notes": "http://hexagonkt.com", "versus": "servlet" }, - "blackbird": { - "json_url": "/json", - "db_url": "/postgresql/db", - "query_url": "/postgresql/query?queries=", - "fortune_url": "/postgresql/pebble/fortunes", - "update_url": "/postgresql/update?queries=", - "cached_query_url": "/postgresql/cached?count=", - "plaintext_url": "/plaintext", - "port": 9090, - "approach": "Realistic", - "classification": "Micro", - "database": "postgres", - "framework": "Hexagon", - "language": "Kotlin", - "orm": "Raw", - "platform": "Servlet", - "webserver": "None", - "os": "Linux", - "database_os": "Linux", - "display_name": "Hexagon Jetty PostgreSQL", - "notes": "http://hexagonkt.com", - "versus": "servlet" - }, "resin": { "json_url": "/json", "db_url": "/postgresql/db", diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index dfbcd24f032..c688baad5a8 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -19,24 +19,6 @@ platform = "Servlet" webserver = "None" versus = "servlet" -[blackbird] -urls.plaintext = "/plaintext" -urls.json = "/json" -urls.db = "/postgresql/db" -urls.query = "/postgresql/query?queries=" -urls.update = "/postgresql/update?queries=" -urls.fortune = "/postgresql/pebble/fortunes" -urls.cached_query = "/postgresql/cached?count=" -approach = "Realistic" -classification = "Micro" -database = "postgres" -database_os = "Linux" -os = "Linux" -orm = "Raw" -platform = "Servlet" -webserver = "None" -versus = "servlet" - [resin] urls.plaintext = "/plaintext" urls.json = "/json" diff --git a/frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile b/frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile deleted file mode 100644 index 07d9771d2e0..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-blackbird.dockerfile +++ /dev/null @@ -1,26 +0,0 @@ -# -# BUILD -# -FROM gradle:7.2-jdk11 AS gradle_build -USER root -WORKDIR /hexagon - -COPY src src -COPY build.gradle build.gradle -RUN gradle --quiet - -# -# RUNTIME -# -FROM adoptopenjdk:11-jre-hotspot-bionic -ENV DBSTORE postgresql -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE jetty -ENV PROJECT hexagon -ENV ENABLE_BLACKBIRD true - -COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT - -EXPOSE 9090 - -ENTRYPOINT /opt/$PROJECT/bin/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index f40c3b93d3d..28a74cb7352 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.2-jdk11 AS gradle_build +FROM gradle:7.3.3-jdk11 AS gradle_build USER root WORKDIR /hexagon @@ -17,6 +17,7 @@ ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE jetty ENV PROJECT hexagon +ENV ENABLE_BLACKBIRD true COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT From 8f9854b4f51f0853838d05d9f2c0eda5a4d20b7f Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 23 Dec 2021 09:22:14 +0100 Subject: [PATCH 015/105] Update dependencies --- frameworks/Kotlin/hexagon/build.gradle | 10 +++++----- frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt | 3 ++- .../Kotlin/hexagon/src/main/kotlin/Controller.kt | 6 +++--- frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt | 4 ++-- .../hexagon/src/main/kotlin/WebListenerServer.kt | 6 +++--- .../hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt | 4 ++-- 6 files changed, 17 insertions(+), 16 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 64e344c8d71..a492c71f81b 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,16 +1,16 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.5.31" + id "org.jetbrains.kotlin.jvm" version "1.6.10" } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.4.7/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.5.1/gradle" - hexagonVersion = "1.4.7" + hexagonVersion = "1.5.1" hikariVersion = "5.0.0" jettyVersion = "10.0.7" - postgresqlVersion = "42.2.24" - cache2kVersion = "2.2.1.Final" + postgresqlVersion = "42.3.1" + cache2kVersion = "2.4.1.Final" jacksonBlackbirdVersion = "2.13.0" } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index bfa87425fe1..2c0ab6a27de 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -1,12 +1,13 @@ package com.hexagonkt import com.fasterxml.jackson.module.blackbird.BlackbirdModule -import com.hexagonkt.helpers.Jvm +import com.hexagonkt.core.helpers.Jvm import com.hexagonkt.http.server.Server import com.hexagonkt.http.server.ServerPort import com.hexagonkt.http.server.ServerSettings import com.hexagonkt.http.server.jetty.JettyServletAdapter import com.hexagonkt.serialization.* +import com.hexagonkt.serialization.json.* import com.hexagonkt.store.BenchmarkSqlStore import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 62f010c2eb2..e95d526691d 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -1,9 +1,9 @@ package com.hexagonkt -import com.hexagonkt.helpers.require +import com.hexagonkt.core.helpers.require import com.hexagonkt.http.server.Call import com.hexagonkt.http.server.Router -import com.hexagonkt.serialization.Json +import com.hexagonkt.serialization.json.Json import com.hexagonkt.serialization.toFieldsMap import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort @@ -91,4 +91,4 @@ class Controller(private val settings: Settings) { catch (e: Exception) { null } -} \ No newline at end of file +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index 578b11b45d9..94992292acc 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -1,6 +1,6 @@ package com.hexagonkt -import com.hexagonkt.helpers.Jvm.systemSetting +import com.hexagonkt.core.helpers.Jvm.systemSetting data class Settings( val bindPort: Int = systemSetting("bindPort") ?: 9090, @@ -25,4 +25,4 @@ data class Settings( val textMessage: String = "Hello, World!", val queriesParam: String = "queries", val cachedQueriesParam: String = "count", -) \ No newline at end of file +) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index 488388534d3..81a912606f1 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -2,8 +2,8 @@ package com.hexagonkt import com.fasterxml.jackson.module.blackbird.BlackbirdModule import com.hexagonkt.http.server.servlet.ServletServer -import com.hexagonkt.serialization.JacksonMapper -import com.hexagonkt.serialization.Json +import com.hexagonkt.serialization.json.JacksonMapper +import com.hexagonkt.serialization.json.Json import com.hexagonkt.serialization.SerializationManager import javax.servlet.annotation.WebListener @@ -14,4 +14,4 @@ import javax.servlet.annotation.WebListener SerializationManager.mapper = JacksonMapper SerializationManager.formats = linkedSetOf(Json) } -} \ No newline at end of file +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index b0fdd6f6f85..acf4e978a6a 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -4,7 +4,7 @@ import com.hexagonkt.CachedWorld import com.hexagonkt.Fortune import com.hexagonkt.Settings import com.hexagonkt.World -import com.hexagonkt.helpers.Jvm +import com.hexagonkt.core.helpers.Jvm import com.zaxxer.hikari.HikariConfig import com.zaxxer.hikari.HikariDataSource import org.cache2k.Cache @@ -100,4 +100,4 @@ internal class BenchmarkSqlStore(engine: String, private val settings: Settings rs.next() return World(rs.getInt(1), rs.getInt(2)) } -} \ No newline at end of file +} From cdf705baa769f2cfc3c6f33c2137b26041300900 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 8 Jan 2022 11:26:03 +0100 Subject: [PATCH 016/105] Use Hexagon version 2.0.0-B1 (and a little cleanup) --- frameworks/Kotlin/hexagon/build.gradle | 10 +- .../hexagon/src/main/kotlin/Benchmark.kt | 39 +++--- .../hexagon/src/main/kotlin/Controller.kt | 116 +++++++++++------- .../hexagon/src/main/kotlin/Settings.kt | 4 + .../src/main/kotlin/WebListenerServer.kt | 16 +-- 5 files changed, 103 insertions(+), 82 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index a492c71f81b..a737206edd9 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,14 +4,13 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/1.5.1/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0-B1/gradle" - hexagonVersion = "1.5.1" + hexagonVersion = "2.0.0-B1" hikariVersion = "5.0.0" - jettyVersion = "10.0.7" + jettyVersion = "11.0.7" postgresqlVersion = "42.3.1" cache2kVersion = "2.4.1.Final" - jacksonBlackbirdVersion = "2.13.0" } apply(from: "$gradleScripts/kotlin.gradle") @@ -35,9 +34,8 @@ dependencies { implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") - implementation("com.hexagonkt:serialization_json:$hexagonVersion") + implementation("com.hexagonkt:serialization_jackson_json:$hexagonVersion") - implementation("com.fasterxml.jackson.module:jackson-module-blackbird:$jacksonBlackbirdVersion") implementation("org.cache2k:cache2k-core:$cache2kVersion") implementation("com.zaxxer:HikariCP:$hikariVersion") implementation("org.postgresql:postgresql:$postgresqlVersion") diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index 2c0ab6a27de..c8174411b35 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -1,47 +1,44 @@ package com.hexagonkt -import com.fasterxml.jackson.module.blackbird.BlackbirdModule -import com.hexagonkt.core.helpers.Jvm -import com.hexagonkt.http.server.Server -import com.hexagonkt.http.server.ServerPort -import com.hexagonkt.http.server.ServerSettings +import com.hexagonkt.http.server.HttpServer +import com.hexagonkt.http.server.HttpServerPort +import com.hexagonkt.http.server.HttpServerSettings import com.hexagonkt.http.server.jetty.JettyServletAdapter -import com.hexagonkt.serialization.* -import com.hexagonkt.serialization.json.* import com.hexagonkt.store.BenchmarkSqlStore import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort import com.hexagonkt.templates.pebble.PebbleAdapter import java.net.InetAddress -internal val benchmarkStores: Map by lazy { +internal val stores: Map by lazy { mapOf("postgresql" to BenchmarkSqlStore("postgresql")) } -internal val benchmarkTemplateEngines: Map by lazy { +internal val templateEngines: Map by lazy { mapOf("pebble" to PebbleAdapter) } -internal val benchmarkEngines: Map by lazy { +private val engines: Map by lazy { mapOf("jetty" to JettyServletAdapter()) } -internal val benchmarkServer: Server by lazy { +private val server: HttpServer by lazy { val settings = Settings() - val engine = benchmarkEngines[settings.webEngine] ?: error("Unsupported server engine") - val serverSettings = ServerSettings( + val engine = engines[settings.webEngine] ?: error("Unsupported server engine") + val controller = Controller(settings, stores, templateEngines) + val serverSettings = HttpServerSettings( bindAddress = InetAddress.getByName(settings.bindAddress), - bindPort = settings.bindPort + bindPort = settings.bindPort, + options = mapOf( + "sendDateHeader" to settings.sendDateHeader, + "sendServerVersion" to settings.sendServerVersion, + "sendXPoweredBy" to settings.sendXPoweredBy, + ), ) - Server(engine, Controller(settings).router, serverSettings) + HttpServer(engine, listOf(controller.path), serverSettings) } fun main() { - if (Jvm.systemFlag("ENABLE_BLACKBIRD")) - Json.mapper.registerModule(BlackbirdModule()) - SerializationManager.mapper = JacksonMapper - SerializationManager.formats = linkedSetOf(Json) - - benchmarkServer.start() + server.start() } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index e95d526691d..c77cc9de631 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -1,78 +1,110 @@ package com.hexagonkt import com.hexagonkt.core.helpers.require -import com.hexagonkt.http.server.Call -import com.hexagonkt.http.server.Router -import com.hexagonkt.serialization.json.Json -import com.hexagonkt.serialization.toFieldsMap +import com.hexagonkt.core.media.ApplicationMedia.JSON +import com.hexagonkt.core.media.TextMedia.HTML +import com.hexagonkt.core.media.TextMedia.PLAIN +import com.hexagonkt.http.model.ContentType +import com.hexagonkt.http.server.handlers.HttpServerContext +import com.hexagonkt.http.server.handlers.PathHandler +import com.hexagonkt.http.server.handlers.path +import com.hexagonkt.serialization.jackson.json.Json +import com.hexagonkt.serialization.serialize import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort + import java.net.URL import java.util.concurrent.ThreadLocalRandom -class Controller(private val settings: Settings) { +import kotlin.text.Charsets.UTF_8 + +internal class Controller( + settings: Settings, + stores: Map, + templateEngines: Map, +) { + private val queriesParam: String = settings.queriesParam + private val cachedQueriesParam: String = settings.cachedQueriesParam + private val worldRows: Int = settings.worldRows + + private val plain: ContentType = ContentType(PLAIN) + private val json: ContentType = ContentType(JSON) + private val html: ContentType = ContentType(HTML, charset = UTF_8) private val templates: Map = mapOf( "pebble" to (urlOrNull("classpath:fortunes.pebble.html") ?: URL("file:/resin/fortunes.pebble.html")) ) - internal val router: Router by lazy { - Router { - before { - response.headers["Server"] = "Servlet/3.1" - response.headers["Transfer-Encoding"] = "chunked" - } - - get("/plaintext") { ok(settings.textMessage, "text/plain") } - get("/json") { ok(Message(settings.textMessage), Json) } - - benchmarkStores.forEach { (storeEngine, store) -> - benchmarkTemplateEngines.forEach { (templateEngineId, templateEngine) -> - val path = "/$storeEngine/${templateEngineId}/fortunes" - - get(path) { listFortunes(store, templateEngineId, templateEngine) } + internal val path: PathHandler by lazy { + path { + get("/plaintext") { ok(settings.textMessage, contentType = plain) } + get("/json") { ok(Message(settings.textMessage).serialize(Json), contentType = json) } + + stores.forEach { (storeEngine, store) -> + path("/$storeEngine") { + templateEngines.forEach { (templateEngineId, templateEngine) -> + get("/${templateEngineId}/fortunes") { listFortunes(store, templateEngineId, templateEngine) } + } + + get("/db") { dbQuery(store) } + get("/query") { getWorlds(store) } + get("/cached") { getCachedWorlds(store) } + get("/update") { updateWorlds(store) } } - - get("/$storeEngine/db") { dbQuery(store) } - get("/$storeEngine/query") { getWorlds(store) } - get("/$storeEngine/cached") { getCachedWorlds(store) } - get("/$storeEngine/update") { updateWorlds(store) } } } } - private fun Call.listFortunes(store: BenchmarkStore, templateKind: String, templateAdapter: TemplatePort) { + private fun HttpServerContext.listFortunes( + store: BenchmarkStore, templateKind: String, templateAdapter: TemplatePort + ): HttpServerContext { val fortunes = store.findAllFortunes() + Fortune(0, "Additional fortune added at request time.") val sortedFortunes = fortunes.sortedBy { it.message } val context = mapOf("fortunes" to sortedFortunes) + val body = templateAdapter.render(templates.require(templateKind), context) - response.contentType = "text/html;charset=utf-8" - ok(templateAdapter.render(templates.require(templateKind), context)) + return ok(body, contentType = html) } - private fun Call.dbQuery(store: BenchmarkStore) { - ok(store.findWorlds(listOf(randomWorld())).first(), Json) + private fun HttpServerContext.dbQuery(store: BenchmarkStore): HttpServerContext { + val ids = listOf(randomWorld()) + val worlds = store.findWorlds(ids) + val world = worlds.first() + + return sendJson(world) } - private fun Call.getWorlds(store: BenchmarkStore) { - val ids = (1..getWorldsCount(settings.queriesParam)).map { randomWorld() } - ok(store.findWorlds(ids), Json) + private fun HttpServerContext.getWorlds(store: BenchmarkStore): HttpServerContext { + val worldsCount = getWorldsCount(queriesParam) + val ids = (1..worldsCount).map { randomWorld() } + val worlds = store.findWorlds(ids) + + return sendJson(worlds) } - private fun Call.getCachedWorlds(store: BenchmarkStore) { - val ids = (1..getWorldsCount(settings.cachedQueriesParam)).map { randomWorld() } - ok(store.findCachedWorlds(ids).map { it.toFieldsMap() }, Json) + private fun HttpServerContext.getCachedWorlds(store: BenchmarkStore): HttpServerContext { + val worldsCount = getWorldsCount(cachedQueriesParam) + val ids = (1..worldsCount).map { randomWorld() } + val worlds = store.findCachedWorlds(ids) + + return sendJson(worlds) } - private fun Call.updateWorlds(store: BenchmarkStore) { - val worlds = (1..getWorldsCount(settings.queriesParam)).map { World(randomWorld(), randomWorld()) } + private fun HttpServerContext.updateWorlds(store: BenchmarkStore): HttpServerContext { + val worldsCount = getWorldsCount(queriesParam) + val worlds = (1..worldsCount).map { World(randomWorld(), randomWorld()) } + store.replaceWorlds(worlds) - ok(worlds, Json) + + return sendJson(worlds) } - private fun Call.getWorldsCount(parameter: String): Int = - queryParametersValues[parameter]?.firstOrNull()?.toIntOrNull().let { + private fun HttpServerContext.sendJson(body: Any): HttpServerContext = + ok(body.serialize(Json), contentType = json) + + private fun HttpServerContext.getWorldsCount(parameter: String): Int = + request.queryParameters[parameter]?.toIntOrNull().let { when { it == null -> 1 it < 1 -> 1 @@ -82,7 +114,7 @@ class Controller(private val settings: Settings) { } private fun randomWorld(): Int = - ThreadLocalRandom.current().nextInt(settings.worldRows) + 1 + ThreadLocalRandom.current().nextInt(worldRows) + 1 private fun urlOrNull(path: String): URL? = try { diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index 94992292acc..71e58b4da42 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -21,6 +21,10 @@ data class Settings( val fortuneName: String = systemSetting("fortuneCollection") ?: "fortune", val databaseName: String = systemSetting("database") ?: "hello_world", + val sendDateHeader: Boolean = systemSetting("sendDateHeader") ?: false, + val sendServerVersion: Boolean = systemSetting("sendServerVersion") ?: true, + val sendXPoweredBy: Boolean = systemSetting("sendXPoweredBy") ?: false, + val worldRows: Int = 10_000, val textMessage: String = "Hello, World!", val queriesParam: String = "queries", diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index 81a912606f1..1c95b0881ad 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -1,17 +1,7 @@ package com.hexagonkt -import com.fasterxml.jackson.module.blackbird.BlackbirdModule import com.hexagonkt.http.server.servlet.ServletServer -import com.hexagonkt.serialization.json.JacksonMapper -import com.hexagonkt.serialization.json.Json -import com.hexagonkt.serialization.SerializationManager -import javax.servlet.annotation.WebListener +import jakarta.servlet.annotation.WebListener -@WebListener class WebListenerServer(settings: Settings = Settings()) : ServletServer(Controller(settings).router) { - - init { - Json.mapper.registerModule(BlackbirdModule()) - SerializationManager.mapper = JacksonMapper - SerializationManager.formats = linkedSetOf(Json) - } -} +@WebListener class WebListenerServer(settings: Settings = Settings()) : + ServletServer(listOf(Controller(settings, stores, templateEngines).path)) From f8236d58e88a8f2f9c96e13e59ecbafda1f19590 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 8 Jan 2022 11:37:09 +0100 Subject: [PATCH 017/105] Use Hexagon version 2.0.0-B1 (and a little cleanup) --- frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index 71e58b4da42..2506fb74e43 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -21,7 +21,7 @@ data class Settings( val fortuneName: String = systemSetting("fortuneCollection") ?: "fortune", val databaseName: String = systemSetting("database") ?: "hello_world", - val sendDateHeader: Boolean = systemSetting("sendDateHeader") ?: false, + val sendDateHeader: Boolean = systemSetting("sendDateHeader") ?: true, val sendServerVersion: Boolean = systemSetting("sendServerVersion") ?: true, val sendXPoweredBy: Boolean = systemSetting("sendXPoweredBy") ?: false, From a344738f4c806abc98693cad622fa0188b76b679 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 8 Jan 2022 15:19:37 +0100 Subject: [PATCH 018/105] Use Tomcat instead Resin to test JEE integration --- frameworks/Kotlin/hexagon/README.md | 2 +- .../Kotlin/hexagon/benchmark_config.json | 4 ++-- frameworks/Kotlin/hexagon/config.toml | 2 +- ...n.dockerfile => hexagon-tomcat.dockerfile} | 8 ++------ .../hexagon/src/main/kotlin/Controller.kt | 12 ++--------- .../hexagon/src/main/kotlin/Settings.kt | 1 + .../src/main/kotlin/WebListenerServer.kt | 20 +++++++++++++++++-- .../main/kotlin/store/BenchmarkSqlStore.kt | 5 +++-- .../src/main/kotlin/store/BenchmarkStore.kt | 4 ++-- 9 files changed, 32 insertions(+), 26 deletions(-) rename frameworks/Kotlin/hexagon/{hexagon-resin.dockerfile => hexagon-tomcat.dockerfile} (61%) diff --git a/frameworks/Kotlin/hexagon/README.md b/frameworks/Kotlin/hexagon/README.md index 54c66442a82..b83921aecdc 100644 --- a/frameworks/Kotlin/hexagon/README.md +++ b/frameworks/Kotlin/hexagon/README.md @@ -31,7 +31,7 @@ and `${TEMPLATE_ENGINE}` with: `pebble` * Database updates: http://localhost:9090/${DB_ENGINE}/update * Database queries: http://localhost:9090/${DB_ENGINE}/query -### Resin +### Tomcat * JSON Encoding Test: http://localhost:8080/json * Plain Text Test: http://localhost:8080/plaintext diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 7bca1a660ad..78527517668 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -25,7 +25,7 @@ "notes": "http://hexagonkt.com", "versus": "servlet" }, - "resin": { + "tomcat": { "json_url": "/json", "db_url": "/postgresql/db", "query_url": "/postgresql/query?queries=", @@ -44,7 +44,7 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Resin PostgreSQL", + "display_name": "Hexagon Tomcat PostgreSQL", "notes": "http://hexagonkt.com", "versus": "servlet" } diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index c688baad5a8..886a19b270f 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -19,7 +19,7 @@ platform = "Servlet" webserver = "None" versus = "servlet" -[resin] +[tomcat] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/postgresql/db" diff --git a/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile similarity index 61% rename from frameworks/Kotlin/hexagon/hexagon-resin.dockerfile rename to frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index 3bc3ddb7838..3351663c034 100644 --- a/frameworks/Kotlin/hexagon/hexagon-resin.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -12,15 +12,11 @@ RUN gradle --quiet # # RUNTIME # -FROM adoptopenjdk:11-jre-hotspot-bionic +FROM tomcat:10.0.14-jre17-temurin ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database -ENV RESIN http://caucho.com/download/resin-4.0.65.tar.gz -WORKDIR /resin -RUN curl -sL $RESIN | tar xz --strip-components=1 -RUN rm -rf webapps/* +WORKDIR /usr/local/tomcat COPY --from=gradle_build /hexagon/build/libs/ROOT.war webapps/ROOT.war COPY src/main/resources/fortunes.pebble.html fortunes.pebble.html EXPOSE 8080 -CMD ["java", "-jar", "lib/resin.jar", "console"] diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index c77cc9de631..dc8045343cf 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -18,7 +18,7 @@ import java.util.concurrent.ThreadLocalRandom import kotlin.text.Charsets.UTF_8 -internal class Controller( +class Controller( settings: Settings, stores: Map, templateEngines: Map, @@ -32,7 +32,7 @@ internal class Controller( private val html: ContentType = ContentType(HTML, charset = UTF_8) private val templates: Map = mapOf( - "pebble" to (urlOrNull("classpath:fortunes.pebble.html") ?: URL("file:/resin/fortunes.pebble.html")) + "pebble" to URL("classpath:fortunes.pebble.html") ) internal val path: PathHandler by lazy { @@ -115,12 +115,4 @@ internal class Controller( private fun randomWorld(): Int = ThreadLocalRandom.current().nextInt(worldRows) + 1 - - private fun urlOrNull(path: String): URL? = - try { - URL(path) - } - catch (e: Exception) { - null - } } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index 2506fb74e43..148b69b62f0 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -20,6 +20,7 @@ data class Settings( val worldName: String = systemSetting("worldCollection") ?: "world", val fortuneName: String = systemSetting("fortuneCollection") ?: "fortune", val databaseName: String = systemSetting("database") ?: "hello_world", + val databaseDriver: String = systemSetting("databaseDriver") ?: "org.postgresql.Driver", val sendDateHeader: Boolean = systemSetting("sendDateHeader") ?: true, val sendServerVersion: Boolean = systemSetting("sendServerVersion") ?: true, diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index 1c95b0881ad..ab8752055bd 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -1,7 +1,23 @@ package com.hexagonkt +import com.hexagonkt.core.helpers.multiMapOf +import com.hexagonkt.http.server.handlers.HttpHandler +import com.hexagonkt.http.server.handlers.OnHandler import com.hexagonkt.http.server.servlet.ServletServer import jakarta.servlet.annotation.WebListener -@WebListener class WebListenerServer(settings: Settings = Settings()) : - ServletServer(listOf(Controller(settings, stores, templateEngines).path)) +@WebListener class WebListenerServer(settings: Settings = Settings()) : ServletServer(createHandlers(settings)) { + + private companion object { + + fun createHandlers(settings: Settings): List { + val controller = Controller(settings, stores, templateEngines) + val controllerPath = controller.path + val serverHeaderHandler = OnHandler { + send(headers = multiMapOf("server" to "Tomcat")) + } + + return listOf(serverHeaderHandler, controllerPath) + } + } +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index acf4e978a6a..d1f4ae726e3 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -27,8 +27,9 @@ internal class BenchmarkSqlStore(engine: String, private val settings: Settings val config = HikariConfig().apply { jdbcUrl = "jdbc:postgresql://$dbHost/${settings.databaseName}" maximumPoolSize = Jvm.systemSetting(Int::class, "maximumPoolSize") ?: poolSize - username = Jvm.systemSetting("databaseUsername") ?: "benchmarkdbuser" - password = Jvm.systemSetting("databasePassword") ?: "benchmarkdbpass" + driverClassName = settings.databaseDriver + username = settings.databaseUsername + password = settings.databasePassword } HikariDataSource(config) } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt index 30eaeb9dfc4..2c6ce918128 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt @@ -7,7 +7,7 @@ import com.hexagonkt.World import org.cache2k.Cache import org.cache2k.Cache2kBuilder -internal abstract class BenchmarkStore(settings: Settings) { +abstract class BenchmarkStore(settings: Settings) { abstract fun findAllFortunes(): List abstract fun findWorlds(ids: List): List @@ -30,4 +30,4 @@ internal abstract class BenchmarkStore(settings: Settings) { fun findCachedWorlds(ids: List): List { return ids.mapNotNull { worldsCache.get(it) } } -} \ No newline at end of file +} From 06fe67aaed0de9b54242b70d93d53c4a40e14d24 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 8 Jan 2022 15:53:24 +0100 Subject: [PATCH 019/105] Remove unused environment variable --- frameworks/Kotlin/hexagon/hexagon.dockerfile | 1 - 1 file changed, 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 28a74cb7352..3d1dab5fb55 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -17,7 +17,6 @@ ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE jetty ENV PROJECT hexagon -ENV ENABLE_BLACKBIRD true COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT From 0f7fff4b78c1bcf21358b175574b4b8db41d8cd9 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 8 Jan 2022 18:21:13 +0100 Subject: [PATCH 020/105] Clean Tomcat dockerfile --- frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index 3351663c034..ae472669f14 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -16,7 +16,5 @@ FROM tomcat:10.0.14-jre17-temurin ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database -WORKDIR /usr/local/tomcat -COPY --from=gradle_build /hexagon/build/libs/ROOT.war webapps/ROOT.war -COPY src/main/resources/fortunes.pebble.html fortunes.pebble.html +COPY --from=gradle_build /hexagon/build/libs/ROOT.war /usr/local/tomcat/webapps/ROOT.war EXPOSE 8080 From 516f4c5da773165c50721c2e4e446988d2deb4cb Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 8 Jan 2022 18:58:35 +0100 Subject: [PATCH 021/105] Minor improvements --- frameworks/Kotlin/hexagon/build.gradle | 4 ++-- frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt | 2 +- frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt | 4 ++-- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index a737206edd9..915f4a3e4e3 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,9 +4,9 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0-B1/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0-B2/gradle" - hexagonVersion = "2.0.0-B1" + hexagonVersion = "2.0.0-B2" hikariVersion = "5.0.0" jettyVersion = "11.0.7" postgresqlVersion = "42.3.1" diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index c8174411b35..00b895d74ea 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -36,7 +36,7 @@ private val server: HttpServer by lazy { ), ) - HttpServer(engine, listOf(controller.path), serverSettings) + HttpServer(engine, controller.path, serverSettings) } fun main() { diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index dc8045343cf..8ecb1eb527f 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -38,7 +38,7 @@ class Controller( internal val path: PathHandler by lazy { path { get("/plaintext") { ok(settings.textMessage, contentType = plain) } - get("/json") { ok(Message(settings.textMessage).serialize(Json), contentType = json) } + get("/json") { ok(Message(settings.textMessage).serialize(Json.raw), contentType = json) } stores.forEach { (storeEngine, store) -> path("/$storeEngine") { @@ -101,7 +101,7 @@ class Controller( } private fun HttpServerContext.sendJson(body: Any): HttpServerContext = - ok(body.serialize(Json), contentType = json) + ok(body.serialize(Json.raw), contentType = json) private fun HttpServerContext.getWorldsCount(parameter: String): Int = request.queryParameters[parameter]?.toIntOrNull().let { From 9e4176a2da4267e5abc60362cbd620e9e1b50f6d Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jan 2022 15:03:37 +0100 Subject: [PATCH 022/105] Minor improvements --- frameworks/Kotlin/hexagon/build.gradle | 4 ++-- .../Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 915f4a3e4e3..43dc7c28bc4 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,9 +4,9 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0-B2/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0-B3/gradle" - hexagonVersion = "2.0.0-B2" + hexagonVersion = "2.0.0-B3" hikariVersion = "5.0.0" jettyVersion = "11.0.7" postgresqlVersion = "42.3.1" diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index ab8752055bd..0794bda5ef4 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -13,7 +13,7 @@ import jakarta.servlet.annotation.WebListener fun createHandlers(settings: Settings): List { val controller = Controller(settings, stores, templateEngines) val controllerPath = controller.path - val serverHeaderHandler = OnHandler { + val serverHeaderHandler = OnHandler("*") { send(headers = multiMapOf("server" to "Tomcat")) } From ccd6fc40d966e0eece147ed247c83f15aa854e51 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 13 Jan 2022 17:59:54 +0100 Subject: [PATCH 023/105] Update to release version --- frameworks/Kotlin/hexagon/build.gradle | 4 ++-- frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt | 2 +- frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt | 2 +- .../Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt | 2 +- .../Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt | 2 +- 5 files changed, 6 insertions(+), 6 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 43dc7c28bc4..b8d18ca7a89 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,9 +4,9 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0-B3/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0/gradle" - hexagonVersion = "2.0.0-B3" + hexagonVersion = "2.0.0" hikariVersion = "5.0.0" jettyVersion = "11.0.7" postgresqlVersion = "42.3.1" diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 8ecb1eb527f..71d770cbb62 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -1,6 +1,6 @@ package com.hexagonkt -import com.hexagonkt.core.helpers.require +import com.hexagonkt.core.require import com.hexagonkt.core.media.ApplicationMedia.JSON import com.hexagonkt.core.media.TextMedia.HTML import com.hexagonkt.core.media.TextMedia.PLAIN diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index 148b69b62f0..cc1fe17ce0c 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -1,6 +1,6 @@ package com.hexagonkt -import com.hexagonkt.core.helpers.Jvm.systemSetting +import com.hexagonkt.core.Jvm.systemSetting data class Settings( val bindPort: Int = systemSetting("bindPort") ?: 9090, diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index 0794bda5ef4..eec6f2571d3 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -1,6 +1,6 @@ package com.hexagonkt -import com.hexagonkt.core.helpers.multiMapOf +import com.hexagonkt.core.multiMapOf import com.hexagonkt.http.server.handlers.HttpHandler import com.hexagonkt.http.server.handlers.OnHandler import com.hexagonkt.http.server.servlet.ServletServer diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index d1f4ae726e3..2c3d20939f7 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -4,7 +4,7 @@ import com.hexagonkt.CachedWorld import com.hexagonkt.Fortune import com.hexagonkt.Settings import com.hexagonkt.World -import com.hexagonkt.core.helpers.Jvm +import com.hexagonkt.core.Jvm import com.zaxxer.hikari.HikariConfig import com.zaxxer.hikari.HikariDataSource import org.cache2k.Cache From f641771f5e907f3ff0bbcbc8b025ebbd6be16727 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 26 Jan 2022 19:32:40 +0100 Subject: [PATCH 024/105] Update to the latest Hexagon release --- frameworks/Kotlin/hexagon/build.gradle | 6 ++--- .../hexagon/src/main/kotlin/Settings.kt | 22 +++++++++---------- .../main/kotlin/store/BenchmarkSqlStore.kt | 6 ++--- 3 files changed, 17 insertions(+), 17 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index b8d18ca7a89..fe6101d4d62 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,10 +4,10 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.0/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.2/gradle" - hexagonVersion = "2.0.0" - hikariVersion = "5.0.0" + hexagonVersion = "2.0.2" + hikariVersion = "5.0.1" jettyVersion = "11.0.7" postgresqlVersion = "42.3.1" cache2kVersion = "2.4.1.Final" diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index cc1fe17ce0c..53b82c5181d 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -1,9 +1,9 @@ package com.hexagonkt -import com.hexagonkt.core.Jvm.systemSetting +import com.hexagonkt.core.Jvm.systemSettingOrNull data class Settings( - val bindPort: Int = systemSetting("bindPort") ?: 9090, + val bindPort: Int = systemSettingOrNull("bindPort") ?: 9090, val bindAddress: String = "0.0.0.0", val database: String = "hello_world", @@ -13,18 +13,18 @@ data class Settings( val databaseUsername: String = "benchmarkdbuser", val databasePassword: String = "benchmarkdbpass", - val maximumPoolSize: Int = systemSetting("maximumPoolSize") ?: 96, + val maximumPoolSize: Int = systemSettingOrNull("maximumPoolSize") ?: 96, - val webEngine: String = systemSetting("WEBENGINE") ?: "jetty", + val webEngine: String = systemSettingOrNull("WEBENGINE") ?: "jetty", - val worldName: String = systemSetting("worldCollection") ?: "world", - val fortuneName: String = systemSetting("fortuneCollection") ?: "fortune", - val databaseName: String = systemSetting("database") ?: "hello_world", - val databaseDriver: String = systemSetting("databaseDriver") ?: "org.postgresql.Driver", + val worldName: String = systemSettingOrNull("worldCollection") ?: "world", + val fortuneName: String = systemSettingOrNull("fortuneCollection") ?: "fortune", + val databaseName: String = systemSettingOrNull("database") ?: "hello_world", + val databaseDriver: String = systemSettingOrNull("databaseDriver") ?: "org.postgresql.Driver", - val sendDateHeader: Boolean = systemSetting("sendDateHeader") ?: true, - val sendServerVersion: Boolean = systemSetting("sendServerVersion") ?: true, - val sendXPoweredBy: Boolean = systemSetting("sendXPoweredBy") ?: false, + val sendDateHeader: Boolean = systemSettingOrNull("sendDateHeader") ?: true, + val sendServerVersion: Boolean = systemSettingOrNull("sendServerVersion") ?: true, + val sendXPoweredBy: Boolean = systemSettingOrNull("sendXPoweredBy") ?: false, val worldRows: Int = 10_000, val textMessage: String = "Hello, World!", diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index 2c3d20939f7..3a724dd900e 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -21,12 +21,12 @@ internal class BenchmarkSqlStore(engine: String, private val settings: Settings } private val dataSource: HikariDataSource by lazy { - val dbHost = Jvm.systemSetting("${engine.uppercase()}_DB_HOST") ?: "localhost" - val environment = Jvm.systemSetting(String::class, "BENCHMARK_ENV")?.lowercase() + val dbHost = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "localhost" + val environment = Jvm.systemSettingOrNull(String::class, "BENCHMARK_ENV")?.lowercase() val poolSize = 8 + if (environment == "citrine") Jvm.cpuCount else Jvm.cpuCount * 2 val config = HikariConfig().apply { jdbcUrl = "jdbc:postgresql://$dbHost/${settings.databaseName}" - maximumPoolSize = Jvm.systemSetting(Int::class, "maximumPoolSize") ?: poolSize + maximumPoolSize = Jvm.systemSettingOrNull(Int::class, "maximumPoolSize") ?: poolSize driverClassName = settings.databaseDriver username = settings.databaseUsername password = settings.databasePassword From a41e4f629de4b456b73c00c2a1f9921d1356ed9d Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 16 Feb 2022 11:32:43 +0100 Subject: [PATCH 025/105] Add Netty adapter test --- .../Kotlin/hexagon/benchmark_config.json | 25 ++++++++++++++++++- frameworks/Kotlin/hexagon/build.gradle | 11 ++++---- frameworks/Kotlin/hexagon/config.toml | 20 ++++++++++++++- .../Kotlin/hexagon/hexagon-netty.dockerfile | 25 +++++++++++++++++++ .../Kotlin/hexagon/hexagon-tomcat.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 2 +- .../hexagon/src/main/kotlin/Benchmark.kt | 18 +++++++------ .../hexagon/src/main/kotlin/Controller.kt | 12 +++++++++ .../hexagon/src/main/kotlin/Settings.kt | 4 +-- 9 files changed, 101 insertions(+), 18 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/hexagon-netty.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 78527517668..d7186d7d9e8 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -25,6 +25,29 @@ "notes": "http://hexagonkt.com", "versus": "servlet" }, + "netty": { + "json_url": "/json", + "db_url": "/postgresql/db", + "query_url": "/postgresql/query?queries=", + "fortune_url": "/postgresql/pebble/fortunes", + "update_url": "/postgresql/update?queries=", + "cached_query_url": "/postgresql/cached?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Netty", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Netty PostgreSQL", + "notes": "http://hexagonkt.com", + "versus": "netty" + }, "tomcat": { "json_url": "/json", "db_url": "/postgresql/db", @@ -41,7 +64,7 @@ "language": "Kotlin", "orm": "Raw", "platform": "Servlet", - "webserver": "None", + "webserver": "Tomcat", "os": "Linux", "database_os": "Linux", "display_name": "Hexagon Tomcat PostgreSQL", diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index fe6101d4d62..dd9480a848c 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,13 +4,13 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.2/gradle" + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.3/gradle" - hexagonVersion = "2.0.2" + hexagonVersion = "2.0.3" hikariVersion = "5.0.1" - jettyVersion = "11.0.7" - postgresqlVersion = "42.3.1" - cache2kVersion = "2.4.1.Final" + jettyVersion = "11.0.8" + postgresqlVersion = "42.3.3" + cache2kVersion = "2.6.1.Final" } apply(from: "$gradleScripts/kotlin.gradle") @@ -31,6 +31,7 @@ war { installDist.dependsOn("war") dependencies { + implementation("com.hexagonkt:http_server_netty:$hexagonVersion") implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index 886a19b270f..91b846defad 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -19,6 +19,24 @@ platform = "Servlet" webserver = "None" versus = "servlet" +[netty] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/postgresql/db" +urls.query = "/postgresql/query?queries=" +urls.update = "/postgresql/update?queries=" +urls.fortune = "/postgresql/pebble/fortunes" +urls.cached_query = "/postgresql/cached?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Netty" +webserver = "None" +versus = "netty" + [tomcat] urls.plaintext = "/plaintext" urls.json = "/json" @@ -34,5 +52,5 @@ database_os = "Linux" os = "Linux" orm = "Raw" platform = "Servlet" -webserver = "None" +webserver = "Tomcat" versus = "servlet" diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile new file mode 100644 index 00000000000..fad88b2d257 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -0,0 +1,25 @@ +# +# BUILD +# +FROM gradle:7.4-jdk11 AS gradle_build +USER root +WORKDIR /hexagon + +COPY src src +COPY build.gradle build.gradle +RUN gradle --quiet + +# +# RUNTIME +# +FROM adoptopenjdk:11-jre-hotspot-bionic +ENV DBSTORE postgresql +ENV POSTGRESQL_DB_HOST tfb-database +ENV WEBENGINE netty +ENV PROJECT hexagon + +COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT + +EXPOSE 9090 + +ENTRYPOINT /opt/$PROJECT/bin/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index ae472669f14..e8ad5a4e2ec 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.2-jdk11 AS gradle_build +FROM gradle:7.4-jdk11 AS gradle_build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 3d1dab5fb55..1c50885a34a 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.3.3-jdk11 AS gradle_build +FROM gradle:7.4-jdk11 AS gradle_build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index 00b895d74ea..70ab0ba2cf2 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -4,12 +4,15 @@ import com.hexagonkt.http.server.HttpServer import com.hexagonkt.http.server.HttpServerPort import com.hexagonkt.http.server.HttpServerSettings import com.hexagonkt.http.server.jetty.JettyServletAdapter +import com.hexagonkt.http.server.netty.NettyServerAdapter import com.hexagonkt.store.BenchmarkSqlStore import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort import com.hexagonkt.templates.pebble.PebbleAdapter import java.net.InetAddress +internal val settings = Settings() + internal val stores: Map by lazy { mapOf("postgresql" to BenchmarkSqlStore("postgresql")) } @@ -19,21 +22,22 @@ internal val templateEngines: Map by lazy { } private val engines: Map by lazy { - mapOf("jetty" to JettyServletAdapter()) + mapOf( + "jetty" to JettyServletAdapter( + sendDateHeader = settings.sendDateHeader, + sendServerVersion = settings.sendServerVersion, + sendXPoweredBy = settings.sendXPoweredBy, + ), + "netty" to NettyServerAdapter(), + ) } private val server: HttpServer by lazy { - val settings = Settings() val engine = engines[settings.webEngine] ?: error("Unsupported server engine") val controller = Controller(settings, stores, templateEngines) val serverSettings = HttpServerSettings( bindAddress = InetAddress.getByName(settings.bindAddress), bindPort = settings.bindPort, - options = mapOf( - "sendDateHeader" to settings.sendDateHeader, - "sendServerVersion" to settings.sendServerVersion, - "sendXPoweredBy" to settings.sendXPoweredBy, - ), ) HttpServer(engine, controller.path, serverSettings) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 71d770cbb62..1454f9f37cc 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -4,16 +4,19 @@ import com.hexagonkt.core.require import com.hexagonkt.core.media.ApplicationMedia.JSON import com.hexagonkt.core.media.TextMedia.HTML import com.hexagonkt.core.media.TextMedia.PLAIN +import com.hexagonkt.core.multiMapOf import com.hexagonkt.http.model.ContentType import com.hexagonkt.http.server.handlers.HttpServerContext import com.hexagonkt.http.server.handlers.PathHandler import com.hexagonkt.http.server.handlers.path +import com.hexagonkt.http.toHttpFormat import com.hexagonkt.serialization.jackson.json.Json import com.hexagonkt.serialization.serialize import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort import java.net.URL +import java.time.LocalDateTime.now import java.util.concurrent.ThreadLocalRandom import kotlin.text.Charsets.UTF_8 @@ -37,6 +40,15 @@ class Controller( internal val path: PathHandler by lazy { path { + on("*") { + val headers = multiMapOf( + "server" to "Hexagon", + "date" to now().toHttpFormat(), + ) + + send(headers = headers) + } + get("/plaintext") { ok(settings.textMessage, contentType = plain) } get("/json") { ok(Message(settings.textMessage).serialize(Json.raw), contentType = json) } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index 53b82c5181d..e5c9994f856 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -22,8 +22,8 @@ data class Settings( val databaseName: String = systemSettingOrNull("database") ?: "hello_world", val databaseDriver: String = systemSettingOrNull("databaseDriver") ?: "org.postgresql.Driver", - val sendDateHeader: Boolean = systemSettingOrNull("sendDateHeader") ?: true, - val sendServerVersion: Boolean = systemSettingOrNull("sendServerVersion") ?: true, + val sendDateHeader: Boolean = systemSettingOrNull("sendDateHeader") ?: false, + val sendServerVersion: Boolean = systemSettingOrNull("sendServerVersion") ?: false, val sendXPoweredBy: Boolean = systemSettingOrNull("sendXPoweredBy") ?: false, val worldRows: Int = 10_000, From 138c9d30c9ca1d11414fd641f4ed9c3ff005d602 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 16 Feb 2022 11:53:50 +0100 Subject: [PATCH 026/105] Remove Gradle Wrapper --- frameworks/Kotlin/hexagon/gradlew | 183 -------------------------- frameworks/Kotlin/hexagon/gradlew.bat | 103 --------------- 2 files changed, 286 deletions(-) delete mode 100755 frameworks/Kotlin/hexagon/gradlew delete mode 100644 frameworks/Kotlin/hexagon/gradlew.bat diff --git a/frameworks/Kotlin/hexagon/gradlew b/frameworks/Kotlin/hexagon/gradlew deleted file mode 100755 index 2fe81a7d95e..00000000000 --- a/frameworks/Kotlin/hexagon/gradlew +++ /dev/null @@ -1,183 +0,0 @@ -#!/usr/bin/env sh - -# -# Copyright 2015 the original author or authors. -# -# Licensed 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 -# -# https://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. -# - -############################################################################## -## -## Gradle start up script for UN*X -## -############################################################################## - -# Attempt to set APP_HOME -# Resolve links: $0 may be a link -PRG="$0" -# Need this for relative symlinks. -while [ -h "$PRG" ] ; do - ls=`ls -ld "$PRG"` - link=`expr "$ls" : '.*-> \(.*\)$'` - if expr "$link" : '/.*' > /dev/null; then - PRG="$link" - else - PRG=`dirname "$PRG"`"/$link" - fi -done -SAVED="`pwd`" -cd "`dirname \"$PRG\"`/" >/dev/null -APP_HOME="`pwd -P`" -cd "$SAVED" >/dev/null - -APP_NAME="Gradle" -APP_BASE_NAME=`basename "$0"` - -# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. -DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' - -# Use the maximum available, or set MAX_FD != -1 to use that value. -MAX_FD="maximum" - -warn () { - echo "$*" -} - -die () { - echo - echo "$*" - echo - exit 1 -} - -# OS specific support (must be 'true' or 'false'). -cygwin=false -msys=false -darwin=false -nonstop=false -case "`uname`" in - CYGWIN* ) - cygwin=true - ;; - Darwin* ) - darwin=true - ;; - MINGW* ) - msys=true - ;; - NONSTOP* ) - nonstop=true - ;; -esac - -CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar - -# Determine the Java command to use to start the JVM. -if [ -n "$JAVA_HOME" ] ; then - if [ -x "$JAVA_HOME/jre/sh/java" ] ; then - # IBM's JDK on AIX uses strange locations for the executables - JAVACMD="$JAVA_HOME/jre/sh/java" - else - JAVACMD="$JAVA_HOME/bin/java" - fi - if [ ! -x "$JAVACMD" ] ; then - die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME - -Please set the JAVA_HOME variable in your environment to match the -location of your Java installation." - fi -else - JAVACMD="java" - which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. - -Please set the JAVA_HOME variable in your environment to match the -location of your Java installation." -fi - -# Increase the maximum file descriptors if we can. -if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then - MAX_FD_LIMIT=`ulimit -H -n` - if [ $? -eq 0 ] ; then - if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then - MAX_FD="$MAX_FD_LIMIT" - fi - ulimit -n $MAX_FD - if [ $? -ne 0 ] ; then - warn "Could not set maximum file descriptor limit: $MAX_FD" - fi - else - warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" - fi -fi - -# For Darwin, add options to specify how the application appears in the dock -if $darwin; then - GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" -fi - -# For Cygwin or MSYS, switch paths to Windows format before running java -if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then - APP_HOME=`cygpath --path --mixed "$APP_HOME"` - CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` - JAVACMD=`cygpath --unix "$JAVACMD"` - - # We build the pattern for arguments to be converted via cygpath - ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` - SEP="" - for dir in $ROOTDIRSRAW ; do - ROOTDIRS="$ROOTDIRS$SEP$dir" - SEP="|" - done - OURCYGPATTERN="(^($ROOTDIRS))" - # Add a user-defined pattern to the cygpath arguments - if [ "$GRADLE_CYGPATTERN" != "" ] ; then - OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" - fi - # Now convert the arguments - kludge to limit ourselves to /bin/sh - i=0 - for arg in "$@" ; do - CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` - CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option - - if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition - eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` - else - eval `echo args$i`="\"$arg\"" - fi - i=`expr $i + 1` - done - case $i in - 0) set -- ;; - 1) set -- "$args0" ;; - 2) set -- "$args0" "$args1" ;; - 3) set -- "$args0" "$args1" "$args2" ;; - 4) set -- "$args0" "$args1" "$args2" "$args3" ;; - 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; - 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; - 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; - 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; - 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; - esac -fi - -# Escape application args -save () { - for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done - echo " " -} -APP_ARGS=`save "$@"` - -# Collect all arguments for the java command, following the shell quoting and substitution rules -eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" - -exec "$JAVACMD" "$@" diff --git a/frameworks/Kotlin/hexagon/gradlew.bat b/frameworks/Kotlin/hexagon/gradlew.bat deleted file mode 100644 index 62bd9b9ccef..00000000000 --- a/frameworks/Kotlin/hexagon/gradlew.bat +++ /dev/null @@ -1,103 +0,0 @@ -@rem -@rem Copyright 2015 the original author or authors. -@rem -@rem Licensed under the Apache License, Version 2.0 (the "License"); -@rem you may not use this file except in compliance with the License. -@rem You may obtain a copy of the License at -@rem -@rem https://www.apache.org/licenses/LICENSE-2.0 -@rem -@rem Unless required by applicable law or agreed to in writing, software -@rem distributed under the License is distributed on an "AS IS" BASIS, -@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -@rem See the License for the specific language governing permissions and -@rem limitations under the License. -@rem - -@if "%DEBUG%" == "" @echo off -@rem ########################################################################## -@rem -@rem Gradle startup script for Windows -@rem -@rem ########################################################################## - -@rem Set local scope for the variables with windows NT shell -if "%OS%"=="Windows_NT" setlocal - -set DIRNAME=%~dp0 -if "%DIRNAME%" == "" set DIRNAME=. -set APP_BASE_NAME=%~n0 -set APP_HOME=%DIRNAME% - -@rem Resolve any "." and ".." in APP_HOME to make it shorter. -for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi - -@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. -set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" - -@rem Find java.exe -if defined JAVA_HOME goto findJavaFromJavaHome - -set JAVA_EXE=java.exe -%JAVA_EXE% -version >NUL 2>&1 -if "%ERRORLEVEL%" == "0" goto init - -echo. -echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. -echo. -echo Please set the JAVA_HOME variable in your environment to match the -echo location of your Java installation. - -goto fail - -:findJavaFromJavaHome -set JAVA_HOME=%JAVA_HOME:"=% -set JAVA_EXE=%JAVA_HOME%/bin/java.exe - -if exist "%JAVA_EXE%" goto init - -echo. -echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% -echo. -echo Please set the JAVA_HOME variable in your environment to match the -echo location of your Java installation. - -goto fail - -:init -@rem Get command-line arguments, handling Windows variants - -if not "%OS%" == "Windows_NT" goto win9xME_args - -:win9xME_args -@rem Slurp the command line arguments. -set CMD_LINE_ARGS= -set _SKIP=2 - -:win9xME_args_slurp -if "x%~1" == "x" goto execute - -set CMD_LINE_ARGS=%* - -:execute -@rem Setup the command line - -set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar - -@rem Execute Gradle -"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS% - -:end -@rem End local scope for the variables with windows NT shell -if "%ERRORLEVEL%"=="0" goto mainEnd - -:fail -rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of -rem the _cmd.exe /c_ return code! -if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 -exit /b 1 - -:mainEnd -if "%OS%"=="Windows_NT" endlocal - -:omega From 2ca72bcf914aae64a7beafc4a093a36872626148 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 18 Feb 2022 15:43:03 +0100 Subject: [PATCH 027/105] Update version --- frameworks/Kotlin/hexagon/build.gradle | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index dd9480a848c..a6c80ec4975 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,13 +4,13 @@ plugins { } ext { - gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/2.0.3/gradle" - - hexagonVersion = "2.0.3" + hexagonVersion = "2.0.4" hikariVersion = "5.0.1" jettyVersion = "11.0.8" postgresqlVersion = "42.3.3" cache2kVersion = "2.6.1.Final" + + gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } apply(from: "$gradleScripts/kotlin.gradle") From 7c1e0607cf9050c4bbcb22781ea62aef269e2647 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 21 Feb 2022 20:43:06 +0100 Subject: [PATCH 028/105] Update version --- frameworks/Kotlin/hexagon/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index a6c80ec4975..b5de5912a03 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,7 +4,7 @@ plugins { } ext { - hexagonVersion = "2.0.4" + hexagonVersion = "2.0.5" hikariVersion = "5.0.1" jettyVersion = "11.0.8" postgresqlVersion = "42.3.3" From 5a0fe666300550792907ada2864eb694ab8af1f2 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 1 Apr 2022 08:08:23 +0200 Subject: [PATCH 029/105] Minimize template --- frameworks/Kotlin/hexagon/build.gradle | 10 ++++++++++ frameworks/Kotlin/hexagon/hexagon.dockerfile | 1 + 2 files changed, 11 insertions(+) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index b5de5912a03..50eec566d02 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -44,3 +44,13 @@ dependencies { // providedCompile excludes the dependency only in the WAR, not in the distribution providedCompile("org.eclipse.jetty:jetty-webapp:$jettyVersion") { exclude module: "slf4j-api" } } + +task("minimizeTemplate") { + doLast { + File template = file("$buildDir/resources/main/fortunes.pebble.html") + List lines = template.readLines().collect { it.trim() } + template.write(lines.join("")) + } +} + +assemble.dependsOn("minimizeTemplate") diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 1c50885a34a..4ca671e517d 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -17,6 +17,7 @@ ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE jetty ENV PROJECT hexagon +ENV DISABLE_CHECKS true COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT From 9c200b4391faf5fb2e2fdfaef10ad8ddae7c1db0 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 18 Apr 2022 18:38:20 +0200 Subject: [PATCH 030/105] Skip Hexagon checks in the container --- frameworks/Kotlin/hexagon/hexagon-netty.dockerfile | 1 + frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile | 1 + 2 files changed, 2 insertions(+) diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index fad88b2d257..95f35051bc8 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -17,6 +17,7 @@ ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE netty ENV PROJECT hexagon +ENV DISABLE_CHECKS true COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index e8ad5a4e2ec..27b931d8626 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -15,6 +15,7 @@ RUN gradle --quiet FROM tomcat:10.0.14-jre17-temurin ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database +ENV DISABLE_CHECKS true COPY --from=gradle_build /hexagon/build/libs/ROOT.war /usr/local/tomcat/webapps/ROOT.war EXPOSE 8080 From cf21e3c3fa9fab60dae117f3d7b87c1e90b3f83c Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 29 Apr 2022 09:19:45 +0200 Subject: [PATCH 031/105] Add Netty Epoll benchmark --- frameworks/Kotlin/hexagon/README.md | 26 ++++++++++++++++--- .../Kotlin/hexagon/benchmark_config.json | 23 ++++++++++++++++ frameworks/Kotlin/hexagon/build.gradle | 11 +++++--- frameworks/Kotlin/hexagon/config.toml | 18 +++++++++++++ .../Kotlin/hexagon/hexagon-netty.dockerfile | 4 +-- .../hexagon/hexagon-nettyepoll.dockerfile | 26 +++++++++++++++++++ .../Kotlin/hexagon/hexagon-tomcat.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 4 +-- .../hexagon/src/main/kotlin/Benchmark.kt | 2 ++ 9 files changed, 103 insertions(+), 13 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile diff --git a/frameworks/Kotlin/hexagon/README.md b/frameworks/Kotlin/hexagon/README.md index b83921aecdc..779811d7c31 100644 --- a/frameworks/Kotlin/hexagon/README.md +++ b/frameworks/Kotlin/hexagon/README.md @@ -6,11 +6,11 @@ of web development platforms. The test utilizes Hexagon routes, serialization an ## Tests -You can run tests against any running server passing the `verify.endpoint` project property. I.e.: -`./gradlew verify -Pverify.endpoint=http://host:1234` +You can verify the benchmarks with the following command (from the project root): +`./tfb --mode verify --test hexagon hexagon-jetty hexagon-tomcat hexagon-netty hexagon-nettyepoll` -* [Hexagon Web](src/main/kotlin/com/hexagonkt/Benchmark.kt) -* [Hexagon Storage](src/main/kotlin/com/hexagonkt/BenchmarkStorage.kt) +To run the full benchmarks locally, on the project root (not this directory) execute: +`./tfb --mode benchmark --test hexagon hexagon-jetty hexagon-tomcat hexagon-netty hexagon-nettyepoll` ## Infrastructure Software Versions @@ -31,6 +31,24 @@ and `${TEMPLATE_ENGINE}` with: `pebble` * Database updates: http://localhost:9090/${DB_ENGINE}/update * Database queries: http://localhost:9090/${DB_ENGINE}/query +### Netty + +* JSON Encoding Test: http://localhost:9090/json +* Plain Text Test: http://localhost:9090/plaintext +* Data-Store/Database Mapping Test: http://localhost:9090/${DB_ENGINE}/db?queries=5 +* Fortunes: http://localhost:9090/${DB_ENGINE}/${TEMPLATE_ENGINE}/fortunes +* Database updates: http://localhost:9090/${DB_ENGINE}/update +* Database queries: http://localhost:9090/${DB_ENGINE}/query + +### Netty Epoll + +* JSON Encoding Test: http://localhost:9090/json +* Plain Text Test: http://localhost:9090/plaintext +* Data-Store/Database Mapping Test: http://localhost:9090/${DB_ENGINE}/db?queries=5 +* Fortunes: http://localhost:9090/${DB_ENGINE}/${TEMPLATE_ENGINE}/fortunes +* Database updates: http://localhost:9090/${DB_ENGINE}/update +* Database queries: http://localhost:9090/${DB_ENGINE}/query + ### Tomcat * JSON Encoding Test: http://localhost:8080/json diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index d7186d7d9e8..aa47cabbe96 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -48,6 +48,29 @@ "notes": "http://hexagonkt.com", "versus": "netty" }, + "nettyepoll": { + "json_url": "/json", + "db_url": "/postgresql/db", + "query_url": "/postgresql/query?queries=", + "fortune_url": "/postgresql/pebble/fortunes", + "update_url": "/postgresql/update?queries=", + "cached_query_url": "/postgresql/cached?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Netty", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Netty Epoll PostgreSQL", + "notes": "http://hexagonkt.com", + "versus": "netty" + }, "tomcat": { "json_url": "/json", "db_url": "/postgresql/db", diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 50eec566d02..a247ae755d1 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,14 +1,15 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.6.10" + id "org.jetbrains.kotlin.jvm" version "1.6.21" } ext { - hexagonVersion = "2.0.5" + hexagonVersion = "2.0.7" hikariVersion = "5.0.1" - jettyVersion = "11.0.8" - postgresqlVersion = "42.3.3" + jettyVersion = "11.0.9" + postgresqlVersion = "42.3.4" cache2kVersion = "2.6.1.Final" + nettyVersion = "4.1.76.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } @@ -32,11 +33,13 @@ installDist.dependsOn("war") dependencies { implementation("com.hexagonkt:http_server_netty:$hexagonVersion") + implementation("com.hexagonkt:http_server_netty_epoll:$hexagonVersion") implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") implementation("com.hexagonkt:serialization_jackson_json:$hexagonVersion") + implementation("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") implementation("org.cache2k:cache2k-core:$cache2kVersion") implementation("com.zaxxer:HikariCP:$hikariVersion") implementation("org.postgresql:postgresql:$postgresqlVersion") diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index 91b846defad..edc7c2cf9aa 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -37,6 +37,24 @@ platform = "Netty" webserver = "None" versus = "netty" +[nettyepoll] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/postgresql/db" +urls.query = "/postgresql/query?queries=" +urls.update = "/postgresql/update?queries=" +urls.fortune = "/postgresql/pebble/fortunes" +urls.cached_query = "/postgresql/cached?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Netty" +webserver = "None" +versus = "netty" + [tomcat] urls.plaintext = "/plaintext" urls.json = "/json" diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index 95f35051bc8..3480f54996e 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.4-jdk11 AS gradle_build +FROM gradle:7.4.2-jdk11 AS gradle_build USER root WORKDIR /hexagon @@ -12,7 +12,7 @@ RUN gradle --quiet # # RUNTIME # -FROM adoptopenjdk:11-jre-hotspot-bionic +FROM eclipse-temurin:17-jre-alpine ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE netty diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile new file mode 100644 index 00000000000..e97878b9e9e --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -0,0 +1,26 @@ +# +# BUILD +# +FROM gradle:7.4.2-jdk11 AS gradle_build +USER root +WORKDIR /hexagon + +COPY src src +COPY build.gradle build.gradle +RUN gradle --quiet + +# +# RUNTIME +# +FROM eclipse-temurin:17-jre-alpine +ENV DBSTORE postgresql +ENV POSTGRESQL_DB_HOST tfb-database +ENV WEBENGINE netty_epoll +ENV PROJECT hexagon +ENV DISABLE_CHECKS true + +COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT + +EXPOSE 9090 + +ENTRYPOINT /opt/$PROJECT/bin/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index 27b931d8626..682ca865413 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.4-jdk11 AS gradle_build +FROM gradle:7.4.2-jdk11 AS gradle_build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 4ca671e517d..8742932ca3b 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.4-jdk11 AS gradle_build +FROM gradle:7.4.2-jdk11 AS gradle_build USER root WORKDIR /hexagon @@ -12,7 +12,7 @@ RUN gradle --quiet # # RUNTIME # -FROM adoptopenjdk:11-jre-hotspot-bionic +FROM eclipse-temurin:17-jre-alpine ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE jetty diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index 70ab0ba2cf2..e86e894e1ec 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -5,6 +5,7 @@ import com.hexagonkt.http.server.HttpServerPort import com.hexagonkt.http.server.HttpServerSettings import com.hexagonkt.http.server.jetty.JettyServletAdapter import com.hexagonkt.http.server.netty.NettyServerAdapter +import com.hexagonkt.http.server.netty.epoll.NettyEpollServerAdapter import com.hexagonkt.store.BenchmarkSqlStore import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort @@ -29,6 +30,7 @@ private val engines: Map by lazy { sendXPoweredBy = settings.sendXPoweredBy, ), "netty" to NettyServerAdapter(), + "netty_epoll" to NettyEpollServerAdapter(), ) } From 45209e632ccb728fb23715396e2bf4faaa7ad053 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 4 May 2022 07:41:57 +0200 Subject: [PATCH 032/105] Database and template improvements --- .../hexagon/src/main/kotlin/Controller.kt | 7 ++++--- .../main/kotlin/store/BenchmarkSqlStore.kt | 20 ++++++++++++++++++- 2 files changed, 23 insertions(+), 4 deletions(-) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 1454f9f37cc..199e8588f75 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -55,7 +55,8 @@ class Controller( stores.forEach { (storeEngine, store) -> path("/$storeEngine") { templateEngines.forEach { (templateEngineId, templateEngine) -> - get("/${templateEngineId}/fortunes") { listFortunes(store, templateEngineId, templateEngine) } + val templateUrl = templates.require(templateEngineId) + get("/${templateEngineId}/fortunes") { listFortunes(store, templateUrl, templateEngine) } } get("/db") { dbQuery(store) } @@ -68,13 +69,13 @@ class Controller( } private fun HttpServerContext.listFortunes( - store: BenchmarkStore, templateKind: String, templateAdapter: TemplatePort + store: BenchmarkStore, templateUrl: URL, templateAdapter: TemplatePort ): HttpServerContext { val fortunes = store.findAllFortunes() + Fortune(0, "Additional fortune added at request time.") val sortedFortunes = fortunes.sortedBy { it.message } val context = mapOf("fortunes" to sortedFortunes) - val body = templateAdapter.render(templates.require(templateKind), context) + val body = templateAdapter.render(templateUrl, context) return ok(body, contentType = html) } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index 3a724dd900e..ccab68ddc10 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -24,8 +24,26 @@ internal class BenchmarkSqlStore(engine: String, private val settings: Settings val dbHost = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "localhost" val environment = Jvm.systemSettingOrNull(String::class, "BENCHMARK_ENV")?.lowercase() val poolSize = 8 + if (environment == "citrine") Jvm.cpuCount else Jvm.cpuCount * 2 + val postgresqlSettings = listOf( + "useSSL=false", + "jdbcCompliantTruncation=false", + "elideSetAutoCommits=true", + "useLocalSessionState=true", + "cachePrepStmts=true", + "cacheCallableStmts=true", + "alwaysSendSetIsolation=false", + "prepStmtCacheSize=4096", + "cacheServerConfiguration=true", + "prepStmtCacheSqlLimit=2048", + "traceProtocol=false", + "useUnbufferedInput=false", + "useReadAheadInput=false", + "maintainTimeStats=false", + "useServerPrepStmts=true", + "cacheRSMetadata=true" + ).joinToString("&") val config = HikariConfig().apply { - jdbcUrl = "jdbc:postgresql://$dbHost/${settings.databaseName}" + jdbcUrl = "jdbc:postgresql://$dbHost/${settings.databaseName}?$postgresqlSettings" maximumPoolSize = Jvm.systemSettingOrNull(Int::class, "maximumPoolSize") ?: poolSize driverClassName = settings.databaseDriver username = settings.databaseUsername From d687db0db69a1d2253cb6c517ce21c2db852f097 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 4 May 2022 08:50:21 +0200 Subject: [PATCH 033/105] Update Hexagon version --- frameworks/Kotlin/hexagon/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index a247ae755d1..04323e8be2e 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,7 +4,7 @@ plugins { } ext { - hexagonVersion = "2.0.7" + hexagonVersion = "2.0.8" hikariVersion = "5.0.1" jettyVersion = "11.0.9" postgresqlVersion = "42.3.4" From 0875de00638050d7f171275356da72d3fe15ca02 Mon Sep 17 00:00:00 2001 From: Juanjo Aguililla Date: Wed, 4 May 2022 09:10:32 +0200 Subject: [PATCH 034/105] Update Hexagon version --- frameworks/Kotlin/hexagon/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index a247ae755d1..04323e8be2e 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,7 +4,7 @@ plugins { } ext { - hexagonVersion = "2.0.7" + hexagonVersion = "2.0.8" hikariVersion = "5.0.1" jettyVersion = "11.0.9" postgresqlVersion = "42.3.4" From d7a1c14f8172c3174a80c785dad18e99c7f7bea8 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 7 May 2022 13:28:10 +0200 Subject: [PATCH 035/105] Update DB settings --- frameworks/Kotlin/hexagon/build.gradle | 2 +- .../main/kotlin/store/BenchmarkSqlStore.kt | 21 +++++-------------- 2 files changed, 6 insertions(+), 17 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 04323e8be2e..45fcb70ef33 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -7,7 +7,7 @@ ext { hexagonVersion = "2.0.8" hikariVersion = "5.0.1" jettyVersion = "11.0.9" - postgresqlVersion = "42.3.4" + postgresqlVersion = "42.3.5" cache2kVersion = "2.6.1.Final" nettyVersion = "4.1.76.Final" diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index ccab68ddc10..a7b58ac2d84 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -25,22 +25,11 @@ internal class BenchmarkSqlStore(engine: String, private val settings: Settings val environment = Jvm.systemSettingOrNull(String::class, "BENCHMARK_ENV")?.lowercase() val poolSize = 8 + if (environment == "citrine") Jvm.cpuCount else Jvm.cpuCount * 2 val postgresqlSettings = listOf( - "useSSL=false", - "jdbcCompliantTruncation=false", - "elideSetAutoCommits=true", - "useLocalSessionState=true", - "cachePrepStmts=true", - "cacheCallableStmts=true", - "alwaysSendSetIsolation=false", - "prepStmtCacheSize=4096", - "cacheServerConfiguration=true", - "prepStmtCacheSqlLimit=2048", - "traceProtocol=false", - "useUnbufferedInput=false", - "useReadAheadInput=false", - "maintainTimeStats=false", - "useServerPrepStmts=true", - "cacheRSMetadata=true" + "ssl=false", + "assumeMinServerVersion=12.10", + "databaseMetadataCacheFieldsMiB=8", + "prepareThreshold=1", + "reWriteBatchedInserts=true", ).joinToString("&") val config = HikariConfig().apply { jdbcUrl = "jdbc:postgresql://$dbHost/${settings.databaseName}?$postgresqlSettings" From 33e5726bdf66bcfd85ff7617ff4474994cbc45d9 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Tue, 7 Jun 2022 23:01:52 +0200 Subject: [PATCH 036/105] Use a single store and template engine to simplify benchmark --- frameworks/Kotlin/hexagon/README.md | 36 ++++++++--------- .../Kotlin/hexagon/benchmark_config.json | 40 +++++++++---------- frameworks/Kotlin/hexagon/build.gradle | 7 ++-- frameworks/Kotlin/hexagon/config.toml | 40 +++++++++---------- .../hexagon/src/main/kotlin/Benchmark.kt | 12 +----- .../hexagon/src/main/kotlin/Controller.kt | 40 +++++++------------ .../src/main/kotlin/WebListenerServer.kt | 10 +++-- .../main/kotlin/store/BenchmarkSqlStore.kt | 4 +- 8 files changed, 83 insertions(+), 106 deletions(-) diff --git a/frameworks/Kotlin/hexagon/README.md b/frameworks/Kotlin/hexagon/README.md index 779811d7c31..11e0c78336e 100644 --- a/frameworks/Kotlin/hexagon/README.md +++ b/frameworks/Kotlin/hexagon/README.md @@ -18,42 +18,38 @@ To run the full benchmarks locally, on the project root (not this directory) exe ## Test URLs -In URLs replace `${DB_ENGINE}` with: `postgresql` - -and `${TEMPLATE_ENGINE}` with: `pebble` - ### Jetty * JSON Encoding Test: http://localhost:9090/json * Plain Text Test: http://localhost:9090/plaintext -* Data-Store/Database Mapping Test: http://localhost:9090/${DB_ENGINE}/db?queries=5 -* Fortunes: http://localhost:9090/${DB_ENGINE}/${TEMPLATE_ENGINE}/fortunes -* Database updates: http://localhost:9090/${DB_ENGINE}/update -* Database queries: http://localhost:9090/${DB_ENGINE}/query +* Data-Store/Database Mapping Test: http://localhost:9090/db?queries=5 +* Fortunes: http://localhost:9090/fortunes +* Database updates: http://localhost:9090/update +* Database queries: http://localhost:9090/query ### Netty * JSON Encoding Test: http://localhost:9090/json * Plain Text Test: http://localhost:9090/plaintext -* Data-Store/Database Mapping Test: http://localhost:9090/${DB_ENGINE}/db?queries=5 -* Fortunes: http://localhost:9090/${DB_ENGINE}/${TEMPLATE_ENGINE}/fortunes -* Database updates: http://localhost:9090/${DB_ENGINE}/update -* Database queries: http://localhost:9090/${DB_ENGINE}/query +* Data-Store/Database Mapping Test: http://localhost:9090/db?queries=5 +* Fortunes: http://localhost:9090/fortunes +* Database updates: http://localhost:9090/update +* Database queries: http://localhost:9090/query ### Netty Epoll * JSON Encoding Test: http://localhost:9090/json * Plain Text Test: http://localhost:9090/plaintext -* Data-Store/Database Mapping Test: http://localhost:9090/${DB_ENGINE}/db?queries=5 -* Fortunes: http://localhost:9090/${DB_ENGINE}/${TEMPLATE_ENGINE}/fortunes -* Database updates: http://localhost:9090/${DB_ENGINE}/update -* Database queries: http://localhost:9090/${DB_ENGINE}/query +* Data-Store/Database Mapping Test: http://localhost:9090/db?queries=5 +* Fortunes: http://localhost:9090/fortunes +* Database updates: http://localhost:9090/update +* Database queries: http://localhost:9090/query ### Tomcat * JSON Encoding Test: http://localhost:8080/json * Plain Text Test: http://localhost:8080/plaintext -* Data-Store/Database Mapping Test: http://localhost:8080/${DB_ENGINE}/db?queries=5 -* Fortunes: http://localhost:8080/${DB_ENGINE}/${TEMPLATE_ENGINE}/fortunes -* Database updates: http://localhost:8080/${DB_ENGINE}/update -* Database queries: http://localhost:8080/${DB_ENGINE}/query +* Data-Store/Database Mapping Test: http://localhost:8080/db?queries=5 +* Fortunes: http://localhost:8080/fortunes +* Database updates: http://localhost:8080/update +* Database queries: http://localhost:8080/query diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index aa47cabbe96..fd4254a3355 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -4,11 +4,11 @@ { "default": { "json_url": "/json", - "db_url": "/postgresql/db", - "query_url": "/postgresql/query?queries=", - "fortune_url": "/postgresql/pebble/fortunes", - "update_url": "/postgresql/update?queries=", - "cached_query_url": "/postgresql/cached?count=", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", @@ -27,11 +27,11 @@ }, "netty": { "json_url": "/json", - "db_url": "/postgresql/db", - "query_url": "/postgresql/query?queries=", - "fortune_url": "/postgresql/pebble/fortunes", - "update_url": "/postgresql/update?queries=", - "cached_query_url": "/postgresql/cached?count=", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", @@ -50,11 +50,11 @@ }, "nettyepoll": { "json_url": "/json", - "db_url": "/postgresql/db", - "query_url": "/postgresql/query?queries=", - "fortune_url": "/postgresql/pebble/fortunes", - "update_url": "/postgresql/update?queries=", - "cached_query_url": "/postgresql/cached?count=", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", @@ -73,11 +73,11 @@ }, "tomcat": { "json_url": "/json", - "db_url": "/postgresql/db", - "query_url": "/postgresql/query?queries=", - "fortune_url": "/postgresql/pebble/fortunes", - "update_url": "/postgresql/update?queries=", - "cached_query_url": "/postgresql/cached?count=", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", "plaintext_url": "/plaintext", "port": 8080, "approach": "Realistic", diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 45fcb70ef33..e0eb8da23d1 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,12 +4,12 @@ plugins { } ext { - hexagonVersion = "2.0.8" + hexagonVersion = "2.0.10" hikariVersion = "5.0.1" jettyVersion = "11.0.9" - postgresqlVersion = "42.3.5" + postgresqlVersion = "42.3.6" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.76.Final" + nettyVersion = "4.1.77.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } @@ -32,7 +32,6 @@ war { installDist.dependsOn("war") dependencies { - implementation("com.hexagonkt:http_server_netty:$hexagonVersion") implementation("com.hexagonkt:http_server_netty_epoll:$hexagonVersion") implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index edc7c2cf9aa..ad228b9203e 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -4,11 +4,11 @@ name = "hexagon" [main] urls.plaintext = "/plaintext" urls.json = "/json" -urls.db = "/postgresql/db" -urls.query = "/postgresql/query?queries=" -urls.update = "/postgresql/update?queries=" -urls.fortune = "/postgresql/pebble/fortunes" -urls.cached_query = "/postgresql/cached?count=" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" approach = "Realistic" classification = "Micro" database = "postgres" @@ -22,11 +22,11 @@ versus = "servlet" [netty] urls.plaintext = "/plaintext" urls.json = "/json" -urls.db = "/postgresql/db" -urls.query = "/postgresql/query?queries=" -urls.update = "/postgresql/update?queries=" -urls.fortune = "/postgresql/pebble/fortunes" -urls.cached_query = "/postgresql/cached?count=" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" approach = "Realistic" classification = "Micro" database = "postgres" @@ -40,11 +40,11 @@ versus = "netty" [nettyepoll] urls.plaintext = "/plaintext" urls.json = "/json" -urls.db = "/postgresql/db" -urls.query = "/postgresql/query?queries=" -urls.update = "/postgresql/update?queries=" -urls.fortune = "/postgresql/pebble/fortunes" -urls.cached_query = "/postgresql/cached?count=" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" approach = "Realistic" classification = "Micro" database = "postgres" @@ -58,11 +58,11 @@ versus = "netty" [tomcat] urls.plaintext = "/plaintext" urls.json = "/json" -urls.db = "/postgresql/db" -urls.query = "/postgresql/query?queries=" -urls.update = "/postgresql/update?queries=" -urls.fortune = "/postgresql/pebble/fortunes" -urls.cached_query = "/postgresql/cached?count=" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" approach = "Realistic" classification = "Micro" database = "postgres" diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index e86e894e1ec..310bbb81c0a 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -7,21 +7,11 @@ import com.hexagonkt.http.server.jetty.JettyServletAdapter import com.hexagonkt.http.server.netty.NettyServerAdapter import com.hexagonkt.http.server.netty.epoll.NettyEpollServerAdapter import com.hexagonkt.store.BenchmarkSqlStore -import com.hexagonkt.store.BenchmarkStore -import com.hexagonkt.templates.TemplatePort import com.hexagonkt.templates.pebble.PebbleAdapter import java.net.InetAddress internal val settings = Settings() -internal val stores: Map by lazy { - mapOf("postgresql" to BenchmarkSqlStore("postgresql")) -} - -internal val templateEngines: Map by lazy { - mapOf("pebble" to PebbleAdapter) -} - private val engines: Map by lazy { mapOf( "jetty" to JettyServletAdapter( @@ -36,7 +26,7 @@ private val engines: Map by lazy { private val server: HttpServer by lazy { val engine = engines[settings.webEngine] ?: error("Unsupported server engine") - val controller = Controller(settings, stores, templateEngines) + val controller = Controller(settings, BenchmarkSqlStore("postgresql"), PebbleAdapter) val serverSettings = HttpServerSettings( bindAddress = InetAddress.getByName(settings.bindAddress), bindPort = settings.bindPort, diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 199e8588f75..2c82ad706b8 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -1,11 +1,11 @@ package com.hexagonkt -import com.hexagonkt.core.require import com.hexagonkt.core.media.ApplicationMedia.JSON import com.hexagonkt.core.media.TextMedia.HTML import com.hexagonkt.core.media.TextMedia.PLAIN -import com.hexagonkt.core.multiMapOf import com.hexagonkt.http.model.ContentType +import com.hexagonkt.http.model.Header +import com.hexagonkt.http.model.HttpFields import com.hexagonkt.http.server.handlers.HttpServerContext import com.hexagonkt.http.server.handlers.PathHandler import com.hexagonkt.http.server.handlers.path @@ -23,8 +23,8 @@ import kotlin.text.Charsets.UTF_8 class Controller( settings: Settings, - stores: Map, - templateEngines: Map, + store: BenchmarkStore, + templateEngine: TemplatePort, ) { private val queriesParam: String = settings.queriesParam private val cachedQueriesParam: String = settings.cachedQueriesParam @@ -34,37 +34,25 @@ class Controller( private val json: ContentType = ContentType(JSON) private val html: ContentType = ContentType(HTML, charset = UTF_8) - private val templates: Map = mapOf( - "pebble" to URL("classpath:fortunes.pebble.html") + private val templateUrl: URL = URL("classpath:fortunes.pebble.html") + + private val headers = HttpFields( + Header("server", "Hexagon"), ) internal val path: PathHandler by lazy { path { on("*") { - val headers = multiMapOf( - "server" to "Hexagon", - "date" to now().toHttpFormat(), - ) - - send(headers = headers) + send(headers = headers + Header("date", now().toHttpFormat())) } get("/plaintext") { ok(settings.textMessage, contentType = plain) } get("/json") { ok(Message(settings.textMessage).serialize(Json.raw), contentType = json) } - - stores.forEach { (storeEngine, store) -> - path("/$storeEngine") { - templateEngines.forEach { (templateEngineId, templateEngine) -> - val templateUrl = templates.require(templateEngineId) - get("/${templateEngineId}/fortunes") { listFortunes(store, templateUrl, templateEngine) } - } - - get("/db") { dbQuery(store) } - get("/query") { getWorlds(store) } - get("/cached") { getCachedWorlds(store) } - get("/update") { updateWorlds(store) } - } - } + get("/fortunes") { listFortunes(store, templateUrl, templateEngine) } + get("/db") { dbQuery(store) } + get("/query") { getWorlds(store) } + get("/cached-queries") { getCachedWorlds(store) } + get("/update") { updateWorlds(store) } } } diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index eec6f2571d3..d269138faec 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -1,20 +1,24 @@ package com.hexagonkt -import com.hexagonkt.core.multiMapOf +import com.hexagonkt.http.model.Header +import com.hexagonkt.http.model.HttpFields import com.hexagonkt.http.server.handlers.HttpHandler import com.hexagonkt.http.server.handlers.OnHandler import com.hexagonkt.http.server.servlet.ServletServer +import com.hexagonkt.store.BenchmarkSqlStore +import com.hexagonkt.templates.pebble.PebbleAdapter import jakarta.servlet.annotation.WebListener @WebListener class WebListenerServer(settings: Settings = Settings()) : ServletServer(createHandlers(settings)) { private companion object { + val headers = HttpFields(Header("server", "Tomcat")) fun createHandlers(settings: Settings): List { - val controller = Controller(settings, stores, templateEngines) + val controller = Controller(settings, BenchmarkSqlStore("postgresql"), PebbleAdapter) val controllerPath = controller.path val serverHeaderHandler = OnHandler("*") { - send(headers = multiMapOf("server" to "Tomcat")) + send(headers = headers) } return listOf(serverHeaderHandler, controllerPath) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index a7b58ac2d84..f2d68d7cb6c 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -42,12 +42,12 @@ internal class BenchmarkSqlStore(engine: String, private val settings: Settings } override fun findAllFortunes(): List { - val fortunes = mutableListOf() + var fortunes = listOf() dataSource.connection.use { con: Connection -> val rs = con.prepareStatement(SELECT_ALL_FORTUNES).executeQuery() while (rs.next()) - fortunes += Fortune(rs.getInt(1), rs.getString(2)) + fortunes = fortunes + Fortune(rs.getInt(1), rs.getString(2)) } return fortunes From fb135f1ab283caaab91c742cd7dd114fb3077f9c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 21 Jun 2022 06:32:27 +0000 Subject: [PATCH 037/105] Bump mysql-connector-java in /frameworks/Java/wicket Bumps [mysql-connector-java](https://github.com/mysql/mysql-connector-j) from 8.0.27 to 8.0.28. - [Release notes](https://github.com/mysql/mysql-connector-j/releases) - [Changelog](https://github.com/mysql/mysql-connector-j/blob/release/8.0/CHANGES) - [Commits](https://github.com/mysql/mysql-connector-j/compare/8.0.27...8.0.28) --- updated-dependencies: - dependency-name: mysql:mysql-connector-java dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/wicket/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/wicket/pom.xml b/frameworks/Java/wicket/pom.xml index 8c8473d6ab0..ec30df52f27 100644 --- a/frameworks/Java/wicket/pom.xml +++ b/frameworks/Java/wicket/pom.xml @@ -64,7 +64,7 @@ mysql mysql-connector-java - 8.0.27 + 8.0.28 From 1192a06038bf88da2fc4c8e41a65e33734836a0b Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 27 Jun 2022 17:27:10 +0000 Subject: [PATCH 038/105] Bump mongodb-driver-sync from 4.2.0 to 4.2.1 in /frameworks/Java/javalin Bumps [mongodb-driver-sync](https://github.com/mongodb/mongo-java-driver) from 4.2.0 to 4.2.1. - [Release notes](https://github.com/mongodb/mongo-java-driver/releases) - [Commits](https://github.com/mongodb/mongo-java-driver/compare/r4.2.0...r4.2.1) --- updated-dependencies: - dependency-name: org.mongodb:mongodb-driver-sync dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/javalin/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/javalin/pom.xml b/frameworks/Java/javalin/pom.xml index 98e5d550d4c..a3ff499ca84 100644 --- a/frameworks/Java/javalin/pom.xml +++ b/frameworks/Java/javalin/pom.xml @@ -16,7 +16,7 @@ 2.12.6.1 4.0.2 42.3.3 - 4.2.0 + 4.2.1 3.1.5 From 310167b127eb1d7d31bc1543fa28ea24ec210c1c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:32:15 +0000 Subject: [PATCH 039/105] Bump ujson from 5.2.0 to 5.4.0 in /frameworks/Python/starlette Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.2.0 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.2.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/starlette/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/starlette/requirements.txt b/frameworks/Python/starlette/requirements.txt index 5d52022437d..a9d791c7b47 100644 --- a/frameworks/Python/starlette/requirements.txt +++ b/frameworks/Python/starlette/requirements.txt @@ -2,6 +2,6 @@ asyncpg==0.25.0 gunicorn==20.1.0 Jinja2==3.1.2 starlette==0.19.1 -ujson==5.2.0 +ujson==5.4.0 uvicorn==0.17.6 uvloop==0.16.0 From 37e0005e273f2d1cb607a564da4d9943e3e98da3 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:40:09 +0000 Subject: [PATCH 040/105] Bump ujson from 5.2.0 to 5.4.0 in /frameworks/Python/django Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.2.0 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.2.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/django/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/django/requirements.txt b/frameworks/Python/django/requirements.txt index e9c9255cbcb..0c8cdd97725 100644 --- a/frameworks/Python/django/requirements.txt +++ b/frameworks/Python/django/requirements.txt @@ -5,4 +5,4 @@ meinheld==1.0.2 mysqlclient==1.4.6 psycopg2==2.8.6 pytz==2020.4 -ujson==5.2.0 \ No newline at end of file +ujson==5.4.0 \ No newline at end of file From 9d1378cde62f3a87fe810e5e10c7ef212a69cfe3 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:40:11 +0000 Subject: [PATCH 041/105] Bump ujson from 5.2.0 to 5.4.0 in /frameworks/Python/routerling Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.2.0 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.2.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/routerling/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/routerling/requirements.txt b/frameworks/Python/routerling/requirements.txt index 9080a3c642b..7b68e45f102 100644 --- a/frameworks/Python/routerling/requirements.txt +++ b/frameworks/Python/routerling/requirements.txt @@ -6,6 +6,6 @@ h11==0.12.0 Jinja2==3.0.1 MarkupSafe==2.0.1 routerling==0.3.1 -ujson==5.2.0 +ujson==5.4.0 uvloop==0.16.0 uvicorn==0.14.0 From e0bb50bc632dd80144d0a50c6ab1444119e21151 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:44:16 +0000 Subject: [PATCH 042/105] Bump ujson from 5.2.0 to 5.4.0 in /frameworks/Python/japronto Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.2.0 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.2.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/japronto/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/japronto/requirements.txt b/frameworks/Python/japronto/requirements.txt index 2990ff079ea..a28213a7c90 100644 --- a/frameworks/Python/japronto/requirements.txt +++ b/frameworks/Python/japronto/requirements.txt @@ -1,2 +1,2 @@ git+https://github.com/squeaky-pl/japronto.git#egg=japronto -ujson==5.2.0 +ujson==5.4.0 From 5299732a41c300aa60f40aa502e3a70d11fbb29b Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:45:58 +0000 Subject: [PATCH 043/105] Bump ujson from 5.2.0 to 5.4.0 in /frameworks/Python/fastapi Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.2.0 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.2.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/fastapi/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/fastapi/requirements.txt b/frameworks/Python/fastapi/requirements.txt index e53fe307dd3..dc928416e92 100644 --- a/frameworks/Python/fastapi/requirements.txt +++ b/frameworks/Python/fastapi/requirements.txt @@ -2,7 +2,7 @@ asyncpg==0.21.0 gunicorn==20.0.4 Jinja2==2.11.3 markupsafe==2.0.1 -ujson==5.2.0 +ujson==5.4.0 uvloop==0.14.0 uvicorn==0.11.3 fastapi==0.65.2 From 8dffc32f73cbad2c3d5a7e1a2bf4bbf50cf885de Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:47:15 +0000 Subject: [PATCH 044/105] Bump ujson from 5.2.0 to 5.4.0 in /frameworks/Python/uvicorn Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.2.0 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.2.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/uvicorn/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/uvicorn/requirements.txt b/frameworks/Python/uvicorn/requirements.txt index 5eabe2676f4..e2bb7f3304a 100644 --- a/frameworks/Python/uvicorn/requirements.txt +++ b/frameworks/Python/uvicorn/requirements.txt @@ -1,6 +1,6 @@ asyncpg==0.21.0 gunicorn==20.0.4 Jinja2==3.0.3 -ujson==5.2.0 +ujson==5.4.0 uvloop==0.14.0 uvicorn==0.11.7 From cf9a280f5a762ccfe7027da718b88c69d6f82e0a Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:52:09 +0000 Subject: [PATCH 045/105] Bump ujson from 5.2.0 to 5.4.0 in /frameworks/Python/flask Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.2.0 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.2.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/flask/requirements-pypy.txt | 2 +- frameworks/Python/flask/requirements.txt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/frameworks/Python/flask/requirements-pypy.txt b/frameworks/Python/flask/requirements-pypy.txt index 756f6e93297..132102fdc92 100644 --- a/frameworks/Python/flask/requirements-pypy.txt +++ b/frameworks/Python/flask/requirements-pypy.txt @@ -11,4 +11,4 @@ MarkupSafe==2.0.1 meinheld==1.0.2 uWSGI==2.0.19.1 Werkzeug==2.0.1 -ujson==5.2.0 \ No newline at end of file +ujson==5.4.0 \ No newline at end of file diff --git a/frameworks/Python/flask/requirements.txt b/frameworks/Python/flask/requirements.txt index 744b623e065..89d3bb2e297 100644 --- a/frameworks/Python/flask/requirements.txt +++ b/frameworks/Python/flask/requirements.txt @@ -12,5 +12,5 @@ MarkupSafe==2.0.1 meinheld==1.0.2 uWSGI==2.0.19.1 Werkzeug==2.0.1 -ujson==5.2.0 +ujson==5.4.0 orjson==3.6.0 From a4fe6ec04baa58a1c9264c4ec58310cb4fc98996 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:57:17 +0000 Subject: [PATCH 046/105] Bump ujson from 5.1 to 5.4.0 in /frameworks/Python/aiohttp Bumps [ujson](https://github.com/ultrajson/ultrajson) from 5.1 to 5.4.0. - [Release notes](https://github.com/ultrajson/ultrajson/releases) - [Commits](https://github.com/ultrajson/ultrajson/compare/5.1.0...5.4.0) --- updated-dependencies: - dependency-name: ujson dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/aiohttp/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/aiohttp/requirements.txt b/frameworks/Python/aiohttp/requirements.txt index b11893aec72..aea8aff7754 100644 --- a/frameworks/Python/aiohttp/requirements.txt +++ b/frameworks/Python/aiohttp/requirements.txt @@ -5,5 +5,5 @@ gunicorn==20.1 jinja2==3.0.3 psycopg2==2.9.2 SQLAlchemy==1.4.29 -ujson==5.1 +ujson==5.4.0 uvloop==0.16 From 31887ce0e5e9e7ef1dc69f4f7f60ea588e84c9e0 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 6 Jul 2022 11:43:52 +0000 Subject: [PATCH 047/105] Bump rails-html-sanitizer from 1.4.2 to 1.4.3 in /frameworks/Ruby/rails Bumps [rails-html-sanitizer](https://github.com/rails/rails-html-sanitizer) from 1.4.2 to 1.4.3. - [Release notes](https://github.com/rails/rails-html-sanitizer/releases) - [Changelog](https://github.com/rails/rails-html-sanitizer/blob/master/CHANGELOG.md) - [Commits](https://github.com/rails/rails-html-sanitizer/compare/v1.4.2...v1.4.3) --- updated-dependencies: - dependency-name: rails-html-sanitizer dependency-type: indirect ... Signed-off-by: dependabot[bot] --- frameworks/Ruby/rails/Gemfile.lock | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/frameworks/Ruby/rails/Gemfile.lock b/frameworks/Ruby/rails/Gemfile.lock index 819c83670c6..dfc9e4fd60e 100644 --- a/frameworks/Ruby/rails/Gemfile.lock +++ b/frameworks/Ruby/rails/Gemfile.lock @@ -80,7 +80,7 @@ GEM listen (3.7.1) rb-fsevent (~> 0.10, >= 0.10.3) rb-inotify (~> 0.9, >= 0.9.10) - loofah (2.13.0) + loofah (2.18.0) crass (~> 1.0.2) nokogiri (>= 1.5.9) mail (2.7.1) @@ -139,7 +139,7 @@ GEM rails-dom-testing (2.0.3) activesupport (>= 4.2.0) nokogiri (>= 1.6) - rails-html-sanitizer (1.4.2) + rails-html-sanitizer (1.4.3) loofah (~> 2.3) railties (7.0.1) actionpack (= 7.0.1) From 8534e0eb2c8b8d6b69be037dd686715ee23e41ef Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 7 Jul 2022 22:15:33 +0000 Subject: [PATCH 048/105] Bump jetty-server in /frameworks/Java/jetty Bumps [jetty-server](https://github.com/eclipse/jetty.project) from 9.4.41.v20210516 to 10.0.10. - [Release notes](https://github.com/eclipse/jetty.project/releases) - [Commits](https://github.com/eclipse/jetty.project/compare/jetty-9.4.41.v20210516...jetty-10.0.10) --- updated-dependencies: - dependency-name: org.eclipse.jetty:jetty-server dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/jetty/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/jetty/pom.xml b/frameworks/Java/jetty/pom.xml index c860b1d4bf4..79112565a05 100644 --- a/frameworks/Java/jetty/pom.xml +++ b/frameworks/Java/jetty/pom.xml @@ -11,7 +11,7 @@ UTF-8 11 11 - 9.4.41.v20210516 + 10.0.10 hello.handler.HelloWebServer From 32f13be742dd857ad7e96e9c758b25c41e879359 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 15 Jul 2022 21:34:24 +0000 Subject: [PATCH 049/105] Bump undertow-core in /frameworks/Java/undertow Bumps [undertow-core](https://github.com/undertow-io/undertow) from 2.2.11.Final to 2.2.15.Final. - [Release notes](https://github.com/undertow-io/undertow/releases) - [Commits](https://github.com/undertow-io/undertow/compare/2.2.11.Final...2.2.15.Final) --- updated-dependencies: - dependency-name: io.undertow:undertow-core dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/undertow/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/undertow/pom.xml b/frameworks/Java/undertow/pom.xml index 61f2251bff3..6d766169f9c 100644 --- a/frameworks/Java/undertow/pom.xml +++ b/frameworks/Java/undertow/pom.xml @@ -19,7 +19,7 @@ 3.2.1 0.9.6 42.3.3 - 2.2.11.Final + 2.2.15.Final From fc3dfc1c41713e1671015fd4c59401bc84c9ff1d Mon Sep 17 00:00:00 2001 From: jaguililla Date: Tue, 19 Jul 2022 18:49:14 +0200 Subject: [PATCH 050/105] Update versions --- frameworks/Kotlin/hexagon/build.gradle | 10 +++++----- frameworks/Kotlin/hexagon/hexagon-netty.dockerfile | 2 +- .../Kotlin/hexagon/hexagon-nettyepoll.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile | 4 ++-- frameworks/Kotlin/hexagon/hexagon.dockerfile | 2 +- 5 files changed, 10 insertions(+), 10 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index e0eb8da23d1..8ee07ba3ca1 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,15 +1,15 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.6.21" + id "org.jetbrains.kotlin.jvm" version "1.7.10" } ext { - hexagonVersion = "2.0.10" + hexagonVersion = "2.0.17" hikariVersion = "5.0.1" - jettyVersion = "11.0.9" - postgresqlVersion = "42.3.6" + jettyVersion = "11.0.11" + postgresqlVersion = "42.4.0" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.77.Final" + nettyVersion = "4.1.79.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index 3480f54996e..579a9402136 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.4.2-jdk11 AS gradle_build +FROM gradle:7.5.0-jdk17-alpine AS gradle_build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile index e97878b9e9e..e9caab6bc32 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.4.2-jdk11 AS gradle_build +FROM gradle:7.5.0-jdk17-alpine AS gradle_build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index 682ca865413..5134fedad4c 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.4.2-jdk11 AS gradle_build +FROM gradle:7.5.0-jdk17-alpine AS gradle_build USER root WORKDIR /hexagon @@ -12,7 +12,7 @@ RUN gradle --quiet # # RUNTIME # -FROM tomcat:10.0.14-jre17-temurin +FROM tomcat:10.1.0-jre17-temurin ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV DISABLE_CHECKS true diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 8742932ca3b..465f2d82146 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.4.2-jdk11 AS gradle_build +FROM gradle:7.5.0-jdk17-alpine AS gradle_build USER root WORKDIR /hexagon From d7715ab8c0886e4f858b230f81f49972671be6ef Mon Sep 17 00:00:00 2001 From: Juanjo Aguililla Date: Wed, 20 Jul 2022 10:56:28 +0200 Subject: [PATCH 051/105] Update README.md --- frameworks/Kotlin/hexagon/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/README.md b/frameworks/Kotlin/hexagon/README.md index 11e0c78336e..28397711a58 100644 --- a/frameworks/Kotlin/hexagon/README.md +++ b/frameworks/Kotlin/hexagon/README.md @@ -2,7 +2,7 @@ # Hexagon Benchmarking Test This is the Hexagon portion of a [benchmarking test suite](../../../README.md) comparing a variety -of web development platforms. The test utilizes Hexagon routes, serialization and database access. +of web development platforms. The test utilizes Hexagon routes and serialization. ## Tests From a1db1c88c79fc93c64f7e5f33b355df0748f73bb Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:21:44 +0000 Subject: [PATCH 052/105] Bump sanic from 22.3.1 to 22.6.1 in /frameworks/Python/sanic Bumps [sanic](https://github.com/sanic-org/sanic) from 22.3.1 to 22.6.1. - [Release notes](https://github.com/sanic-org/sanic/releases) - [Changelog](https://github.com/sanic-org/sanic/blob/main/CHANGELOG.rst) - [Commits](https://github.com/sanic-org/sanic/compare/v22.3.1...v22.6.1) --- updated-dependencies: - dependency-name: sanic dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Python/sanic/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Python/sanic/requirements.txt b/frameworks/Python/sanic/requirements.txt index 13b48a818a3..36f8d2c8246 100644 --- a/frameworks/Python/sanic/requirements.txt +++ b/frameworks/Python/sanic/requirements.txt @@ -1,4 +1,4 @@ asyncpg==0.25.0 Jinja2==3.1.2 -sanic==22.3.1 +sanic==22.6.1 uvloop==0.16.0 From 6325b02dcb6fb9188f6f9406319bcc05e3c97ca3 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:24 +0000 Subject: [PATCH 053/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/light-java Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/light-java/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/light-java/pom.xml b/frameworks/Java/light-java/pom.xml index 14cf18d003c..ebe3634dc9d 100644 --- a/frameworks/Java/light-java/pom.xml +++ b/frameworks/Java/light-java/pom.xml @@ -28,7 +28,7 @@ 2.2.15.Final 3.3.1 8.0.28 - 42.3.3 + 42.4.1 1.8.4 0.9.6 3.8.0 From 382854885dc78c7aa2a1a68ddbcd57fc64a59853 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:24 +0000 Subject: [PATCH 054/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/rapidoid Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/rapidoid/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/rapidoid/pom.xml b/frameworks/Java/rapidoid/pom.xml index 57b2e1c9c6b..eed7ef401d9 100644 --- a/frameworks/Java/rapidoid/pom.xml +++ b/frameworks/Java/rapidoid/pom.xml @@ -28,7 +28,7 @@ org.postgresql postgresql - 42.3.3 + 42.4.1 com.zaxxer From 7c3305d41807547cdb3c9dbcf1a351eb37b8395a Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:24 +0000 Subject: [PATCH 055/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/jooby Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/jooby/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/jooby/pom.xml b/frameworks/Java/jooby/pom.xml index efb0b9d81c9..8839413f957 100644 --- a/frameworks/Java/jooby/pom.xml +++ b/frameworks/Java/jooby/pom.xml @@ -14,7 +14,7 @@ 2.9.5 4.1.77.Final 1.9.5 - 42.3.3 + 42.4.1 UTF-8 11 11 From f0d8e988577bcfceab0797cabbc64417cd33da06 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:24 +0000 Subject: [PATCH 056/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/servlet Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/servlet/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/servlet/pom.xml b/frameworks/Java/servlet/pom.xml index 631fb2788b5..fd63f64978f 100644 --- a/frameworks/Java/servlet/pom.xml +++ b/frameworks/Java/servlet/pom.xml @@ -108,7 +108,7 @@ org.postgresql postgresql - 42.3.3 + 42.4.1 From 70aebd078421c6bb86db9d806484ab56be9c899d Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:25 +0000 Subject: [PATCH 057/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/spring-webflux Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/spring-webflux/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/spring-webflux/pom.xml b/frameworks/Java/spring-webflux/pom.xml index e0e17a2cdef..43b7bedcaef 100644 --- a/frameworks/Java/spring-webflux/pom.xml +++ b/frameworks/Java/spring-webflux/pom.xml @@ -21,7 +21,7 @@ 11 UTF-8 1.0.0.M2 - 42.3.3 + 42.4.1 0.11.4 0.2.4 1.0.0.M7 From 9bddbe971e80e5ea2d976b5dc6484b45170c75cf Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:25 +0000 Subject: [PATCH 058/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/smart-socket Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/smart-socket/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/smart-socket/pom.xml b/frameworks/Java/smart-socket/pom.xml index 9bd1b1f1af3..1c48ccf3ea4 100644 --- a/frameworks/Java/smart-socket/pom.xml +++ b/frameworks/Java/smart-socket/pom.xml @@ -56,7 +56,7 @@ org.postgresql postgresql - 42.3.3 + 42.4.1 From 58b628d75de475b623cc1a53d1b37288505e63e0 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:25 +0000 Subject: [PATCH 059/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/act Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/act/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/act/pom.xml b/frameworks/Java/act/pom.xml index a27f7409769..c65ea1dfce7 100644 --- a/frameworks/Java/act/pom.xml +++ b/frameworks/Java/act/pom.xml @@ -70,7 +70,7 @@ 1.8 5.1.47 - 42.3.3 + 42.4.1 1.3.2 3.4 com.techempower.act.AppEntry From 1f8d756e10dc72057d0af9541e204624e47a6594 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:27 +0000 Subject: [PATCH 060/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Kotlin/kooby Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Kotlin/kooby/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/kooby/pom.xml b/frameworks/Kotlin/kooby/pom.xml index 51160f7f72a..0dfc7bc9f84 100644 --- a/frameworks/Kotlin/kooby/pom.xml +++ b/frameworks/Kotlin/kooby/pom.xml @@ -13,7 +13,7 @@ 2.9.5 - 42.3.3 + 42.4.1 UTF-8 11 11 From 468cb594cffe85e37cfa65aa94b8576600ed5ab2 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:56:27 +0000 Subject: [PATCH 061/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/dropwizard Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/dropwizard/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/dropwizard/pom.xml b/frameworks/Java/dropwizard/pom.xml index 8fcbeb3c6b6..319c13f37ff 100644 --- a/frameworks/Java/dropwizard/pom.xml +++ b/frameworks/Java/dropwizard/pom.xml @@ -19,7 +19,7 @@ 2.3.0 8.0.28 2.9.4 - 42.3.3 + 42.4.1 3.8.0 3.1.0 3.1.1 From ee593a29ca8d3c9a8d2850b68daa7fb3100fea02 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 05:59:58 +0000 Subject: [PATCH 062/105] Bump postgresql from 42.3.3 to 42.4.1 in /frameworks/Java/hserver Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.3.3 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.3.3...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/hserver/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/hserver/pom.xml b/frameworks/Java/hserver/pom.xml index 291ff8be9a2..8699552d1ba 100644 --- a/frameworks/Java/hserver/pom.xml +++ b/frameworks/Java/hserver/pom.xml @@ -10,7 +10,7 @@ UTF-8 3.3.1 - 42.3.3 + 42.4.1 2.9.90 From 03ca6af0c9aa1aad7231fe25f7da0f482cb4d766 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 06:07:01 +0000 Subject: [PATCH 063/105] Bump postgresql from 42.4.0 to 42.4.1 in /frameworks/Java/undertow Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.4.0 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.4.0...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/undertow/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/undertow/pom.xml b/frameworks/Java/undertow/pom.xml index f13755d14d7..080c2cf7ae3 100644 --- a/frameworks/Java/undertow/pom.xml +++ b/frameworks/Java/undertow/pom.xml @@ -19,7 +19,7 @@ 3.3.0 3.2.2 0.9.10 - 42.4.0 + 42.4.1 2.2.18.Final From 36ae7377838e58e6202b4b95eca0ac8b51c6043c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sat, 6 Aug 2022 07:04:23 +0000 Subject: [PATCH 064/105] Bump postgresql from 42.2.23 to 42.4.1 in /frameworks/Kotlin/ktor/ktor Bumps [postgresql](https://github.com/pgjdbc/pgjdbc) from 42.2.23 to 42.4.1. - [Release notes](https://github.com/pgjdbc/pgjdbc/releases) - [Changelog](https://github.com/pgjdbc/pgjdbc/blob/master/CHANGELOG.md) - [Commits](https://github.com/pgjdbc/pgjdbc/compare/REL42.2.23...REL42.4.1) --- updated-dependencies: - dependency-name: org.postgresql:postgresql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Kotlin/ktor/ktor/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/ktor/ktor/pom.xml b/frameworks/Kotlin/ktor/ktor/pom.xml index b891cc71479..ab847c5b2c0 100644 --- a/frameworks/Kotlin/ktor/ktor/pom.xml +++ b/frameworks/Kotlin/ktor/ktor/pom.xml @@ -20,7 +20,7 @@ 5.0.0 1.2.4 8.0.28 - 42.2.23 + 42.4.1 From b851884430cda491cebc1251a71f6bad294a223d Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 6 Aug 2022 13:34:08 +0200 Subject: [PATCH 065/105] Update dependencies --- frameworks/Kotlin/hexagon/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 8ee07ba3ca1..1b41c2be7ce 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -7,7 +7,7 @@ ext { hexagonVersion = "2.0.17" hikariVersion = "5.0.1" jettyVersion = "11.0.11" - postgresqlVersion = "42.4.0" + postgresqlVersion = "42.4.1" cache2kVersion = "2.6.1.Final" nettyVersion = "4.1.79.Final" From 4759c4c0335c1767d59b89b27f0f5dcff2a77646 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 18 Aug 2022 19:09:33 +0000 Subject: [PATCH 066/105] Bump undertow-core in /frameworks/Java/light-java Bumps [undertow-core](https://github.com/undertow-io/undertow) from 2.2.15.Final to 2.2.19.Final. - [Release notes](https://github.com/undertow-io/undertow/releases) - [Commits](https://github.com/undertow-io/undertow/compare/2.2.15.Final...2.2.19.Final) --- updated-dependencies: - dependency-name: io.undertow:undertow-core dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/light-java/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/light-java/pom.xml b/frameworks/Java/light-java/pom.xml index ebe3634dc9d..499d698332b 100644 --- a/frameworks/Java/light-java/pom.xml +++ b/frameworks/Java/light-java/pom.xml @@ -25,7 +25,7 @@ 11 2.0.1 1.2.3 - 2.2.15.Final + 2.2.19.Final 3.3.1 8.0.28 42.4.1 From be64e352cfd44ca7acd5c5e6664f3ddbae19ab88 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 18 Aug 2022 19:09:43 +0000 Subject: [PATCH 067/105] Bump undertow-core in /frameworks/Java/undertow Bumps [undertow-core](https://github.com/undertow-io/undertow) from 2.2.18.Final to 2.2.19.Final. - [Release notes](https://github.com/undertow-io/undertow/releases) - [Commits](https://github.com/undertow-io/undertow/compare/2.2.18.Final...2.2.19.Final) --- updated-dependencies: - dependency-name: io.undertow:undertow-core dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- frameworks/Java/undertow/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Java/undertow/pom.xml b/frameworks/Java/undertow/pom.xml index 080c2cf7ae3..7244e5c4253 100644 --- a/frameworks/Java/undertow/pom.xml +++ b/frameworks/Java/undertow/pom.xml @@ -20,7 +20,7 @@ 3.2.2 0.9.10 42.4.1 - 2.2.18.Final + 2.2.19.Final From 05f31bfb8e1a32e5625fe7f95d2071591ded31c5 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 8 Sep 2022 17:11:53 +0200 Subject: [PATCH 068/105] Delete Gradle Wrapper --- .../hexagon/gradle/wrapper/gradle-wrapper.jar | Bin 59821 -> 0 bytes .../gradle/wrapper/gradle-wrapper.properties | 5 - frameworks/Kotlin/hexagon/gradlew | 234 ------------------ frameworks/Kotlin/hexagon/gradlew.bat | 89 ------- 4 files changed, 328 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar delete mode 100644 frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties delete mode 100755 frameworks/Kotlin/hexagon/gradlew delete mode 100644 frameworks/Kotlin/hexagon/gradlew.bat diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar deleted file mode 100644 index 41d9927a4d4fb3f96a785543079b8df6723c946b..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 59821 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 diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties deleted file mode 100644 index 41dfb87909a..00000000000 --- a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties +++ /dev/null @@ -1,5 +0,0 @@ -distributionBase=GRADLE_USER_HOME -distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-7.4-bin.zip -zipStoreBase=GRADLE_USER_HOME -zipStorePath=wrapper/dists diff --git a/frameworks/Kotlin/hexagon/gradlew b/frameworks/Kotlin/hexagon/gradlew deleted file mode 100755 index 1b6c787337f..00000000000 --- a/frameworks/Kotlin/hexagon/gradlew +++ /dev/null @@ -1,234 +0,0 @@ -#!/bin/sh - -# -# Copyright © 2015-2021 the original authors. -# -# Licensed 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 -# -# https://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. -# - -############################################################################## -# -# Gradle start up script for POSIX generated by Gradle. -# -# Important for running: -# -# (1) You need a POSIX-compliant shell to run this script. If your /bin/sh is -# noncompliant, but you have some other compliant shell such as ksh or -# bash, then to run this script, type that shell name before the whole -# command line, like: -# -# ksh Gradle -# -# Busybox and similar reduced shells will NOT work, because this script -# requires all of these POSIX shell features: -# * functions; -# * expansions «$var», «${var}», «${var:-default}», «${var+SET}», -# «${var#prefix}», «${var%suffix}», and «$( cmd )»; -# * compound commands having a testable exit status, especially «case»; -# * various built-in commands including «command», «set», and «ulimit». -# -# Important for patching: -# -# (2) This script targets any POSIX shell, so it avoids extensions provided -# by Bash, Ksh, etc; in particular arrays are avoided. -# -# The "traditional" practice of packing multiple parameters into a -# space-separated string is a well documented source of bugs and security -# problems, so this is (mostly) avoided, by progressively accumulating -# options in "$@", and eventually passing that to Java. -# -# Where the inherited environment variables (DEFAULT_JVM_OPTS, JAVA_OPTS, -# and GRADLE_OPTS) rely on word-splitting, this is performed explicitly; -# see the in-line comments for details. -# -# There are tweaks for specific operating systems such as AIX, CygWin, -# Darwin, MinGW, and NonStop. -# -# (3) This script is generated from the Groovy template -# https://github.com/gradle/gradle/blob/master/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt -# within the Gradle project. -# -# You can find Gradle at https://github.com/gradle/gradle/. -# -############################################################################## - -# Attempt to set APP_HOME - -# Resolve links: $0 may be a link -app_path=$0 - -# Need this for daisy-chained symlinks. -while - APP_HOME=${app_path%"${app_path##*/}"} # leaves a trailing /; empty if no leading path - [ -h "$app_path" ] -do - ls=$( ls -ld "$app_path" ) - link=${ls#*' -> '} - case $link in #( - /*) app_path=$link ;; #( - *) app_path=$APP_HOME$link ;; - esac -done - -APP_HOME=$( cd "${APP_HOME:-./}" && pwd -P ) || exit - -APP_NAME="Gradle" -APP_BASE_NAME=${0##*/} - -# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. -DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' - -# Use the maximum available, or set MAX_FD != -1 to use that value. -MAX_FD=maximum - -warn () { - echo "$*" -} >&2 - -die () { - echo - echo "$*" - echo - exit 1 -} >&2 - -# OS specific support (must be 'true' or 'false'). -cygwin=false -msys=false -darwin=false -nonstop=false -case "$( uname )" in #( - CYGWIN* ) cygwin=true ;; #( - Darwin* ) darwin=true ;; #( - MSYS* | MINGW* ) msys=true ;; #( - NONSTOP* ) nonstop=true ;; -esac - -CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar - - -# Determine the Java command to use to start the JVM. -if [ -n "$JAVA_HOME" ] ; then - if [ -x "$JAVA_HOME/jre/sh/java" ] ; then - # IBM's JDK on AIX uses strange locations for the executables - JAVACMD=$JAVA_HOME/jre/sh/java - else - JAVACMD=$JAVA_HOME/bin/java - fi - if [ ! -x "$JAVACMD" ] ; then - die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME - -Please set the JAVA_HOME variable in your environment to match the -location of your Java installation." - fi -else - JAVACMD=java - which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. - -Please set the JAVA_HOME variable in your environment to match the -location of your Java installation." -fi - -# Increase the maximum file descriptors if we can. -if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then - case $MAX_FD in #( - max*) - MAX_FD=$( ulimit -H -n ) || - warn "Could not query maximum file descriptor limit" - esac - case $MAX_FD in #( - '' | soft) :;; #( - *) - ulimit -n "$MAX_FD" || - warn "Could not set maximum file descriptor limit to $MAX_FD" - esac -fi - -# Collect all arguments for the java command, stacking in reverse order: -# * args from the command line -# * the main class name -# * -classpath -# * -D...appname settings -# * --module-path (only if needed) -# * DEFAULT_JVM_OPTS, JAVA_OPTS, and GRADLE_OPTS environment variables. - -# For Cygwin or MSYS, switch paths to Windows format before running java -if "$cygwin" || "$msys" ; then - APP_HOME=$( cygpath --path --mixed "$APP_HOME" ) - CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" ) - - JAVACMD=$( cygpath --unix "$JAVACMD" ) - - # Now convert the arguments - kludge to limit ourselves to /bin/sh - for arg do - if - case $arg in #( - -*) false ;; # don't mess with options #( - /?*) t=${arg#/} t=/${t%%/*} # looks like a POSIX filepath - [ -e "$t" ] ;; #( - *) false ;; - esac - then - arg=$( cygpath --path --ignore --mixed "$arg" ) - fi - # Roll the args list around exactly as many times as the number of - # args, so each arg winds up back in the position where it started, but - # possibly modified. - # - # NB: a `for` loop captures its iteration list before it begins, so - # changing the positional parameters here affects neither the number of - # iterations, nor the values presented in `arg`. - shift # remove old arg - set -- "$@" "$arg" # push replacement arg - done -fi - -# Collect all arguments for the java command; -# * $DEFAULT_JVM_OPTS, $JAVA_OPTS, and $GRADLE_OPTS can contain fragments of -# shell script including quotes and variable substitutions, so put them in -# double quotes to make sure that they get re-expanded; and -# * put everything else in single quotes, so that it's not re-expanded. - -set -- \ - "-Dorg.gradle.appname=$APP_BASE_NAME" \ - -classpath "$CLASSPATH" \ - org.gradle.wrapper.GradleWrapperMain \ - "$@" - -# Use "xargs" to parse quoted args. -# -# With -n1 it outputs one arg per line, with the quotes and backslashes removed. -# -# In Bash we could simply go: -# -# readarray ARGS < <( xargs -n1 <<<"$var" ) && -# set -- "${ARGS[@]}" "$@" -# -# but POSIX shell has neither arrays nor command substitution, so instead we -# post-process each arg (as a line of input to sed) to backslash-escape any -# character that might be a shell metacharacter, then use eval to reverse -# that process (while maintaining the separation between arguments), and wrap -# the whole thing up as a single "set" statement. -# -# This will of course break if any of these variables contains a newline or -# an unmatched quote. -# - -eval "set -- $( - printf '%s\n' "$DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS" | - xargs -n1 | - sed ' s~[^-[:alnum:]+,./:=@_]~\\&~g; ' | - tr '\n' ' ' - )" '"$@"' - -exec "$JAVACMD" "$@" diff --git a/frameworks/Kotlin/hexagon/gradlew.bat b/frameworks/Kotlin/hexagon/gradlew.bat deleted file mode 100644 index 107acd32c4e..00000000000 --- a/frameworks/Kotlin/hexagon/gradlew.bat +++ /dev/null @@ -1,89 +0,0 @@ -@rem -@rem Copyright 2015 the original author or authors. -@rem -@rem Licensed under the Apache License, Version 2.0 (the "License"); -@rem you may not use this file except in compliance with the License. -@rem You may obtain a copy of the License at -@rem -@rem https://www.apache.org/licenses/LICENSE-2.0 -@rem -@rem Unless required by applicable law or agreed to in writing, software -@rem distributed under the License is distributed on an "AS IS" BASIS, -@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -@rem See the License for the specific language governing permissions and -@rem limitations under the License. -@rem - -@if "%DEBUG%" == "" @echo off -@rem ########################################################################## -@rem -@rem Gradle startup script for Windows -@rem -@rem ########################################################################## - -@rem Set local scope for the variables with windows NT shell -if "%OS%"=="Windows_NT" setlocal - -set DIRNAME=%~dp0 -if "%DIRNAME%" == "" set DIRNAME=. -set APP_BASE_NAME=%~n0 -set APP_HOME=%DIRNAME% - -@rem Resolve any "." and ".." in APP_HOME to make it shorter. -for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi - -@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. -set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" - -@rem Find java.exe -if defined JAVA_HOME goto findJavaFromJavaHome - -set JAVA_EXE=java.exe -%JAVA_EXE% -version >NUL 2>&1 -if "%ERRORLEVEL%" == "0" goto execute - -echo. -echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. -echo. -echo Please set the JAVA_HOME variable in your environment to match the -echo location of your Java installation. - -goto fail - -:findJavaFromJavaHome -set JAVA_HOME=%JAVA_HOME:"=% -set JAVA_EXE=%JAVA_HOME%/bin/java.exe - -if exist "%JAVA_EXE%" goto execute - -echo. -echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% -echo. -echo Please set the JAVA_HOME variable in your environment to match the -echo location of your Java installation. - -goto fail - -:execute -@rem Setup the command line - -set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar - - -@rem Execute Gradle -"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* - -:end -@rem End local scope for the variables with windows NT shell -if "%ERRORLEVEL%"=="0" goto mainEnd - -:fail -rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of -rem the _cmd.exe /c_ return code! -if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 -exit /b 1 - -:mainEnd -if "%OS%"=="Windows_NT" endlocal - -:omega From 189e19de6cc85450cc23fd23237e9cd75899a324 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 8 Sep 2022 22:42:39 +0200 Subject: [PATCH 069/105] Use different JSON serializer --- frameworks/Kotlin/hexagon/build.gradle | 8 +++--- .../hexagon/src/main/kotlin/Controller.kt | 28 +++++++++++++++---- 2 files changed, 26 insertions(+), 10 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 1b41c2be7ce..4d3e714d3f4 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,12 +4,12 @@ plugins { } ext { - hexagonVersion = "2.0.17" + hexagonVersion = "2.0.22" hikariVersion = "5.0.1" jettyVersion = "11.0.11" - postgresqlVersion = "42.4.1" + postgresqlVersion = "42.5.0" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.79.Final" + nettyVersion = "4.1.80.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } @@ -36,7 +36,7 @@ dependencies { implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") implementation("com.hexagonkt:templates_pebble:$hexagonVersion") implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") - implementation("com.hexagonkt:serialization_jackson_json:$hexagonVersion") + implementation("com.hexagonkt:serialization_dsl_json:$hexagonVersion") implementation("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") implementation("org.cache2k:cache2k-core:$cache2kVersion") diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index 2c82ad706b8..b805071c521 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -1,5 +1,6 @@ package com.hexagonkt +import com.hexagonkt.core.fieldsMapOf import com.hexagonkt.core.media.ApplicationMedia.JSON import com.hexagonkt.core.media.TextMedia.HTML import com.hexagonkt.core.media.TextMedia.PLAIN @@ -10,7 +11,7 @@ import com.hexagonkt.http.server.handlers.HttpServerContext import com.hexagonkt.http.server.handlers.PathHandler import com.hexagonkt.http.server.handlers.path import com.hexagonkt.http.toHttpFormat -import com.hexagonkt.serialization.jackson.json.Json +import com.hexagonkt.serialization.dsl.json.Json import com.hexagonkt.serialization.serialize import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort @@ -47,7 +48,7 @@ class Controller( } get("/plaintext") { ok(settings.textMessage, contentType = plain) } - get("/json") { ok(Message(settings.textMessage).serialize(Json.raw), contentType = json) } + get("/json") { ok(Message(settings.textMessage).toMap().serialize(Json.raw), contentType = json) } get("/fortunes") { listFortunes(store, templateUrl, templateEngine) } get("/db") { dbQuery(store) } get("/query") { getWorlds(store) } @@ -71,7 +72,7 @@ class Controller( private fun HttpServerContext.dbQuery(store: BenchmarkStore): HttpServerContext { val ids = listOf(randomWorld()) val worlds = store.findWorlds(ids) - val world = worlds.first() + val world = worlds.first().toMap() return sendJson(world) } @@ -79,7 +80,7 @@ class Controller( private fun HttpServerContext.getWorlds(store: BenchmarkStore): HttpServerContext { val worldsCount = getWorldsCount(queriesParam) val ids = (1..worldsCount).map { randomWorld() } - val worlds = store.findWorlds(ids) + val worlds = store.findWorlds(ids).map { it.toMap() } return sendJson(worlds) } @@ -87,7 +88,7 @@ class Controller( private fun HttpServerContext.getCachedWorlds(store: BenchmarkStore): HttpServerContext { val worldsCount = getWorldsCount(cachedQueriesParam) val ids = (1..worldsCount).map { randomWorld() } - val worlds = store.findCachedWorlds(ids) + val worlds = store.findCachedWorlds(ids).map { it.toMap() } return sendJson(worlds) } @@ -98,7 +99,7 @@ class Controller( store.replaceWorlds(worlds) - return sendJson(worlds) + return sendJson(worlds.map { it.toMap() }) } private fun HttpServerContext.sendJson(body: Any): HttpServerContext = @@ -116,4 +117,19 @@ class Controller( private fun randomWorld(): Int = ThreadLocalRandom.current().nextInt(worldRows) + 1 + + private fun Message.toMap(): Map = + fieldsMapOf(Message::message to message) + + private fun World.toMap(): Map = + fieldsMapOf( + World::id to id, + World::randomNumber to randomNumber, + ) + + private fun CachedWorld.toMap(): Map = + fieldsMapOf( + CachedWorld::id to id, + CachedWorld::randomNumber to randomNumber, + ) } From 5e47af8fcd3b54154c169473195e2409c80cd75d Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 8 Sep 2022 22:53:18 +0200 Subject: [PATCH 070/105] Restore non Hexagon files --- frameworks/Java/dropwizard/pom.xml | 2 +- frameworks/Python/sanic/requirements.txt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/frameworks/Java/dropwizard/pom.xml b/frameworks/Java/dropwizard/pom.xml index 319c13f37ff..8fcbeb3c6b6 100644 --- a/frameworks/Java/dropwizard/pom.xml +++ b/frameworks/Java/dropwizard/pom.xml @@ -19,7 +19,7 @@ 2.3.0 8.0.28 2.9.4 - 42.4.1 + 42.3.3 3.8.0 3.1.0 3.1.1 diff --git a/frameworks/Python/sanic/requirements.txt b/frameworks/Python/sanic/requirements.txt index 36f8d2c8246..13b48a818a3 100644 --- a/frameworks/Python/sanic/requirements.txt +++ b/frameworks/Python/sanic/requirements.txt @@ -1,4 +1,4 @@ asyncpg==0.25.0 Jinja2==3.1.2 -sanic==22.6.1 +sanic==22.3.1 uvloop==0.16.0 From 67f6bf1a1794ee0450c3654cd23f7dba733ebdba Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 8 Sep 2022 23:25:40 +0200 Subject: [PATCH 071/105] Update Hexagon version --- frameworks/Kotlin/hexagon/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 4d3e714d3f4..fd9276185c4 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,7 +4,7 @@ plugins { } ext { - hexagonVersion = "2.0.22" + hexagonVersion = "2.0.23" hikariVersion = "5.0.1" jettyVersion = "11.0.11" postgresqlVersion = "42.5.0" From c2f187e8661ed5673a0e014a085848118ee9eb56 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 8 Sep 2022 23:45:00 +0200 Subject: [PATCH 072/105] Run pipeline From 61b499fbb3b447c38034566337db100c2ee8ad49 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 9 Sep 2022 08:19:30 +0200 Subject: [PATCH 073/105] Run pipeline From 4422de8915e70cdca67a07c2e0fdb0610757924b Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 15 Sep 2022 03:28:55 +0000 Subject: [PATCH 074/105] Bump axum-core from 0.2.7 to 0.2.8 in /frameworks/Rust/axum Bumps [axum-core](https://github.com/tokio-rs/axum) from 0.2.7 to 0.2.8. - [Release notes](https://github.com/tokio-rs/axum/releases) - [Changelog](https://github.com/tokio-rs/axum/blob/main/CHANGELOG.md) - [Commits](https://github.com/tokio-rs/axum/compare/axum-core-v0.2.7...axum-core-v0.2.8) --- updated-dependencies: - dependency-name: axum-core dependency-type: indirect ... Signed-off-by: dependabot[bot] --- frameworks/Rust/axum/Cargo.lock | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/frameworks/Rust/axum/Cargo.lock b/frameworks/Rust/axum/Cargo.lock index f7ced7468a4..dd0590e28d8 100644 --- a/frameworks/Rust/axum/Cargo.lock +++ b/frameworks/Rust/axum/Cargo.lock @@ -123,9 +123,9 @@ dependencies = [ [[package]] name = "axum-core" -version = "0.2.7" +version = "0.2.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e4f44a0e6200e9d11a1cdc989e4b358f6e3d354fbf48478f345a17f4e43f8635" +checksum = "d9f0c0a60006f2a293d82d571f635042a72edf927539b7685bd62d361963839b" dependencies = [ "async-trait", "bytes", @@ -133,6 +133,8 @@ dependencies = [ "http", "http-body", "mime", + "tower-layer", + "tower-service", ] [[package]] From 534bc5f5811e580b680ebd366449df3d2d37deb3 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 15 Sep 2022 11:28:41 +0200 Subject: [PATCH 075/105] Revert "Bump axum-core from 0.2.7 to 0.2.8 in /frameworks/Rust/axum" This reverts commit 4422de8915e70cdca67a07c2e0fdb0610757924b. --- frameworks/Rust/axum/Cargo.lock | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/frameworks/Rust/axum/Cargo.lock b/frameworks/Rust/axum/Cargo.lock index dd0590e28d8..f7ced7468a4 100644 --- a/frameworks/Rust/axum/Cargo.lock +++ b/frameworks/Rust/axum/Cargo.lock @@ -123,9 +123,9 @@ dependencies = [ [[package]] name = "axum-core" -version = "0.2.8" +version = "0.2.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9f0c0a60006f2a293d82d571f635042a72edf927539b7685bd62d361963839b" +checksum = "e4f44a0e6200e9d11a1cdc989e4b358f6e3d354fbf48478f345a17f4e43f8635" dependencies = [ "async-trait", "bytes", @@ -133,8 +133,6 @@ dependencies = [ "http", "http-body", "mime", - "tower-layer", - "tower-service", ] [[package]] From 9df2ba8c02756000be15e874e6a8151fc6b5ecc1 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Tue, 29 Nov 2022 14:22:23 +0100 Subject: [PATCH 076/105] Version updates, code refactor and new benchmark cases --- .../Kotlin/hexagon/benchmark_config.json | 69 +++++ frameworks/Kotlin/hexagon/build.gradle | 10 +- frameworks/Kotlin/hexagon/config.toml | 54 ++++ .../hexagon/gradle/wrapper/gradle-wrapper.jar | Bin 59536 -> 61574 bytes .../gradle/wrapper/gradle-wrapper.properties | 3 +- frameworks/Kotlin/hexagon/gradlew | 269 +++++++++++------- frameworks/Kotlin/hexagon/gradlew.bat | 15 +- .../hexagon-jettyloom-pgclient.dockerfile | 27 ++ .../hexagon/hexagon-jettyloom.dockerfile | 27 ++ .../Kotlin/hexagon/hexagon-netty.dockerfile | 9 +- .../hexagon-nettyepoll-pgclient.dockerfile | 27 ++ .../hexagon/hexagon-nettyepoll.dockerfile | 9 +- .../Kotlin/hexagon/hexagon-tomcat.dockerfile | 9 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 9 +- .../hexagon/src/main/kotlin/Benchmark.kt | 20 +- .../hexagon/src/main/kotlin/Controller.kt | 7 +- .../Kotlin/hexagon/src/main/kotlin/Model.kt | 6 - .../hexagon/src/main/kotlin/Settings.kt | 1 + .../src/main/kotlin/WebListenerServer.kt | 6 +- .../src/main/kotlin/model/CachedWorld.kt | 3 + .../hexagon/src/main/kotlin/model/Fortune.kt | 3 + .../hexagon/src/main/kotlin/model/Message.kt | 3 + .../hexagon/src/main/kotlin/model/World.kt | 3 + .../kotlin/store/BenchmarkPgClientStore.kt | 116 ++++++++ .../main/kotlin/store/BenchmarkSqlStore.kt | 21 +- .../src/main/kotlin/store/BenchmarkStore.kt | 6 +- 26 files changed, 574 insertions(+), 158 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile create mode 100644 frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile create mode 100644 frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile delete mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/Model.kt create mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/model/CachedWorld.kt create mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/model/Fortune.kt create mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/model/Message.kt create mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/model/World.kt create mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkPgClientStore.kt diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index fd4254a3355..2a4022a088b 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -25,6 +25,52 @@ "notes": "http://hexagonkt.com", "versus": "servlet" }, + "jettyloom": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Servlet", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Jetty Loom PostgreSQL", + "notes": "http://hexagonkt.com", + "versus": "servlet" + }, + "jettyloom-pgclient": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Servlet", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Jetty Loom PgClient", + "notes": "http://hexagonkt.com", + "versus": "servlet" + }, "netty": { "json_url": "/json", "db_url": "/db", @@ -71,6 +117,29 @@ "notes": "http://hexagonkt.com", "versus": "netty" }, + "nettyepoll-pgclient": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Netty", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Netty Epoll PgClient", + "notes": "http://hexagonkt.com", + "versus": "netty" + }, "tomcat": { "json_url": "/json", "db_url": "/db", diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index fd9276185c4..ad55d00bcfd 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,15 +1,16 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.7.10" + id "org.jetbrains.kotlin.jvm" version "1.7.22" } ext { - hexagonVersion = "2.0.23" + hexagonVersion = "2.2.7" hikariVersion = "5.0.1" - jettyVersion = "11.0.11" + jettyVersion = "11.0.12" postgresqlVersion = "42.5.0" + vertxVersion = "4.3.5" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.80.Final" + nettyVersion = "4.1.85.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } @@ -42,6 +43,7 @@ dependencies { implementation("org.cache2k:cache2k-core:$cache2kVersion") implementation("com.zaxxer:HikariCP:$hikariVersion") implementation("org.postgresql:postgresql:$postgresqlVersion") + implementation("io.vertx:vertx-pg-client:$vertxVersion") // providedCompile excludes the dependency only in the WAR, not in the distribution providedCompile("org.eclipse.jetty:jetty-webapp:$jettyVersion") { exclude module: "slf4j-api" } diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index ad228b9203e..d51d0e8ccf6 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -19,6 +19,42 @@ platform = "Servlet" webserver = "None" versus = "servlet" +[jettyloom] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Servlet" +webserver = "None" +versus = "servlet" + +[jettyloom-pgclient] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Servlet" +webserver = "None" +versus = "servlet" + [netty] urls.plaintext = "/plaintext" urls.json = "/json" @@ -55,6 +91,24 @@ platform = "Netty" webserver = "None" versus = "netty" +[nettyepoll-pgclient] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Netty" +webserver = "None" +versus = "netty" + [tomcat] urls.plaintext = "/plaintext" urls.json = "/json" diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar index 7454180f2ae8848c63b8b4dea2cb829da983f2fa..943f0cbfa754578e88a3dae77fce6e3dea56edbf 100644 GIT binary patch delta 36900 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

yHlr~Qj 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 GTKgBj+ffbx diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties index 05679dc3c18..3f4def4a917 100644 --- a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties +++ b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties @@ -1,5 +1,6 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-7.1.1-bin.zip +distributionUrl=https://services.gradle.org/distributions/gradle-7.6-bin.zip +networkTimeout=10000 zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/frameworks/Kotlin/hexagon/gradlew b/frameworks/Kotlin/hexagon/gradlew index 744e882ed57..65dcd68d65c 100755 --- a/frameworks/Kotlin/hexagon/gradlew +++ b/frameworks/Kotlin/hexagon/gradlew @@ -1,7 +1,7 @@ -#!/usr/bin/env sh +#!/bin/sh # -# Copyright 2015 the original author or authors. +# Copyright © 2015-2021 the original authors. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. @@ -17,67 +17,101 @@ # ############################################################################## -## -## Gradle start up script for UN*X -## +# +# Gradle start up script for POSIX generated by Gradle. +# +# Important for running: +# +# (1) You need a POSIX-compliant shell to run this script. If your /bin/sh is +# noncompliant, but you have some other compliant shell such as ksh or +# bash, then to run this script, type that shell name before the whole +# command line, like: +# +# ksh Gradle +# +# Busybox and similar reduced shells will NOT work, because this script +# requires all of these POSIX shell features: +# * functions; +# * expansions «$var», «${var}», «${var:-default}», «${var+SET}», +# «${var#prefix}», «${var%suffix}», and «$( cmd )»; +# * compound commands having a testable exit status, especially «case»; +# * various built-in commands including «command», «set», and «ulimit». +# +# Important for patching: +# +# (2) This script targets any POSIX shell, so it avoids extensions provided +# by Bash, Ksh, etc; in particular arrays are avoided. +# +# The "traditional" practice of packing multiple parameters into a +# space-separated string is a well documented source of bugs and security +# problems, so this is (mostly) avoided, by progressively accumulating +# options in "$@", and eventually passing that to Java. +# +# Where the inherited environment variables (DEFAULT_JVM_OPTS, JAVA_OPTS, +# and GRADLE_OPTS) rely on word-splitting, this is performed explicitly; +# see the in-line comments for details. +# +# There are tweaks for specific operating systems such as AIX, CygWin, +# Darwin, MinGW, and NonStop. +# +# (3) This script is generated from the Groovy template +# https://github.com/gradle/gradle/blob/HEAD/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt +# within the Gradle project. +# +# You can find Gradle at https://github.com/gradle/gradle/. +# ############################################################################## # Attempt to set APP_HOME + # Resolve links: $0 may be a link -PRG="$0" -# Need this for relative symlinks. -while [ -h "$PRG" ] ; do - ls=`ls -ld "$PRG"` - link=`expr "$ls" : '.*-> \(.*\)$'` - if expr "$link" : '/.*' > /dev/null; then - PRG="$link" - else - PRG=`dirname "$PRG"`"/$link" - fi +app_path=$0 + +# Need this for daisy-chained symlinks. +while + APP_HOME=${app_path%"${app_path##*/}"} # leaves a trailing /; empty if no leading path + [ -h "$app_path" ] +do + ls=$( ls -ld "$app_path" ) + link=${ls#*' -> '} + case $link in #( + /*) app_path=$link ;; #( + *) app_path=$APP_HOME$link ;; + esac done -SAVED="`pwd`" -cd "`dirname \"$PRG\"`/" >/dev/null -APP_HOME="`pwd -P`" -cd "$SAVED" >/dev/null -APP_NAME="Gradle" -APP_BASE_NAME=`basename "$0"` +# This is normally unused +# shellcheck disable=SC2034 +APP_BASE_NAME=${0##*/} +APP_HOME=$( cd "${APP_HOME:-./}" && pwd -P ) || exit # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' # Use the maximum available, or set MAX_FD != -1 to use that value. -MAX_FD="maximum" +MAX_FD=maximum warn () { echo "$*" -} +} >&2 die () { echo echo "$*" echo exit 1 -} +} >&2 # OS specific support (must be 'true' or 'false'). cygwin=false msys=false darwin=false nonstop=false -case "`uname`" in - CYGWIN* ) - cygwin=true - ;; - Darwin* ) - darwin=true - ;; - MSYS* | MINGW* ) - msys=true - ;; - NONSTOP* ) - nonstop=true - ;; +case "$( uname )" in #( + CYGWIN* ) cygwin=true ;; #( + Darwin* ) darwin=true ;; #( + MSYS* | MINGW* ) msys=true ;; #( + NONSTOP* ) nonstop=true ;; esac CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar @@ -87,9 +121,9 @@ CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar if [ -n "$JAVA_HOME" ] ; then if [ -x "$JAVA_HOME/jre/sh/java" ] ; then # IBM's JDK on AIX uses strange locations for the executables - JAVACMD="$JAVA_HOME/jre/sh/java" + JAVACMD=$JAVA_HOME/jre/sh/java else - JAVACMD="$JAVA_HOME/bin/java" + JAVACMD=$JAVA_HOME/bin/java fi if [ ! -x "$JAVACMD" ] ; then die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME @@ -98,7 +132,7 @@ Please set the JAVA_HOME variable in your environment to match the location of your Java installation." fi else - JAVACMD="java" + JAVACMD=java which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. Please set the JAVA_HOME variable in your environment to match the @@ -106,80 +140,105 @@ location of your Java installation." fi # Increase the maximum file descriptors if we can. -if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then - MAX_FD_LIMIT=`ulimit -H -n` - if [ $? -eq 0 ] ; then - if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then - MAX_FD="$MAX_FD_LIMIT" - fi - ulimit -n $MAX_FD - if [ $? -ne 0 ] ; then - warn "Could not set maximum file descriptor limit: $MAX_FD" - fi - else - warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" - fi +if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then + case $MAX_FD in #( + max*) + # In POSIX sh, ulimit -H is undefined. That's why the result is checked to see if it worked. + # shellcheck disable=SC3045 + MAX_FD=$( ulimit -H -n ) || + warn "Could not query maximum file descriptor limit" + esac + case $MAX_FD in #( + '' | soft) :;; #( + *) + # In POSIX sh, ulimit -n is undefined. That's why the result is checked to see if it worked. + # shellcheck disable=SC3045 + ulimit -n "$MAX_FD" || + warn "Could not set maximum file descriptor limit to $MAX_FD" + esac fi -# For Darwin, add options to specify how the application appears in the dock -if $darwin; then - GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" -fi +# Collect all arguments for the java command, stacking in reverse order: +# * args from the command line +# * the main class name +# * -classpath +# * -D...appname settings +# * --module-path (only if needed) +# * DEFAULT_JVM_OPTS, JAVA_OPTS, and GRADLE_OPTS environment variables. # For Cygwin or MSYS, switch paths to Windows format before running java -if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then - APP_HOME=`cygpath --path --mixed "$APP_HOME"` - CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` - - JAVACMD=`cygpath --unix "$JAVACMD"` - - # We build the pattern for arguments to be converted via cygpath - ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` - SEP="" - for dir in $ROOTDIRSRAW ; do - ROOTDIRS="$ROOTDIRS$SEP$dir" - SEP="|" - done - OURCYGPATTERN="(^($ROOTDIRS))" - # Add a user-defined pattern to the cygpath arguments - if [ "$GRADLE_CYGPATTERN" != "" ] ; then - OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" - fi +if "$cygwin" || "$msys" ; then + APP_HOME=$( cygpath --path --mixed "$APP_HOME" ) + CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" ) + + JAVACMD=$( cygpath --unix "$JAVACMD" ) + # Now convert the arguments - kludge to limit ourselves to /bin/sh - i=0 - for arg in "$@" ; do - CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` - CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option - - if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition - eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` - else - eval `echo args$i`="\"$arg\"" + for arg do + if + case $arg in #( + -*) false ;; # don't mess with options #( + /?*) t=${arg#/} t=/${t%%/*} # looks like a POSIX filepath + [ -e "$t" ] ;; #( + *) false ;; + esac + then + arg=$( cygpath --path --ignore --mixed "$arg" ) fi - i=`expr $i + 1` + # Roll the args list around exactly as many times as the number of + # args, so each arg winds up back in the position where it started, but + # possibly modified. + # + # NB: a `for` loop captures its iteration list before it begins, so + # changing the positional parameters here affects neither the number of + # iterations, nor the values presented in `arg`. + shift # remove old arg + set -- "$@" "$arg" # push replacement arg done - case $i in - 0) set -- ;; - 1) set -- "$args0" ;; - 2) set -- "$args0" "$args1" ;; - 3) set -- "$args0" "$args1" "$args2" ;; - 4) set -- "$args0" "$args1" "$args2" "$args3" ;; - 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; - 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; - 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; - 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; - 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; - esac fi -# Escape application args -save () { - for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done - echo " " -} -APP_ARGS=`save "$@"` +# Collect all arguments for the java command; +# * $DEFAULT_JVM_OPTS, $JAVA_OPTS, and $GRADLE_OPTS can contain fragments of +# shell script including quotes and variable substitutions, so put them in +# double quotes to make sure that they get re-expanded; and +# * put everything else in single quotes, so that it's not re-expanded. + +set -- \ + "-Dorg.gradle.appname=$APP_BASE_NAME" \ + -classpath "$CLASSPATH" \ + org.gradle.wrapper.GradleWrapperMain \ + "$@" + +# Stop when "xargs" is not available. +if ! command -v xargs >/dev/null 2>&1 +then + die "xargs is not available" +fi + +# Use "xargs" to parse quoted args. +# +# With -n1 it outputs one arg per line, with the quotes and backslashes removed. +# +# In Bash we could simply go: +# +# readarray ARGS < <( xargs -n1 <<<"$var" ) && +# set -- "${ARGS[@]}" "$@" +# +# but POSIX shell has neither arrays nor command substitution, so instead we +# post-process each arg (as a line of input to sed) to backslash-escape any +# character that might be a shell metacharacter, then use eval to reverse +# that process (while maintaining the separation between arguments), and wrap +# the whole thing up as a single "set" statement. +# +# This will of course break if any of these variables contains a newline or +# an unmatched quote. +# -# Collect all arguments for the java command, following the shell quoting and substitution rules -eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" +eval "set -- $( + printf '%s\n' "$DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS" | + xargs -n1 | + sed ' s~[^-[:alnum:]+,./:=@_]~\\&~g; ' | + tr '\n' ' ' + )" '"$@"' exec "$JAVACMD" "$@" diff --git a/frameworks/Kotlin/hexagon/gradlew.bat b/frameworks/Kotlin/hexagon/gradlew.bat index 107acd32c4e..93e3f59f135 100644 --- a/frameworks/Kotlin/hexagon/gradlew.bat +++ b/frameworks/Kotlin/hexagon/gradlew.bat @@ -14,7 +14,7 @@ @rem limitations under the License. @rem -@if "%DEBUG%" == "" @echo off +@if "%DEBUG%"=="" @echo off @rem ########################################################################## @rem @rem Gradle startup script for Windows @@ -25,7 +25,8 @@ if "%OS%"=="Windows_NT" setlocal set DIRNAME=%~dp0 -if "%DIRNAME%" == "" set DIRNAME=. +if "%DIRNAME%"=="" set DIRNAME=. +@rem This is normally unused set APP_BASE_NAME=%~n0 set APP_HOME=%DIRNAME% @@ -40,7 +41,7 @@ if defined JAVA_HOME goto findJavaFromJavaHome set JAVA_EXE=java.exe %JAVA_EXE% -version >NUL 2>&1 -if "%ERRORLEVEL%" == "0" goto execute +if %ERRORLEVEL% equ 0 goto execute echo. echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. @@ -75,13 +76,15 @@ set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar :end @rem End local scope for the variables with windows NT shell -if "%ERRORLEVEL%"=="0" goto mainEnd +if %ERRORLEVEL% equ 0 goto mainEnd :fail rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of rem the _cmd.exe /c_ return code! -if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 -exit /b 1 +set EXIT_CODE=%ERRORLEVEL% +if %EXIT_CODE% equ 0 set EXIT_CODE=1 +if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE% +exit /b %EXIT_CODE% :mainEnd if "%OS%"=="Windows_NT" endlocal diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile new file mode 100644 index 00000000000..18d9d309d13 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile @@ -0,0 +1,27 @@ +# +# BUILD +# +FROM gradle:7.5.1-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +COPY src src +COPY build.gradle build.gradle +RUN gradle --quiet -x test + +# +# RUNTIME +# +FROM eclipse-temurin:19-jre-alpine +ENV DBSTORE pg_client +ENV POSTGRESQL_DB_HOST tfb-database +ENV WEBENGINE jetty_loom +ENV PROJECT hexagon +ENV DISABLE_CHECKS true +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT + +EXPOSE 9090 + +ENTRYPOINT /opt/$PROJECT/bin/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile new file mode 100644 index 00000000000..e681fc03572 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile @@ -0,0 +1,27 @@ +# +# BUILD +# +FROM gradle:7.5.1-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +COPY src src +COPY build.gradle build.gradle +RUN gradle --quiet -x test + +# +# RUNTIME +# +FROM eclipse-temurin:19-jre-alpine +ENV DBSTORE postgresql +ENV POSTGRESQL_DB_HOST tfb-database +ENV WEBENGINE jetty_loom +ENV PROJECT hexagon +ENV DISABLE_CHECKS true +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT + +EXPOSE 9090 + +ENTRYPOINT /opt/$PROJECT/bin/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index 579a9402136..05c93562cf0 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -1,25 +1,26 @@ # # BUILD # -FROM gradle:7.5.0-jdk17-alpine AS gradle_build +FROM gradle:7.5.1-jdk17-alpine AS build USER root WORKDIR /hexagon COPY src src COPY build.gradle build.gradle -RUN gradle --quiet +RUN gradle --quiet -x test # # RUNTIME # -FROM eclipse-temurin:17-jre-alpine +FROM eclipse-temurin:19-jre-alpine ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE netty ENV PROJECT hexagon ENV DISABLE_CHECKS true +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile new file mode 100644 index 00000000000..efc4db12aaa --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile @@ -0,0 +1,27 @@ +# +# BUILD +# +FROM gradle:7.5.1-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +COPY src src +COPY build.gradle build.gradle +RUN gradle --quiet -x test + +# +# RUNTIME +# +FROM eclipse-temurin:19-jre-alpine +ENV DBSTORE pg_client +ENV POSTGRESQL_DB_HOST tfb-database +ENV WEBENGINE netty_epoll +ENV PROJECT hexagon +ENV DISABLE_CHECKS true +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT + +EXPOSE 9090 + +ENTRYPOINT /opt/$PROJECT/bin/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile index e9caab6bc32..87260f430e9 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -1,25 +1,26 @@ # # BUILD # -FROM gradle:7.5.0-jdk17-alpine AS gradle_build +FROM gradle:7.5.1-jdk17-alpine AS build USER root WORKDIR /hexagon COPY src src COPY build.gradle build.gradle -RUN gradle --quiet +RUN gradle --quiet -x test # # RUNTIME # -FROM eclipse-temurin:17-jre-alpine +FROM eclipse-temurin:19-jre-alpine ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE netty_epoll ENV PROJECT hexagon ENV DISABLE_CHECKS true +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index 5134fedad4c..d15c7180a93 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -1,21 +1,22 @@ # # BUILD # -FROM gradle:7.5.0-jdk17-alpine AS gradle_build +FROM gradle:7.5.1-jdk17-alpine AS build USER root WORKDIR /hexagon COPY src src COPY build.gradle build.gradle -RUN gradle --quiet +RUN gradle --quiet -x test # # RUNTIME # -FROM tomcat:10.1.0-jre17-temurin +FROM tomcat:10.1.2-jre17-temurin ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV DISABLE_CHECKS true +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=gradle_build /hexagon/build/libs/ROOT.war /usr/local/tomcat/webapps/ROOT.war +COPY --from=build /hexagon/build/libs/ROOT.war /usr/local/tomcat/webapps/ROOT.war EXPOSE 8080 diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 465f2d82146..6edc32dc1dd 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,25 +1,26 @@ # # BUILD # -FROM gradle:7.5.0-jdk17-alpine AS gradle_build +FROM gradle:7.5.1-jdk17-alpine AS build USER root WORKDIR /hexagon COPY src src COPY build.gradle build.gradle -RUN gradle --quiet +RUN gradle --quiet -x test # # RUNTIME # -FROM eclipse-temurin:17-jre-alpine +FROM eclipse-temurin:19-jre-alpine ENV DBSTORE postgresql ENV POSTGRESQL_DB_HOST tfb-database ENV WEBENGINE jetty ENV PROJECT hexagon ENV DISABLE_CHECKS true +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=gradle_build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt index 310bbb81c0a..a296a9d261d 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt @@ -6,7 +6,9 @@ import com.hexagonkt.http.server.HttpServerSettings import com.hexagonkt.http.server.jetty.JettyServletAdapter import com.hexagonkt.http.server.netty.NettyServerAdapter import com.hexagonkt.http.server.netty.epoll.NettyEpollServerAdapter +import com.hexagonkt.store.BenchmarkPgClientStore import com.hexagonkt.store.BenchmarkSqlStore +import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.pebble.PebbleAdapter import java.net.InetAddress @@ -19,14 +21,28 @@ private val engines: Map by lazy { sendServerVersion = settings.sendServerVersion, sendXPoweredBy = settings.sendXPoweredBy, ), + "jetty_loom" to JettyServletAdapter( + sendDateHeader = settings.sendDateHeader, + sendServerVersion = settings.sendServerVersion, + sendXPoweredBy = settings.sendXPoweredBy, + useVirtualThreads = true, + ), "netty" to NettyServerAdapter(), "netty_epoll" to NettyEpollServerAdapter(), ) } -private val server: HttpServer by lazy { +private val stores: Map by lazy { + mapOf( + "postgresql" to BenchmarkSqlStore("postgresql"), + "pg_client" to BenchmarkPgClientStore("postgresql"), + ) +} + +internal val server: HttpServer by lazy { val engine = engines[settings.webEngine] ?: error("Unsupported server engine") - val controller = Controller(settings, BenchmarkSqlStore("postgresql"), PebbleAdapter) + val store = stores[settings.dataStore] ?: error("Unsupported data store") + val controller = Controller(settings, store, PebbleAdapter()) val serverSettings = HttpServerSettings( bindAddress = InetAddress.getByName(settings.bindAddress), bindPort = settings.bindPort, diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt index b805071c521..ce82a5c152f 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt @@ -6,11 +6,12 @@ import com.hexagonkt.core.media.TextMedia.HTML import com.hexagonkt.core.media.TextMedia.PLAIN import com.hexagonkt.http.model.ContentType import com.hexagonkt.http.model.Header -import com.hexagonkt.http.model.HttpFields +import com.hexagonkt.http.model.Headers import com.hexagonkt.http.server.handlers.HttpServerContext import com.hexagonkt.http.server.handlers.PathHandler import com.hexagonkt.http.server.handlers.path import com.hexagonkt.http.toHttpFormat +import com.hexagonkt.model.* import com.hexagonkt.serialization.dsl.json.Json import com.hexagonkt.serialization.serialize import com.hexagonkt.store.BenchmarkStore @@ -37,7 +38,7 @@ class Controller( private val templateUrl: URL = URL("classpath:fortunes.pebble.html") - private val headers = HttpFields( + private val headers = Headers( Header("server", "Hexagon"), ) @@ -106,7 +107,7 @@ class Controller( ok(body.serialize(Json.raw), contentType = json) private fun HttpServerContext.getWorldsCount(parameter: String): Int = - request.queryParameters[parameter]?.toIntOrNull().let { + request.queryParameters[parameter]?.value?.toIntOrNull().let { when { it == null -> 1 it < 1 -> 1 diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Model.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Model.kt deleted file mode 100644 index be314dcd20a..00000000000 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Model.kt +++ /dev/null @@ -1,6 +0,0 @@ -package com.hexagonkt - -data class Message(val message: String) -data class Fortune(val id: Int, val message: String) -data class World(val id: Int, val randomNumber: Int) -data class CachedWorld(val id: Int, val randomNumber: Int) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt index e5c9994f856..36c8f8f44e2 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt @@ -16,6 +16,7 @@ data class Settings( val maximumPoolSize: Int = systemSettingOrNull("maximumPoolSize") ?: 96, val webEngine: String = systemSettingOrNull("WEBENGINE") ?: "jetty", + val dataStore: String = systemSettingOrNull("DATASTORE") ?: "postgresql", val worldName: String = systemSettingOrNull("worldCollection") ?: "world", val fortuneName: String = systemSettingOrNull("fortuneCollection") ?: "fortune", diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt index d269138faec..7da14b44cf5 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt @@ -1,7 +1,7 @@ package com.hexagonkt import com.hexagonkt.http.model.Header -import com.hexagonkt.http.model.HttpFields +import com.hexagonkt.http.model.Headers import com.hexagonkt.http.server.handlers.HttpHandler import com.hexagonkt.http.server.handlers.OnHandler import com.hexagonkt.http.server.servlet.ServletServer @@ -12,10 +12,10 @@ import jakarta.servlet.annotation.WebListener @WebListener class WebListenerServer(settings: Settings = Settings()) : ServletServer(createHandlers(settings)) { private companion object { - val headers = HttpFields(Header("server", "Tomcat")) + val headers = Headers(Header("server", "Tomcat")) fun createHandlers(settings: Settings): List { - val controller = Controller(settings, BenchmarkSqlStore("postgresql"), PebbleAdapter) + val controller = Controller(settings, BenchmarkSqlStore("postgresql"), PebbleAdapter()) val controllerPath = controller.path val serverHeaderHandler = OnHandler("*") { send(headers = headers) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/CachedWorld.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/model/CachedWorld.kt new file mode 100644 index 00000000000..101176e3c39 --- /dev/null +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/model/CachedWorld.kt @@ -0,0 +1,3 @@ +package com.hexagonkt.model + +data class CachedWorld(val id: Int, val randomNumber: Int) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/Fortune.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/model/Fortune.kt new file mode 100644 index 00000000000..b4781735ec1 --- /dev/null +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/model/Fortune.kt @@ -0,0 +1,3 @@ +package com.hexagonkt.model + +data class Fortune(val id: Int, val message: String) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/Message.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/model/Message.kt new file mode 100644 index 00000000000..090dcbf0be6 --- /dev/null +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/model/Message.kt @@ -0,0 +1,3 @@ +package com.hexagonkt.model + +data class Message(val message: String) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/World.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/model/World.kt new file mode 100644 index 00000000000..5f3316f9a5a --- /dev/null +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/model/World.kt @@ -0,0 +1,3 @@ +package com.hexagonkt.model + +data class World(val id: Int, val randomNumber: Int) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkPgClientStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkPgClientStore.kt new file mode 100644 index 00000000000..cd467c6c34d --- /dev/null +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkPgClientStore.kt @@ -0,0 +1,116 @@ +package com.hexagonkt.store + +import com.hexagonkt.Settings +import com.hexagonkt.core.Jvm +import com.hexagonkt.model.CachedWorld +import com.hexagonkt.model.Fortune +import com.hexagonkt.model.World +import io.vertx.core.Future +import io.vertx.pgclient.PgConnectOptions +import io.vertx.pgclient.PgPool +import io.vertx.sqlclient.* +import org.cache2k.Cache + +internal class BenchmarkPgClientStore( + engine: String, private val settings: Settings = Settings() +) : BenchmarkStore(settings) { + + companion object { + private const val SELECT_WORLD: String = "select * from world where id = $1" + private const val UPDATE_WORLD: String = "update world set randomNumber = $1 where id = $2" + private const val SELECT_ALL_FORTUNES: String = "select * from fortune" + } + + private val connectOptions: PgConnectOptions by lazy { + PgConnectOptions().apply { + host = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "localhost" + database = settings.databaseName + user = settings.databaseUsername + password = settings.databasePassword + cachePreparedStatements = true + } + } + + private val poolOptions: PoolOptions by lazy { + PoolOptions().apply { + val environment = Jvm.systemSettingOrNull("BENCHMARK_ENV")?.lowercase() + maxSize = 8 + if (environment == "citrine") Jvm.cpuCount else Jvm.cpuCount * 2 + } + } + + private val dataSource: SqlClient by lazy { PgPool.client(connectOptions, poolOptions) } + + override fun findAllFortunes(): List = + dataSource.preparedQuery(SELECT_ALL_FORTUNES) + .execute() + .map { rowSet -> + rowSet.map { row -> + Fortune(row.getInteger(0), row.getString(1)) + } + } + .toCompletionStage() + .toCompletableFuture() + .get() + + override fun findWorlds(ids: List): List = + ids.map { + findWorld(it, dataSource).toCompletionStage().toCompletableFuture().get() + } + + override fun replaceWorlds(worlds: List) { + worlds.forEach { + val worldId = it.id + val newRandomNumber = it.randomNumber + dataSource + .preparedQuery(SELECT_WORLD) + .execute(Tuple.of(worldId)) + .map { rowSet -> + val row = rowSet.iterator().next() + row.getInteger(1) // Read 'randomNumber' to comply with Test type 5, point 6 + dataSource + .preparedQuery(UPDATE_WORLD) + .execute(Tuple.of(newRandomNumber, worldId)) + } + .toCompletionStage() + .toCompletableFuture() + .get() + + } + } + + override fun initWorldsCache(cache: Cache) { + dataSource + .preparedQuery("select * from world") + .execute() + .map { rowSet -> + rowSet.map { row -> + val id = row.getInteger(0) + val randomNumber = row.getInteger(1) + cache.put(id, CachedWorld(id, randomNumber)) + } + } + .toCompletionStage() + .toCompletableFuture() + .get() + } + + override fun loadCachedWorld(id: Int): CachedWorld = + findWorld(id, dataSource) + .map { world -> CachedWorld(world.id, world.randomNumber) } + .toCompletionStage() + .toCompletableFuture() + .get() + + override fun close() { + dataSource.close() + } + + private fun findWorld(id: Int, client: SqlClient): Future = + client + .preparedQuery(SELECT_WORLD) + .execute(Tuple.of(id)) + .map { rowSet -> + val row = rowSet.iterator().next() + World(row.getInteger(0), row.getInteger(1)) + } +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt index f2d68d7cb6c..157ad7c982c 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt @@ -1,9 +1,9 @@ package com.hexagonkt.store -import com.hexagonkt.CachedWorld -import com.hexagonkt.Fortune +import com.hexagonkt.model.CachedWorld +import com.hexagonkt.model.Fortune import com.hexagonkt.Settings -import com.hexagonkt.World +import com.hexagonkt.model.World import com.hexagonkt.core.Jvm import com.zaxxer.hikari.HikariConfig import com.zaxxer.hikari.HikariDataSource @@ -11,13 +11,14 @@ import org.cache2k.Cache import java.sql.Connection import java.sql.PreparedStatement -internal class BenchmarkSqlStore(engine: String, private val settings: Settings = Settings()) - : BenchmarkStore(settings) { +internal class BenchmarkSqlStore( + engine: String, private val settings: Settings = Settings() +) : BenchmarkStore(settings) { companion object { - private const val SELECT_WORLD = "select * from world where id = ?" - private const val UPDATE_WORLD = "update world set randomNumber = ? where id = ?" - private const val SELECT_ALL_FORTUNES = "select * from fortune" + private const val SELECT_WORLD: String = "select * from world where id = ?" + private const val UPDATE_WORLD: String = "update world set randomNumber = ? where id = ?" + private const val SELECT_ALL_FORTUNES: String = "select * from fortune" } private val dataSource: HikariDataSource by lazy { @@ -102,7 +103,9 @@ internal class BenchmarkSqlStore(engine: String, private val settings: Settings dataSource.close() } - private fun Connection.findWorld(id: Int, stmtSelect: PreparedStatement = prepareStatement(SELECT_WORLD)): World { + private fun Connection.findWorld( + id: Int, stmtSelect: PreparedStatement = prepareStatement(SELECT_WORLD) + ): World { stmtSelect.setInt(1, id) val rs = stmtSelect.executeQuery() rs.next() diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt index 2c6ce918128..5182fe4ccae 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt +++ b/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt @@ -1,9 +1,9 @@ package com.hexagonkt.store -import com.hexagonkt.CachedWorld -import com.hexagonkt.Fortune +import com.hexagonkt.model.CachedWorld +import com.hexagonkt.model.Fortune import com.hexagonkt.Settings -import com.hexagonkt.World +import com.hexagonkt.model.World import org.cache2k.Cache import org.cache2k.Cache2kBuilder From 2eda84c7a5658c100df2b8cfa246149e53b24331 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Tue, 3 Jan 2023 20:20:22 +0100 Subject: [PATCH 077/105] Version updates --- frameworks/Kotlin/hexagon/build.gradle | 15 ++++++++------- .../hexagon/hexagon-jettyloom-pgclient.dockerfile | 2 +- .../Kotlin/hexagon/hexagon-jettyloom.dockerfile | 2 +- .../Kotlin/hexagon/hexagon-netty.dockerfile | 2 +- .../hexagon-nettyepoll-pgclient.dockerfile | 2 +- .../Kotlin/hexagon/hexagon-nettyepoll.dockerfile | 2 +- .../Kotlin/hexagon/hexagon-tomcat.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 2 +- 8 files changed, 15 insertions(+), 14 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index ad55d00bcfd..d4830752b19 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,16 +1,17 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.7.22" + id "org.jetbrains.kotlin.jvm" version "1.8.0" } ext { - hexagonVersion = "2.2.7" + hexagonVersion = "2.3.1" + hexagonExtraVersion = "2.3.1" hikariVersion = "5.0.1" - jettyVersion = "11.0.12" - postgresqlVersion = "42.5.0" - vertxVersion = "4.3.5" + jettyVersion = "11.0.13" + postgresqlVersion = "42.5.1" + vertxVersion = "4.3.7" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.85.Final" + nettyVersion = "4.1.86.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } @@ -49,7 +50,7 @@ dependencies { providedCompile("org.eclipse.jetty:jetty-webapp:$jettyVersion") { exclude module: "slf4j-api" } } -task("minimizeTemplate") { +tasks.register("minimizeTemplate") { doLast { File template = file("$buildDir/resources/main/fortunes.pebble.html") List lines = template.readLines().collect { it.trim() } diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile index 18d9d309d13..0325868b645 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.5.1-jdk17-alpine AS build +FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile index e681fc03572..2bd37096b09 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.5.1-jdk17-alpine AS build +FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index 05c93562cf0..9c11f65f9ae 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.5.1-jdk17-alpine AS build +FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile index efc4db12aaa..2ceeae57fe7 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.5.1-jdk17-alpine AS build +FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile index 87260f430e9..31052f788cd 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.5.1-jdk17-alpine AS build +FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index d15c7180a93..ecef1005aad 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.5.1-jdk17-alpine AS build +FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 6edc32dc1dd..45a775be916 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.5.1-jdk17-alpine AS build +FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon From 40afa7e5dbd7c0ee9de65fe2de5326671e47af32 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 6 Jan 2023 19:16:12 +0100 Subject: [PATCH 078/105] Version updates --- frameworks/Kotlin/hexagon/build.gradle | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index d4830752b19..cc2cd56c48b 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,8 +4,8 @@ plugins { } ext { - hexagonVersion = "2.3.1" - hexagonExtraVersion = "2.3.1" + hexagonVersion = "2.4.0" + hexagonExtraVersion = "2.4.0" hikariVersion = "5.0.1" jettyVersion = "11.0.13" postgresqlVersion = "42.5.1" From 9515299f484a45c20c031dae153e2eec61a62a90 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 7 Jan 2023 00:28:11 +0100 Subject: [PATCH 079/105] Version updates --- frameworks/Kotlin/hexagon/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index cc2cd56c48b..471454d5304 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -4,7 +4,7 @@ plugins { } ext { - hexagonVersion = "2.4.0" + hexagonVersion = "2.4.1" hexagonExtraVersion = "2.4.0" hikariVersion = "5.0.1" jettyVersion = "11.0.13" From 243d6beadda4666780c77ca12624d8a6d8b2aa6a Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 1 Feb 2023 15:35:16 +0100 Subject: [PATCH 080/105] [Hexagon] Refactor and updates: * Update Hexagon version * Use Rocker template * Modularize the different scenarios --- frameworks/Kotlin/hexagon/build.gradle | 55 ++++-------------- frameworks/Kotlin/hexagon/core/build.gradle | 34 +++++++++++ .../hexagon/core/src/main/kotlin/Benchmark.kt | 27 +++++++++ .../{ => core}/src/main/kotlin/Controller.kt | 25 ++++----- .../{ => core}/src/main/kotlin/Settings.kt | 7 ++- .../src/main/kotlin/model/CachedWorld.kt | 0 .../src/main/kotlin/model/Fortune.kt | 0 .../src/main/kotlin/model/Message.kt | 0 .../{ => core}/src/main/kotlin/model/World.kt | 0 .../src/main/kotlin/store/BenchmarkStore.kt | 0 .../src/main/resources/fortunes.pebble.html | 0 .../src/main/resources/fortunes.rocker.html | 24 ++++++++ .../hexagon-jettyloom-pgclient.dockerfile | 14 ++--- .../hexagon/hexagon-jettyloom.dockerfile | 14 ++--- .../Kotlin/hexagon/hexagon-netty.dockerfile | 16 ++---- .../hexagon-nettyepoll-pgclient.dockerfile | 16 ++---- .../hexagon/hexagon-nettyepoll.dockerfile | 16 ++---- .../Kotlin/hexagon/hexagon-tomcat.dockerfile | 12 ++-- frameworks/Kotlin/hexagon/hexagon.dockerfile | 16 ++---- .../hexagon_jetty_pgclient/build.gradle | 13 +++++ .../src/main/kotlin/Benchmark.kt | 23 ++++++++ .../hexagon_jetty_postgresql/build.gradle | 13 +++++ .../src/main/kotlin/Benchmark.kt | 23 ++++++++ .../hexagon_netty_postgresql/build.gradle | 13 +++++ .../src/main/kotlin/Benchmark.kt | 17 ++++++ .../hexagon_nettyepoll_pgclient/build.gradle | 14 +++++ .../src/main/kotlin/Benchmark.kt | 17 ++++++ .../build.gradle | 14 +++++ .../src/main/kotlin/Benchmark.kt | 17 ++++++ .../hexagon_tomcat_postgresql/build.gradle | 15 +++++ .../src/main/kotlin/WebListenerServer.kt | 12 +++- frameworks/Kotlin/hexagon/settings.gradle | 13 +++++ .../hexagon/src/main/kotlin/Benchmark.kt | 56 ------------------- .../hexagon/store_pgclient/build.gradle | 6 ++ .../main/kotlin}/BenchmarkPgClientStore.kt | 5 +- .../Kotlin/hexagon/store_sql/build.gradle | 6 ++ .../src/main/kotlin}/BenchmarkSqlStore.kt | 2 +- 37 files changed, 367 insertions(+), 188 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/core/build.gradle create mode 100644 frameworks/Kotlin/hexagon/core/src/main/kotlin/Benchmark.kt rename frameworks/Kotlin/hexagon/{ => core}/src/main/kotlin/Controller.kt (88%) rename frameworks/Kotlin/hexagon/{ => core}/src/main/kotlin/Settings.kt (82%) rename frameworks/Kotlin/hexagon/{ => core}/src/main/kotlin/model/CachedWorld.kt (100%) rename frameworks/Kotlin/hexagon/{ => core}/src/main/kotlin/model/Fortune.kt (100%) rename frameworks/Kotlin/hexagon/{ => core}/src/main/kotlin/model/Message.kt (100%) rename frameworks/Kotlin/hexagon/{ => core}/src/main/kotlin/model/World.kt (100%) rename frameworks/Kotlin/hexagon/{ => core}/src/main/kotlin/store/BenchmarkStore.kt (100%) rename frameworks/Kotlin/hexagon/{ => core}/src/main/resources/fortunes.pebble.html (100%) create mode 100644 frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.rocker.html create mode 100644 frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/hexagon_netty_postgresql/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/hexagon_tomcat_postgresql/build.gradle rename frameworks/Kotlin/hexagon/{ => hexagon_tomcat_postgresql}/src/main/kotlin/WebListenerServer.kt (62%) create mode 100644 frameworks/Kotlin/hexagon/settings.gradle delete mode 100644 frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/store_pgclient/build.gradle rename frameworks/Kotlin/hexagon/{src/main/kotlin/store => store_pgclient/src/main/kotlin}/BenchmarkPgClientStore.kt (97%) create mode 100644 frameworks/Kotlin/hexagon/store_sql/build.gradle rename frameworks/Kotlin/hexagon/{src/main/kotlin/store => store_sql/src/main/kotlin}/BenchmarkSqlStore.kt (99%) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 471454d5304..c20ee5868d8 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,61 +1,26 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.8.0" + id "org.jetbrains.kotlin.jvm" version "1.8.0" apply false } +version = "1.0.0" +description = "TFB benchmark" +group = "com.hexagonkt" + ext { - hexagonVersion = "2.4.1" - hexagonExtraVersion = "2.4.0" + hexagonVersion = "2.5.0" hikariVersion = "5.0.1" jettyVersion = "11.0.13" postgresqlVersion = "42.5.1" vertxVersion = "4.3.7" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.86.Final" + nettyVersion = "4.1.87.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } -apply(from: "$gradleScripts/kotlin.gradle") -apply(from: "$gradleScripts/application.gradle") - -apply(plugin: "war") +defaultTasks("build") -defaultTasks("installDist") - -application { - mainClass.set("com.hexagonkt.BenchmarkKt") +subprojects { + apply(from: "$gradleScripts/kotlin.gradle") } - -war { - archiveFileName = "ROOT.war" -} - -installDist.dependsOn("war") - -dependencies { - implementation("com.hexagonkt:http_server_netty_epoll:$hexagonVersion") - implementation("com.hexagonkt:http_server_jetty:$hexagonVersion") - implementation("com.hexagonkt:templates_pebble:$hexagonVersion") - implementation("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") - implementation("com.hexagonkt:serialization_dsl_json:$hexagonVersion") - - implementation("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") - implementation("org.cache2k:cache2k-core:$cache2kVersion") - implementation("com.zaxxer:HikariCP:$hikariVersion") - implementation("org.postgresql:postgresql:$postgresqlVersion") - implementation("io.vertx:vertx-pg-client:$vertxVersion") - - // providedCompile excludes the dependency only in the WAR, not in the distribution - providedCompile("org.eclipse.jetty:jetty-webapp:$jettyVersion") { exclude module: "slf4j-api" } -} - -tasks.register("minimizeTemplate") { - doLast { - File template = file("$buildDir/resources/main/fortunes.pebble.html") - List lines = template.readLines().collect { it.trim() } - template.write(lines.join("")) - } -} - -assemble.dependsOn("minimizeTemplate") diff --git a/frameworks/Kotlin/hexagon/core/build.gradle b/frameworks/Kotlin/hexagon/core/build.gradle new file mode 100644 index 00000000000..45d18cda86f --- /dev/null +++ b/frameworks/Kotlin/hexagon/core/build.gradle @@ -0,0 +1,34 @@ + +plugins { + id("nu.studer.rocker") version("3.0.4") +} + +dependencies { + api("com.hexagonkt:http_server:$hexagonVersion") + api("com.hexagonkt:templates_pebble:$hexagonVersion") + api("com.hexagonkt:templates_rocker:$hexagonVersion") + api("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") + api("com.hexagonkt:serialization_dsl_json:$hexagonVersion") + api("org.cache2k:cache2k-core:$cache2kVersion") +} + +tasks.register("minimizeTemplate") { + doLast { + [ "fortunes.pebble.html", "fortunes.rocker.html" ].forEach { t -> + File template = file("$buildDir/resources/main/$t") + List lines = template.readLines().collect { it.trim() } + template.write(lines.join("")) + } + } +} + +jar.dependsOn("minimizeTemplate") + +rocker { + configurations { + create("main") { + templateDir.set(file("src/main/resources")) + optimize.set(true) + } + } +} diff --git a/frameworks/Kotlin/hexagon/core/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..ef2da876dae --- /dev/null +++ b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Benchmark.kt @@ -0,0 +1,27 @@ +package com.hexagonkt + +import com.hexagonkt.http.server.HttpServer +import com.hexagonkt.http.server.HttpServerPort +import com.hexagonkt.http.server.HttpServerSettings +import com.hexagonkt.store.BenchmarkStore +import com.hexagonkt.templates.TemplatePort +import java.net.InetAddress +import java.net.URL + +class Benchmark( + private val engine: HttpServerPort, + private val store: BenchmarkStore, + private val template: TemplatePort, + private val templateUrl: URL, + private val settings: Settings = Settings(), +) { + val server: HttpServer by lazy { + val controller = Controller(settings, store, template, templateUrl) + val serverSettings = HttpServerSettings( + bindAddress = InetAddress.getByName(settings.bindAddress), + bindPort = settings.bindPort, + ) + + HttpServer(engine, controller.path, serverSettings) + } +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt similarity index 88% rename from frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt rename to frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt index ce82a5c152f..4ad7055e8e1 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt @@ -7,10 +7,10 @@ import com.hexagonkt.core.media.TextMedia.PLAIN import com.hexagonkt.http.model.ContentType import com.hexagonkt.http.model.Header import com.hexagonkt.http.model.Headers +import com.hexagonkt.http.server.callbacks.DateCallback import com.hexagonkt.http.server.handlers.HttpServerContext import com.hexagonkt.http.server.handlers.PathHandler import com.hexagonkt.http.server.handlers.path -import com.hexagonkt.http.toHttpFormat import com.hexagonkt.model.* import com.hexagonkt.serialization.dsl.json.Json import com.hexagonkt.serialization.serialize @@ -18,7 +18,6 @@ import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort import java.net.URL -import java.time.LocalDateTime.now import java.util.concurrent.ThreadLocalRandom import kotlin.text.Charsets.UTF_8 @@ -27,29 +26,26 @@ class Controller( settings: Settings, store: BenchmarkStore, templateEngine: TemplatePort, + templateUrl: URL, ) { private val queriesParam: String = settings.queriesParam private val cachedQueriesParam: String = settings.cachedQueriesParam private val worldRows: Int = settings.worldRows + private val textMessage: String = settings.textMessage private val plain: ContentType = ContentType(PLAIN) private val json: ContentType = ContentType(JSON) private val html: ContentType = ContentType(HTML, charset = UTF_8) - private val templateUrl: URL = URL("classpath:fortunes.pebble.html") + private val headers = Headers(Header("server", "Hexagon")) - private val headers = Headers( - Header("server", "Hexagon"), - ) - - internal val path: PathHandler by lazy { + val path: PathHandler by lazy { path { - on("*") { - send(headers = headers + Header("date", now().toHttpFormat())) - } + on("*") { send(headers = headers) } + on("*", DateCallback()) - get("/plaintext") { ok(settings.textMessage, contentType = plain) } - get("/json") { ok(Message(settings.textMessage).toMap().serialize(Json.raw), contentType = json) } + get("/plaintext") { ok(textMessage, contentType = plain) } + get("/json") { ok(Message(textMessage).toJson(), contentType = json) } get("/fortunes") { listFortunes(store, templateUrl, templateEngine) } get("/db") { dbQuery(store) } get("/query") { getWorlds(store) } @@ -58,6 +54,9 @@ class Controller( } } + private fun Message.toJson(): String = + toMap().serialize(Json.raw) + private fun HttpServerContext.listFortunes( store: BenchmarkStore, templateUrl: URL, templateAdapter: TemplatePort ): HttpServerContext { diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Settings.kt similarity index 82% rename from frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt rename to frameworks/Kotlin/hexagon/core/src/main/kotlin/Settings.kt index 36c8f8f44e2..b11ed02c9e9 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Settings.kt +++ b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Settings.kt @@ -1,5 +1,6 @@ package com.hexagonkt +import com.hexagonkt.core.Jvm.systemFlag import com.hexagonkt.core.Jvm.systemSettingOrNull data class Settings( @@ -23,9 +24,9 @@ data class Settings( val databaseName: String = systemSettingOrNull("database") ?: "hello_world", val databaseDriver: String = systemSettingOrNull("databaseDriver") ?: "org.postgresql.Driver", - val sendDateHeader: Boolean = systemSettingOrNull("sendDateHeader") ?: false, - val sendServerVersion: Boolean = systemSettingOrNull("sendServerVersion") ?: false, - val sendXPoweredBy: Boolean = systemSettingOrNull("sendXPoweredBy") ?: false, + val sendDateHeader: Boolean = systemFlag("sendDateHeader"), + val sendServerVersion: Boolean = systemFlag("sendServerVersion"), + val sendXPoweredBy: Boolean = systemFlag("sendXPoweredBy"), val worldRows: Int = 10_000, val textMessage: String = "Hello, World!", diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/CachedWorld.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/model/CachedWorld.kt similarity index 100% rename from frameworks/Kotlin/hexagon/src/main/kotlin/model/CachedWorld.kt rename to frameworks/Kotlin/hexagon/core/src/main/kotlin/model/CachedWorld.kt diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/Fortune.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/model/Fortune.kt similarity index 100% rename from frameworks/Kotlin/hexagon/src/main/kotlin/model/Fortune.kt rename to frameworks/Kotlin/hexagon/core/src/main/kotlin/model/Fortune.kt diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/Message.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/model/Message.kt similarity index 100% rename from frameworks/Kotlin/hexagon/src/main/kotlin/model/Message.kt rename to frameworks/Kotlin/hexagon/core/src/main/kotlin/model/Message.kt diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/model/World.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/model/World.kt similarity index 100% rename from frameworks/Kotlin/hexagon/src/main/kotlin/model/World.kt rename to frameworks/Kotlin/hexagon/core/src/main/kotlin/model/World.kt diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/store/BenchmarkStore.kt similarity index 100% rename from frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkStore.kt rename to frameworks/Kotlin/hexagon/core/src/main/kotlin/store/BenchmarkStore.kt diff --git a/frameworks/Kotlin/hexagon/src/main/resources/fortunes.pebble.html b/frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.pebble.html similarity index 100% rename from frameworks/Kotlin/hexagon/src/main/resources/fortunes.pebble.html rename to frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.pebble.html diff --git a/frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.rocker.html b/frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.rocker.html new file mode 100644 index 00000000000..c9a9d4037e5 --- /dev/null +++ b/frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.rocker.html @@ -0,0 +1,24 @@ +@import java.util.* +@import com.hexagonkt.model.Fortune +@args(Map context) + + + + + Fortunes + + + + + + + + @for ((fortune) : (Collection)context.get("fortunes")) { + + + + + } +
idmessage
@fortune.getId()@fortune.getMessage()
+ + diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile index 0325868b645..c04d91d0118 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile @@ -5,22 +5,18 @@ FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon -COPY src src -COPY build.gradle build.gradle +ADD . . +RUN gradle --quiet compileRocker RUN gradle --quiet -x test # # RUNTIME # FROM eclipse-temurin:19-jre-alpine -ENV DBSTORE pg_client -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE jetty_loom -ENV PROJECT hexagon -ENV DISABLE_CHECKS true -ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +ENV PROJECT hexagon_jetty_pgclient +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -DvirtualThreads=true -COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile index 2bd37096b09..656cf8f03ed 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile @@ -5,22 +5,18 @@ FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon -COPY src src -COPY build.gradle build.gradle +ADD . . +RUN gradle --quiet compileRocker RUN gradle --quiet -x test # # RUNTIME # FROM eclipse-temurin:19-jre-alpine -ENV DBSTORE postgresql -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE jetty_loom -ENV PROJECT hexagon -ENV DISABLE_CHECKS true -ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +ENV PROJECT hexagon_jetty_postgresql +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -DvirtualThreads=true -COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index 9c11f65f9ae..c11b0302d41 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -5,22 +5,18 @@ FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon -COPY src src -COPY build.gradle build.gradle +ADD . . +RUN gradle --quiet compileRocker RUN gradle --quiet -x test # # RUNTIME # -FROM eclipse-temurin:19-jre-alpine -ENV DBSTORE postgresql -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE netty -ENV PROJECT hexagon -ENV DISABLE_CHECKS true -ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +FROM eclipse-temurin:17-jre-alpine +ENV PROJECT hexagon_netty_postgresql +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile index 2ceeae57fe7..e9d065bbf95 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile @@ -5,22 +5,18 @@ FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon -COPY src src -COPY build.gradle build.gradle +ADD . . +RUN gradle --quiet compileRocker RUN gradle --quiet -x test # # RUNTIME # -FROM eclipse-temurin:19-jre-alpine -ENV DBSTORE pg_client -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE netty_epoll -ENV PROJECT hexagon -ENV DISABLE_CHECKS true -ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +FROM eclipse-temurin:17-jre-alpine +ENV PROJECT hexagon_nettyepoll_pgclient +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile index 31052f788cd..c7beb493420 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -5,22 +5,18 @@ FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon -COPY src src -COPY build.gradle build.gradle +ADD . . +RUN gradle --quiet compileRocker RUN gradle --quiet -x test # # RUNTIME # -FROM eclipse-temurin:19-jre-alpine -ENV DBSTORE postgresql -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE netty_epoll -ENV PROJECT hexagon -ENV DISABLE_CHECKS true -ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +FROM eclipse-temurin:17-jre-alpine +ENV PROJECT hexagon_nettyepoll_postgresql +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index ecef1005aad..c8c2f74a319 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -5,18 +5,16 @@ FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon -COPY src src -COPY build.gradle build.gradle +ADD . . +RUN gradle --quiet compileRocker RUN gradle --quiet -x test # # RUNTIME # FROM tomcat:10.1.2-jre17-temurin -ENV DBSTORE postgresql -ENV POSTGRESQL_DB_HOST tfb-database -ENV DISABLE_CHECKS true -ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +ENV MODULE /hexagon/hexagon_tomcat_postgresql +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=build /hexagon/build/libs/ROOT.war /usr/local/tomcat/webapps/ROOT.war +COPY --from=build $MODULE/build/libs/ROOT.war /usr/local/tomcat/webapps/ROOT.war EXPOSE 8080 diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 45a775be916..2d1ee3d3819 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -5,22 +5,18 @@ FROM gradle:7.6-jdk17-alpine AS build USER root WORKDIR /hexagon -COPY src src -COPY build.gradle build.gradle +ADD . . +RUN gradle --quiet compileRocker RUN gradle --quiet -x test # # RUNTIME # -FROM eclipse-temurin:19-jre-alpine -ENV DBSTORE postgresql -ENV POSTGRESQL_DB_HOST tfb-database -ENV WEBENGINE jetty -ENV PROJECT hexagon -ENV DISABLE_CHECKS true -ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +FROM eclipse-temurin:17-jre-alpine +ENV PROJECT hexagon_jetty_postgresql +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -COPY --from=build /hexagon/build/install/$PROJECT /opt/$PROJECT +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT EXPOSE 9090 diff --git a/frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/build.gradle b/frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/build.gradle new file mode 100644 index 00000000000..71e2dc0f44f --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/build.gradle @@ -0,0 +1,13 @@ + +apply(from: "$gradleScripts/application.gradle") + +application { + mainClass.set("com.hexagonkt.BenchmarkKt") +} + +dependencies { + api(project(":store_pgclient")) + api("com.hexagonkt:http_server_jetty:$hexagonVersion") +} + +build.dependsOn("installDist") diff --git a/frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..983831ad866 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_jetty_pgclient/src/main/kotlin/Benchmark.kt @@ -0,0 +1,23 @@ +package com.hexagonkt + +import com.hexagonkt.core.Jvm.systemFlag +import com.hexagonkt.http.server.jetty.JettyServletAdapter +import com.hexagonkt.store.BenchmarkPgClientStore +import com.hexagonkt.templates.rocker.RockerAdapter +import java.net.URL + +fun main() { + val settings = Settings() + val store = BenchmarkPgClientStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = URL("classpath:fortunes.rocker.html") + val engine = JettyServletAdapter( + sendDateHeader = settings.sendDateHeader, + sendServerVersion = settings.sendServerVersion, + sendXPoweredBy = settings.sendXPoweredBy, + useVirtualThreads = systemFlag("virtualThreads"), + ) + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/build.gradle b/frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/build.gradle new file mode 100644 index 00000000000..09dde4a8327 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/build.gradle @@ -0,0 +1,13 @@ + +apply(from: "$gradleScripts/application.gradle") + +application { + mainClass.set("com.hexagonkt.BenchmarkKt") +} + +dependencies { + api(project(":store_sql")) + api("com.hexagonkt:http_server_jetty:$hexagonVersion") +} + +build.dependsOn("installDist") diff --git a/frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..1ba499672b8 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_jetty_postgresql/src/main/kotlin/Benchmark.kt @@ -0,0 +1,23 @@ +package com.hexagonkt + +import com.hexagonkt.core.Jvm.systemFlag +import com.hexagonkt.http.server.jetty.JettyServletAdapter +import com.hexagonkt.store.BenchmarkSqlStore +import com.hexagonkt.templates.rocker.RockerAdapter +import java.net.URL + +fun main() { + val settings = Settings() + val store = BenchmarkSqlStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = URL("classpath:fortunes.rocker.html") + val engine = JettyServletAdapter( + sendDateHeader = settings.sendDateHeader, + sendServerVersion = settings.sendServerVersion, + sendXPoweredBy = settings.sendXPoweredBy, + useVirtualThreads = systemFlag("virtualThreads"), + ) + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/build.gradle b/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/build.gradle new file mode 100644 index 00000000000..e06ac14aff0 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/build.gradle @@ -0,0 +1,13 @@ + +apply(from: "$gradleScripts/application.gradle") + +application { + mainClass.set("com.hexagonkt.BenchmarkKt") +} + +dependencies { + api(project(":store_sql")) + api("com.hexagonkt:http_server_netty:$hexagonVersion") +} + +build.dependsOn("installDist") diff --git a/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..100af29d51e --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt @@ -0,0 +1,17 @@ +package com.hexagonkt + +import com.hexagonkt.http.server.netty.NettyServerAdapter +import com.hexagonkt.store.BenchmarkSqlStore +import com.hexagonkt.templates.rocker.RockerAdapter +import java.net.URL + +fun main() { + val settings = Settings() + val store = BenchmarkSqlStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = URL("classpath:fortunes.rocker.html") + val engine = NettyServerAdapter() + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/build.gradle new file mode 100644 index 00000000000..07ecf663690 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/build.gradle @@ -0,0 +1,14 @@ + +apply(from: "$gradleScripts/application.gradle") + +application { + mainClass.set("com.hexagonkt.BenchmarkKt") +} + +dependencies { + api(project(":store_pgclient")) + api("com.hexagonkt:http_server_netty_epoll:$hexagonVersion") + api("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") +} + +build.dependsOn("installDist") diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..abe085171f2 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_pgclient/src/main/kotlin/Benchmark.kt @@ -0,0 +1,17 @@ +package com.hexagonkt + +import com.hexagonkt.http.server.netty.epoll.NettyEpollServerAdapter +import com.hexagonkt.store.BenchmarkPgClientStore +import com.hexagonkt.templates.rocker.RockerAdapter +import java.net.URL + +fun main() { + val settings = Settings() + val store = BenchmarkPgClientStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = URL("classpath:fortunes.rocker.html") + val engine = NettyEpollServerAdapter() + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle new file mode 100644 index 00000000000..b314102ff80 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle @@ -0,0 +1,14 @@ + +apply(from: "$gradleScripts/application.gradle") + +application { + mainClass.set("com.hexagonkt.BenchmarkKt") +} + +dependencies { + api(project(":store_sql")) + api("com.hexagonkt:http_server_netty_epoll:$hexagonVersion") + api("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") +} + +build.dependsOn("installDist") diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..d0c2aa58347 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/src/main/kotlin/Benchmark.kt @@ -0,0 +1,17 @@ +package com.hexagonkt + +import com.hexagonkt.http.server.netty.epoll.NettyEpollServerAdapter +import com.hexagonkt.store.BenchmarkSqlStore +import com.hexagonkt.templates.rocker.RockerAdapter +import java.net.URL + +fun main() { + val settings = Settings() + val store = BenchmarkSqlStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = URL("classpath:fortunes.rocker.html") + val engine = NettyEpollServerAdapter() + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/hexagon_tomcat_postgresql/build.gradle b/frameworks/Kotlin/hexagon/hexagon_tomcat_postgresql/build.gradle new file mode 100644 index 00000000000..3c72b9d4b0a --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_tomcat_postgresql/build.gradle @@ -0,0 +1,15 @@ + +apply(plugin: "war") + +war { + archiveFileName = "ROOT.war" +} + +build.dependsOn("war") + +dependencies { + api(project(":store_sql")) + api("com.hexagonkt:http_server_servlet:$hexagonVersion") + + compileOnly("jakarta.servlet:jakarta.servlet-api:5.0.0") +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt b/frameworks/Kotlin/hexagon/hexagon_tomcat_postgresql/src/main/kotlin/WebListenerServer.kt similarity index 62% rename from frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt rename to frameworks/Kotlin/hexagon/hexagon_tomcat_postgresql/src/main/kotlin/WebListenerServer.kt index 7da14b44cf5..cdf911e1ee9 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/WebListenerServer.kt +++ b/frameworks/Kotlin/hexagon/hexagon_tomcat_postgresql/src/main/kotlin/WebListenerServer.kt @@ -6,16 +6,22 @@ import com.hexagonkt.http.server.handlers.HttpHandler import com.hexagonkt.http.server.handlers.OnHandler import com.hexagonkt.http.server.servlet.ServletServer import com.hexagonkt.store.BenchmarkSqlStore -import com.hexagonkt.templates.pebble.PebbleAdapter +import com.hexagonkt.templates.rocker.RockerAdapter import jakarta.servlet.annotation.WebListener +import java.net.URL -@WebListener class WebListenerServer(settings: Settings = Settings()) : ServletServer(createHandlers(settings)) { +@WebListener class WebListenerServer( + settings: Settings = Settings() +) : ServletServer(createHandlers(settings)) { private companion object { val headers = Headers(Header("server", "Tomcat")) fun createHandlers(settings: Settings): List { - val controller = Controller(settings, BenchmarkSqlStore("postgresql"), PebbleAdapter()) + val store = BenchmarkSqlStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = URL("classpath:fortunes.rocker.html") + val controller = Controller(settings, store, templateEngine, templateUrl) val controllerPath = controller.path val serverHeaderHandler = OnHandler("*") { send(headers = headers) diff --git a/frameworks/Kotlin/hexagon/settings.gradle b/frameworks/Kotlin/hexagon/settings.gradle new file mode 100644 index 00000000000..2d571cdc706 --- /dev/null +++ b/frameworks/Kotlin/hexagon/settings.gradle @@ -0,0 +1,13 @@ + +include( + "core", + "store_pgclient", + "store_sql", + + "hexagon_jetty_pgclient", + "hexagon_jetty_postgresql", + "hexagon_netty_postgresql", + "hexagon_nettyepoll_pgclient", + "hexagon_nettyepoll_postgresql", + "hexagon_tomcat_postgresql", +) diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt deleted file mode 100644 index a296a9d261d..00000000000 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/Benchmark.kt +++ /dev/null @@ -1,56 +0,0 @@ -package com.hexagonkt - -import com.hexagonkt.http.server.HttpServer -import com.hexagonkt.http.server.HttpServerPort -import com.hexagonkt.http.server.HttpServerSettings -import com.hexagonkt.http.server.jetty.JettyServletAdapter -import com.hexagonkt.http.server.netty.NettyServerAdapter -import com.hexagonkt.http.server.netty.epoll.NettyEpollServerAdapter -import com.hexagonkt.store.BenchmarkPgClientStore -import com.hexagonkt.store.BenchmarkSqlStore -import com.hexagonkt.store.BenchmarkStore -import com.hexagonkt.templates.pebble.PebbleAdapter -import java.net.InetAddress - -internal val settings = Settings() - -private val engines: Map by lazy { - mapOf( - "jetty" to JettyServletAdapter( - sendDateHeader = settings.sendDateHeader, - sendServerVersion = settings.sendServerVersion, - sendXPoweredBy = settings.sendXPoweredBy, - ), - "jetty_loom" to JettyServletAdapter( - sendDateHeader = settings.sendDateHeader, - sendServerVersion = settings.sendServerVersion, - sendXPoweredBy = settings.sendXPoweredBy, - useVirtualThreads = true, - ), - "netty" to NettyServerAdapter(), - "netty_epoll" to NettyEpollServerAdapter(), - ) -} - -private val stores: Map by lazy { - mapOf( - "postgresql" to BenchmarkSqlStore("postgresql"), - "pg_client" to BenchmarkPgClientStore("postgresql"), - ) -} - -internal val server: HttpServer by lazy { - val engine = engines[settings.webEngine] ?: error("Unsupported server engine") - val store = stores[settings.dataStore] ?: error("Unsupported data store") - val controller = Controller(settings, store, PebbleAdapter()) - val serverSettings = HttpServerSettings( - bindAddress = InetAddress.getByName(settings.bindAddress), - bindPort = settings.bindPort, - ) - - HttpServer(engine, controller.path, serverSettings) -} - -fun main() { - server.start() -} diff --git a/frameworks/Kotlin/hexagon/store_pgclient/build.gradle b/frameworks/Kotlin/hexagon/store_pgclient/build.gradle new file mode 100644 index 00000000000..6d0c88ad20e --- /dev/null +++ b/frameworks/Kotlin/hexagon/store_pgclient/build.gradle @@ -0,0 +1,6 @@ + +dependencies { + api(project(":core")) + implementation("io.vertx:vertx-pg-client:$vertxVersion") + implementation("com.ongres.scram:client:2.1") +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkPgClientStore.kt b/frameworks/Kotlin/hexagon/store_pgclient/src/main/kotlin/BenchmarkPgClientStore.kt similarity index 97% rename from frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkPgClientStore.kt rename to frameworks/Kotlin/hexagon/store_pgclient/src/main/kotlin/BenchmarkPgClientStore.kt index cd467c6c34d..5cd13ccee0a 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkPgClientStore.kt +++ b/frameworks/Kotlin/hexagon/store_pgclient/src/main/kotlin/BenchmarkPgClientStore.kt @@ -11,8 +11,9 @@ import io.vertx.pgclient.PgPool import io.vertx.sqlclient.* import org.cache2k.Cache -internal class BenchmarkPgClientStore( - engine: String, private val settings: Settings = Settings() +class BenchmarkPgClientStore( + engine: String, + private val settings: Settings = Settings(), ) : BenchmarkStore(settings) { companion object { diff --git a/frameworks/Kotlin/hexagon/store_sql/build.gradle b/frameworks/Kotlin/hexagon/store_sql/build.gradle new file mode 100644 index 00000000000..f154eb6dbae --- /dev/null +++ b/frameworks/Kotlin/hexagon/store_sql/build.gradle @@ -0,0 +1,6 @@ + +dependencies { + api(project(":core")) + implementation("com.zaxxer:HikariCP:$hikariVersion") + implementation("org.postgresql:postgresql:$postgresqlVersion") +} diff --git a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/store_sql/src/main/kotlin/BenchmarkSqlStore.kt similarity index 99% rename from frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt rename to frameworks/Kotlin/hexagon/store_sql/src/main/kotlin/BenchmarkSqlStore.kt index 157ad7c982c..ea871ec1b13 100644 --- a/frameworks/Kotlin/hexagon/src/main/kotlin/store/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/store_sql/src/main/kotlin/BenchmarkSqlStore.kt @@ -11,7 +11,7 @@ import org.cache2k.Cache import java.sql.Connection import java.sql.PreparedStatement -internal class BenchmarkSqlStore( +class BenchmarkSqlStore( engine: String, private val settings: Settings = Settings() ) : BenchmarkStore(settings) { From 90717cc577e1b5b6882b6b632d2eff6223456031 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 1 Feb 2023 16:03:10 +0100 Subject: [PATCH 081/105] Fix connection problems --- frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile | 1 + frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile | 1 + frameworks/Kotlin/hexagon/hexagon-netty.dockerfile | 1 + frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile | 1 + frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile | 1 + frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile | 1 + frameworks/Kotlin/hexagon/hexagon.dockerfile | 1 + 7 files changed, 7 insertions(+) diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile index c04d91d0118..388fd1036b2 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile @@ -13,6 +13,7 @@ RUN gradle --quiet -x test # RUNTIME # FROM eclipse-temurin:19-jre-alpine +ENV POSTGRESQL_DB_HOST tfb-database ENV PROJECT hexagon_jetty_pgclient ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -DvirtualThreads=true diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile index 656cf8f03ed..ccf6f8711ee 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile @@ -13,6 +13,7 @@ RUN gradle --quiet -x test # RUNTIME # FROM eclipse-temurin:19-jre-alpine +ENV POSTGRESQL_DB_HOST tfb-database ENV PROJECT hexagon_jetty_postgresql ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA -DvirtualThreads=true diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index c11b0302d41..687f0ce38d1 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -13,6 +13,7 @@ RUN gradle --quiet -x test # RUNTIME # FROM eclipse-temurin:17-jre-alpine +ENV POSTGRESQL_DB_HOST tfb-database ENV PROJECT hexagon_netty_postgresql ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile index e9d065bbf95..f3f948746da 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile @@ -13,6 +13,7 @@ RUN gradle --quiet -x test # RUNTIME # FROM eclipse-temurin:17-jre-alpine +ENV POSTGRESQL_DB_HOST tfb-database ENV PROJECT hexagon_nettyepoll_pgclient ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile index c7beb493420..1bfd11780d3 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -13,6 +13,7 @@ RUN gradle --quiet -x test # RUNTIME # FROM eclipse-temurin:17-jre-alpine +ENV POSTGRESQL_DB_HOST tfb-database ENV PROJECT hexagon_nettyepoll_postgresql ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index c8c2f74a319..677823b9ba7 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -13,6 +13,7 @@ RUN gradle --quiet -x test # RUNTIME # FROM tomcat:10.1.2-jre17-temurin +ENV POSTGRESQL_DB_HOST tfb-database ENV MODULE /hexagon/hexagon_tomcat_postgresql ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 2d1ee3d3819..d0e259d10e0 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -13,6 +13,7 @@ RUN gradle --quiet -x test # RUNTIME # FROM eclipse-temurin:17-jre-alpine +ENV POSTGRESQL_DB_HOST tfb-database ENV PROJECT hexagon_jetty_postgresql ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA From 45f074343d0025f2a5d1e0613d5c4de9008543aa Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 9 Mar 2023 18:25:35 +0100 Subject: [PATCH 082/105] Update Hexagon --- frameworks/Kotlin/hexagon/build.gradle | 12 ++++++------ .../hexagon/core/src/main/kotlin/Controller.kt | 14 ++++++-------- 2 files changed, 12 insertions(+), 14 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index c20ee5868d8..31ab9116d9d 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,6 +1,6 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.8.0" apply false + id "org.jetbrains.kotlin.jvm" version "1.8.10" apply false } version = "1.0.0" @@ -8,13 +8,13 @@ description = "TFB benchmark" group = "com.hexagonkt" ext { - hexagonVersion = "2.5.0" + hexagonVersion = "2.6.3" hikariVersion = "5.0.1" - jettyVersion = "11.0.13" - postgresqlVersion = "42.5.1" - vertxVersion = "4.3.7" + jettyVersion = "11.0.14" + postgresqlVersion = "42.5.4" + vertxVersion = "4.4.0" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.87.Final" + nettyVersion = "4.1.89.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } diff --git a/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt index 4ad7055e8e1..c747fa889e9 100644 --- a/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt @@ -1,9 +1,9 @@ package com.hexagonkt import com.hexagonkt.core.fieldsMapOf -import com.hexagonkt.core.media.ApplicationMedia.JSON -import com.hexagonkt.core.media.TextMedia.HTML -import com.hexagonkt.core.media.TextMedia.PLAIN +import com.hexagonkt.core.media.APPLICATION_JSON +import com.hexagonkt.core.media.TEXT_HTML +import com.hexagonkt.core.media.TEXT_PLAIN import com.hexagonkt.http.model.ContentType import com.hexagonkt.http.model.Header import com.hexagonkt.http.model.Headers @@ -16,10 +16,8 @@ import com.hexagonkt.serialization.dsl.json.Json import com.hexagonkt.serialization.serialize import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort - import java.net.URL import java.util.concurrent.ThreadLocalRandom - import kotlin.text.Charsets.UTF_8 class Controller( @@ -33,9 +31,9 @@ class Controller( private val worldRows: Int = settings.worldRows private val textMessage: String = settings.textMessage - private val plain: ContentType = ContentType(PLAIN) - private val json: ContentType = ContentType(JSON) - private val html: ContentType = ContentType(HTML, charset = UTF_8) + private val plain: ContentType = ContentType(TEXT_PLAIN) + private val json: ContentType = ContentType(APPLICATION_JSON) + private val html: ContentType = ContentType(TEXT_HTML, charset = UTF_8) private val headers = Headers(Header("server", "Hexagon")) From 5df374d3f34b034f9175d7f644501c1f6ed70f97 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 9 Mar 2023 18:55:41 +0100 Subject: [PATCH 083/105] Update Gradle --- .../Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties | 2 +- frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon-netty.dockerfile | 2 +- .../Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 2 +- 8 files changed, 8 insertions(+), 8 deletions(-) diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties index 3f4def4a917..f0ae57febc4 100644 --- a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties +++ b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https://services.gradle.org/distributions/gradle-7.6-bin.zip +distributionUrl=https://services.gradle.org/distributions/gradle-8.0.2-bin.zip networkTimeout=10000 zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile index 388fd1036b2..f047e7e599b 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.6-jdk17-alpine AS build +FROM gradle:8.0.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile index ccf6f8711ee..18963d4dfe1 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.6-jdk17-alpine AS build +FROM gradle:8.0.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index 687f0ce38d1..e343078fb6e 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.6-jdk17-alpine AS build +FROM gradle:8.0.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile index f3f948746da..d40959b0e0e 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.6-jdk17-alpine AS build +FROM gradle:8.0.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile index 1bfd11780d3..575378b8583 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.6-jdk17-alpine AS build +FROM gradle:8.0.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index 677823b9ba7..7ca5725be48 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.6-jdk17-alpine AS build +FROM gradle:8.0.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index d0e259d10e0..e228bd5a7db 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM gradle:7.6-jdk17-alpine AS build +FROM gradle:8.0.2-jdk17-alpine AS build USER root WORKDIR /hexagon From 8978ca1c145fa3ee44cee04fed604197abed8d32 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sun, 19 Mar 2023 16:41:10 +0100 Subject: [PATCH 084/105] Update dependencies --- frameworks/Kotlin/hexagon/build.gradle | 6 +++--- frameworks/Kotlin/hexagon/core/build.gradle | 3 +-- .../Kotlin/hexagon/core/src/main/kotlin/Controller.kt | 2 +- 3 files changed, 5 insertions(+), 6 deletions(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 31ab9116d9d..6b15fbd1da9 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -8,13 +8,13 @@ description = "TFB benchmark" group = "com.hexagonkt" ext { - hexagonVersion = "2.6.3" + hexagonVersion = "2.6.5" hikariVersion = "5.0.1" jettyVersion = "11.0.14" - postgresqlVersion = "42.5.4" + postgresqlVersion = "42.6.0" vertxVersion = "4.4.0" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.89.Final" + nettyVersion = "4.1.90.Final" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } diff --git a/frameworks/Kotlin/hexagon/core/build.gradle b/frameworks/Kotlin/hexagon/core/build.gradle index 45d18cda86f..af7552398d3 100644 --- a/frameworks/Kotlin/hexagon/core/build.gradle +++ b/frameworks/Kotlin/hexagon/core/build.gradle @@ -5,10 +5,9 @@ plugins { dependencies { api("com.hexagonkt:http_server:$hexagonVersion") - api("com.hexagonkt:templates_pebble:$hexagonVersion") api("com.hexagonkt:templates_rocker:$hexagonVersion") api("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") - api("com.hexagonkt:serialization_dsl_json:$hexagonVersion") + api("com.hexagonkt:serialization_jackson_json:$hexagonVersion") api("org.cache2k:cache2k-core:$cache2kVersion") } diff --git a/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt index c747fa889e9..b4714a76049 100644 --- a/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt @@ -12,7 +12,7 @@ import com.hexagonkt.http.server.handlers.HttpServerContext import com.hexagonkt.http.server.handlers.PathHandler import com.hexagonkt.http.server.handlers.path import com.hexagonkt.model.* -import com.hexagonkt.serialization.dsl.json.Json +import com.hexagonkt.serialization.jackson.json.Json import com.hexagonkt.serialization.serialize import com.hexagonkt.store.BenchmarkStore import com.hexagonkt.templates.TemplatePort From 370a13223bc2dbe1df194e9980a19f95d94b9ab2 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 20 Mar 2023 14:20:58 +0100 Subject: [PATCH 085/105] Update Hexagon version --- frameworks/Kotlin/hexagon/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 6b15fbd1da9..4aad4ab8f98 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -8,7 +8,7 @@ description = "TFB benchmark" group = "com.hexagonkt" ext { - hexagonVersion = "2.6.5" + hexagonVersion = "2.6.6" hikariVersion = "5.0.1" jettyVersion = "11.0.14" postgresqlVersion = "42.6.0" From 147afa02f39d62659a37954c2bbeeb77798e51e7 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Thu, 30 Mar 2023 19:56:54 +0200 Subject: [PATCH 086/105] Update Gradle Wrapper --- .../hexagon/gradle/wrapper/gradle-wrapper.jar | Bin 61574 -> 61608 bytes frameworks/Kotlin/hexagon/gradlew | 4 ++-- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar index 943f0cbfa754578e88a3dae77fce6e3dea56edbf..ccebba7710deaf9f98673a68957ea02138b60d0a 100644 GIT binary patch delta 5094 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 delta 5107 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 I6Xdi10eY*&F8}}l diff --git a/frameworks/Kotlin/hexagon/gradlew b/frameworks/Kotlin/hexagon/gradlew index 65dcd68d65c..79a61d421cc 100755 --- a/frameworks/Kotlin/hexagon/gradlew +++ b/frameworks/Kotlin/hexagon/gradlew @@ -144,7 +144,7 @@ if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then case $MAX_FD in #( max*) # In POSIX sh, ulimit -H is undefined. That's why the result is checked to see if it worked. - # shellcheck disable=SC3045 + # shellcheck disable=SC3045 MAX_FD=$( ulimit -H -n ) || warn "Could not query maximum file descriptor limit" esac @@ -152,7 +152,7 @@ if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then '' | soft) :;; #( *) # In POSIX sh, ulimit -n is undefined. That's why the result is checked to see if it worked. - # shellcheck disable=SC3045 + # shellcheck disable=SC3045 ulimit -n "$MAX_FD" || warn "Could not set maximum file descriptor limit to $MAX_FD" esac From 89352f11b0173bd30053c9a4381af7dc10cdaba3 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 7 Jun 2023 13:39:48 +0200 Subject: [PATCH 087/105] Add async and native support --- frameworks/Kotlin/hexagon/.dockerignore | 2 + frameworks/Kotlin/hexagon/build.gradle | 19 ++- frameworks/Kotlin/hexagon/core/build.gradle | 9 +- .../core/src/main/kotlin/Controller.kt | 24 ++-- .../core/native-image.properties | 7 + .../core/reflect-config.json | 23 +++ .../src/main/resources/fortunes.pebble.html | 21 --- .../Kotlin/hexagon/core_async/build.gradle | 32 +++++ .../core_async/src/main/kotlin/Benchmark.kt | 28 ++++ .../core_async/src/main/kotlin/Controller.kt | 133 ++++++++++++++++++ .../src/main/kotlin/store/BenchmarkStore.kt | 34 +++++ .../core/native-image.properties | 7 + .../core/reflect-config.json | 23 +++ .../src/main/resources/fortunes.rocker.html | 24 ++++ .../hexagon/gradle/wrapper/gradle-wrapper.jar | Bin 61608 -> 62076 bytes .../gradle/wrapper/gradle-wrapper.properties | 2 +- frameworks/Kotlin/hexagon/gradlew | 7 +- .../hexagon/hexagon-jetty-native.dockerfile | 21 +++ .../hexagon-jettyloom-pgclient.dockerfile | 15 +- .../hexagon/hexagon-jettyloom.dockerfile | 15 +- .../hexagon/hexagon-netty-native.dockerfile | 21 +++ .../Kotlin/hexagon/hexagon-netty.dockerfile | 15 +- .../hexagon-nettyepoll-pgclient.dockerfile | 15 +- .../hexagon/hexagon-nettyepoll.dockerfile | 15 +- .../Kotlin/hexagon/hexagon-tomcat.dockerfile | 10 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 15 +- .../hexagon_jetty_pgclient/build.gradle | 6 - .../hexagon_jetty_postgresql/build.gradle | 7 +- .../hexagon_netty_async_pgclient/build.gradle | 7 + .../src/main/kotlin/Benchmark.kt | 25 ++++ .../hexagon_netty_postgresql/build.gradle | 7 +- .../src/main/kotlin/Benchmark.kt | 7 + .../hexagon_nettyepoll_pgclient/build.gradle | 6 - .../src/main/kotlin/Benchmark.kt | 7 + .../build.gradle | 6 - .../src/main/kotlin/Benchmark.kt | 7 + .../src/main/kotlin/WebListenerServer.kt | 4 +- .../hexagon_vertx_pgclient/build.gradle | 9 ++ .../src/main/kotlin/Benchmark.kt | 33 +++++ frameworks/Kotlin/hexagon/model/build.gradle | 4 + .../src/main/kotlin/Settings.kt | 0 .../src/main/kotlin/model/CachedWorld.kt | 0 .../src/main/kotlin/model/Fortune.kt | 0 .../src/main/kotlin/model/Message.kt | 0 .../src/main/kotlin/model/World.kt | 0 frameworks/Kotlin/hexagon/settings.gradle | 5 + .../hexagon/store_pgclient_async/build.gradle | 6 + .../src/main/kotlin/BenchmarkPgClientStore.kt | 114 +++++++++++++++ 48 files changed, 663 insertions(+), 134 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/.dockerignore create mode 100644 frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties create mode 100644 frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json delete mode 100644 frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.pebble.html create mode 100644 frameworks/Kotlin/hexagon/core_async/build.gradle create mode 100644 frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Controller.kt create mode 100644 frameworks/Kotlin/hexagon/core_async/src/main/kotlin/store/BenchmarkStore.kt create mode 100644 frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties create mode 100644 frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json create mode 100644 frameworks/Kotlin/hexagon/core_async/src/main/resources/fortunes.rocker.html create mode 100644 frameworks/Kotlin/hexagon/hexagon-jetty-native.dockerfile create mode 100644 frameworks/Kotlin/hexagon/hexagon-netty-native.dockerfile create mode 100644 frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/model/build.gradle rename frameworks/Kotlin/hexagon/{core => model}/src/main/kotlin/Settings.kt (100%) rename frameworks/Kotlin/hexagon/{core => model}/src/main/kotlin/model/CachedWorld.kt (100%) rename frameworks/Kotlin/hexagon/{core => model}/src/main/kotlin/model/Fortune.kt (100%) rename frameworks/Kotlin/hexagon/{core => model}/src/main/kotlin/model/Message.kt (100%) rename frameworks/Kotlin/hexagon/{core => model}/src/main/kotlin/model/World.kt (100%) create mode 100644 frameworks/Kotlin/hexagon/store_pgclient_async/build.gradle create mode 100644 frameworks/Kotlin/hexagon/store_pgclient_async/src/main/kotlin/BenchmarkPgClientStore.kt diff --git a/frameworks/Kotlin/hexagon/.dockerignore b/frameworks/Kotlin/hexagon/.dockerignore new file mode 100644 index 00000000000..5b154f2de67 --- /dev/null +++ b/frameworks/Kotlin/hexagon/.dockerignore @@ -0,0 +1,2 @@ + +**/build/ diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 4aad4ab8f98..755096930bc 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,6 +1,7 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.8.10" apply false + id "org.jetbrains.kotlin.jvm" version "1.8.21" apply false + id "org.graalvm.buildtools.native" version "0.9.22" apply false } version = "1.0.0" @@ -8,19 +9,23 @@ description = "TFB benchmark" group = "com.hexagonkt" ext { - hexagonVersion = "2.6.6" + hexagonVersion = "3.0.0-B1" + jettyVersion = "11.0.15" + nettyVersion = "4.1.93.Final" + hikariVersion = "5.0.1" - jettyVersion = "11.0.14" postgresqlVersion = "42.6.0" - vertxVersion = "4.4.0" + vertxVersion = "4.4.2" cache2kVersion = "2.6.1.Final" - nettyVersion = "4.1.90.Final" + applicationClass = "com.hexagonkt.BenchmarkKt" + modules = "java.naming,java.sql,java.management" + options = "--enable-preview" gradleScripts = "https://raw.githubusercontent.com/hexagonkt/hexagon/$hexagonVersion/gradle" } -defaultTasks("build") - subprojects { + version = rootProject.version + apply(from: "$gradleScripts/kotlin.gradle") } diff --git a/frameworks/Kotlin/hexagon/core/build.gradle b/frameworks/Kotlin/hexagon/core/build.gradle index af7552398d3..4cf6f44b80c 100644 --- a/frameworks/Kotlin/hexagon/core/build.gradle +++ b/frameworks/Kotlin/hexagon/core/build.gradle @@ -4,6 +4,7 @@ plugins { } dependencies { + api(project(":model")) api("com.hexagonkt:http_server:$hexagonVersion") api("com.hexagonkt:templates_rocker:$hexagonVersion") api("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") @@ -13,11 +14,9 @@ dependencies { tasks.register("minimizeTemplate") { doLast { - [ "fortunes.pebble.html", "fortunes.rocker.html" ].forEach { t -> - File template = file("$buildDir/resources/main/$t") - List lines = template.readLines().collect { it.trim() } - template.write(lines.join("")) - } + File template = file("$buildDir/resources/main/fortunes.rocker.html") + List lines = template.readLines().collect { it.trim() } + template.write(lines.join("")) } } diff --git a/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt index b4714a76049..37ab786e791 100644 --- a/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt +++ b/frameworks/Kotlin/hexagon/core/src/main/kotlin/Controller.kt @@ -8,9 +8,9 @@ import com.hexagonkt.http.model.ContentType import com.hexagonkt.http.model.Header import com.hexagonkt.http.model.Headers import com.hexagonkt.http.server.callbacks.DateCallback -import com.hexagonkt.http.server.handlers.HttpServerContext -import com.hexagonkt.http.server.handlers.PathHandler -import com.hexagonkt.http.server.handlers.path +import com.hexagonkt.http.handlers.HttpContext +import com.hexagonkt.http.handlers.PathHandler +import com.hexagonkt.http.handlers.path import com.hexagonkt.model.* import com.hexagonkt.serialization.jackson.json.Json import com.hexagonkt.serialization.serialize @@ -55,9 +55,9 @@ class Controller( private fun Message.toJson(): String = toMap().serialize(Json.raw) - private fun HttpServerContext.listFortunes( + private fun HttpContext.listFortunes( store: BenchmarkStore, templateUrl: URL, templateAdapter: TemplatePort - ): HttpServerContext { + ): HttpContext { val fortunes = store.findAllFortunes() + Fortune(0, "Additional fortune added at request time.") val sortedFortunes = fortunes.sortedBy { it.message } @@ -67,7 +67,7 @@ class Controller( return ok(body, contentType = html) } - private fun HttpServerContext.dbQuery(store: BenchmarkStore): HttpServerContext { + private fun HttpContext.dbQuery(store: BenchmarkStore): HttpContext { val ids = listOf(randomWorld()) val worlds = store.findWorlds(ids) val world = worlds.first().toMap() @@ -75,7 +75,7 @@ class Controller( return sendJson(world) } - private fun HttpServerContext.getWorlds(store: BenchmarkStore): HttpServerContext { + private fun HttpContext.getWorlds(store: BenchmarkStore): HttpContext { val worldsCount = getWorldsCount(queriesParam) val ids = (1..worldsCount).map { randomWorld() } val worlds = store.findWorlds(ids).map { it.toMap() } @@ -83,7 +83,7 @@ class Controller( return sendJson(worlds) } - private fun HttpServerContext.getCachedWorlds(store: BenchmarkStore): HttpServerContext { + private fun HttpContext.getCachedWorlds(store: BenchmarkStore): HttpContext { val worldsCount = getWorldsCount(cachedQueriesParam) val ids = (1..worldsCount).map { randomWorld() } val worlds = store.findCachedWorlds(ids).map { it.toMap() } @@ -91,7 +91,7 @@ class Controller( return sendJson(worlds) } - private fun HttpServerContext.updateWorlds(store: BenchmarkStore): HttpServerContext { + private fun HttpContext.updateWorlds(store: BenchmarkStore): HttpContext { val worldsCount = getWorldsCount(queriesParam) val worlds = (1..worldsCount).map { World(randomWorld(), randomWorld()) } @@ -100,11 +100,11 @@ class Controller( return sendJson(worlds.map { it.toMap() }) } - private fun HttpServerContext.sendJson(body: Any): HttpServerContext = + private fun HttpContext.sendJson(body: Any): HttpContext = ok(body.serialize(Json.raw), contentType = json) - private fun HttpServerContext.getWorldsCount(parameter: String): Int = - request.queryParameters[parameter]?.value?.toIntOrNull().let { + private fun HttpContext.getWorldsCount(parameter: String): Int = + request.queryParameters[parameter]?.string()?.toIntOrNull().let { when { it == null -> 1 it < 1 -> 1 diff --git a/frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties b/frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties new file mode 100644 index 00000000000..ee1c0199d95 --- /dev/null +++ b/frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties @@ -0,0 +1,7 @@ +Args= \ + -H:IncludeResources=.*\\.(html|class) \ + --enable-preview \ + --static \ + --initialize-at-build-time=org.slf4j.jul.JDK14LoggerAdapter \ + --initialize-at-build-time=org.slf4j.jul.JDK14LoggerAdapter$1 \ + --initialize-at-build-time=org.slf4j.LoggerFactory diff --git a/frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json b/frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json new file mode 100644 index 00000000000..11815306be2 --- /dev/null +++ b/frameworks/Kotlin/hexagon/core/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json @@ -0,0 +1,23 @@ +[ + { + "name": "fortunes", + "allPublicMethods": true, + "allDeclaredFields": true, + "allDeclaredMethods": true, + "allDeclaredConstructors": true + }, + { + "name": "fortunes$Template", + "allPublicMethods": true, + "allDeclaredFields": true, + "allDeclaredMethods": true, + "allDeclaredConstructors": true + }, + { + "name": "fortunes$PlainText", + "allPublicMethods": true, + "allDeclaredFields": true, + "allDeclaredMethods": true, + "allDeclaredConstructors": true + } +] diff --git a/frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.pebble.html b/frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.pebble.html deleted file mode 100644 index 1a74dd9800c..00000000000 --- a/frameworks/Kotlin/hexagon/core/src/main/resources/fortunes.pebble.html +++ /dev/null @@ -1,21 +0,0 @@ - - - - - Fortunes - - - - - - - - {% for fortune in fortunes %} - - - - - {% endfor %} -
idmessage
{{ fortune.id }}{{ fortune.message }}
- - diff --git a/frameworks/Kotlin/hexagon/core_async/build.gradle b/frameworks/Kotlin/hexagon/core_async/build.gradle new file mode 100644 index 00000000000..0a33387738e --- /dev/null +++ b/frameworks/Kotlin/hexagon/core_async/build.gradle @@ -0,0 +1,32 @@ + +plugins { + id("nu.studer.rocker") version("3.0.4") +} + +dependencies { + api(project(":model")) + api("com.hexagonkt:http_server_async:$hexagonVersion") + api("com.hexagonkt:templates_rocker:$hexagonVersion") + api("com.hexagonkt:logging_slf4j_jul:$hexagonVersion") + api("com.hexagonkt:serialization_jackson_json:$hexagonVersion") + api("org.cache2k:cache2k-core:$cache2kVersion") +} + +tasks.register("minimizeTemplate") { + doLast { + File template = file("$buildDir/resources/main/fortunes.rocker.html") + List lines = template.readLines().collect { it.trim() } + template.write(lines.join("")) + } +} + +jar.dependsOn("minimizeTemplate") + +rocker { + configurations { + create("main") { + templateDir.set(file("src/main/resources")) + optimize.set(true) + } + } +} diff --git a/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..2bda28da73e --- /dev/null +++ b/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Benchmark.kt @@ -0,0 +1,28 @@ +package com.hexagonkt.async + +import com.hexagonkt.Settings +import com.hexagonkt.http.server.async.HttpServer +import com.hexagonkt.http.server.async.HttpServerPort +import com.hexagonkt.http.server.async.HttpServerSettings +import com.hexagonkt.async.store.BenchmarkStore +import com.hexagonkt.templates.TemplatePort +import java.net.InetAddress +import java.net.URL + +class Benchmark( + private val engine: HttpServerPort, + private val store: BenchmarkStore, + private val template: TemplatePort, + private val templateUrl: URL, + private val settings: Settings = Settings(), +) { + val server: HttpServer by lazy { + val controller = Controller(settings, store, template, templateUrl) + val serverSettings = HttpServerSettings( + bindAddress = InetAddress.getByName(settings.bindAddress), + bindPort = settings.bindPort, + ) + + HttpServer(engine, controller.path, serverSettings) + } +} diff --git a/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Controller.kt b/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Controller.kt new file mode 100644 index 00000000000..683d39f4ffa --- /dev/null +++ b/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/Controller.kt @@ -0,0 +1,133 @@ +package com.hexagonkt.async + +import com.hexagonkt.Settings +import com.hexagonkt.core.fieldsMapOf +import com.hexagonkt.core.media.APPLICATION_JSON +import com.hexagonkt.core.media.TEXT_HTML +import com.hexagonkt.core.media.TEXT_PLAIN +import com.hexagonkt.handlers.async.done +import com.hexagonkt.http.model.ContentType +import com.hexagonkt.http.model.Header +import com.hexagonkt.http.model.Headers +import com.hexagonkt.http.server.async.callbacks.DateCallback +import com.hexagonkt.http.handlers.async.HttpContext +import com.hexagonkt.http.handlers.async.PathHandler +import com.hexagonkt.http.handlers.async.path +import com.hexagonkt.model.* +import com.hexagonkt.serialization.jackson.json.Json +import com.hexagonkt.serialization.serialize +import com.hexagonkt.async.store.BenchmarkStore +import com.hexagonkt.templates.TemplatePort +import java.net.URL +import java.util.concurrent.CompletableFuture +import java.util.concurrent.ThreadLocalRandom +import kotlin.text.Charsets.UTF_8 + +class Controller( + settings: Settings, + store: BenchmarkStore, + templateEngine: TemplatePort, + templateUrl: URL, +) { + private val queriesParam: String = settings.queriesParam + private val cachedQueriesParam: String = settings.cachedQueriesParam + private val worldRows: Int = settings.worldRows + private val textMessage: String = settings.textMessage + + private val plain: ContentType = ContentType(TEXT_PLAIN) + private val json: ContentType = ContentType(APPLICATION_JSON) + private val html: ContentType = ContentType(TEXT_HTML, charset = UTF_8) + + private val headers = Headers(Header("server", "Hexagon")) + + val path: PathHandler by lazy { + path { + on("*") { send(headers = headers).done() } + on("*", DateCallback()) + + get("/plaintext") { ok(textMessage, contentType = plain).done() } + get("/json") { ok(Message(textMessage).toJson(), contentType = json).done() } + get("/fortunes") { listFortunes(store, templateUrl, templateEngine) } + get("/db") { dbQuery(store) } + get("/query") { getWorlds(store) } + get("/cached-queries") { getCachedWorlds(store) } + get("/update") { updateWorlds(store) } + } + } + + private fun Message.toJson(): String = + toMap().serialize(Json.raw) + + private fun HttpContext.listFortunes( + store: BenchmarkStore, templateUrl: URL, templateAdapter: TemplatePort + ): CompletableFuture = + store + .findAllFortunes() + .thenApply { it + Fortune(0, "Additional fortune added at request time.") } + .thenApply { fortunes -> fortunes.sortedBy { it.message } } + .thenApply { sortedFortunes -> mapOf("fortunes" to sortedFortunes) } + .thenApply { context -> templateAdapter.render(templateUrl, context) } + .thenApply { body -> ok(body, contentType = html) } + + private fun HttpContext.dbQuery(store: BenchmarkStore): CompletableFuture { + val ids = listOf(randomWorld()) + return store.findWorlds(ids) + .thenApply { worlds -> worlds.first().toMap()} + .thenApply { world -> sendJson(world) } + } + + private fun HttpContext.getWorlds(store: BenchmarkStore): CompletableFuture { + val worldsCount = getWorldsCount(queriesParam) + val ids = (1..worldsCount).map { randomWorld() } + return store.findWorlds(ids) + .thenApply { worlds -> worlds.map { it.toMap() } } + .thenApply { worlds -> sendJson(worlds) } + } + + private fun HttpContext.getCachedWorlds(store: BenchmarkStore): CompletableFuture { + val worldsCount = getWorldsCount(cachedQueriesParam) + val ids = (1..worldsCount).map { randomWorld() } + val worlds = store.findCachedWorlds(ids).map { it.toMap() } + + return sendJson(worlds).done() + } + + private fun HttpContext.updateWorlds(store: BenchmarkStore): CompletableFuture { + val worldsCount = getWorldsCount(queriesParam) + val worlds = (1..worldsCount).map { World(randomWorld(), randomWorld()) } + + return store.replaceWorlds(worlds) + .thenApply { sendJson(worlds.map { it.toMap() }) } + } + + private fun HttpContext.sendJson(body: Any): HttpContext = + ok(body.serialize(Json.raw), contentType = json) + + private fun HttpContext.getWorldsCount(parameter: String): Int = + request.queryParameters[parameter]?.string()?.toIntOrNull().let { + when { + it == null -> 1 + it < 1 -> 1 + it > 500 -> 500 + else -> it + } + } + + private fun randomWorld(): Int = + ThreadLocalRandom.current().nextInt(worldRows) + 1 + + private fun Message.toMap(): Map = + fieldsMapOf(Message::message to message) + + private fun World.toMap(): Map = + fieldsMapOf( + World::id to id, + World::randomNumber to randomNumber, + ) + + private fun CachedWorld.toMap(): Map = + fieldsMapOf( + CachedWorld::id to id, + CachedWorld::randomNumber to randomNumber, + ) +} diff --git a/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/store/BenchmarkStore.kt b/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/store/BenchmarkStore.kt new file mode 100644 index 00000000000..13f5aae7108 --- /dev/null +++ b/frameworks/Kotlin/hexagon/core_async/src/main/kotlin/store/BenchmarkStore.kt @@ -0,0 +1,34 @@ +package com.hexagonkt.async.store + +import com.hexagonkt.model.CachedWorld +import com.hexagonkt.model.Fortune +import com.hexagonkt.Settings +import com.hexagonkt.model.World +import org.cache2k.Cache +import org.cache2k.Cache2kBuilder +import java.util.concurrent.CompletableFuture + +abstract class BenchmarkStore(settings: Settings) { + + abstract fun findAllFortunes(): CompletableFuture> + abstract fun findWorlds(ids: List): CompletableFuture> + abstract fun replaceWorlds(worlds: List): CompletableFuture<*> + abstract fun initWorldsCache(cache: Cache) + abstract fun loadCachedWorld(id: Int): CachedWorld + abstract fun close() + + private val worldsCache: Cache by lazy { + object : Cache2kBuilder() {} + .eternal(true) + .disableMonitoring(true) + .disableStatistics(true) + .entryCapacity(settings.worldRows.toLong()) + .loader { id -> loadCachedWorld(id) } + .build() + .apply { initWorldsCache(this) } + } + + fun findCachedWorlds(ids: List): List { + return ids.mapNotNull { worldsCache.get(it) } + } +} diff --git a/frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties b/frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties new file mode 100644 index 00000000000..ee1c0199d95 --- /dev/null +++ b/frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/native-image.properties @@ -0,0 +1,7 @@ +Args= \ + -H:IncludeResources=.*\\.(html|class) \ + --enable-preview \ + --static \ + --initialize-at-build-time=org.slf4j.jul.JDK14LoggerAdapter \ + --initialize-at-build-time=org.slf4j.jul.JDK14LoggerAdapter$1 \ + --initialize-at-build-time=org.slf4j.LoggerFactory diff --git a/frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json b/frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json new file mode 100644 index 00000000000..11815306be2 --- /dev/null +++ b/frameworks/Kotlin/hexagon/core_async/src/main/resources/META-INF/native-image/com.hexagonkt.benchmark/core/reflect-config.json @@ -0,0 +1,23 @@ +[ + { + "name": "fortunes", + "allPublicMethods": true, + "allDeclaredFields": true, + "allDeclaredMethods": true, + "allDeclaredConstructors": true + }, + { + "name": "fortunes$Template", + "allPublicMethods": true, + "allDeclaredFields": true, + "allDeclaredMethods": true, + "allDeclaredConstructors": true + }, + { + "name": "fortunes$PlainText", + "allPublicMethods": true, + "allDeclaredFields": true, + "allDeclaredMethods": true, + "allDeclaredConstructors": true + } +] diff --git a/frameworks/Kotlin/hexagon/core_async/src/main/resources/fortunes.rocker.html b/frameworks/Kotlin/hexagon/core_async/src/main/resources/fortunes.rocker.html new file mode 100644 index 00000000000..c9a9d4037e5 --- /dev/null +++ b/frameworks/Kotlin/hexagon/core_async/src/main/resources/fortunes.rocker.html @@ -0,0 +1,24 @@ +@import java.util.* +@import com.hexagonkt.model.Fortune +@args(Map context) + + + + + Fortunes + + + + + + + + @for ((fortune) : (Collection)context.get("fortunes")) { + + + + + } +
idmessage
@fortune.getId()@fortune.getMessage()
+ + diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar index ccebba7710deaf9f98673a68957ea02138b60d0a..c1962a79e29d3e0ab67b14947c167a862655af9b 100644 GIT binary patch delta 8979 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 F{TFmrHLU;u delta 8469 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"BENCHMARK_ENV")?.lowercase() + maxSize = 8 + if (environment == "citrine") Jvm.cpuCount else Jvm.cpuCount * 2 + } + } + + private val dataSource: SqlClient by lazy { PgPool.pool(vertx(), connectOptions, poolOptions) } + + override fun findAllFortunes(): CompletableFuture> = + dataSource.preparedQuery(SELECT_ALL_FORTUNES) + .execute() + .map { rowSet -> + rowSet.map { row -> Fortune(row.getInteger(0), row.getString(1)) } + } + .toCompletionStage() + .toCompletableFuture() + + override fun findWorlds(ids: List): CompletableFuture> { + val futures = ids.map { findWorld(it, dataSource) } + return all(futures).map { it.list() }.toCompletionStage().toCompletableFuture() + } + + override fun replaceWorlds(worlds: List): CompletableFuture<*> { + val futures = worlds.map { + val worldId = it.id + val newRandomNumber = it.randomNumber + dataSource + .preparedQuery(SELECT_WORLD) + .execute(Tuple.of(worldId)) + .flatMap { rowSet -> + val row = rowSet.iterator().next() + row.getInteger(1) // Read 'randomNumber' to comply with Test type 5, point 6 + dataSource + .preparedQuery(UPDATE_WORLD) + .execute(Tuple.of(newRandomNumber, worldId)) + } + } + return all(futures).toCompletionStage().toCompletableFuture() + } + + override fun initWorldsCache(cache: Cache) { + dataSource + .preparedQuery("select * from world") + .execute() + .map { rowSet -> + rowSet.map { row -> + val id = row.getInteger(0) + val randomNumber = row.getInteger(1) + cache.put(id, CachedWorld(id, randomNumber)) + } + } + .toCompletionStage() + .toCompletableFuture() + .get() + } + + override fun loadCachedWorld(id: Int): CachedWorld = + findWorld(id, dataSource) + .map { world -> CachedWorld(world.id, world.randomNumber) } + .toCompletionStage() + .toCompletableFuture() + .get() + + override fun close() { + dataSource.close() + } + + private fun findWorld(id: Int, client: SqlClient): Future = + client + .preparedQuery(SELECT_WORLD) + .execute(Tuple.of(id)) + .map { rowSet -> + val row = rowSet.iterator().next() + World(row.getInteger(0), row.getInteger(1)) + } +} From 745aabf430b2a95fee6352dbc815608743ecb624 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 7 Jun 2023 16:05:40 +0200 Subject: [PATCH 088/105] Add async and native support --- .../Kotlin/hexagon/benchmark_config.json | 69 +++++++++++++++++++ frameworks/Kotlin/hexagon/config.toml | 54 +++++++++++++++ .../hexagon-netty-async-pgclient.dockerfile | 23 +++++++ .../hexagon/hexagon-vertx-pgclient.dockerfile | 23 +++++++ .../src/main/kotlin/BenchmarkPgClientStore.kt | 2 +- .../src/main/kotlin/BenchmarkPgClientStore.kt | 2 +- .../src/main/kotlin/BenchmarkSqlStore.kt | 2 +- 7 files changed, 172 insertions(+), 3 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile create mode 100644 frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 4bcc8b23f66..d5134ade6c8 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -136,6 +136,75 @@ "notes": "http://hexagonkt.com", "versus": "netty" }, + "netty-native": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Netty", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Netty Native PostgreSQL", + "notes": "http://hexagonkt.com", + "versus": "netty" + }, + "netty-async-pgclient": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Netty", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Netty Async PgClient", + "notes": "http://hexagonkt.com", + "versus": "netty" + }, + "vertx-pgclient": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Vertx", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Vertx PgClient", + "notes": "http://hexagonkt.com", + "versus": "vertx" + }, "tomcat": { "json_url": "/json", "db_url": "/db", diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index d51d0e8ccf6..baeb6ac78ad 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -73,6 +73,24 @@ platform = "Netty" webserver = "None" versus = "netty" +[netty-native] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Netty" +webserver = "None" +versus = "netty" + [nettyepoll] urls.plaintext = "/plaintext" urls.json = "/json" @@ -109,6 +127,24 @@ platform = "Netty" webserver = "None" versus = "netty" +[nettyepoll-async-pgclient] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Netty" +webserver = "None" +versus = "netty" + [tomcat] urls.plaintext = "/plaintext" urls.json = "/json" @@ -126,3 +162,21 @@ orm = "Raw" platform = "Servlet" webserver = "Tomcat" versus = "servlet" + +[vertx-pgclient] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Vertx" +webserver = "None" +versus = "vertx" diff --git a/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile new file mode 100644 index 00000000000..09845f263cb --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile @@ -0,0 +1,23 @@ +# +# BUILD +# +FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +ADD . . +RUN gradle --quiet classes +RUN gradle --quiet -x test installDist + +# +# RUNTIME +# +FROM docker.io/eclipse-temurin:17-jre-alpine +ARG PROJECT=hexagon_netty_async_pgclient + +ENV POSTGRESQL_DB_HOST tfb-database +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT + +ENTRYPOINT [ "/opt/hexagon_netty_async_pgclient/bin/hexagon_netty_async_pgclient" ] diff --git a/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile new file mode 100644 index 00000000000..5b8ff2cd1b1 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile @@ -0,0 +1,23 @@ +# +# BUILD +# +FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +ADD . . +RUN gradle --quiet classes +RUN gradle --quiet -x test installDist + +# +# RUNTIME +# +FROM docker.io/eclipse-temurin:17-jre-alpine +ARG PROJECT=hexagon_vertx_pgclient + +ENV POSTGRESQL_DB_HOST tfb-database +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT + +ENTRYPOINT [ "/opt/hexagon_vertx_pgclient/bin/hexagon_vertx_pgclient" ] diff --git a/frameworks/Kotlin/hexagon/store_pgclient/src/main/kotlin/BenchmarkPgClientStore.kt b/frameworks/Kotlin/hexagon/store_pgclient/src/main/kotlin/BenchmarkPgClientStore.kt index 5cd13ccee0a..1fb9547353f 100644 --- a/frameworks/Kotlin/hexagon/store_pgclient/src/main/kotlin/BenchmarkPgClientStore.kt +++ b/frameworks/Kotlin/hexagon/store_pgclient/src/main/kotlin/BenchmarkPgClientStore.kt @@ -24,7 +24,7 @@ class BenchmarkPgClientStore( private val connectOptions: PgConnectOptions by lazy { PgConnectOptions().apply { - host = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "localhost" + host = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "tfb-database" database = settings.databaseName user = settings.databaseUsername password = settings.databasePassword diff --git a/frameworks/Kotlin/hexagon/store_pgclient_async/src/main/kotlin/BenchmarkPgClientStore.kt b/frameworks/Kotlin/hexagon/store_pgclient_async/src/main/kotlin/BenchmarkPgClientStore.kt index f7b0350bfe9..8266b3120e4 100644 --- a/frameworks/Kotlin/hexagon/store_pgclient_async/src/main/kotlin/BenchmarkPgClientStore.kt +++ b/frameworks/Kotlin/hexagon/store_pgclient_async/src/main/kotlin/BenchmarkPgClientStore.kt @@ -27,7 +27,7 @@ class BenchmarkPgClientStore( private val connectOptions: PgConnectOptions by lazy { PgConnectOptions().apply { - host = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "localhost" + host = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "tfb-database" database = settings.databaseName user = settings.databaseUsername password = settings.databasePassword diff --git a/frameworks/Kotlin/hexagon/store_sql/src/main/kotlin/BenchmarkSqlStore.kt b/frameworks/Kotlin/hexagon/store_sql/src/main/kotlin/BenchmarkSqlStore.kt index ea871ec1b13..501a4d9ce34 100644 --- a/frameworks/Kotlin/hexagon/store_sql/src/main/kotlin/BenchmarkSqlStore.kt +++ b/frameworks/Kotlin/hexagon/store_sql/src/main/kotlin/BenchmarkSqlStore.kt @@ -22,7 +22,7 @@ class BenchmarkSqlStore( } private val dataSource: HikariDataSource by lazy { - val dbHost = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "localhost" + val dbHost = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "tfb-database" val environment = Jvm.systemSettingOrNull(String::class, "BENCHMARK_ENV")?.lowercase() val poolSize = 8 + if (environment == "citrine") Jvm.cpuCount else Jvm.cpuCount * 2 val postgresqlSettings = listOf( From f54f8803eabf78bb55ac83e3a3582dff3fbf2306 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Wed, 7 Jun 2023 16:12:35 +0200 Subject: [PATCH 089/105] Add async and native support --- frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index 77cf13f6cbb..e35db7b9f68 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -7,7 +7,7 @@ WORKDIR /hexagon ADD . . RUN gradle --quiet classes -RUN gradle --quiet -x test +RUN gradle --quiet -x test war # # RUNTIME From 267c4b626513161721edfce382629d5c79ce7d83 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 16 Jun 2023 11:26:16 +0200 Subject: [PATCH 090/105] Replace Vert.x adapter by Netty Epoll Async adapter --- frameworks/Kotlin/hexagon/build.gradle | 6 ++--- ...xagon-nettyepoll-async-pgclient.dockerfile | 23 +++++++++++++++++++ .../build.gradle | 8 +++++++ .../src/main/kotlin/Benchmark.kt | 4 ++-- .../hexagon_vertx_pgclient/build.gradle | 9 -------- frameworks/Kotlin/hexagon/settings.gradle | 2 +- 6 files changed, 37 insertions(+), 15 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile create mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle rename frameworks/Kotlin/hexagon/{hexagon_vertx_pgclient => hexagon_nettyepoll_async_pgclient}/src/main/kotlin/Benchmark.kt (89%) delete mode 100644 frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/build.gradle diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index 755096930bc..f4a2ad995c7 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,6 +1,6 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.8.21" apply false + id "org.jetbrains.kotlin.jvm" version "1.8.22" apply false id "org.graalvm.buildtools.native" version "0.9.22" apply false } @@ -9,13 +9,13 @@ description = "TFB benchmark" group = "com.hexagonkt" ext { - hexagonVersion = "3.0.0-B1" + hexagonVersion = "3.0.0-B3" jettyVersion = "11.0.15" nettyVersion = "4.1.93.Final" hikariVersion = "5.0.1" postgresqlVersion = "42.6.0" - vertxVersion = "4.4.2" + vertxVersion = "4.4.3" cache2kVersion = "2.6.1.Final" applicationClass = "com.hexagonkt.BenchmarkKt" diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile new file mode 100644 index 00000000000..17234b76d4f --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile @@ -0,0 +1,23 @@ +# +# BUILD +# +FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +ADD . . +RUN gradle --quiet classes +RUN gradle --quiet -x test installDist + +# +# RUNTIME +# +FROM docker.io/eclipse-temurin:17-jre-alpine +ARG PROJECT=hexagon_nettyepoll_async_pgclient + +ENV POSTGRESQL_DB_HOST tfb-database +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT + +ENTRYPOINT [ "/opt/hexagon_vertx_pgclient/bin/hexagon_vertx_pgclient" ] diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle new file mode 100644 index 00000000000..9fb1cc22c05 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle @@ -0,0 +1,8 @@ + +apply(from: "$gradleScripts/application.gradle") + +dependencies { + api(project(":store_pgclient_async")) + api("com.hexagonkt:http_server_netty_epoll_async:$hexagonVersion") + api("io.netty:netty-transport-native-epoll:$nettyVersion") +} diff --git a/frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt similarity index 89% rename from frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/src/main/kotlin/Benchmark.kt rename to frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt index 6b52be6d68f..1e40fa3ffaf 100644 --- a/frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt @@ -2,7 +2,7 @@ package com.hexagonkt import com.hexagonkt.async.Benchmark import com.hexagonkt.async.store.BenchmarkPgClientStore -import com.hexagonkt.http.server.vertx.VertxServerAdapter +import com.hexagonkt.http.server.netty.epoll.async.NettyEpollServerAdapter import com.hexagonkt.templates.rocker.RockerAdapter import io.netty.util.ResourceLeakDetector import io.netty.util.ResourceLeakDetector.Level.DISABLED @@ -26,7 +26,7 @@ fun main() { val store = BenchmarkPgClientStore("postgresql") val templateEngine = RockerAdapter() val templateUrl = URL("classpath:fortunes.rocker.html") - val engine = VertxServerAdapter(preferNativeTransport = true) + val engine = NettyEpollServerAdapter(bossGroupThreads = 48) val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) benchmark.server.start() diff --git a/frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/build.gradle b/frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/build.gradle deleted file mode 100644 index 2d5cdaf23d7..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon_vertx_pgclient/build.gradle +++ /dev/null @@ -1,9 +0,0 @@ - -apply(from: "$gradleScripts/application.gradle") - -dependencies { - api(project(":store_pgclient_async")) - api("com.hexagonkt:http_server_vertx_async:$hexagonVersion") - api("io.vertx:vertx-io_uring-incubator:4.4.2") - api("io.netty:netty-transport-native-epoll:4.1.93.Final") -} diff --git a/frameworks/Kotlin/hexagon/settings.gradle b/frameworks/Kotlin/hexagon/settings.gradle index 7b6af470769..cf4ad98fdac 100644 --- a/frameworks/Kotlin/hexagon/settings.gradle +++ b/frameworks/Kotlin/hexagon/settings.gradle @@ -12,7 +12,7 @@ include( "hexagon_netty_postgresql", "hexagon_netty_async_pgclient", "hexagon_nettyepoll_pgclient", + "hexagon_nettyepoll_async_pgclient", "hexagon_nettyepoll_postgresql", - "hexagon_vertx_pgclient", "hexagon_tomcat_postgresql", ) From 9c2385b3785dee56e4843d771e3d52fbdd6e6678 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 16 Jun 2023 12:31:53 +0200 Subject: [PATCH 091/105] Replace Vert.x adapter by Netty Epoll Async adapter --- .../Kotlin/hexagon/benchmark_config.json | 6 ++--- frameworks/Kotlin/hexagon/config.toml | 6 ++--- .../hexagon/hexagon-vertx-pgclient.dockerfile | 23 ------------------- 3 files changed, 6 insertions(+), 29 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index d5134ade6c8..d9f60d20b6f 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -182,7 +182,7 @@ "notes": "http://hexagonkt.com", "versus": "netty" }, - "vertx-pgclient": { + "nettyepoll-async-pgclient": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -197,13 +197,13 @@ "framework": "Hexagon", "language": "Kotlin", "orm": "Raw", - "platform": "Vertx", + "platform": "Netty", "webserver": "None", "os": "Linux", "database_os": "Linux", "display_name": "Hexagon Vertx PgClient", "notes": "http://hexagonkt.com", - "versus": "vertx" + "versus": "netty" }, "tomcat": { "json_url": "/json", diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index baeb6ac78ad..d30e5353e5a 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -163,7 +163,7 @@ platform = "Servlet" webserver = "Tomcat" versus = "servlet" -[vertx-pgclient] +[nettyepoll-async-pgclient] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/db" @@ -177,6 +177,6 @@ database = "postgres" database_os = "Linux" os = "Linux" orm = "Raw" -platform = "Vertx" +platform = "Netty" webserver = "None" -versus = "vertx" +versus = "netty" diff --git a/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile deleted file mode 100644 index 5b8ff2cd1b1..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile +++ /dev/null @@ -1,23 +0,0 @@ -# -# BUILD -# -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build -USER root -WORKDIR /hexagon - -ADD . . -RUN gradle --quiet classes -RUN gradle --quiet -x test installDist - -# -# RUNTIME -# -FROM docker.io/eclipse-temurin:17-jre-alpine -ARG PROJECT=hexagon_vertx_pgclient - -ENV POSTGRESQL_DB_HOST tfb-database -ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA - -COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT - -ENTRYPOINT [ "/opt/hexagon_vertx_pgclient/bin/hexagon_vertx_pgclient" ] From 10081f798389d199144618e4446b731d5a80fdee Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 16 Jun 2023 14:20:51 +0200 Subject: [PATCH 092/105] Replace Vert.x adapter by Netty Epoll Async adapter --- .../Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile index 17234b76d4f..7e4c80d6cd4 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile @@ -20,4 +20,4 @@ ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT -ENTRYPOINT [ "/opt/hexagon_vertx_pgclient/bin/hexagon_vertx_pgclient" ] +ENTRYPOINT [ "/opt/hexagon_nettyepoll_async_pgclient/bin/hexagon_nettyepoll_async_pgclient" ] From 10b312c8765639fd0343ad45da4b89276953fd15 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Fri, 16 Jun 2023 16:18:31 +0200 Subject: [PATCH 093/105] Replace Vert.x adapter by Netty Epoll Async adapter --- .../hexagon/hexagon_nettyepoll_async_pgclient/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle index 9fb1cc22c05..148de98b406 100644 --- a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/build.gradle @@ -4,5 +4,5 @@ apply(from: "$gradleScripts/application.gradle") dependencies { api(project(":store_pgclient_async")) api("com.hexagonkt:http_server_netty_epoll_async:$hexagonVersion") - api("io.netty:netty-transport-native-epoll:$nettyVersion") + api("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") } From efc7321d5a7f065bb306c01588747bf251a6b44d Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 17 Jun 2023 12:58:42 +0200 Subject: [PATCH 094/105] Replace Vert.x adapter by Netty Epoll Async adapter --- .../Kotlin/hexagon/benchmark_config.json | 18 +++++++-------- frameworks/Kotlin/hexagon/config.toml | 18 --------------- ...xagon-nettyepoll-async-pgclient.dockerfile | 2 +- .../hexagon/hexagon-vertx-pgclient.dockerfile | 23 ------------------- .../src/main/kotlin/Benchmark.kt | 8 ------- 5 files changed, 9 insertions(+), 60 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index d5134ade6c8..90db8bffd93 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -136,14 +136,12 @@ "notes": "http://hexagonkt.com", "versus": "netty" }, - "netty-native": { - "json_url": "/json", + "nettyepoll-async-pgclient": { "db_url": "/db", "query_url": "/query?queries=", "fortune_url": "/fortunes", "update_url": "/update?queries=", "cached_query_url": "/cached-queries?count=", - "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", "classification": "Micro", @@ -155,11 +153,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Native PostgreSQL", + "display_name": "Hexagon Netty Epoll PgClient", "notes": "http://hexagonkt.com", "versus": "netty" }, - "netty-async-pgclient": { + "netty-native": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -178,11 +176,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Async PgClient", + "display_name": "Hexagon Netty Native PostgreSQL", "notes": "http://hexagonkt.com", "versus": "netty" }, - "vertx-pgclient": { + "netty-async-pgclient": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -197,13 +195,13 @@ "framework": "Hexagon", "language": "Kotlin", "orm": "Raw", - "platform": "Vertx", + "platform": "Netty", "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Vertx PgClient", + "display_name": "Hexagon Netty Async PgClient", "notes": "http://hexagonkt.com", - "versus": "vertx" + "versus": "netty" }, "tomcat": { "json_url": "/json", diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index baeb6ac78ad..488f052bb61 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -162,21 +162,3 @@ orm = "Raw" platform = "Servlet" webserver = "Tomcat" versus = "servlet" - -[vertx-pgclient] -urls.plaintext = "/plaintext" -urls.json = "/json" -urls.db = "/db" -urls.query = "/query?queries=" -urls.update = "/update?queries=" -urls.fortune = "/fortunes" -urls.cached_query = "/cached-queries?count=" -approach = "Realistic" -classification = "Micro" -database = "postgres" -database_os = "Linux" -os = "Linux" -orm = "Raw" -platform = "Vertx" -webserver = "None" -versus = "vertx" diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile index 17234b76d4f..7e4c80d6cd4 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile @@ -20,4 +20,4 @@ ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT -ENTRYPOINT [ "/opt/hexagon_vertx_pgclient/bin/hexagon_vertx_pgclient" ] +ENTRYPOINT [ "/opt/hexagon_nettyepoll_async_pgclient/bin/hexagon_nettyepoll_async_pgclient" ] diff --git a/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile deleted file mode 100644 index 5b8ff2cd1b1..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-vertx-pgclient.dockerfile +++ /dev/null @@ -1,23 +0,0 @@ -# -# BUILD -# -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build -USER root -WORKDIR /hexagon - -ADD . . -RUN gradle --quiet classes -RUN gradle --quiet -x test installDist - -# -# RUNTIME -# -FROM docker.io/eclipse-temurin:17-jre-alpine -ARG PROJECT=hexagon_vertx_pgclient - -ENV POSTGRESQL_DB_HOST tfb-database -ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA - -COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT - -ENTRYPOINT [ "/opt/hexagon_vertx_pgclient/bin/hexagon_vertx_pgclient" ] diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt index 1e40fa3ffaf..0b21842bc8f 100644 --- a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt @@ -11,14 +11,6 @@ import java.net.URL fun main() { ResourceLeakDetector.setLevel(DISABLED) - System.setProperty("vertx.disableMetrics", "true") - System.setProperty("vertx.disableH2c", "true") - System.setProperty("vertx.disableWebsockets", "true") - System.setProperty("vertx.flashPolicyHandler", "false") - System.setProperty("vertx.threadChecks", "false") - System.setProperty("vertx.disableContextTimings", "true") - System.setProperty("vertx.disableTCCL", "true") - System.setProperty("vertx.disableHttpHeadersValidation", "true") System.setProperty("io.netty.buffer.checkBounds", "false") System.setProperty("io.netty.buffer.checkAccessible", "false") From 3b053f41613114925dcb8973536360aa52e6fcfb Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sat, 17 Jun 2023 22:16:45 +0200 Subject: [PATCH 095/105] Add Jasync store --- .../Kotlin/hexagon/benchmark_config.json | 23 ++++ frameworks/Kotlin/hexagon/build.gradle | 1 + frameworks/Kotlin/hexagon/config.toml | 18 +++ ...hexagon-nettyepoll-async-jasync.dockerfile | 23 ++++ .../build.gradle | 8 ++ .../src/main/kotlin/Benchmark.kt | 25 +++++ .../src/main/kotlin/Benchmark.kt | 8 ++ frameworks/Kotlin/hexagon/settings.gradle | 2 + .../Kotlin/hexagon/store_jasync/build.gradle | 5 + .../src/main/kotlin/BenchmarkJasyncStore.kt | 106 ++++++++++++++++++ 10 files changed, 219 insertions(+) create mode 100644 frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile create mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt create mode 100644 frameworks/Kotlin/hexagon/store_jasync/build.gradle create mode 100644 frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 90db8bffd93..e16837acbe8 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -180,6 +180,29 @@ "notes": "http://hexagonkt.com", "versus": "netty" }, + "netty-async-jasync": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Netty", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Netty Async Jasync", + "notes": "http://hexagonkt.com", + "versus": "netty" + }, "netty-async-pgclient": { "json_url": "/json", "db_url": "/db", diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index f4a2ad995c7..47101f72dbf 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -16,6 +16,7 @@ ext { hikariVersion = "5.0.1" postgresqlVersion = "42.6.0" vertxVersion = "4.4.3" + jasyncVersion = "2.2.0" cache2kVersion = "2.6.1.Final" applicationClass = "com.hexagonkt.BenchmarkKt" diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index 488f052bb61..be5cfb36a91 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -145,6 +145,24 @@ platform = "Netty" webserver = "None" versus = "netty" +[nettyepoll-async-jasync] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Netty" +webserver = "None" +versus = "netty" + [tomcat] urls.plaintext = "/plaintext" urls.json = "/json" diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile new file mode 100644 index 00000000000..d35474e1b0b --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile @@ -0,0 +1,23 @@ +# +# BUILD +# +FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +ADD . . +RUN gradle --quiet classes +RUN gradle --quiet -x test installDist + +# +# RUNTIME +# +FROM docker.io/eclipse-temurin:17-jre-alpine +ARG PROJECT=hexagon_nettyepoll_async_jasync + +ENV POSTGRESQL_DB_HOST tfb-database +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT + +ENTRYPOINT [ "/opt/hexagon_nettyepoll_async_jasync/bin/hexagon_nettyepoll_async_jasync" ] diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle new file mode 100644 index 00000000000..62804c2f8c4 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle @@ -0,0 +1,8 @@ + +apply(from: "$gradleScripts/application.gradle") + +dependencies { + api(project(":store_jasync")) + api("com.hexagonkt:http_server_netty_epoll_async:$hexagonVersion") + api("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") +} diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..eee45899d05 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt @@ -0,0 +1,25 @@ +package com.hexagonkt + +import com.hexagonkt.async.Benchmark +import com.hexagonkt.async.store.BenchmarkJasyncStore +import com.hexagonkt.http.server.netty.epoll.async.NettyEpollServerAdapter +import com.hexagonkt.templates.rocker.RockerAdapter +import io.netty.util.ResourceLeakDetector +import io.netty.util.ResourceLeakDetector.Level.DISABLED +import java.net.URL + +fun main() { + ResourceLeakDetector.setLevel(DISABLED) + + System.setProperty("io.netty.buffer.checkBounds", "false") + System.setProperty("io.netty.buffer.checkAccessible", "false") + + val settings = Settings() + val store = BenchmarkJasyncStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = URL("classpath:fortunes.rocker.html") + val engine = NettyEpollServerAdapter(bossGroupThreads = 48) + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt index 0b21842bc8f..1e40fa3ffaf 100644 --- a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_pgclient/src/main/kotlin/Benchmark.kt @@ -11,6 +11,14 @@ import java.net.URL fun main() { ResourceLeakDetector.setLevel(DISABLED) + System.setProperty("vertx.disableMetrics", "true") + System.setProperty("vertx.disableH2c", "true") + System.setProperty("vertx.disableWebsockets", "true") + System.setProperty("vertx.flashPolicyHandler", "false") + System.setProperty("vertx.threadChecks", "false") + System.setProperty("vertx.disableContextTimings", "true") + System.setProperty("vertx.disableTCCL", "true") + System.setProperty("vertx.disableHttpHeadersValidation", "true") System.setProperty("io.netty.buffer.checkBounds", "false") System.setProperty("io.netty.buffer.checkAccessible", "false") diff --git a/frameworks/Kotlin/hexagon/settings.gradle b/frameworks/Kotlin/hexagon/settings.gradle index cf4ad98fdac..d07b35f2779 100644 --- a/frameworks/Kotlin/hexagon/settings.gradle +++ b/frameworks/Kotlin/hexagon/settings.gradle @@ -3,6 +3,7 @@ include( "model", "core", "core_async", + "store_jasync", "store_pgclient", "store_pgclient_async", "store_sql", @@ -12,6 +13,7 @@ include( "hexagon_netty_postgresql", "hexagon_netty_async_pgclient", "hexagon_nettyepoll_pgclient", + "hexagon_nettyepoll_async_jasync", "hexagon_nettyepoll_async_pgclient", "hexagon_nettyepoll_postgresql", "hexagon_tomcat_postgresql", diff --git a/frameworks/Kotlin/hexagon/store_jasync/build.gradle b/frameworks/Kotlin/hexagon/store_jasync/build.gradle new file mode 100644 index 00000000000..5ead678dd16 --- /dev/null +++ b/frameworks/Kotlin/hexagon/store_jasync/build.gradle @@ -0,0 +1,5 @@ + +dependencies { + api(project(":core_async")) + implementation("com.github.jasync-sql:jasync-postgresql:$jasyncVersion") +} diff --git a/frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt b/frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt new file mode 100644 index 00000000000..0f5702c5e84 --- /dev/null +++ b/frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt @@ -0,0 +1,106 @@ +package com.hexagonkt.async.store + +import com.github.jasync.sql.db.ConnectionPoolConfigurationBuilder +import com.github.jasync.sql.db.pool.ConnectionPool +import com.github.jasync.sql.db.postgresql.PostgreSQLConnection +import com.github.jasync.sql.db.postgresql.PostgreSQLConnectionBuilder +import com.hexagonkt.Settings +import com.hexagonkt.core.Jvm +import com.hexagonkt.model.CachedWorld +import com.hexagonkt.model.Fortune +import com.hexagonkt.model.World +import org.cache2k.Cache +import java.util.concurrent.CompletableFuture +import java.util.concurrent.CompletableFuture.allOf + +class BenchmarkJasyncStore( + engine: String, + private val settings: Settings = Settings(), +) : BenchmarkStore(settings) { + + companion object { + private const val SELECT_WORLD: String = "select * from world where id = $1" + private const val UPDATE_WORLD: String = "update world set randomNumber = $1 where id = $2" + private const val SELECT_ALL_FORTUNES: String = "select * from fortune" + } + + private val dataSource: ConnectionPool by lazy { + ConnectionPoolConfigurationBuilder().let { + val environment = Jvm.systemSettingOrNull("BENCHMARK_ENV")?.lowercase() + val cpuCount = Jvm.cpuCount + + it.maxActiveConnections = 8 + if (environment == "citrine") cpuCount else cpuCount * 2 + it.host = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "tfb-database" + it.database = settings.databaseName + it.username = settings.databaseUsername + it.password = settings.databasePassword + + PostgreSQLConnectionBuilder.createConnectionPool(it.build()) + } + } + + override fun findAllFortunes(): CompletableFuture> = + dataSource.sendPreparedStatement(SELECT_ALL_FORTUNES) + .thenApply { result -> + val rowSet = result.rows + rowSet.map { row -> + val id = row.getInt(0) ?: error("") + val message = row.getString(1) ?: error("") + Fortune(id, message) + } + } + + override fun findWorlds(ids: List): CompletableFuture> { + val futures = ids.map { findWorld(it, dataSource) }.toTypedArray() + return allOf(*futures).thenApply { futures.map { f -> f.get() ?: error("") } } + } + + override fun replaceWorlds(worlds: List): CompletableFuture<*> { + val futures = worlds.map { + val worldId = it.id + val newRandomNumber = it.randomNumber + dataSource + .sendPreparedStatement(SELECT_WORLD, listOf(worldId)) + .thenApply { rowSet -> + val row = rowSet.rows.iterator().next() + row.getInt(1) // Read 'randomNumber' to comply with Test type 5, point 6 + dataSource + .sendPreparedStatement(UPDATE_WORLD, listOf(newRandomNumber, worldId)) + } + }.toTypedArray() + + return allOf(*futures).thenApply { futures.map { f -> f.get() ?: error("") } } + } + + override fun initWorldsCache(cache: Cache) { + dataSource + .sendPreparedStatement("select * from world") + .thenApply { rowSet -> + rowSet.rows.map { row -> + val id = row.getInt(0) ?: error("") + val randomNumber = row.getInt(1) ?: error("") + cache.put(id, CachedWorld(id, randomNumber)) + } + } + .get() + } + + override fun loadCachedWorld(id: Int): CachedWorld = + findWorld(id, dataSource) + .thenApply { world -> CachedWorld(world.id, world.randomNumber) } + .get() + + override fun close() { + dataSource.disconnect().get() + } + + private fun findWorld(id: Int, client: ConnectionPool<*>): CompletableFuture = + client + .sendPreparedStatement(SELECT_WORLD, listOf(id)) + .thenApply { rowSet -> + val row = rowSet.rows.iterator().next() + val id1 = row.getInt(0) ?: error("") + val randomNumber = row.getInt(1) ?: error("") + World(id1, randomNumber) + } +} From 3c6475953104029274b29ae9a91ee0fa8cf5e8ce Mon Sep 17 00:00:00 2001 From: jaguililla Date: Sun, 18 Jun 2023 08:52:52 +0200 Subject: [PATCH 096/105] Add Jasync store --- frameworks/Kotlin/hexagon/benchmark_config.json | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index e16837acbe8..4874edffd24 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -153,11 +153,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Epoll PgClient", + "display_name": "Hexagon Netty Epoll Async PgClient", "notes": "http://hexagonkt.com", "versus": "netty" }, - "netty-native": { + "nettyepoll-async-jasync": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -176,11 +176,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Native PostgreSQL", + "display_name": "Hexagon Netty Epoll Async Jasync", "notes": "http://hexagonkt.com", "versus": "netty" }, - "netty-async-jasync": { + "netty-native": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -199,7 +199,7 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Async Jasync", + "display_name": "Hexagon Netty Native PostgreSQL", "notes": "http://hexagonkt.com", "versus": "netty" }, From 4c921b4bdf41ca9efb676f2588b8f496e5c4382f Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 19:39:26 +0200 Subject: [PATCH 097/105] Update --- frameworks/Kotlin/hexagon/build.gradle | 10 +- .../hexagon-jettyloom-pgclient.dockerfile | 2 +- .../hexagon/hexagon-jettyloom.dockerfile | 2 +- .../hexagon-netty-async-pgclient.dockerfile | 2 +- .../Kotlin/hexagon/hexagon-netty.dockerfile | 2 +- ...hexagon-nettyepoll-async-jasync.dockerfile | 10 +- .../hexagon/hexagon-nettyepoll.dockerfile | 2 +- frameworks/Kotlin/hexagon/hexagon.dockerfile | 2 +- .../build.gradle | 8 -- .../src/main/kotlin/Benchmark.kt | 25 ----- .../Kotlin/hexagon/store_jasync/build.gradle | 5 - .../src/main/kotlin/BenchmarkJasyncStore.kt | 106 ------------------ 12 files changed, 12 insertions(+), 164 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle delete mode 100644 frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt delete mode 100644 frameworks/Kotlin/hexagon/store_jasync/build.gradle delete mode 100644 frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt diff --git a/frameworks/Kotlin/hexagon/build.gradle b/frameworks/Kotlin/hexagon/build.gradle index f4a2ad995c7..fecbf1174e6 100644 --- a/frameworks/Kotlin/hexagon/build.gradle +++ b/frameworks/Kotlin/hexagon/build.gradle @@ -1,7 +1,7 @@ plugins { - id "org.jetbrains.kotlin.jvm" version "1.8.22" apply false - id "org.graalvm.buildtools.native" version "0.9.22" apply false + id "org.jetbrains.kotlin.jvm" version "1.9.0" apply false + id "org.graalvm.buildtools.native" version "0.9.23" apply false } version = "1.0.0" @@ -9,13 +9,13 @@ description = "TFB benchmark" group = "com.hexagonkt" ext { - hexagonVersion = "3.0.0-B3" + hexagonVersion = "3.0.0-B8" jettyVersion = "11.0.15" - nettyVersion = "4.1.93.Final" + nettyVersion = "4.1.94.Final" hikariVersion = "5.0.1" postgresqlVersion = "42.6.0" - vertxVersion = "4.4.3" + vertxVersion = "4.4.4" cache2kVersion = "2.6.1.Final" applicationClass = "com.hexagonkt.BenchmarkKt" diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile index 804555dae57..390ce706bc6 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile index 1d64e9246dd..97809e8cc05 100644 --- a/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-jettyloom.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile index 09845f263cb..ddb35d90de8 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile index 18fce97d813..16b71649263 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile index 9307f4120ab..aae9e180c7d 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon @@ -13,19 +13,11 @@ RUN gradle --quiet -x test installDist # RUNTIME # FROM docker.io/eclipse-temurin:17-jre-alpine -<<<<<<<< HEAD:frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile -ARG PROJECT=hexagon_nettyepoll_async_jasync -======== ARG PROJECT=hexagon_nettyepoll_async_pgclient ->>>>>>>> 1d0e4006abc9d1d1cfee1f3f2e5bdbc9fbab8f11:frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile ENV POSTGRESQL_DB_HOST tfb-database ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT -<<<<<<<< HEAD:frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile -ENTRYPOINT [ "/opt/hexagon_nettyepoll_async_jasync/bin/hexagon_nettyepoll_async_jasync" ] -======== ENTRYPOINT [ "/opt/hexagon_nettyepoll_async_pgclient/bin/hexagon_nettyepoll_async_pgclient" ] ->>>>>>>> 1d0e4006abc9d1d1cfee1f3f2e5bdbc9fbab8f11:frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile index c8a5592b67e..9b083b9683d 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon.dockerfile b/frameworks/Kotlin/hexagon/hexagon.dockerfile index 6bc878580ab..2cf68db7f9f 100644 --- a/frameworks/Kotlin/hexagon/hexagon.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle deleted file mode 100644 index 62804c2f8c4..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/build.gradle +++ /dev/null @@ -1,8 +0,0 @@ - -apply(from: "$gradleScripts/application.gradle") - -dependencies { - api(project(":store_jasync")) - api("com.hexagonkt:http_server_netty_epoll_async:$hexagonVersion") - api("io.netty:netty-transport-native-epoll:$nettyVersion:linux-x86_64") -} diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt deleted file mode 100644 index eee45899d05..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_async_jasync/src/main/kotlin/Benchmark.kt +++ /dev/null @@ -1,25 +0,0 @@ -package com.hexagonkt - -import com.hexagonkt.async.Benchmark -import com.hexagonkt.async.store.BenchmarkJasyncStore -import com.hexagonkt.http.server.netty.epoll.async.NettyEpollServerAdapter -import com.hexagonkt.templates.rocker.RockerAdapter -import io.netty.util.ResourceLeakDetector -import io.netty.util.ResourceLeakDetector.Level.DISABLED -import java.net.URL - -fun main() { - ResourceLeakDetector.setLevel(DISABLED) - - System.setProperty("io.netty.buffer.checkBounds", "false") - System.setProperty("io.netty.buffer.checkAccessible", "false") - - val settings = Settings() - val store = BenchmarkJasyncStore("postgresql") - val templateEngine = RockerAdapter() - val templateUrl = URL("classpath:fortunes.rocker.html") - val engine = NettyEpollServerAdapter(bossGroupThreads = 48) - - val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) - benchmark.server.start() -} diff --git a/frameworks/Kotlin/hexagon/store_jasync/build.gradle b/frameworks/Kotlin/hexagon/store_jasync/build.gradle deleted file mode 100644 index 5ead678dd16..00000000000 --- a/frameworks/Kotlin/hexagon/store_jasync/build.gradle +++ /dev/null @@ -1,5 +0,0 @@ - -dependencies { - api(project(":core_async")) - implementation("com.github.jasync-sql:jasync-postgresql:$jasyncVersion") -} diff --git a/frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt b/frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt deleted file mode 100644 index 0f5702c5e84..00000000000 --- a/frameworks/Kotlin/hexagon/store_jasync/src/main/kotlin/BenchmarkJasyncStore.kt +++ /dev/null @@ -1,106 +0,0 @@ -package com.hexagonkt.async.store - -import com.github.jasync.sql.db.ConnectionPoolConfigurationBuilder -import com.github.jasync.sql.db.pool.ConnectionPool -import com.github.jasync.sql.db.postgresql.PostgreSQLConnection -import com.github.jasync.sql.db.postgresql.PostgreSQLConnectionBuilder -import com.hexagonkt.Settings -import com.hexagonkt.core.Jvm -import com.hexagonkt.model.CachedWorld -import com.hexagonkt.model.Fortune -import com.hexagonkt.model.World -import org.cache2k.Cache -import java.util.concurrent.CompletableFuture -import java.util.concurrent.CompletableFuture.allOf - -class BenchmarkJasyncStore( - engine: String, - private val settings: Settings = Settings(), -) : BenchmarkStore(settings) { - - companion object { - private const val SELECT_WORLD: String = "select * from world where id = $1" - private const val UPDATE_WORLD: String = "update world set randomNumber = $1 where id = $2" - private const val SELECT_ALL_FORTUNES: String = "select * from fortune" - } - - private val dataSource: ConnectionPool by lazy { - ConnectionPoolConfigurationBuilder().let { - val environment = Jvm.systemSettingOrNull("BENCHMARK_ENV")?.lowercase() - val cpuCount = Jvm.cpuCount - - it.maxActiveConnections = 8 + if (environment == "citrine") cpuCount else cpuCount * 2 - it.host = Jvm.systemSettingOrNull("${engine.uppercase()}_DB_HOST") ?: "tfb-database" - it.database = settings.databaseName - it.username = settings.databaseUsername - it.password = settings.databasePassword - - PostgreSQLConnectionBuilder.createConnectionPool(it.build()) - } - } - - override fun findAllFortunes(): CompletableFuture> = - dataSource.sendPreparedStatement(SELECT_ALL_FORTUNES) - .thenApply { result -> - val rowSet = result.rows - rowSet.map { row -> - val id = row.getInt(0) ?: error("") - val message = row.getString(1) ?: error("") - Fortune(id, message) - } - } - - override fun findWorlds(ids: List): CompletableFuture> { - val futures = ids.map { findWorld(it, dataSource) }.toTypedArray() - return allOf(*futures).thenApply { futures.map { f -> f.get() ?: error("") } } - } - - override fun replaceWorlds(worlds: List): CompletableFuture<*> { - val futures = worlds.map { - val worldId = it.id - val newRandomNumber = it.randomNumber - dataSource - .sendPreparedStatement(SELECT_WORLD, listOf(worldId)) - .thenApply { rowSet -> - val row = rowSet.rows.iterator().next() - row.getInt(1) // Read 'randomNumber' to comply with Test type 5, point 6 - dataSource - .sendPreparedStatement(UPDATE_WORLD, listOf(newRandomNumber, worldId)) - } - }.toTypedArray() - - return allOf(*futures).thenApply { futures.map { f -> f.get() ?: error("") } } - } - - override fun initWorldsCache(cache: Cache) { - dataSource - .sendPreparedStatement("select * from world") - .thenApply { rowSet -> - rowSet.rows.map { row -> - val id = row.getInt(0) ?: error("") - val randomNumber = row.getInt(1) ?: error("") - cache.put(id, CachedWorld(id, randomNumber)) - } - } - .get() - } - - override fun loadCachedWorld(id: Int): CachedWorld = - findWorld(id, dataSource) - .thenApply { world -> CachedWorld(world.id, world.randomNumber) } - .get() - - override fun close() { - dataSource.disconnect().get() - } - - private fun findWorld(id: Int, client: ConnectionPool<*>): CompletableFuture = - client - .sendPreparedStatement(SELECT_WORLD, listOf(id)) - .thenApply { rowSet -> - val row = rowSet.rows.iterator().next() - val id1 = row.getInt(0) ?: error("") - val randomNumber = row.getInt(1) ?: error("") - World(id1, randomNumber) - } -} From da155321b774f18accc5d4880b830b9afb101fc0 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 19:39:52 +0200 Subject: [PATCH 098/105] Update --- ...hexagon-nettyepoll-async-jasync.dockerfile | 23 ------------------- 1 file changed, 23 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile deleted file mode 100644 index aae9e180c7d..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-jasync.dockerfile +++ /dev/null @@ -1,23 +0,0 @@ -# -# BUILD -# -FROM docker.io/gradle:8.2-jdk17-alpine AS build -USER root -WORKDIR /hexagon - -ADD . . -RUN gradle --quiet classes -RUN gradle --quiet -x test installDist - -# -# RUNTIME -# -FROM docker.io/eclipse-temurin:17-jre-alpine -ARG PROJECT=hexagon_nettyepoll_async_pgclient - -ENV POSTGRESQL_DB_HOST tfb-database -ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA - -COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT - -ENTRYPOINT [ "/opt/hexagon_nettyepoll_async_pgclient/bin/hexagon_nettyepoll_async_pgclient" ] From 8bf5f23aa2bf2eff013b517166fe67bea9b99512 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 19:53:05 +0200 Subject: [PATCH 099/105] Update --- .../Kotlin/hexagon/benchmark_config.json | 60 +++---------------- frameworks/Kotlin/hexagon/config.toml | 20 +------ .../hexagon/hexagon-jetty-native.dockerfile | 21 ------- .../hexagon-netty-async-pgclient.dockerfile | 23 ------- 4 files changed, 9 insertions(+), 115 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon-jetty-native.dockerfile delete mode 100644 frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index a9e45ab3204..7319f7f601a 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -92,7 +92,7 @@ "notes": "http://hexagonkt.com", "versus": "netty" }, - "nettyepoll": { + "netty-native": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -111,53 +111,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Epoll PostgreSQL", - "notes": "http://hexagonkt.com", - "versus": "netty" - }, - "nettyepoll-pgclient": { - "db_url": "/db", - "query_url": "/query?queries=", - "fortune_url": "/fortunes", - "update_url": "/update?queries=", - "cached_query_url": "/cached-queries?count=", - "port": 9090, - "approach": "Realistic", - "classification": "Micro", - "database": "postgres", - "framework": "Hexagon", - "language": "Kotlin", - "orm": "Raw", - "platform": "Netty", - "webserver": "None", - "os": "Linux", - "database_os": "Linux", - "display_name": "Hexagon Netty Epoll PgClient", - "notes": "http://hexagonkt.com", - "versus": "netty" - }, - "nettyepoll-async-pgclient": { - "db_url": "/db", - "query_url": "/query?queries=", - "fortune_url": "/fortunes", - "update_url": "/update?queries=", - "cached_query_url": "/cached-queries?count=", - "port": 9090, - "approach": "Realistic", - "classification": "Micro", - "database": "postgres", - "framework": "Hexagon", - "language": "Kotlin", - "orm": "Raw", - "platform": "Netty", - "webserver": "None", - "os": "Linux", - "database_os": "Linux", - "display_name": "Hexagon Netty Epoll Async PgClient", + "display_name": "Hexagon Netty Native PostgreSQL", "notes": "http://hexagonkt.com", "versus": "netty" }, - "nettyepoll-async-jasync": { + "nettyepoll": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -176,11 +134,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Epoll Async Jasync", + "display_name": "Hexagon Netty Epoll PostgreSQL", "notes": "http://hexagonkt.com", "versus": "netty" }, - "netty-native": { + "nettyepoll-async-pgclient": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -199,18 +157,16 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Native PostgreSQL", + "display_name": "Hexagon Netty Epoll Async PgClient", "notes": "http://hexagonkt.com", "versus": "netty" }, - "nettyepoll-async-pgclient": { - "json_url": "/json", + "nettyepoll-pgclient": { "db_url": "/db", "query_url": "/query?queries=", "fortune_url": "/fortunes", "update_url": "/update?queries=", "cached_query_url": "/cached-queries?count=", - "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", "classification": "Micro", @@ -222,7 +178,7 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Async PgClient", + "display_name": "Hexagon Netty Epoll PgClient", "notes": "http://hexagonkt.com", "versus": "netty" }, diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index a670485de47..edb6b6e4a5f 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -109,24 +109,6 @@ platform = "Netty" webserver = "None" versus = "netty" -[nettyepoll-pgclient] -urls.plaintext = "/plaintext" -urls.json = "/json" -urls.db = "/db" -urls.query = "/query?queries=" -urls.update = "/update?queries=" -urls.fortune = "/fortunes" -urls.cached_query = "/cached-queries?count=" -approach = "Realistic" -classification = "Micro" -database = "postgres" -database_os = "Linux" -os = "Linux" -orm = "Raw" -platform = "Netty" -webserver = "None" -versus = "netty" - [nettyepoll-async-pgclient] urls.plaintext = "/plaintext" urls.json = "/json" @@ -145,7 +127,7 @@ platform = "Netty" webserver = "None" versus = "netty" -[nettyepoll-async-pgclient] +[nettyepoll-pgclient] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/db" diff --git a/frameworks/Kotlin/hexagon/hexagon-jetty-native.dockerfile b/frameworks/Kotlin/hexagon/hexagon-jetty-native.dockerfile deleted file mode 100644 index 223aae81894..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-jetty-native.dockerfile +++ /dev/null @@ -1,21 +0,0 @@ -# -# BUILD -# -FROM ghcr.io/graalvm/native-image:ol9-java17-22.3.2 as build -USER root -WORKDIR /hexagon - -ADD . . -RUN microdnf -y install findutils -RUN ./gradlew --quiet classes -RUN ./gradlew --quiet -x test nativeCompile - -# -# RUNTIME -# -FROM scratch -ARG PROJECT=hexagon_jetty_postgresql - -COPY --from=build /hexagon/$PROJECT/build/native/nativeCompile/$PROJECT / - -ENTRYPOINT [ "/hexagon_jetty_postgresql" ] diff --git a/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile deleted file mode 100644 index ddb35d90de8..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-netty-async-pgclient.dockerfile +++ /dev/null @@ -1,23 +0,0 @@ -# -# BUILD -# -FROM docker.io/gradle:8.2-jdk17-alpine AS build -USER root -WORKDIR /hexagon - -ADD . . -RUN gradle --quiet classes -RUN gradle --quiet -x test installDist - -# -# RUNTIME -# -FROM docker.io/eclipse-temurin:17-jre-alpine -ARG PROJECT=hexagon_netty_async_pgclient - -ENV POSTGRESQL_DB_HOST tfb-database -ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA - -COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT - -ENTRYPOINT [ "/opt/hexagon_netty_async_pgclient/bin/hexagon_netty_async_pgclient" ] From c55d98afa600bf3c5ddc36f7cc674bb12d0888dd Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 20:47:53 +0200 Subject: [PATCH 100/105] Update Gradle --- .../hexagon/gradle/wrapper/gradle-wrapper.jar | Bin 62076 -> 63375 bytes .../gradle/wrapper/gradle-wrapper.properties | 3 ++- frameworks/Kotlin/hexagon/gradlew | 5 ++++- 3 files changed, 6 insertions(+), 2 deletions(-) diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.jar index c1962a79e29d3e0ab67b14947c167a862655af9b..033e24c4cdf41af1ab109bc7f253b2b887023340 100644 GIT binary patch delta 16170 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 delta 14892 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 diff --git a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties index ed4fda0fcea..ab1eb5eecd1 100644 --- a/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties +++ b/frameworks/Kotlin/hexagon/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,7 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https://services.gradle.org/distributions/gradle-8.1.1-bin.zip +distributionUrl=https://services.gradle.org/distributions/gradle-8.2.1-bin.zip networkTimeout=10000 +validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/frameworks/Kotlin/hexagon/gradlew b/frameworks/Kotlin/hexagon/gradlew index aeb74cbb43e..fcb6fca147c 100755 --- a/frameworks/Kotlin/hexagon/gradlew +++ b/frameworks/Kotlin/hexagon/gradlew @@ -130,10 +130,13 @@ location of your Java installation." fi else JAVACMD=java - which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. + if ! command -v java >/dev/null 2>&1 + then + die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. Please set the JAVA_HOME variable in your environment to match the location of your Java installation." + fi fi # Increase the maximum file descriptors if we can. From 5083e68d01c43e03cafcdbd524ffc3f81d25d5eb Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 20:50:12 +0200 Subject: [PATCH 101/105] Benchmark Netty Epoll only --- .../hexagon_netty_async_pgclient/build.gradle | 7 ------ .../src/main/kotlin/Benchmark.kt | 25 ------------------- .../src/main/kotlin/Benchmark.kt | 24 ------------------ .../build.gradle | 1 + 4 files changed, 1 insertion(+), 56 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/build.gradle delete mode 100644 frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/src/main/kotlin/Benchmark.kt delete mode 100644 frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt diff --git a/frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/build.gradle b/frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/build.gradle deleted file mode 100644 index f29d1703b61..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/build.gradle +++ /dev/null @@ -1,7 +0,0 @@ - -apply(from: "$gradleScripts/application.gradle") - -dependencies { - api(project(":store_pgclient_async")) - api("com.hexagonkt:http_server_netty_async:$hexagonVersion") -} diff --git a/frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/src/main/kotlin/Benchmark.kt deleted file mode 100644 index e5a9de4c597..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon_netty_async_pgclient/src/main/kotlin/Benchmark.kt +++ /dev/null @@ -1,25 +0,0 @@ -package com.hexagonkt - -import com.hexagonkt.async.Benchmark -import com.hexagonkt.async.store.BenchmarkPgClientStore -import com.hexagonkt.http.server.netty.async.NettyServerAdapter -import com.hexagonkt.templates.rocker.RockerAdapter -import io.netty.util.ResourceLeakDetector -import io.netty.util.ResourceLeakDetector.Level.DISABLED -import java.net.URL - -fun main() { - ResourceLeakDetector.setLevel(DISABLED) - - System.setProperty("io.netty.buffer.checkBounds", "false") - System.setProperty("io.netty.buffer.checkAccessible", "false") - - val settings = Settings() - val store = BenchmarkPgClientStore("postgresql") - val templateEngine = RockerAdapter() - val templateUrl = URL("classpath:fortunes.rocker.html") - val engine = NettyServerAdapter(bossGroupThreads = 48) - - val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) - benchmark.server.start() -} diff --git a/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt deleted file mode 100644 index 2a95e7385fc..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/src/main/kotlin/Benchmark.kt +++ /dev/null @@ -1,24 +0,0 @@ -package com.hexagonkt - -import com.hexagonkt.http.server.netty.NettyServerAdapter -import com.hexagonkt.store.BenchmarkSqlStore -import com.hexagonkt.templates.rocker.RockerAdapter -import io.netty.util.ResourceLeakDetector -import io.netty.util.ResourceLeakDetector.Level.DISABLED -import java.net.URL - -fun main() { - ResourceLeakDetector.setLevel(DISABLED) - - System.setProperty("io.netty.buffer.checkBounds", "false") - System.setProperty("io.netty.buffer.checkAccessible", "false") - - val settings = Settings() - val store = BenchmarkSqlStore("postgresql") - val templateEngine = RockerAdapter() - val templateUrl = URL("classpath:fortunes.rocker.html") - val engine = NettyServerAdapter() - - val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) - benchmark.server.start() -} diff --git a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle index 243fa57c121..d3ce42499e4 100644 --- a/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle +++ b/frameworks/Kotlin/hexagon/hexagon_nettyepoll_postgresql/build.gradle @@ -1,4 +1,5 @@ +apply(from: "$gradleScripts/native.gradle") apply(from: "$gradleScripts/application.gradle") dependencies { From 927a7001a1bc4e2e3713a599c2cac733b1213cdb Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 20:54:37 +0200 Subject: [PATCH 102/105] Add Nima adapter --- .../Kotlin/hexagon/benchmark_config.json | 55 +++++++++++++------ frameworks/Kotlin/hexagon/config.toml | 36 +++++++++--- .../hexagon_nima_pgclient/build.gradle | 7 +++ .../src/main/kotlin/Benchmark.kt | 17 ++++++ .../build.gradle | 2 +- .../src/main/kotlin/Benchmark.kt | 17 ++++++ frameworks/Kotlin/hexagon/settings.gradle | 4 +- 7 files changed, 110 insertions(+), 28 deletions(-) create mode 100644 frameworks/Kotlin/hexagon/hexagon_nima_pgclient/build.gradle create mode 100644 frameworks/Kotlin/hexagon/hexagon_nima_pgclient/src/main/kotlin/Benchmark.kt rename frameworks/Kotlin/hexagon/{hexagon_netty_postgresql => hexagon_nima_postgresql}/build.gradle (70%) create mode 100644 frameworks/Kotlin/hexagon/hexagon_nima_postgresql/src/main/kotlin/Benchmark.kt diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index 7319f7f601a..a03055d3a3d 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -69,7 +69,7 @@ "notes": "http://hexagonkt.com", "versus": "servlet" }, - "netty": { + "nettyepoll": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -88,11 +88,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty PostgreSQL", + "display_name": "Hexagon Netty Epoll PostgreSQL", "notes": "http://hexagonkt.com", "versus": "netty" }, - "netty-native": { + "nettyepoll-async-pgclient": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -111,18 +111,16 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Native PostgreSQL", + "display_name": "Hexagon Netty Epoll Async PgClient", "notes": "http://hexagonkt.com", "versus": "netty" }, - "nettyepoll": { - "json_url": "/json", + "nettyepoll-pgclient": { "db_url": "/db", "query_url": "/query?queries=", "fortune_url": "/fortunes", "update_url": "/update?queries=", "cached_query_url": "/cached-queries?count=", - "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", "classification": "Micro", @@ -134,11 +132,11 @@ "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Epoll PostgreSQL", + "display_name": "Hexagon Netty Epoll PgClient", "notes": "http://hexagonkt.com", "versus": "netty" }, - "nettyepoll-async-pgclient": { + "nima": { "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", @@ -153,20 +151,22 @@ "framework": "Hexagon", "language": "Kotlin", "orm": "Raw", - "platform": "Netty", + "platform": "Helidon", "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Epoll Async PgClient", + "display_name": "Hexagon Nima PostgreSQL", "notes": "http://hexagonkt.com", - "versus": "netty" + "versus": "helidon-nima" }, - "nettyepoll-pgclient": { + "nima-native": { + "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", "fortune_url": "/fortunes", "update_url": "/update?queries=", "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", "classification": "Micro", @@ -174,13 +174,36 @@ "framework": "Hexagon", "language": "Kotlin", "orm": "Raw", - "platform": "Netty", + "platform": "Helidon", "webserver": "None", "os": "Linux", "database_os": "Linux", - "display_name": "Hexagon Netty Epoll PgClient", + "display_name": "Hexagon Nima Native PostgreSQL", "notes": "http://hexagonkt.com", - "versus": "netty" + "versus": "helidon-nima" + }, + "nima-pgclient": { + "json_url": "/json", + "db_url": "/db", + "query_url": "/query?queries=", + "fortune_url": "/fortunes", + "update_url": "/update?queries=", + "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", + "port": 9090, + "approach": "Realistic", + "classification": "Micro", + "database": "postgres", + "framework": "Hexagon", + "language": "Kotlin", + "orm": "Raw", + "platform": "Helidon", + "webserver": "None", + "os": "Linux", + "database_os": "Linux", + "display_name": "Hexagon Nima PgClient", + "notes": "http://hexagonkt.com", + "versus": "helidon-nima" }, "tomcat": { "json_url": "/json", diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index edb6b6e4a5f..10a0418dbe4 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -55,7 +55,7 @@ platform = "Servlet" webserver = "None" versus = "servlet" -[netty] +[nettyepoll] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/db" @@ -73,7 +73,7 @@ platform = "Netty" webserver = "None" versus = "netty" -[netty-native] +[nettyepoll-async-pgclient] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/db" @@ -91,7 +91,7 @@ platform = "Netty" webserver = "None" versus = "netty" -[nettyepoll] +[nettyepoll-pgclient] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/db" @@ -109,7 +109,7 @@ platform = "Netty" webserver = "None" versus = "netty" -[nettyepoll-async-pgclient] +[nima] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/db" @@ -123,11 +123,11 @@ database = "postgres" database_os = "Linux" os = "Linux" orm = "Raw" -platform = "Netty" +platform = "Helidon" webserver = "None" -versus = "netty" +versus = "helidon-nima" -[nettyepoll-pgclient] +[nima-native] urls.plaintext = "/plaintext" urls.json = "/json" urls.db = "/db" @@ -141,9 +141,27 @@ database = "postgres" database_os = "Linux" os = "Linux" orm = "Raw" -platform = "Netty" +platform = "Helidon" webserver = "None" -versus = "netty" +versus = "helidon-nima" + +[nima-pgclient] +urls.plaintext = "/plaintext" +urls.json = "/json" +urls.db = "/db" +urls.query = "/query?queries=" +urls.update = "/update?queries=" +urls.fortune = "/fortunes" +urls.cached_query = "/cached-queries?count=" +approach = "Realistic" +classification = "Micro" +database = "postgres" +database_os = "Linux" +os = "Linux" +orm = "Raw" +platform = "Helidon" +webserver = "None" +versus = "helidon-nima" [tomcat] urls.plaintext = "/plaintext" diff --git a/frameworks/Kotlin/hexagon/hexagon_nima_pgclient/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nima_pgclient/build.gradle new file mode 100644 index 00000000000..86d2692a326 --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nima_pgclient/build.gradle @@ -0,0 +1,7 @@ + +apply(from: "$gradleScripts/application.gradle") + +dependencies { + api(project(":store_pgclient")) + api("com.hexagonkt:http_server_nima:$hexagonVersion") +} diff --git a/frameworks/Kotlin/hexagon/hexagon_nima_pgclient/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nima_pgclient/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..9df2914829b --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nima_pgclient/src/main/kotlin/Benchmark.kt @@ -0,0 +1,17 @@ +package com.hexagonkt + +import com.hexagonkt.core.urlOf +import com.hexagonkt.http.server.nima.NimaServerAdapter +import com.hexagonkt.store.BenchmarkPgClientStore +import com.hexagonkt.templates.rocker.RockerAdapter + +fun main() { + val settings = Settings() + val store = BenchmarkPgClientStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = urlOf("classpath:fortunes.rocker.html") + val engine = NimaServerAdapter() + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/build.gradle b/frameworks/Kotlin/hexagon/hexagon_nima_postgresql/build.gradle similarity index 70% rename from frameworks/Kotlin/hexagon/hexagon_netty_postgresql/build.gradle rename to frameworks/Kotlin/hexagon/hexagon_nima_postgresql/build.gradle index 01884cb3583..2957919e905 100644 --- a/frameworks/Kotlin/hexagon/hexagon_netty_postgresql/build.gradle +++ b/frameworks/Kotlin/hexagon/hexagon_nima_postgresql/build.gradle @@ -4,5 +4,5 @@ apply(from: "$gradleScripts/native.gradle") dependencies { api(project(":store_sql")) - api("com.hexagonkt:http_server_netty:$hexagonVersion") + api("com.hexagonkt:http_server_nima:$hexagonVersion") } diff --git a/frameworks/Kotlin/hexagon/hexagon_nima_postgresql/src/main/kotlin/Benchmark.kt b/frameworks/Kotlin/hexagon/hexagon_nima_postgresql/src/main/kotlin/Benchmark.kt new file mode 100644 index 00000000000..16e4797e37a --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon_nima_postgresql/src/main/kotlin/Benchmark.kt @@ -0,0 +1,17 @@ +package com.hexagonkt + +import com.hexagonkt.core.urlOf +import com.hexagonkt.http.server.nima.NimaServerAdapter +import com.hexagonkt.store.BenchmarkSqlStore +import com.hexagonkt.templates.rocker.RockerAdapter + +fun main() { + val settings = Settings() + val store = BenchmarkSqlStore("postgresql") + val templateEngine = RockerAdapter() + val templateUrl = urlOf("classpath:fortunes.rocker.html") + val engine = NimaServerAdapter() + + val benchmark = Benchmark(engine, store, templateEngine, templateUrl, settings) + benchmark.server.start() +} diff --git a/frameworks/Kotlin/hexagon/settings.gradle b/frameworks/Kotlin/hexagon/settings.gradle index cf4ad98fdac..2b234d2bbc6 100644 --- a/frameworks/Kotlin/hexagon/settings.gradle +++ b/frameworks/Kotlin/hexagon/settings.gradle @@ -9,8 +9,8 @@ include( "hexagon_jetty_pgclient", "hexagon_jetty_postgresql", - "hexagon_netty_postgresql", - "hexagon_netty_async_pgclient", + "hexagon_nima_pgclient", + "hexagon_nima_postgresql", "hexagon_nettyepoll_pgclient", "hexagon_nettyepoll_async_pgclient", "hexagon_nettyepoll_postgresql", From 494167f5a5d87ff72fed01753af6b56f87aa3d07 Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 20:58:12 +0200 Subject: [PATCH 103/105] Update container builds --- ...xagon-nettyepoll-async-pgclient.dockerfile | 2 +- .../hexagon-nettyepoll-pgclient.dockerfile | 2 +- ...kerfile => hexagon-nima-native.dockerfile} | 6 ++--- ...rfile => hexagon-nima-pgclient.dockerfile} | 4 ++-- .../Kotlin/hexagon/hexagon-nima.dockerfile | 23 +++++++++++++++++++ .../Kotlin/hexagon/hexagon-tomcat.dockerfile | 2 +- 6 files changed, 31 insertions(+), 8 deletions(-) rename frameworks/Kotlin/hexagon/{hexagon-netty-native.dockerfile => hexagon-nima-native.dockerfile} (64%) rename frameworks/Kotlin/hexagon/{hexagon-netty.dockerfile => hexagon-nima-pgclient.dockerfile} (78%) create mode 100644 frameworks/Kotlin/hexagon/hexagon-nima.dockerfile diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile index 7e4c80d6cd4..aae9e180c7d 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-async-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile index afe2e155ccc..e753730c6e4 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nettyepoll-pgclient.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon diff --git a/frameworks/Kotlin/hexagon/hexagon-netty-native.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile similarity index 64% rename from frameworks/Kotlin/hexagon/hexagon-netty-native.dockerfile rename to frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile index 5443b48eb8f..004b0dba351 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty-native.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM ghcr.io/graalvm/native-image:ol9-java17-22.3.2 as build +FROM ghcr.io/graalvm/native-image-community:17-ol9 as build USER root WORKDIR /hexagon @@ -14,8 +14,8 @@ RUN ./gradlew --quiet -x test nativeCompile # RUNTIME # FROM scratch -ARG PROJECT=hexagon_netty_postgresql +ARG PROJECT=hexagon_nima_postgresql COPY --from=build /hexagon/$PROJECT/build/native/nativeCompile/$PROJECT / -ENTRYPOINT [ "/hexagon_netty_postgresql" ] +ENTRYPOINT [ "/hexagon_nima_postgresql" ] diff --git a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nima-pgclient.dockerfile similarity index 78% rename from frameworks/Kotlin/hexagon/hexagon-netty.dockerfile rename to frameworks/Kotlin/hexagon/hexagon-nima-pgclient.dockerfile index 16b71649263..88861993f80 100644 --- a/frameworks/Kotlin/hexagon/hexagon-netty.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nima-pgclient.dockerfile @@ -13,11 +13,11 @@ RUN gradle --quiet -x test installDist # RUNTIME # FROM docker.io/eclipse-temurin:17-jre-alpine -ARG PROJECT=hexagon_netty_postgresql +ARG PROJECT=hexagon_nima_pgclient ENV POSTGRESQL_DB_HOST tfb-database ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT -ENTRYPOINT [ "/opt/hexagon_netty_postgresql/bin/hexagon_netty_postgresql" ] +ENTRYPOINT [ "/opt/hexagon_nima_pgclient/bin/hexagon_nima_pgclient" ] diff --git a/frameworks/Kotlin/hexagon/hexagon-nima.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nima.dockerfile new file mode 100644 index 00000000000..64e403b8eed --- /dev/null +++ b/frameworks/Kotlin/hexagon/hexagon-nima.dockerfile @@ -0,0 +1,23 @@ +# +# BUILD +# +FROM docker.io/gradle:8.2-jdk17-alpine AS build +USER root +WORKDIR /hexagon + +ADD . . +RUN gradle --quiet classes +RUN gradle --quiet -x test installDist + +# +# RUNTIME +# +FROM docker.io/eclipse-temurin:17-jre-alpine +ARG PROJECT=hexagon_nima_postgresql + +ENV POSTGRESQL_DB_HOST tfb-database +ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA + +COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT + +ENTRYPOINT [ "/opt/hexagon_nima_postgresql/bin/hexagon_nima_postgresql" ] diff --git a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile index e35db7b9f68..7fd1f9ca4e4 100644 --- a/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-tomcat.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM docker.io/gradle:8.1.1-jdk17-alpine AS build +FROM docker.io/gradle:8.2-jdk17-alpine AS build USER root WORKDIR /hexagon From 8c6ae8e8a7830e529eb288076bbf45c2576b54ea Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 21:05:04 +0200 Subject: [PATCH 104/105] Fix missing endpoints --- frameworks/Kotlin/hexagon/benchmark_config.json | 4 ++++ frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile | 2 +- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index a03055d3a3d..f88f6dcd6da 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -49,11 +49,13 @@ "versus": "servlet" }, "jettyloom-pgclient": { + "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", "fortune_url": "/fortunes", "update_url": "/update?queries=", "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", "classification": "Micro", @@ -116,11 +118,13 @@ "versus": "netty" }, "nettyepoll-pgclient": { + "json_url": "/json", "db_url": "/db", "query_url": "/query?queries=", "fortune_url": "/fortunes", "update_url": "/update?queries=", "cached_query_url": "/cached-queries?count=", + "plaintext_url": "/plaintext", "port": 9090, "approach": "Realistic", "classification": "Micro", diff --git a/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile index 004b0dba351..2f43ec310d0 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile @@ -1,7 +1,7 @@ # # BUILD # -FROM ghcr.io/graalvm/native-image-community:17-ol9 as build +FROM ghcr.io/graalvm/native-image-community:20-ol9 as build USER root WORKDIR /hexagon From 8917827356bcb7368fbd3833336ef1eca363a35f Mon Sep 17 00:00:00 2001 From: jaguililla Date: Mon, 10 Jul 2023 21:45:56 +0200 Subject: [PATCH 105/105] Fix Nima benchmarks --- .../Kotlin/hexagon/benchmark_config.json | 23 ------------------- frameworks/Kotlin/hexagon/config.toml | 18 --------------- .../hexagon/hexagon-nima-native.dockerfile | 21 ----------------- .../hexagon/hexagon-nima-pgclient.dockerfile | 4 ++-- .../Kotlin/hexagon/hexagon-nima.dockerfile | 4 ++-- 5 files changed, 4 insertions(+), 66 deletions(-) delete mode 100644 frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile diff --git a/frameworks/Kotlin/hexagon/benchmark_config.json b/frameworks/Kotlin/hexagon/benchmark_config.json index f88f6dcd6da..c98335451d2 100644 --- a/frameworks/Kotlin/hexagon/benchmark_config.json +++ b/frameworks/Kotlin/hexagon/benchmark_config.json @@ -163,29 +163,6 @@ "notes": "http://hexagonkt.com", "versus": "helidon-nima" }, - "nima-native": { - "json_url": "/json", - "db_url": "/db", - "query_url": "/query?queries=", - "fortune_url": "/fortunes", - "update_url": "/update?queries=", - "cached_query_url": "/cached-queries?count=", - "plaintext_url": "/plaintext", - "port": 9090, - "approach": "Realistic", - "classification": "Micro", - "database": "postgres", - "framework": "Hexagon", - "language": "Kotlin", - "orm": "Raw", - "platform": "Helidon", - "webserver": "None", - "os": "Linux", - "database_os": "Linux", - "display_name": "Hexagon Nima Native PostgreSQL", - "notes": "http://hexagonkt.com", - "versus": "helidon-nima" - }, "nima-pgclient": { "json_url": "/json", "db_url": "/db", diff --git a/frameworks/Kotlin/hexagon/config.toml b/frameworks/Kotlin/hexagon/config.toml index 10a0418dbe4..5629b5a7d8d 100644 --- a/frameworks/Kotlin/hexagon/config.toml +++ b/frameworks/Kotlin/hexagon/config.toml @@ -127,24 +127,6 @@ platform = "Helidon" webserver = "None" versus = "helidon-nima" -[nima-native] -urls.plaintext = "/plaintext" -urls.json = "/json" -urls.db = "/db" -urls.query = "/query?queries=" -urls.update = "/update?queries=" -urls.fortune = "/fortunes" -urls.cached_query = "/cached-queries?count=" -approach = "Realistic" -classification = "Micro" -database = "postgres" -database_os = "Linux" -os = "Linux" -orm = "Raw" -platform = "Helidon" -webserver = "None" -versus = "helidon-nima" - [nima-pgclient] urls.plaintext = "/plaintext" urls.json = "/json" diff --git a/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile deleted file mode 100644 index 2f43ec310d0..00000000000 --- a/frameworks/Kotlin/hexagon/hexagon-nima-native.dockerfile +++ /dev/null @@ -1,21 +0,0 @@ -# -# BUILD -# -FROM ghcr.io/graalvm/native-image-community:20-ol9 as build -USER root -WORKDIR /hexagon - -ADD . . -RUN microdnf -y install findutils -RUN ./gradlew --quiet classes -RUN ./gradlew --quiet -x test nativeCompile - -# -# RUNTIME -# -FROM scratch -ARG PROJECT=hexagon_nima_postgresql - -COPY --from=build /hexagon/$PROJECT/build/native/nativeCompile/$PROJECT / - -ENTRYPOINT [ "/hexagon_nima_postgresql" ] diff --git a/frameworks/Kotlin/hexagon/hexagon-nima-pgclient.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nima-pgclient.dockerfile index 88861993f80..f99ae730145 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nima-pgclient.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nima-pgclient.dockerfile @@ -12,11 +12,11 @@ RUN gradle --quiet -x test installDist # # RUNTIME # -FROM docker.io/eclipse-temurin:17-jre-alpine +FROM docker.io/eclipse-temurin:20-jre-alpine ARG PROJECT=hexagon_nima_pgclient ENV POSTGRESQL_DB_HOST tfb-database -ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT diff --git a/frameworks/Kotlin/hexagon/hexagon-nima.dockerfile b/frameworks/Kotlin/hexagon/hexagon-nima.dockerfile index 64e403b8eed..cfb1f55454d 100644 --- a/frameworks/Kotlin/hexagon/hexagon-nima.dockerfile +++ b/frameworks/Kotlin/hexagon/hexagon-nima.dockerfile @@ -12,11 +12,11 @@ RUN gradle --quiet -x test installDist # # RUNTIME # -FROM docker.io/eclipse-temurin:17-jre-alpine +FROM docker.io/eclipse-temurin:20-jre-alpine ARG PROJECT=hexagon_nima_postgresql ENV POSTGRESQL_DB_HOST tfb-database -ENV JDK_JAVA_OPTIONS -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA +ENV JDK_JAVA_OPTIONS --enable-preview -XX:+AlwaysPreTouch -XX:+UseParallelGC -XX:+UseNUMA COPY --from=build /hexagon/$PROJECT/build/install/$PROJECT /opt/$PROJECT