Kotlin中的多平台InputStream替代方案?

时间:2018-10-26 18:23:27

标签: kotlin inputstream kotlin-multiplatform

我正在寻找输入流的多平台替代方案。我的具体任务是通过https从远程服务器获取加密文件,并按需对其解密。

在Java领域中,我将实现一个InputStream实施器,该代理将读取操作从https库代理到输入流。如何在针对多个平台的kotlin中做同样的事情。

我看到ktor返回了ByteReadChannel,但是我不知道哪个函数。

我迷路了,不知道从哪里开始。感谢您的帮助。

1 个答案:

答案 0 :(得分:1)

如果您使用的框架没有为您提供完整的InputStream实现,那么剩下的唯一机会就是编写自己的框架。就像ktor开发人员所做的一样:ByteReadChannel只是“从通道读取字节”的抽象。 这种抽象存在于公共部分,并允许围绕它编写应用程序和业务逻辑。

在Kotlin Multiplatform项目中进行此工作的关键是,需要在特定于平台的部分中提供实际的实现。 ktor项目的JVM特定代码实际上具有使用InputStreamInputStream.toByteReadChannel的实现。

您当然不必像ktor项目中的示例那样进行操作,并且可以对从字节通道到文件表示的所有内容进行建模。如果您想利用Kotlin框架类,Sequences可能会很方便。看起来可能像这样:

// in common
interface FileFetcher {
  fun fetch(): Sequence<Byte>
}

expect fun fileFetcher(source: String): FileFetcher

// in jvm
class JvmFileFetcher(val input: java.io.InputStream): FileFetcher {
  override fun fetch(): Sequence<Byte> = input.readBytes().asSequence()
}

actual fun fileFetcher(source: String): FileFetcher {
  val input = java.net.URL(source).openStream()
  return JvmFileFetcher(input)
}

您将在公共部分定义接口FileFetcher以及工厂功能fileFetcher。通过在expect函数上使用fileFetcher关键字,您需要为定义的所有目标平台提供特定于平台的实现。使用公共部分中的FileFetcher接口来实现您的逻辑(解密文件内容等)。有关如何使用它的信息,请参见Sequence的文档。

然后为所有平台实现工厂功能,并在它们上使用actual关键字。然后,您将需要编写FileFetcher的特定于平台的实现。我的示例显示了FileFetcher接口的JVM版本。

该示例当然是非常基础的,您可能不希望完全像这样进行(我想至少需要一些缓冲)。此外,在JVM部分,您还可以轻松利用自己喜欢的网络/ HTTP库。