Skip to content

Commit

Permalink
ZIO 2: Update ZIO to 2.0 final (#641)
Browse files Browse the repository at this point in the history
ZIO 2 final support.
Temporaily disabled publishing of zio-json-golden.
  • Loading branch information
fsvehla authored Jun 26, 2022
1 parent 9d47559 commit e513f15
Show file tree
Hide file tree
Showing 5 changed files with 176 additions and 160 deletions.
23 changes: 11 additions & 12 deletions build.sbt
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ addCommandAlias("prepare", "fmt")

addCommandAlias(
"testJVM",
"zioJsonJVM/test; zioJsonYaml/test; zioJsonGolden/test; zioJsonMacrosJVM/test; zioJsonInteropHttp4s/test; zioJsonInteropScalaz7xJVM/test; zioJsonInteropScalaz7xJS/test; zioJsonInteropRefinedJVM/test; zioJsonInteropRefinedJS/test"
"zioJsonJVM/test; zioJsonYaml/test; zioJsonMacrosJVM/test; zioJsonInteropHttp4s/test; zioJsonInteropScalaz7xJVM/test; zioJsonInteropScalaz7xJS/test; zioJsonInteropRefinedJVM/test; zioJsonInteropRefinedJS/test"
)

addCommandAlias(
Expand All @@ -35,7 +35,7 @@ addCommandAlias(

addCommandAlias("testJS", "zioJsonJS/test")

val zioVersion = "2.0.0-RC6"
val zioVersion = "2.0.0"

lazy val root = project
.in(file("."))
Expand All @@ -48,7 +48,6 @@ lazy val root = project
zioJsonJVM,
zioJsonJS,
zioJsonYaml,
zioJsonGolden,
zioJsonMacrosJVM,
zioJsonMacrosJS,
zioJsonInteropHttp4s,
Expand Down Expand Up @@ -227,12 +226,12 @@ lazy val zioJsonGolden = project
.settings(buildInfoSettings("zio.json.golden"))
.settings(
libraryDependencies ++= Seq(
"dev.zio" %% "zio" % zioVersion,
"dev.zio" %% "zio-nio" % "2.0.0-RC7",
"dev.zio" %% "zio-test" % zioVersion,
"dev.zio" %% "zio-test-sbt" % zioVersion,
"dev.zio" %% "zio-test-magnolia" % zioVersion,
"org.scala-lang" % "scala-reflect" % scalaVersion.value % Provided,
"dev.zio" %% "zio" % zioVersion,
"dev.zio" %% "zio-nio" % "2.0.0",
"dev.zio" %% "zio-test" % zioVersion,
"dev.zio" %% "zio-test-sbt" % zioVersion,
"dev.zio" %% "zio-test-magnolia" % zioVersion,
"org.scala-lang" % "scala-reflect" % scalaVersion.value % Provided
),
testFrameworks += new TestFramework("zio.test.sbt.ZTestFramework")
)
Expand Down Expand Up @@ -287,9 +286,9 @@ lazy val zioJsonInteropHttp4s = project
"org.http4s" %% "http4s-dsl" % "0.23.7",
"dev.zio" %% "zio" % zioVersion,
"org.typelevel" %% "cats-effect" % "3.3.0",
"dev.zio" %% "zio-interop-cats" % "3.3.0-RC7" % "test",
"dev.zio" %% "zio-test" % zioVersion % "test",
"dev.zio" %% "zio-test-sbt" % zioVersion % "test"
"dev.zio" %% "zio-interop-cats" % "3.3.0" % "test",
"dev.zio" %% "zio-test" % zioVersion % "test",
"dev.zio" %% "zio-test-sbt" % zioVersion % "test"
),
testFrameworks += new TestFramework("zio.test.sbt.ZTestFramework")
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@ import zio.json.interop.scalaz7x._
import zio.test.Assertion._
import zio.test._

object ScalaSpec extends ZIOSpecDefault {
val spec: Spec[Environment, Any] =
object ScalazSpec extends ZIOSpecDefault {
def spec =
suite("Scalaz")(
test("scalaz.IList[A]") {
assert(IList[Int]().toJson)(equalTo("[]")) &&
Expand Down
8 changes: 6 additions & 2 deletions zio-json/jvm/src/jmh/scala/zio/json/UUIDBenchmarks.scala
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package zio.json

import org.openjdk.jmh.annotations._
import zio.Chunk
import zio.{ Chunk, Unsafe }
import zio.json.uuid.UUIDParser
import zio.test.Gen

Expand Down Expand Up @@ -29,7 +29,11 @@ class UUIDBenchmarks {
s5 <- section5
} yield s"$s1-$s2-$s3-$s4-$s5"

unparsedUUIDChunk = zio.Runtime.default.unsafeRun(gen.runCollectN(10000).map(Chunk.fromIterable))
unparsedUUIDChunk = {
Unsafe.unsafeCompat { implicit u =>
zio.Runtime.default.unsafe.run(gen.runCollectN(10000).map(Chunk.fromIterable)).getOrThrow()
}
}
}

@Benchmark
Expand Down
215 changes: 112 additions & 103 deletions zio-json/jvm/src/main/scala/zio/json/JsonDecoderPlatformSpecific.scala
Original file line number Diff line number Diff line change
Expand Up @@ -53,118 +53,127 @@ trait JsonDecoderPlatformSpecific[A] { self: JsonDecoder[A] =>

final def decodeJsonPipeline(
delimiter: JsonStreamDelimiter = JsonStreamDelimiter.Array
): ZPipeline[Any, Throwable, Char, A] =
ZPipeline.fromPush {
for {
// format: off
runtime <- ZIO.runtime[Any]
inQueue <- Queue.unbounded[Take[Nothing, Char]]
outQueue <- Queue.unbounded[Take[Throwable, A]]
ended <- Ref.make(false)
reader <- ZIO.fromAutoCloseable {
ZIO.succeed {
def readPull: Iterator[Chunk[Char]] =
runtime.unsafeRun(inQueue.take)
.fold(
end = Iterator.empty,
error = _ => Iterator.empty, // impossible
value = v => Iterator.single(v) ++ readPull
)

new zio.stream.internal.ZReader(Iterator.empty ++ readPull)
}
}
jsonReader <- ZIO.fromAutoCloseable(ZIO.succeed(new WithRetractReader(reader)))
process <- ZIO.attemptBlockingInterrupt {
// Exceptions fall through and are pushed into the queue
@tailrec def loop(atBeginning: Boolean): Unit = {
val nextElem = try {
if (atBeginning && delimiter == JsonStreamDelimiter.Array) {
Lexer.char(Nil, jsonReader, '[')

jsonReader.nextNonWhitespace() match {
case ']' =>
// returning empty here instead of falling through, which would
// attempt to decode a value that we know doesn’t exist.
return ()

case _ =>
jsonReader.retract()
}
} else {
delimiter match {
case JsonStreamDelimiter.Newline =>
jsonReader.readChar() match {
case '\r' =>
jsonReader.readChar() match {
case '\n' => ()
case _ => jsonReader.retract()
}
case '\n' => ()
case _ => jsonReader.retract()
}

case JsonStreamDelimiter.Array =>
jsonReader.nextNonWhitespace() match {
case ',' | ']' => ()
case _ => jsonReader.retract()
}
}
): ZPipeline[Any, Throwable, Char, A] = {
Unsafe.unsafeCompat { (u: Unsafe) =>
implicit val unsafe: Unsafe = u

ZPipeline.fromPush {
for {
// format: off
runtime <- ZIO.runtime[Any]
inQueue <- Queue.unbounded[Take[Nothing, Char]]
outQueue <- Queue.unbounded[Take[Throwable, A]]
ended <- Ref.make(false)
reader <- ZIO.fromAutoCloseable {
ZIO.succeed {
def readPull: Iterator[Chunk[Char]] =
runtime.unsafe.run(inQueue.take).getOrThrow()
.fold(
end = Iterator.empty,
error = _ => Iterator.empty, // impossible
value = v => Iterator.single(v) ++ readPull
)

new zio.stream.internal.ZReader(Iterator.empty ++ readPull)
}
}
jsonReader <- ZIO.fromAutoCloseable(ZIO.succeed(new WithRetractReader(reader)))
process <- ZIO.attemptBlockingInterrupt {
// Exceptions fall through and are pushed into the queue
@tailrec def loop(atBeginning: Boolean): Unit = {
val nextElem = try {
if (atBeginning && delimiter == JsonStreamDelimiter.Array) {
Lexer.char(Nil, jsonReader, '[')

jsonReader.nextNonWhitespace() match {
case ']' =>
// returning empty here instead of falling through, which would
// attempt to decode a value that we know doesn’t exist.
return ()

case _ =>
jsonReader.retract()
}
} else {
delimiter match {
case JsonStreamDelimiter.Newline =>
jsonReader.readChar() match {
case '\r' =>
jsonReader.readChar() match {
case '\n' => ()
case _ => jsonReader.retract()
}
case '\n' => ()
case _ => jsonReader.retract()
}

unsafeDecode(Nil, jsonReader)
} catch {
case t @ JsonDecoder.UnsafeJson(trace) =>
throw new Exception(JsonError.render(trace))
}

runtime.unsafeRun(outQueue.offer(Take.single(nextElem)))

loop(false)
case JsonStreamDelimiter.Array =>
jsonReader.nextNonWhitespace() match {
case ',' | ']' => ()
case _ => jsonReader.retract()
}
}
}

loop(true)
}
.catchAll {
case t: zio.json.internal.UnexpectedEnd =>
// swallow if stream ended
ZIO.unlessZIO(ended.get) {
outQueue.offer(Take.fail(t))
}

case t: Throwable =>
outQueue.offer(Take.fail(t))
}
.interruptible
.forkScoped
push = { (is: Option[Chunk[Char]]) =>
val pollElements: IO[Throwable, Chunk[A]] =
outQueue
.takeUpTo(ZStream.DefaultChunkSize)
.flatMap { takes =>
ZIO.foldLeft(takes)(Chunk[A]()) { case (acc, take) =>
take.fold(ZIO.succeedNow(acc), e => ZIO.fail(e.squash), c => ZIO.succeedNow(acc ++ c))
unsafeDecode(Nil, jsonReader)
} catch {
case t @ JsonDecoder.UnsafeJson(trace) =>
throw new Exception(JsonError.render(trace))
}
}

val pullRest =
outQueue
.takeAll
.flatMap { takes =>
ZIO.foldLeft(takes)(Chunk[A]()) { case (acc, take) =>
take.fold(ZIO.succeedNow(acc), e => ZIO.fail(e.squash), c => ZIO.succeedNow(acc ++ c))
Unsafe.unsafeCompat { (u: Unsafe) =>
implicit val unsafe: Unsafe = u

runtime.unsafe.run(outQueue.offer(Take.single(nextElem))).getOrThrow()
}
}

is match {
case Some(c) =>
inQueue.offer(Take.chunk(c)) *> pollElements
loop(false)
}

case None =>
ended.set(true) *> inQueue.offer(Take.end) *> process.join *> pullRest
}
loop(true)
}
.catchAll {
case t: zio.json.internal.UnexpectedEnd =>
// swallow if stream ended
ZIO.unlessZIO(ended.get) {
outQueue.offer(Take.fail(t))
}

case t: Throwable =>
outQueue.offer(Take.fail(t))
}
.interruptible
.forkScoped
push = { (is: Option[Chunk[Char]]) =>
val pollElements: IO[Throwable, Chunk[A]] =
outQueue
.takeUpTo(ZStream.DefaultChunkSize)
.flatMap { takes =>
ZIO.foldLeft(takes)(Chunk[A]()) { case (acc, take) =>
take.fold(ZIO.succeedNow(acc), e => ZIO.fail(e.squash), c => ZIO.succeedNow(acc ++ c))
}
}

val pullRest =
outQueue
.takeAll
.flatMap { takes =>
ZIO.foldLeft(takes)(Chunk[A]()) { case (acc, take) =>
take.fold(ZIO.succeedNow(acc), e => ZIO.fail(e.squash), c => ZIO.succeedNow(acc ++ c))
}
}

is match {
case Some(c) =>
inQueue.offer(Take.chunk(c)) *> pollElements

case None =>
ended.set(true) *> inQueue.offer(Take.end) *> process.join *> pullRest
}
}
} yield push
// format: on
}
} yield push
// format: on
}
}
}
Loading

0 comments on commit e513f15

Please sign in to comment.