diff options
author | Mathias <mathias@spray.cc> | 2012-02-03 15:52:43 +0100 |
---|---|---|
committer | Mathias <mathias@spray.cc> | 2012-02-03 15:52:43 +0100 |
commit | 25b428758a36145e85033fba059ce85aad224929 (patch) | |
tree | b0ea9205790f8f8148f4e655fd3569d24c7fc4fc /src/test/scala/cc/spray | |
parent | 3df2a713d9251d62efcbf12165c6b81460a02047 (diff) | |
parent | 129760aa1a75c62e6cd2088fa6ad37ff7ee35d68 (diff) | |
download | spray-json-25b428758a36145e85033fba059ce85aad224929.tar.gz spray-json-25b428758a36145e85033fba059ce85aad224929.tar.bz2 spray-json-25b428758a36145e85033fba059ce85aad224929.zip |
Merge branch 'release/1.1.0'v1.1.0
Diffstat (limited to 'src/test/scala/cc/spray')
10 files changed, 319 insertions, 76 deletions
diff --git a/src/test/scala/cc/spray/json/AdditionalFormatsSpec.scala b/src/test/scala/cc/spray/json/AdditionalFormatsSpec.scala index 7368128..f25c9d8 100644 --- a/src/test/scala/cc/spray/json/AdditionalFormatsSpec.scala +++ b/src/test/scala/cc/spray/json/AdditionalFormatsSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -10,8 +26,8 @@ class AdditionalFormatsSpec extends Specification { implicit def containerReader[T :JsonFormat] = lift { new JsonReader[Container[T]] { def read(value: JsValue) = value match { - case JsObject(JsField("content", obj: JsValue) :: Nil) => Container(Some(jsonReader[T].read(obj))) - case _ => throw new DeserializationException("Unexpected format: " + value.toString) + case JsObject(fields) if fields.contains("content") => Container(Some(jsonReader[T].read(fields("content")))) + case _ => deserializationError("Unexpected format: " + value.toString) } } } @@ -20,7 +36,7 @@ class AdditionalFormatsSpec extends Specification { object WriterProtocol extends DefaultJsonProtocol { implicit def containerWriter[T :JsonFormat] = lift { new JsonWriter[Container[T]] { - def write(obj: Container[T]) = JsObject(JsField("content", obj.inner.toJson)) + def write(obj: Container[T]) = JsObject("content" -> obj.inner.toJson) } } } @@ -35,7 +51,21 @@ class AdditionalFormatsSpec extends Specification { "properly read a Container[Container[List[Int]]] from JSON" in { import ReaderProtocol._ - JsonParser("""{"content":{"content":[1,2,3]}}""").fromJson[Container[Container[List[Int]]]] mustEqual obj + """{"content":{"content":[1,2,3]}}""".asJson.convertTo[Container[Container[List[Int]]]] mustEqual obj + } + } + + case class Foo(id: Long, name: String, foos: Option[List[Foo]] = None) + + object FooProtocol extends DefaultJsonProtocol { + implicit val FooProtocol: JsonFormat[Foo] = lazyFormat(jsonFormat(Foo, "id", "name", "foos")) + } + + "The lazyFormat wrapper" should { + "enable recursive format definitions" in { + import FooProtocol._ + Foo(1, "a", Some(Foo(2, "b", Some(Foo(3, "c") :: Nil)) :: Foo(4, "d") :: Nil)).toJson.toString mustEqual + """{"id":1,"name":"a","foos":[{"id":2,"name":"b","foos":[{"id":3,"name":"c"}]},{"id":4,"name":"d"}]}""" } } }
\ No newline at end of file diff --git a/src/test/scala/cc/spray/json/BasicFormatsSpec.scala b/src/test/scala/cc/spray/json/BasicFormatsSpec.scala index fcae4bb..f873948 100644 --- a/src/test/scala/cc/spray/json/BasicFormatsSpec.scala +++ b/src/test/scala/cc/spray/json/BasicFormatsSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -9,7 +25,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { 42.toJson mustEqual JsNumber(42) } "convert a JsNumber to an Int" in { - JsNumber(42).fromJson[Int] mustEqual 42 + JsNumber(42).convertTo[Int] mustEqual 42 } } @@ -18,7 +34,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { 42L.toJson mustEqual JsNumber(42L) } "convert a JsNumber to a Long" in { - JsNumber(42L).fromJson[Long] mustEqual 42L + JsNumber(42L).convertTo[Long] mustEqual 42L } } @@ -26,8 +42,20 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { "convert a Float to a JsNumber" in { 4.2f.toJson mustEqual JsNumber(4.2f) } + "convert a Float.NaN to a JsNull" in { + Float.NaN.toJson mustEqual JsNull + } + "convert a Float.PositiveInfinity to a JsNull" in { + Float.PositiveInfinity.toJson mustEqual JsNull + } + "convert a Float.NegativeInfinity to a JsNull" in { + Float.NegativeInfinity.toJson mustEqual JsNull + } "convert a JsNumber to a Float" in { - JsNumber(4.2f).fromJson[Float] mustEqual 4.2f + JsNumber(4.2f).convertTo[Float] mustEqual 4.2f + } + "convert a JsNull to a Float" in { + JsNull.convertTo[Float].isNaN mustEqual Float.NaN.isNaN } } @@ -35,8 +63,20 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { "convert a Double to a JsNumber" in { 4.2.toJson mustEqual JsNumber(4.2) } + "convert a Double.NaN to a JsNull" in { + Double.NaN.toJson mustEqual JsNull + } + "convert a Double.PositiveInfinity to a JsNull" in { + Double.PositiveInfinity.toJson mustEqual JsNull + } + "convert a Double.NegativeInfinity to a JsNull" in { + Double.NegativeInfinity.toJson mustEqual JsNull + } "convert a JsNumber to a Double" in { - JsNumber(4.2).fromJson[Double] mustEqual 4.2 + JsNumber(4.2).convertTo[Double] mustEqual 4.2 + } + "convert a JsNull to a Double" in { + JsNull.convertTo[Double].isNaN mustEqual Double.NaN.isNaN } } @@ -45,7 +85,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { 42.asInstanceOf[Byte].toJson mustEqual JsNumber(42) } "convert a JsNumber to a Byte" in { - JsNumber(42).fromJson[Byte] mustEqual 42 + JsNumber(42).convertTo[Byte] mustEqual 42 } } @@ -54,7 +94,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { 42.asInstanceOf[Short].toJson mustEqual JsNumber(42) } "convert a JsNumber to a Short" in { - JsNumber(42).fromJson[Short] mustEqual 42 + JsNumber(42).convertTo[Short] mustEqual 42 } } @@ -63,7 +103,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { BigDecimal(42).toJson mustEqual JsNumber(42) } "convert a JsNumber to a BigDecimal" in { - JsNumber(42).fromJson[BigDecimal] mustEqual BigDecimal(42) + JsNumber(42).convertTo[BigDecimal] mustEqual BigDecimal(42) } } @@ -72,7 +112,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { BigInt(42).toJson mustEqual JsNumber(42) } "convert a JsNumber to a BigInt" in { - JsNumber(42).fromJson[BigInt] mustEqual BigInt(42) + JsNumber(42).convertTo[BigInt] mustEqual BigInt(42) } } @@ -81,15 +121,15 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { ().toJson mustEqual JsNumber(1) } "convert a JsNumber to Unit" in { - JsNumber(1).fromJson[Unit] mustEqual () + JsNumber(1).convertTo[Unit] mustEqual () } } "The BooleanJsonFormat" should { "convert true to a JsTrue" in { true.toJson mustEqual JsTrue } "convert false to a JsFalse" in { false.toJson mustEqual JsFalse } - "convert a JsTrue to true" in { JsTrue.fromJson[Boolean] mustEqual true } - "convert a JsFalse to false" in { JsFalse.fromJson[Boolean] mustEqual false } + "convert a JsTrue to true" in { JsTrue.convertTo[Boolean] mustEqual true } + "convert a JsFalse to false" in { JsFalse.convertTo[Boolean] mustEqual false } } "The CharJsonFormat" should { @@ -97,7 +137,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { 'c'.toJson mustEqual JsString("c") } "convert a JsString to a Char" in { - JsString("c").fromJson[Char] mustEqual 'c' + JsString("c").convertTo[Char] mustEqual 'c' } } @@ -106,7 +146,7 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { "Hello".toJson mustEqual JsString("Hello") } "convert a JsString to a String" in { - JsString("Hello").fromJson[String] mustEqual "Hello" + JsString("Hello").convertTo[String] mustEqual "Hello" } } @@ -115,8 +155,8 @@ class BasicFormatsSpec extends Specification with DefaultJsonProtocol { 'Hello.toJson mustEqual JsString("Hello") } "convert a JsString to a Symbol" in { - JsString("Hello").fromJson[Symbol] mustEqual 'Hello + JsString("Hello").convertTo[Symbol] mustEqual 'Hello } } -}
\ No newline at end of file +} diff --git a/src/test/scala/cc/spray/json/CollectionFormatsSpec.scala b/src/test/scala/cc/spray/json/CollectionFormatsSpec.scala index d0cb509..a252b1f 100644 --- a/src/test/scala/cc/spray/json/CollectionFormatsSpec.scala +++ b/src/test/scala/cc/spray/json/CollectionFormatsSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -12,7 +28,7 @@ class CollectionFormatsSpec extends Specification with DefaultJsonProtocol { list.toJson mustEqual json } "convert a JsArray of JsNumbers to a List[Int]" in { - json.fromJson[List[Int]] mustEqual list + json.convertTo[List[Int]] mustEqual list } } @@ -23,18 +39,18 @@ class CollectionFormatsSpec extends Specification with DefaultJsonProtocol { array.toJson mustEqual json } "convert a JsArray of JsNumbers to an Array[Int]" in { - Arrays.equals(json.fromJson[Array[Int]], array) must beTrue + Arrays.equals(json.convertTo[Array[Int]], array) must beTrue } } "The mapFormat" should { val map = Map("a" -> 1, "b" -> 2, "c" -> 3) - val json = JsObject(JsField("a", 1), JsField("b", 2), JsField("c", 3)) + val json = JsObject("a" -> JsNumber(1), "b" -> JsNumber(2), "c" -> JsNumber(3)) "convert a Map[String, Long] to a JsObject" in { map.toJson mustEqual json } "be able to convert a JsObject to a Map[String, Long]" in { - json.fromJson[Map[String, Long]] mustEqual map + json.convertTo[Map[String, Long]] mustEqual map } "throw an Exception when trying to serialize a map whose key are not serialized to JsStrings" in { Map(1 -> "a").toJson must throwA(new SerializationException("Map key must be formatted as JsString, not '1'")) @@ -48,7 +64,7 @@ class CollectionFormatsSpec extends Specification with DefaultJsonProtocol { set.toJson mustEqual json } "convert a JsArray of JsNumbers to a Set[Int]" in { - json.fromJson[Set[Int]] mustEqual set + json.convertTo[Set[Int]] mustEqual set } } @@ -59,7 +75,7 @@ class CollectionFormatsSpec extends Specification with DefaultJsonProtocol { seq.toJson mustEqual json } "convert a JsArray of JsNumbers to a IndexedSeq[Int]" in { - json.fromJson[collection.IndexedSeq[Int]] mustEqual seq + json.convertTo[collection.IndexedSeq[Int]] mustEqual seq } } diff --git a/src/test/scala/cc/spray/json/CompactPrinterSpec.scala b/src/test/scala/cc/spray/json/CompactPrinterSpec.scala index 3bc4870..c441864 100644 --- a/src/test/scala/cc/spray/json/CompactPrinterSpec.scala +++ b/src/test/scala/cc/spray/json/CompactPrinterSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -36,11 +52,11 @@ class CompactPrinterSpec extends Specification { CompactPrinter(JsString("\"\\\b\f\n\r\t\u12AB")) mustEqual """"\"\\\b\f\n\r\t""" + "\\u12ab\"" } "properly print a simple JsObject" in ( - CompactPrinter(JsObject(JsField("key", 42), JsField("key2", "value"))) + CompactPrinter(JsObject("key" -> JsNumber(42), "key2" -> JsString("value"))) mustEqual """{"key":42,"key2":"value"}""" ) "properly print a simple JsArray" in ( - CompactPrinter(JsArray(JsNull, JsNumber(1.23), JsObject(JsField("key", true)))) + CompactPrinter(JsArray(JsNull, JsNumber(1.23), JsObject("key" -> JsBoolean(true)))) mustEqual """[null,1.23,{"key":true}]""" ) "properly print a JSON padding (JSONP) if requested" in { diff --git a/src/test/scala/cc/spray/json/CustomFormatSpec.scala b/src/test/scala/cc/spray/json/CustomFormatSpec.scala new file mode 100644 index 0000000..e8feb59 --- /dev/null +++ b/src/test/scala/cc/spray/json/CustomFormatSpec.scala @@ -0,0 +1,45 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package cc.spray.json + +import org.specs2.mutable.Specification + +class CustomFormatSpec extends Specification with DefaultJsonProtocol { + + case class MyType(name: String, value: Int) + + implicit val MyTypeProtocol = new RootJsonFormat[MyType] { + def read(json: JsValue) = { + json.asJsObject.getFields("name", "value") match { + case Seq(JsString(name), JsNumber(value)) => MyType(name, value.toInt) + case _ => deserializationError("Expected fields: 'name' (JSON string) and 'value' (JSON number)") + } + } + def write(obj: MyType) = JsObject("name" -> JsString(obj.name), "value" -> JsNumber(obj.value)) + } + + "A custom JsonFormat built with 'asJsonObject'" should { + val value = MyType("bob", 42) + "correctly deserialize valid JSON content" in { + """{ "name": "bob", "value": 42 }""".asJson.convertTo[MyType] mustEqual value + } + "support full round-trip (de)serialization" in { + value.toJson.convertTo[MyType] mustEqual value + } + } + +}
\ No newline at end of file diff --git a/src/test/scala/cc/spray/json/JsonParserSpec.scala b/src/test/scala/cc/spray/json/JsonParserSpec.scala index 0860d05..cfe270f 100644 --- a/src/test/scala/cc/spray/json/JsonParserSpec.scala +++ b/src/test/scala/cc/spray/json/JsonParserSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -35,16 +51,16 @@ class JsonParserSpec extends Specification { } "properly parse a simple JsObject" in ( JsonParser(""" { "key" :42, "key2": "value" }""") mustEqual - JsObject(JsField("key", 42), JsField("key2", "value")) + JsObject("key" -> JsNumber(42), "key2" -> JsString("value")) ) "properly parse a simple JsArray" in ( JsonParser("""[null, 1.23 ,{"key":true } ] """) mustEqual - JsArray(JsNull, JsNumber(1.23), JsObject(JsField("key", true))) + JsArray(JsNull, JsNumber(1.23), JsObject("key" -> JsBoolean(true))) ) "be reentrant" in { val largeJsonSource = FileUtils.readAllCharsFromResource("test.json") List.fill(20)(largeJsonSource).par.map(JsonParser(_)).toList.map { - _.asInstanceOf[JsObject].asMap("questions").asInstanceOf[JsArray].elements.size + _.asInstanceOf[JsObject].fields("questions").asInstanceOf[JsArray].elements.size } mustEqual List.fill(20)(100) } } diff --git a/src/test/scala/cc/spray/json/PrettyPrinterSpec.scala b/src/test/scala/cc/spray/json/PrettyPrinterSpec.scala index feed8a9..3bc29ff 100644 --- a/src/test/scala/cc/spray/json/PrettyPrinterSpec.scala +++ b/src/test/scala/cc/spray/json/PrettyPrinterSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ diff --git a/src/test/scala/cc/spray/json/ProductFormatsSpec.scala b/src/test/scala/cc/spray/json/ProductFormatsSpec.scala index 9a692ec..c34f491 100644 --- a/src/test/scala/cc/spray/json/ProductFormatsSpec.scala +++ b/src/test/scala/cc/spray/json/ProductFormatsSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -9,8 +25,8 @@ class ProductFormatsSpec extends Specification { trait TestProtocol { this: DefaultJsonProtocol => - implicit val test2Format = jsonFormat(Test2, "a", "b") - implicit def test3Format[A: JsonFormat, B: JsonFormat] = jsonFormat(Test3.apply[A, B], "as", "bs") + implicit val test2Format = jsonFormat2(Test2) + implicit def test3Format[A: JsonFormat, B: JsonFormat] = jsonFormat2(Test3.apply[A, B]) } object TestProtocol1 extends DefaultJsonProtocol with TestProtocol object TestProtocol2 extends DefaultJsonProtocol with TestProtocol with NullOptions @@ -18,38 +34,38 @@ class ProductFormatsSpec extends Specification { "A JsonFormat created with `jsonFormat`, for a case class with 2 elements," should { import TestProtocol1._ val obj = Test2(42, Some(4.2)) - val json = JsObject(JsField("a", 42), JsField("b", 4.2)) + val json = JsObject("a" -> JsNumber(42), "b" -> JsNumber(4.2)) "convert to a respective JsObject" in { obj.toJson mustEqual json } "convert a JsObject to the respective case class instance" in { - json.fromJson[Test2] mustEqual obj + json.convertTo[Test2] mustEqual obj } "throw a DeserializationException if the JsObject does not all required members" in ( - JsObject(JsField("b", 4.2)).fromJson[Test2] must + JsObject("b" -> JsNumber(4.2)).convertTo[Test2] must throwA(new DeserializationException("Object is missing required member 'a'")) ) "not require the presence of optional fields for deserialization" in { - JsObject(JsField("a", 42)).fromJson[Test2] mustEqual Test2(42, None) + JsObject("a" -> JsNumber(42)).convertTo[Test2] mustEqual Test2(42, None) } "not render `None` members during serialization" in { - Test2(42, None).toJson mustEqual JsObject(JsField("a", 42)) + Test2(42, None).toJson mustEqual JsObject("a" -> JsNumber(42)) } "ignore additional members during deserialization" in { - JsObject(JsField("a", 42), JsField("b", 4.2), JsField("c", 'no)).fromJson[Test2] mustEqual obj + JsObject("a" -> JsNumber(42), "b" -> JsNumber(4.2), "c" -> JsString('no)).convertTo[Test2] mustEqual obj } "not depend on any specific member order for deserialization" in { - JsObject(JsField("b", 4.2), JsField("a", 42)).fromJson[Test2] mustEqual obj + JsObject("b" -> JsNumber(4.2), "a" -> JsNumber(42)).convertTo[Test2] mustEqual obj } "throw a DeserializationException if the JsValue is not a JsObject" in ( - JsNull.fromJson[Test2] must throwA(new DeserializationException("Object expected")) + JsNull.convertTo[Test2] must throwA(new DeserializationException("Object expected")) ) } "A JsonProtocol mixing in NullOptions" should { "render `None` members to `null`" in { import TestProtocol2._ - Test2(42, None).toJson mustEqual JsObject(JsField("a", 42), JsField("b", JsNull)) + Test2(42, None).toJson mustEqual JsObject("a" -> JsNumber(42), "b" -> JsNull) } } @@ -57,14 +73,14 @@ class ProductFormatsSpec extends Specification { import TestProtocol1._ val obj = Test3(42 :: 43 :: Nil, "x" :: "y" :: "z" :: Nil) val json = JsObject( - JsField("as", JsArray(JsNumber(42), JsNumber(43))), - JsField("bs", JsArray(JsString("x"), JsString("y"), JsString("z"))) + "as" -> JsArray(JsNumber(42), JsNumber(43)), + "bs" -> JsArray(JsString("x"), JsString("y"), JsString("z")) ) "convert to a respective JsObject" in { obj.toJson mustEqual json } "convert a JsObject to the respective case class instance" in { - json.fromJson[Test3[Int, String]] mustEqual obj + json.convertTo[Test3[Int, String]] mustEqual obj } } diff --git a/src/test/scala/cc/spray/json/ReadmeSpec.scala b/src/test/scala/cc/spray/json/ReadmeSpec.scala index 843d1fc..791720f 100644 --- a/src/test/scala/cc/spray/json/ReadmeSpec.scala +++ b/src/test/scala/cc/spray/json/ReadmeSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -8,58 +24,74 @@ class ReadmeSpec extends Specification { "behave as expected" in { import DefaultJsonProtocol._ - val json = """{ "some": "JSON source" }""" - val jsonAst = JsonParser(json) - jsonAst mustEqual JsObject(JsField("some", "JSON source")) + val source = """{ "some": "JSON source" }""" + val jsonAst = source.asJson + jsonAst mustEqual JsObject("some" -> JsString("JSON source")) - val json2 = PrettyPrinter(jsonAst) + val json2 = jsonAst.prettyPrint json2 mustEqual """{ | "some": "JSON source" |}""".stripMargin - + val jsonAst2 = List(1, 2, 3).toJson jsonAst2 mustEqual JsArray(JsNumber(1), JsNumber(2), JsNumber(3)) } } - + case class Color(name: String, red: Int, green: Int, blue: Int) - + val color = Color("CadetBlue", 95, 158, 160) + "The case class example" should { "behave as expected" in { object MyJsonProtocol extends DefaultJsonProtocol { - implicit val colorFormat = jsonFormat(Color, "name", "red", "green", "blue") - } + implicit val colorFormat = jsonFormat4(Color) + } import MyJsonProtocol._ - - val json = Color("CadetBlue", 95, 158, 160).toJson - val color = json.fromJson[Color] - - color mustEqual Color("CadetBlue", 95, 158, 160) + color.toJson.convertTo[Color] mustEqual color } } - - "The non case class example" should { + + "The non case class (array) example" should { "behave as expected" in { object MyJsonProtocol extends DefaultJsonProtocol { implicit object ColorJsonFormat extends JsonFormat[Color] { - def write(c: Color) = { + def write(c: Color) = JsArray(JsString(c.name), JsNumber(c.red), JsNumber(c.green), JsNumber(c.blue)) - } + def read(value: JsValue) = value match { - case JsArray(JsString(name) :: JsNumber(red) :: JsNumber(green) :: JsNumber(blue) :: Nil) => { + case JsArray(JsString(name) :: JsNumber(red) :: JsNumber(green) :: JsNumber(blue) :: Nil) => new Color(name, red.toInt, green.toInt, blue.toInt) + case _ => deserializationError("Color expected") + } + } + } + import MyJsonProtocol._ + color.toJson.convertTo[Color] mustEqual color + } + } + + "The non case class (object) example" should { + "behave as expected" in { + object MyJsonProtocol extends DefaultJsonProtocol { + implicit object ColorJsonFormat extends JsonFormat[Color] { + def write(c: Color) = JsObject( + "name" -> JsString(c.name), + "red" -> JsNumber(c.red), + "green" -> JsNumber(c.green), + "blue" -> JsNumber(c.blue) + ) + def read(value: JsValue) = { + value.asJsObject.getFields("name", "red", "green", "blue") match { + case Seq(JsString(name), JsNumber(red), JsNumber(green), JsNumber(blue)) => + new Color(name, red.toInt, green.toInt, blue.toInt) + case _ => throw new DeserializationException("Color expected") } - case _ => throw new DeserializationException("Color expected") } } - } + } import MyJsonProtocol._ - - val json = Color("CadetBlue", 95, 158, 160).toJson - val color = json.fromJson[Color] - - color mustEqual Color("CadetBlue", 95, 158, 160) + color.toJson.convertTo[Color] mustEqual color } } diff --git a/src/test/scala/cc/spray/json/StandardFormatsSpec.scala b/src/test/scala/cc/spray/json/StandardFormatsSpec.scala index ad9485c..ed6283f 100644 --- a/src/test/scala/cc/spray/json/StandardFormatsSpec.scala +++ b/src/test/scala/cc/spray/json/StandardFormatsSpec.scala @@ -1,3 +1,19 @@ +/* + * Copyright (C) 2011 Mathias Doenitz + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + package cc.spray.json import org.specs2.mutable._ @@ -10,13 +26,13 @@ class StandardFormatsSpec extends Specification with DefaultJsonProtocol { None.asInstanceOf[Option[Int]].toJson mustEqual JsNull } "convert JsNull to None" in { - JsNull.fromJson[Option[Int]] mustEqual None + JsNull.convertTo[Option[Int]] mustEqual None } "convert Some(Hello) to JsString(Hello)" in { Some("Hello").asInstanceOf[Option[String]].toJson mustEqual JsString("Hello") } "convert JsString(Hello) to Some(Hello)" in { - JsString("Hello").fromJson[Option[String]] mustEqual Some("Hello") + JsString("Hello").convertTo[Option[String]] mustEqual Some("Hello") } } @@ -31,10 +47,10 @@ class StandardFormatsSpec extends Specification with DefaultJsonProtocol { b.toJson mustEqual JsString("Hello") } "convert the left side of an Either value from Json" in { - JsNumber(42).fromJson[Either[Int, String]] mustEqual Left(42) + JsNumber(42).convertTo[Either[Int, String]] mustEqual Left(42) } "convert the right side of an Either value from Json" in { - JsString("Hello").fromJson[Either[Int, String]] mustEqual Right("Hello") + JsString("Hello").convertTo[Either[Int, String]] mustEqual Right("Hello") } } @@ -43,7 +59,7 @@ class StandardFormatsSpec extends Specification with DefaultJsonProtocol { Tuple1(42).toJson mustEqual JsNumber(42) } "be able to convert a JsNumber to a Tuple1[Int]" in { - JsNumber(42).fromJson[Tuple1[Int]] mustEqual Tuple1(42) + JsNumber(42).convertTo[Tuple1[Int]] mustEqual Tuple1(42) } } @@ -53,7 +69,7 @@ class StandardFormatsSpec extends Specification with DefaultJsonProtocol { (42, 4.2).toJson mustEqual json } "be able to convert a JsArray to a (Int, Double)]" in { - json.fromJson[(Int, Double)] mustEqual (42, 4.2) + json.convertTo[(Int, Double)] mustEqual (42, 4.2) } } |