Skip to content

Commit

Permalink
Apply workaround to hanging compression (ktorio#708, ktorio#685)
Browse files Browse the repository at this point in the history
  • Loading branch information
Sergey Mashkov authored and Thorsten Schleinzer committed Feb 26, 2019
1 parent 311cc08 commit 2b6ac57
Show file tree
Hide file tree
Showing 3 changed files with 45 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,13 @@ class DispatcherWithShutdown(delegate: CoroutineDispatcher) : CoroutineDispatche
if (shutdownPool.isInitialized()) shutdownPool.value.shutdown()
}

override fun isDispatchNeeded(context: CoroutineContext): Boolean {
return when (shutdownPhase) {
ShutdownPhase.None -> delegate?.isDispatchNeeded(context) ?: true
else -> true
}
}

override fun dispatch(context: CoroutineContext, block: Runnable) {
when (shutdownPhase) {
ShutdownPhase.None -> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -152,7 +152,9 @@ abstract class BaseApplicationResponse(override val call: ApplicationCall) : App
// Call user code to send data
// val before = totalBytesWritten
try {
content.writeTo(this)
withContext(Dispatchers.IO) {
content.writeTo(this@use)
}
} catch (closed: ClosedWriteChannelException) {
throw ChannelWriteException(exception = closed)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1714,6 +1714,41 @@ abstract class EngineTestSuite<TEngine : ApplicationEngine, TConfiguration : App
}
}

@Test
fun testCompressionWriteToLarge() {
val count = 655350
fun Appendable.produceText() {
for (i in 1..count) {
append("test $i\n".padStart(10, ' '))
}
}

createAndStartServer {
application.install(Compression)

get("/") {
call.respondTextWriter(contentType = ContentType.Text.Plain) {
produceText()
}
}
}

withUrl("/", {
headers.append(HttpHeaders.AcceptEncoding, "gzip")
}) {
// ensure the server is running
val expected = buildString {
produceText()
}
call.receive<HttpResponse>().use { response ->
assertTrue { HttpHeaders.ContentEncoding in response.headers }
val array = response.receive<ByteArray>()
val text = GZIPInputStream(ByteArrayInputStream(array)).readBytes().toString(Charsets.UTF_8)
assertEquals(expected, text)
}
}
}

private fun String.urlPath() = replace("\\", "/")
private class ExpectedException(message: String) : RuntimeException(message)

Expand Down

0 comments on commit 2b6ac57

Please sign in to comment.