ktor tests hanging

Created on 10 Nov 2018  路  6Comments  路  Source: ktorio/ktor

I'm added ktor to the Gradle project and the main code works find but I have problems with the tests. They are hanging

The server code:

package comfortable.data.server

import io.ktor.application.Application
import io.ktor.application.call
import io.ktor.http.ContentType
import io.ktor.response.respondText
import io.ktor.routing.get
import io.ktor.routing.routing
import io.ktor.server.engine.embeddedServer
import io.ktor.server.netty.Netty

fun Application.main() {
    val server = embeddedServer(Netty, port = 8080) {
        routing {
            get("/books") {
                val json = this::class.java.getResource("/books.json").readText()
                call.respondText(json, ContentType.Application.Json)
            }
        }
    }
    server.start(wait = true)
}

and the test code:

package comfortable.data.server

import io.ktor.application.Application
import org.junit.jupiter.api.Test
import org.junit.jupiter.api.Assertions.assertEquals

import io.ktor.server.testing.withTestApplication
import io.ktor.server.testing.handleRequest
import io.ktor.http.HttpMethod
import io.ktor.http.HttpStatusCode

/**
 * Testing class Server.
 */
class ServerTest {
    @Test
    fun testBookRequest() = withTestApplication(Application::main) {
        with(handleRequest(HttpMethod.Get, "/books")) {
            assertEquals(HttpStatusCode.OK, response.status())
            assertEquals(true, response?.content?.contains("Solaris"))
        }
    }
}

Running with gradle test -i:
(after a while I use Ctrl-C to stop it)

> Task :test

comfortable.data.server.ServerTest > testBookRequest() STANDARD_OUT
    10:42:42.468 [Test worker] INFO ktor.test - No ktor.deployment.watch patterns specified, automatic reload is not active
    10:42:42.602 [Test worker] DEBUG io.netty.util.internal.logging.InternalLoggerFactory - Using SLF4J as the default logging framework
    10:42:42.613 [Test worker] DEBUG io.netty.channel.MultithreadEventLoopGroup - -Dio.netty.eventLoopThreads: 8
    10:42:42.686 [Test worker] DEBUG io.netty.channel.nio.NioEventLoop - -Dio.netty.noKeySetOptimization: false
    10:42:42.687 [Test worker] DEBUG io.netty.channel.nio.NioEventLoop - -Dio.netty.selectorAutoRebuildThreshold: 512
    10:42:42.754 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - -Dio.netty.noUnsafe: false
    10:42:42.755 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - Java version: 8
    10:42:42.760 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - sun.misc.Unsafe.theUnsafe: available
    10:42:42.764 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - sun.misc.Unsafe.copyMemory: available
    10:42:42.772 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - java.nio.Buffer.address: available
    10:42:42.783 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - direct buffer constructor: available
    10:42:42.786 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - java.nio.Bits.unaligned: available, true
    10:42:42.787 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - jdk.internal.misc.Unsafe.allocateUninitializedArray(int): unavailable prior to Java9
    10:42:42.787 [Test worker] DEBUG io.netty.util.internal.PlatformDependent0 - java.nio.DirectByteBuffer.<init>(long, int): available
    10:42:42.787 [Test worker] DEBUG io.netty.util.internal.PlatformDependent - sun.misc.Unsafe: available
    10:42:42.788 [Test worker] DEBUG io.netty.util.internal.PlatformDependent - -Dio.netty.tmpdir: /tmp (java.io.tmpdir)
    10:42:42.788 [Test worker] DEBUG io.netty.util.internal.PlatformDependent - -Dio.netty.bitMode: 64 (sun.arch.data.model)
    10:42:42.797 [Test worker] DEBUG io.netty.util.internal.PlatformDependent - -Dio.netty.noPreferDirect: false
    10:42:42.797 [Test worker] DEBUG io.netty.util.internal.PlatformDependent - -Dio.netty.maxDirectMemory: 2276458496 bytes
    10:42:42.797 [Test worker] DEBUG io.netty.util.internal.PlatformDependent - -Dio.netty.uninitializedArrayAllocationThreshold: -1
    10:42:42.800 [Test worker] DEBUG io.netty.util.internal.CleanerJava6 - java.nio.ByteBuffer.cleaner(): available
    10:42:42.851 [Test worker] DEBUG io.netty.util.internal.PlatformDependent - org.jctools-core.MpscChunkedArrayQueue: available
    10:42:42.919 [Test worker] INFO ktor.application - No ktor.deployment.watch patterns specified, automatic reload is not active
    10:42:43.006 [Test worker] INFO ktor.application - Responding at http://0.0.0.0:8080
    10:42:43.068 [Test worker] DEBUG io.netty.channel.DefaultChannelId - -Dio.netty.processId: 28808 (auto-detected)
    10:42:43.093 [Test worker] DEBUG io.netty.util.NetUtil - -Djava.net.preferIPv4Stack: false
    10:42:43.096 [Test worker] DEBUG io.netty.util.NetUtil - -Djava.net.preferIPv6Addresses: false
    10:42:43.103 [Test worker] DEBUG io.netty.util.NetUtil - Loopback interface: lo (lo, 0:0:0:0:0:0:0:1%lo)
    10:42:43.107 [Test worker] DEBUG io.netty.util.NetUtil - /proc/sys/net/core/somaxconn: 128
    10:42:43.109 [Test worker] DEBUG io.netty.channel.DefaultChannelId - -Dio.netty.machineId: 08:00:27:ff:fe:6e:7c:21 (auto-detected)
    10:42:43.127 [Test worker] DEBUG io.netty.util.internal.InternalThreadLocalMap - -Dio.netty.threadLocalMap.stringBuilder.initialSize: 1024
    10:42:43.128 [Test worker] DEBUG io.netty.util.internal.InternalThreadLocalMap - -Dio.netty.threadLocalMap.stringBuilder.maxSize: 4096
    10:42:43.201 [Test worker] DEBUG io.netty.util.ResourceLeakDetector - -Dio.netty.leakDetection.level: simple
    10:42:43.202 [Test worker] DEBUG io.netty.util.ResourceLeakDetector - -Dio.netty.leakDetection.targetRecords: 4
    10:42:43.301 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.numHeapArenas: 8
    10:42:43.303 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.numDirectArenas: 8
    10:42:43.305 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.pageSize: 8192
    10:42:43.313 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.maxOrder: 11
    10:42:43.318 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.chunkSize: 16777216
    10:42:43.321 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.tinyCacheSize: 512
    10:42:43.323 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.smallCacheSize: 256
    10:42:43.324 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.normalCacheSize: 64
    10:42:43.325 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.maxCachedBufferCapacity: 32768
    10:42:43.327 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.cacheTrimInterval: 8192
    10:42:43.329 [Test worker] DEBUG io.netty.buffer.PooledByteBufAllocator - -Dio.netty.allocator.useCacheForAllThreads: true
    10:42:43.377 [Test worker] DEBUG io.netty.buffer.ByteBufUtil - -Dio.netty.allocator.type: pooled
    10:42:43.381 [Test worker] DEBUG io.netty.buffer.ByteBufUtil - -Dio.netty.threadLocalDirectBufferSize: 0
    10:42:43.386 [Test worker] DEBUG io.netty.buffer.ByteBufUtil - -Dio.netty.maxThreadLocalCharBufferSize: 16384
