Skip to content

Commit

Permalink
Fix charset decoder crash when converting ByteReadChannel to `CharI…
Browse files Browse the repository at this point in the history
…terator`
  • Loading branch information
msasikanth committed Jun 4, 2024
1 parent f4256b6 commit 47b2fa5
Show file tree
Hide file tree
Showing 3 changed files with 7 additions and 16 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,6 @@ import io.ktor.http.HttpStatusCode
import io.ktor.http.URLBuilder
import io.ktor.http.URLProtocol
import io.ktor.http.Url
import io.ktor.http.charset
import io.ktor.http.contentType
import me.tatarka.inject.annotations.Inject

Expand Down Expand Up @@ -98,8 +97,7 @@ class FeedFetcher(private val httpClient: HttpClient, private val feedParser: Fe
}
} else {
val content = response.bodyAsChannel()
val feedPayload =
feedParser.parse(content = content, charset = response.charset(), feedUrl = url)
val feedPayload = feedParser.parse(content = content, feedUrl = url)

FeedFetchResult.Success(feedPayload)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,14 +24,13 @@ import io.ktor.http.URLBuilder
import io.ktor.http.URLProtocol
import io.ktor.http.set
import io.ktor.utils.io.ByteReadChannel
import io.ktor.utils.io.charsets.Charset
import io.ktor.utils.io.charsets.Charsets
import io.ktor.utils.io.charsets.decode
import io.ktor.utils.io.core.readBytes
import kotlin.coroutines.CoroutineContext
import kotlin.coroutines.EmptyCoroutineContext
import kotlinx.coroutines.runBlocking
import kotlinx.coroutines.withContext
import me.tatarka.inject.annotations.Inject
import okio.internal.commonToUtf8String
import org.kobjects.ktxml.api.XmlPullParserException
import org.kobjects.ktxml.mini.MiniXmlPullParser

Expand All @@ -42,12 +41,10 @@ class FeedParser(private val dispatchersProvider: DispatchersProvider) {
suspend fun parse(
content: ByteReadChannel,
feedUrl: String,
charset: Charset?,
): FeedPayload {
return try {
withContext(dispatchersProvider.io) {
val parser =
MiniXmlPullParser(source = content.toCharIterator(charset = charset ?: Charsets.UTF_8))
val parser = MiniXmlPullParser(source = content.toCharIterator())

parser.nextTag()

Expand Down Expand Up @@ -142,7 +139,6 @@ class FeedParser(private val dispatchersProvider: DispatchersProvider) {
}

private fun ByteReadChannel.toCharIterator(
charset: Charset,
context: CoroutineContext = EmptyCoroutineContext
): CharIterator {
return object : CharIterator() {
Expand All @@ -157,9 +153,7 @@ private fun ByteReadChannel.toCharIterator(
if (this@toCharIterator.isClosedForRead) return false

val packet = runBlocking(context) { this@toCharIterator.readRemaining(DEFAULT_BUFFER_SIZE) }
val decoder = charset.newDecoder()

currentBuffer = decoder.decode(packet).toCharArray()
currentBuffer = packet.readBytes().commonToUtf8String().toCharArray()
packet.release()
currentIndex = 0
return currentBuffer.isNotEmpty()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,6 @@ import dev.sasikanth.rss.reader.core.model.remote.FeedPayload
import dev.sasikanth.rss.reader.core.model.remote.PostPayload
import dev.sasikanth.rss.reader.core.network.parser.FeedParser
import io.ktor.utils.io.ByteReadChannel
import io.ktor.utils.io.charsets.Charsets
import io.ktor.utils.io.core.toByteArray
import kotlin.test.Test
import kotlin.test.assertEquals
Expand Down Expand Up @@ -114,7 +113,7 @@ class FeedParserTest {

// when
val content = ByteReadChannel(rssXmlContent.toByteArray())
val payload = feedParser.parse(content, feedUrl, Charsets.UTF_8)
val payload = feedParser.parse(content, feedUrl)

// then
assertEquals(expectedFeedPayload, payload)
Expand Down Expand Up @@ -191,7 +190,7 @@ class FeedParserTest {

// when
val content = ByteReadChannel(atomXmlContent.toByteArray())
val payload = feedParser.parse(content, feedUrl, Charsets.UTF_8)
val payload = feedParser.parse(content, feedUrl)

// then
assertEquals(expectedFeedPayload, payload)
Expand Down

0 comments on commit 47b2fa5

Please sign in to comment.