Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
io.iteratee.files.package.scala Maven / Gradle / Ivy
package io.iteratee
import cats.effect.Sync
import io.iteratee.internal.Step
import java.io.{
BufferedInputStream,
BufferedOutputStream,
BufferedReader,
BufferedWriter,
File,
FileInputStream,
FileOutputStream,
FileReader,
FileWriter,
InputStream,
InputStreamReader,
OutputStream,
OutputStreamWriter
}
import java.util.zip.{ ZipEntry, ZipFile }
import scala.Predef.genericArrayOps
import scala.collection.JavaConverters._
package object files {
def readLines[F[_]](file: File)(implicit F: Sync[F]): Enumerator[F, String] =
enumerateLines(new BufferedReader(new FileReader(file)))
def readLinesFromStream[F[_]](stream: InputStream)(implicit F: Sync[F]): Enumerator[F, String] =
enumerateLines(new BufferedReader(new InputStreamReader(stream)))
def readBytes[F[_]](file: File)(implicit F: Sync[F]): Enumerator[F, Array[Byte]] =
enumerateBytes(new BufferedInputStream(new FileInputStream(file)))
def readBytesFromStream[F[_]](stream: InputStream)(implicit F: Sync[F]): Enumerator[F, Array[Byte]] =
enumerateBytes(new BufferedInputStream(stream))
def readZipStreams[F[_]](file: File)(implicit F: Sync[F]): Enumerator[F, (ZipEntry, InputStream)] =
Enumerator.liftM(F.delay(new ZipFile(file))).flatMap { zipFile =>
new ZipFileEnumerator(zipFile, zipFile.entries.asScala).ensure(F.delay(zipFile.close()))
}
def listFiles[F[_]](dir: File)(implicit F: Sync[F]): Enumerator[F, File] =
Enumerator.liftM(F.delay(dir.listFiles)).flatMap {
case null => Enumerator.empty[F, File]
case files => Enumerator.enumVector(Vector(files: _*))
}
def listFilesRec[F[_]](dir: File)(implicit F: Sync[F]): Enumerator[F, File] = listFiles[F](dir).flatMap {
case item if item.isDirectory => listFilesRec(item)
case item => Enumerator.enumOne(item)
}
def writeLines[F[_]](file: File)(implicit F: Sync[F]): Iteratee[F, String, Unit] =
Iteratee.liftM(F.delay(new BufferedWriter(new FileWriter(file)))).flatMap { writer =>
Iteratee
.foldM[F, String, Unit](())(
(_, line) =>
F.delay {
writer.write(line)
writer.newLine()
}
)
.ensure(F.delay(writer.close()))
}
def writeLinesToStream[F[_]](stream: OutputStream)(implicit F: Sync[F]): Iteratee[F, String, Unit] =
Iteratee.liftM(F.delay(new BufferedWriter(new OutputStreamWriter(stream)))).flatMap { writer =>
Iteratee
.foldM[F, String, Unit](())(
(_, line) =>
F.delay {
writer.write(line)
writer.newLine()
}
)
.ensure(F.delay(writer.close()))
}
def writeBytes[F[_]](file: File)(implicit F: Sync[F]): Iteratee[F, Array[Byte], Unit] =
Iteratee.liftM(F.delay(new BufferedOutputStream(new FileOutputStream(file)))).flatMap { stream =>
Iteratee
.foldM[F, Array[Byte], Unit](())((_, bytes) => F.delay(stream.write(bytes)))
.ensure(F.delay(stream.close()))
}
def writeBytesToStream[F[_]](stream: OutputStream)(implicit F: Sync[F]): Iteratee[F, Array[Byte], Unit] =
Iteratee.liftM(F.delay(new BufferedOutputStream(stream))).flatMap { stream =>
Iteratee
.foldM[F, Array[Byte], Unit](())((_, bytes) => F.delay(stream.write(bytes)))
.ensure(F.delay(stream.close()))
}
private[this] def enumerateLines[F[_]](reader: => BufferedReader)(implicit F: Sync[F]): Enumerator[F, String] =
Enumerator.liftM(F.delay(reader)).flatMap(reader => new LineEnumerator(reader).ensure(F.delay(reader.close())))
private[this] def enumerateBytes[F[_]](stream: => InputStream)(implicit F: Sync[F]): Enumerator[F, Array[Byte]] =
Enumerator.liftM(F.delay(stream)).flatMap(reader => new ByteEnumerator(stream).ensure(F.delay(stream.close())))
private[this] final class LineEnumerator[F[_]](reader: BufferedReader)(implicit F: Sync[F])
extends Enumerator[F, String] {
final def apply[A](s: Step[F, String, A]): F[Step[F, String, A]] =
if (s.isDone) F.pure(s)
else
F.flatMap(F.delay(reader.readLine())) {
case null => F.pure(s)
case line => F.flatMap(s.feedEl(line))(apply)
}
}
private[this] final class ByteEnumerator[F[_]](stream: InputStream, bufferSize: Int = 8192)(implicit F: Sync[F])
extends Enumerator[F, Array[Byte]] {
final def apply[A](s: Step[F, Array[Byte], A]): F[Step[F, Array[Byte], A]] =
if (s.isDone) F.pure(s)
else
F.flatten(
F.delay {
val array = new Array[Byte](bufferSize)
val bytesRead = stream.read(array, 0, bufferSize)
val read = if (bytesRead == bufferSize) array else array.slice(0, bytesRead)
if (bytesRead == -1) F.pure(s) else F.flatMap(s.feedEl(read))(apply(_))
}
)
}
private[this] final class ZipFileEnumerator[F[_]](zipFile: ZipFile, iterator: Iterator[ZipEntry])(implicit F: Sync[F])
extends Enumerator[F, (ZipEntry, InputStream)] {
final def apply[A](s: Step[F, (ZipEntry, InputStream), A]): F[Step[F, (ZipEntry, InputStream), A]] =
if (s.isDone) F.pure(s)
else
F.flatten(
F.delay(
if (iterator.hasNext) {
val entry = iterator.next
F.flatMap(s.feedEl((entry, zipFile.getInputStream(entry))))(apply)
} else F.pure(s)
)
)
}
}