<============-> 92% EXECUTING [1m 21s]
> :test > 8 tests completed
> :test > Executing test comfortable.data.server.ServerTest

Most helpful comment

The tests start that Application.main method when you call testApp in your test. server.start never response, so that never finishes.

I had the same issue, and the same workaround. In order to get it working you need a new main file, which looks something like this:

import io.ktor.server.engine.commandLineEnvironment
import io.ktor.server.engine.embeddedServer
import io.ktor.server.netty.Netty

fun main(args: Array<String>) {
    embeddedServer(Netty, commandLineEnvironment(args)).start()
}

This is, in my estimation, a documentation bug more than anything

All 6 comments

When I change the Application to this ... the tests work fine but then I fail on running the server in normal mode

fun Application.main() {
    routing {
        get("/books") {
            val json = this::class.java.getResource("/books.json").readText()
            call.respondText(json, ContentType.Application.Json)
        }
    }
}

My application.conf look like following

ktor {
    deployment {
        port = 8080
    }

    application {
        main = [ io.ktor.server.netty.EngineMain ]
    }
}

In the build.gradle

jar {
    manifest {
        attributes(
            'Main-Class': 'io.ktor.server.netty.EngineMain',
...

Running the jar I get an empty HTML page only ...

The tests start that Application.main method when you call testApp in your test. server.start never response, so that never finishes.

I had the same issue, and the same workaround. In order to get it working you need a new main file, which looks something like this:

import io.ktor.server.engine.commandLineEnvironment
import io.ktor.server.engine.embeddedServer
import io.ktor.server.netty.Netty

fun main(args: Array<String>) {
    embeddedServer(Netty, commandLineEnvironment(args)).start()
}

This is, in my estimation, a documentation bug more than anything

Thanks @wildunne I ran into this as well.

because at the beginning everything is difficult and usually people who run into this issue are just starting their adventure with ktor and maybe kotlin too, i've put @wildunne and @Nachtfeuer 's code together

Main.kt:

fun main(args: Array<String>) {
    embeddedServer(Netty, commandLineEnvironment(args)).start()
}

Application.kt:

fun Application.module() {
    routing {
        get("/test") {
            call.respondText("Hello login!!!", ContentType.Text.Plain)
        }
    }
}

ApplicationTest:

class ApplicationTest {
    @Test
    fun testRequestsOK() = withTestApplication(Application::module) {
        with(handleRequest(HttpMethod.Get, "/test")) {
            assertEquals(HttpStatusCode.OK, response.status())
            assertEquals("Hello login!!!", response.content)
        }
    }
}

Please check the following ticket on YouTrack for follow-ups to this issue. GitHub issues will be closed in the coming weeks.

Resloved. Closed

Was this page helpful?
0 / 5 - 0 ratings