Skip to content

Commit 4b0ba58

Browse files
authored
Add BSONReader.collect combinator (#424)
1 parent d37704e commit 4b0ba58

File tree

2 files changed

+47
-7
lines changed

2 files changed

+47
-7
lines changed

api/src/main/scala/BSONReader.scala

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,22 @@ trait BSONReader[T] { self =>
7474
def afterRead[U](f: T => U): BSONReader[U] =
7575
new BSONReader.MappedReader[T, U](self, f)
7676

77+
/**
78+
* '''EXPERIMENTAL:''' (API may change without notice)
79+
*/
80+
def collect[U](read: PartialFunction[T, U]): BSONReader[U] =
81+
BSONReader.from[U] { bson =>
82+
self.readTry(bson).flatMap { v =>
83+
read.lift(v) match {
84+
case Some(result) =>
85+
Success(result)
86+
87+
case None =>
88+
Failure(exceptions.ValueDoesNotMatchException(s"${v}"))
89+
}
90+
}
91+
}
92+
7793
/**
7894
* $beforeReadDescription
7995
*
@@ -250,7 +266,7 @@ object BSONReader extends BSONReaderCompat with BSONReaderInstances {
250266
iterable[T, Seq](read)
251267

252268
/**
253-
* '''EXPERIMENTAL:''' Creates a [[BSONDocumentReader]] that reads
269+
* '''EXPERIMENTAL:''' Creates a [[BSONReader]] that reads
254270
* the [[BSONArray]] elements.
255271
*
256272
* {{{
@@ -276,7 +292,7 @@ object BSONReader extends BSONReaderCompat with BSONReaderInstances {
276292
}
277293

278294
/**
279-
* '''EXPERIMENTAL:''' Creates a [[BSONDocumentReader]] that reads
295+
* '''EXPERIMENTAL:''' Creates a [[BSONReader]] that reads
280296
* the [[BSONArray]] elements.
281297
*
282298
* @see [[tuple2]]
@@ -295,7 +311,7 @@ object BSONReader extends BSONReaderCompat with BSONReaderInstances {
295311
}
296312

297313
/**
298-
* '''EXPERIMENTAL:''' Creates a [[BSONDocumentReader]] that reads
314+
* '''EXPERIMENTAL:''' Creates a [[BSONReader]] that reads
299315
* the [[BSONArray]] elements.
300316
*
301317
* @see [[tuple2]]
@@ -319,7 +335,7 @@ object BSONReader extends BSONReaderCompat with BSONReaderInstances {
319335
}
320336

321337
/**
322-
* '''EXPERIMENTAL:''' Creates a [[BSONDocumentReader]] that reads
338+
* '''EXPERIMENTAL:''' Creates a [[BSONReader]] that reads
323339
* the [[BSONArray]] elements.
324340
*
325341
* @see [[tuple2]]

api/src/test/scala/HandlerSpec.scala

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -243,11 +243,33 @@ final class HandlerSpec
243243
}
244244
}
245245

246-
"Complex Array" should {
246+
"Complex array" should {
247247
"be of size = 6" in {
248248
array.size must_=== 6
249249
}
250250

251+
"be collect'ed" in {
252+
val reader =
253+
implicitly[BSONReader[Seq[BSONValue]]].collect[::[BSONValue]] {
254+
case head :: tail => ::(head, tail)
255+
}
256+
257+
reader.readTry(array) must beSuccessfulTry(
258+
::(
259+
BSONString("elem0"),
260+
List(
261+
BSONInteger(1),
262+
BSONDouble(2.222),
263+
BSONDocument("name" -> "Joe"),
264+
BSONArray(0L),
265+
BSONString("pp[4]")
266+
)
267+
)
268+
) and {
269+
reader.readTry(BSONArray.empty) must beFailedTry[Seq[BSONValue]]
270+
}
271+
}
272+
251273
"have a an int = 2 at index 2" in {
252274
array.get(1) must beSome(BSONInteger(1)) and (array.getAsOpt[Int](
253275
1
@@ -399,8 +421,10 @@ final class HandlerSpec
399421
"fails from array" in {
400422
BSONDocument("foo" -> BSONArray.empty).getAsTry[BSONDocument](
401423
"foo"
402-
) must_=== Failure(TypeDoesNotMatchException("BSONDocument", "[]"))
403-
}
424+
) must_=== Failure(
425+
TypeDoesNotMatchException("BSONDocument", "Array ([])")
426+
)
427+
} tag "wip"
404428
}
405429

406430
"BSONDateTime" should {

0 commit comments

Comments
 (0)