Scala 2.10,它对 JSON 库和案例类验证/创建的影响

2024-05-09

显然,在 Scala 2.10 中我们得到了改进的反射。

这将如何影响 lift-json、jerkson、sjson 和朋友?此外,我们能否期望在不久的将来,Scala 中会出现内置的 JSON 语言功能,如 Groovy 的出色 GSON?

我问的原因是我非常想做:

case class Foo(a: String, b: Int, bar: Bar)
case class Bar(c: Int)
val foo = Foo("hey", 10, Bar(23))
val json = foo.toJson

无需跳圈(即样板式的准备工作),即使具有任意复杂的对象图。也许我的要求太多了,但人总是可以梦想的。请粉碎我的 2.10 梦想,或者启发我了解备受期待的 Scala 版本将开辟哪些新途径。Next

另外,对于案例类,对于验证/创建来说,scalaz 验证似乎是首选武器。它看起来非常美妙,充当对象创建的安全代理或错误收集器。然而,作为一名 Scewbie,我发现 scalaz 有点具有挑战性,并且尽管它的力量显而易见,但我仍在抵制它的黑暗面;-)

无论如何,这里的要点是,通过 2.10 反射,我们应该能够在运行时将字段(例如表单帖子)绑定到案例类的属性,并仅根据属性类型执行基本验证(即不会有指定单独的验证逻辑,指定属性 foo 必须是 String,因为它的类型已经在我们现在可以正确反映的案例类中定义)

那么,美丽的新世界即将到来,还是现有的工具将成为可预见的未来的支柱?


前言

让我给出一种不同的解决方案,它不依赖于任何基于 Java 的库,而只依赖于纯 Scala 库。

实际上,正如 @Steve 结果评论中所讨论的,Play 2 的 scala 版本使用 Jerkson 将 Json 反/序列化为域模型。 Jerkson 是一个用于处理 Json 的非常好的 Java 库的 DSL 包装器。

Answer

上面没有回答你的问题,因为你问是否已经设想使用 Scala 2.10 的反射和宏功能来简化这项任务!通过消除大多数样板文件。

事实上这是一个非常好的想法,因为从 Play 2.1 版本开始,Json Scala API 不再使用 Jerkson,而是使用自己的机制。

该机制实际上是通过引入基于以下两点的全新 API 来利用 Scala 新 2.10 版本的优势:

  • 适合能够读取和写入 Json 或域实例的功能结构(Applicative Builder)。这些构建器用于粘合组合器(用于读取或写入),以定义粗粒度结构(就像我们对解析器组合器所做的那样)
  • 一堆宏,能够发现哪些组合器隐式可用,并为它们构造复杂的组合器案例类别(或者至少具有以下类型apply and unapply方法)。

归根结底,我们可以使用此 API 执行以下操作:

import play.api.libs.json._
import play.api.libs.functional.syntax._

case class Person(name: String, age: Int, lovesChocolate: Boolean)

implicit val personReads = Json.format[Person] //a format is a Reader and a Writer

//this format will be implicitly used by the following from/toJson functions
val person:JsResult[Person] = Json.fromJson(json) //JsResult is like JsSucces/JsError
val jsObject = Json.toJson(person)

代码复制并改编自:JSON Inception(基于 Scala 2.10 宏) http://mandubian.com/2012/11/11/JSON-inception/

一点注意:新的 API 甚至足够智能,能够通过累积错误来验证“读取”......

参考

我在这里推荐 @mandubian 的一系列博客,因为它们非常有启发性!

  • JsPath 和读取组合器:http://mandubian.com/2012/09/08/unveiling-play-2-dot-1-json-api-part1-jspath-reads-combinators/ http://mandubian.com/2012/09/08/unveiling-play-2-dot-1-json-api-part1-jspath-reads-combinators/
  • 写入/格式组合器:http://mandubian.com/2012/10/01/unveiling-play-2-dot-1-json-api-part2-writes-format-combinators/ http://mandubian.com/2012/10/01/unveiling-play-2-dot-1-json-api-part2-writes-format-combinators/
  • JSON 转换器:http://mandubian.com/2012/10/29/unveiling-play-2-dot-1-json-api-part3-json-transformers/ http://mandubian.com/2012/10/29/unveiling-play-2-dot-1-json-api-part3-json-transformers/
  • JSON Inception(基于 Scala 2.10 宏):http://mandubian.com/2012/11/11/JSON-inception/ http://mandubian.com/2012/11/11/JSON-inception/

最后说明

可悲的是,Play 2 的模块化...不允许我们单独使用这个 API!因此,它应该从整个播放库中使用:/ 这在未来可能会改变......

EDIT

未来已经越来越近了,因为帕斯卡有这个repo https://github.com/mandubian/play-json-alone使我们能够使用 play-json API。

因此,在 Play 2.2 发布之前可以使用此存储库。事实上,这个版本将与 json 或 iteratees 等几个 API 完全解耦,因此,我们将能够直接使用 playframework 存储库。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Scala 2.10,它对 JSON 库和案例类验证/创建的影响 的相关文章

  • 来自 iPhone/iPad 的 json Web 服务

    有人可以帮助我解决如何从 iphone 或 ipad 使用 json Web 服务的问题吗 这里我的要求是使用 API 密钥实现 json webservice 如果可能的话发布一些教程或示例链接 谢谢 规范的 JSON 处理库是here
  • 带有 Odata Next Page 和 Count 的 Web Api 未出现在 JSON 响应中

    我有一个 webapi 方法 我想打开 oData 分页等 我按照中的例子http www asp net web api overview odata support in aspnet web api supporting odata
  • Spark:查找前 n 个值的高性能方法

    我有一个很大的数据集 我想找到具有 n 个最高值的行 id count id1 10 id2 15 id3 5 我能想到的唯一方法是使用row number没有分区就像 val window Window orderBy desc coun
  • 在 ASP.NET Core 2.0 Web Api 中返回“原始”json

    AFAIK 在 ASP NET Core Web Api 中返回数据的标准方法是使用IActionResult并提供例如一个OkObject结果 这对于对象来说效果很好 但是如果我以某种方式获得了一个 JSON 字符串 并且我只想将该 JS
  • 实现只有一个居民的类型的价值

    感谢 MilesSabin 的answer https stackoverflow com a 32157259 867671我可以编写类型级别的斐波那契序列 sealed trait Digit case object Zero exte
  • 过滤器的 Scala 集合类型

    假设您有一个 List 1 1 其类型为 List Any 这当然是正确的且符合预期 现在如果我像这样映射列表 scala gt List 1 1 map case x Int gt x case y String gt y toInt 结
  • sbt 找不到启动器 jar:./bin/sbt-launch.jar

    我已经成功地使用 sbt 进行基本的 Scala 编译好几年了 但有一天它由于某种原因停止工作 我在自己的帐户中使用它 但我决定让我的系统管理员在我们的本地网络上安装最新版本 当我尝试运行它时 我得到 找不到启动器 jar bin sbt
  • 如何将 Dataframe 列名称与 Scala 案例类属性相匹配?

    本示例中的 Spark sql 列名来自case class Person case class Person name String age Int val people RDD Person An RDD of case class o
  • 使用 apply 方法的泛型类型的 Scala 工厂?

    假设我有以下特征 它定义了一个接口并采用几个类型参数 trait Foo A B implementation details not important 我想使用伴随对象作为该特征的具体实现的工厂 我还想强制用户使用Foo接口而不是子类所
  • InvalidRequestException(为什么:empid 如果包含 Equal,则不能被多个关系限制)

    这是关于我从 Apache Spark 查询 Cassandra 时遇到的问题 Spark 的正常查询工作正常 没有任何问题 但是当我使用关键条件进行查询时 出现以下错误 最初 我尝试查询复合键列族 它也给出了与下面相同的问题 由以下原因引
  • Python 相当于 Scala 案例类

    Python 中是否有与 Scala 的 Case Class 等效的东西 就像自动生成分配给字段而无需编写样板的构造函数一样 当前执行此操作的现代方法 从 Python 3 7 开始 是使用数据类 https www python org
  • C语言中如何通过内存地址映射函数名和行号?

    如何用 GCC 中的内存地址映射回函数名称和行号 即假设一个 C 语言原型 void func Get the address of caller maybe this could be avoided MemoryAddress get
  • SQL查询json字典数据

    我的表中的 CLOB 字段包含 JSON 如下所示 a value1 b value2 c value3 我正在尝试编写一个 SQL 查询来返回一个包含键和值字段的表 如下所示 key value a value1 b value2 c v
  • 如何使方法通用而不出现“未找到匹配的形状”

    除了编写大量样板文件之外 我不知道如何克服这个 找不到匹配的形状 错误 要点中说明的基本思想是 我有一个非常基本的方法版本 有效 但非常具体 然后是一个采用mapper参数并且更通用 也可以工作 但特定于一种特定类型 然后是第三个版本 它采
  • 从 JSON 响应中删除元素

    我有一个 JSON 字符串 我希望能够从中删除一些数据 以下是 JSON 响应 ResponseType VirtualBill Response BillHeader BillId 7134 DocumentId MN003 052206
  • 无法将数据加载到 mvc 4 中的 jTable 中

    好的 我第一次尝试 jTable 我可以加载表 但这对我没有什么好处 因为它不会加载我的任何数据 当我调试程序时 我想要的表中的所有行都存储在我的列表中 因此我很困惑为什么当我运行应用程序时会弹出一个对话框 显示 与服务器通信时发生错误 H
  • Scala 为了在 JVM 上运行做出了哪些妥协?

    Scala 是一种很棒的语言 但我想知道如果它有自己的运行时 如何改进 IE 由于 JVM 的选择 做出了哪些设计选择 我所知道的两个最重要的妥协是 类型擦除 http java sun com docs books tutorial ja
  • 迭代变量并查找特定类型实例的技术

    我想迭代进程中内存中的变量 通过插件动态加载 并查找特定类型的实例 以前我可以找到特定类型 或内存中的所有类型 我可以创建类型的实例 我可以获取作为不同类型的字段包含的实例 但我无论如何都不知道只是 搜索 特定类型的实例 一种方法是使用 W
  • 如何记录来自 Akka (Java) 的所有传入消息

    在 Scala 中 您可以使用 LoggingReceive 包装接收函数 如何通过 Java API 实现相同的目标 def receive LoggingReceive case x do something Scala API 有Lo
  • Slick:将操作与 DBIOAction 的 Seq 组合起来

    我有 工作 以下代码 val actions for lt slickUsers insertOrUpdate dbUser loginInfo lt loginInfoAction lt slickUserLoginInfos DBUse

随机推荐

  • Spring Boot:在映射级别指定端口

    Spring Boot 我希望实现以下目标 一些 URL 路径映射到一个端口 一些映射到另一个端口 换句话说 我想要这样的东西 public class Controller1 RequestMapping value path1 port
  • 运行此 AVD 需要 HAXM

    我在 android studio 中创建了模拟器并在其中创建了一些应用程序 当我运行时 它给我一个错误 参见图 1 当我用谷歌搜索时 它告诉我你的系统不支持虚拟化 但我的系统支持它 参见图 2 现在我的问题是 当我的系统支持虚拟化时 为什
  • 线程睡眠阻止我的 Swing 应用程序执行

    我的应用程序发生的事情是有道理的 但我不知道如何修复它 以下是我的应用程序功能的简要描述 计时器窗口应显示在屏幕右下角并显示实时时间 一小时后 它应该执行一些操作 我还没有决定该操作 我面临的问题是定时器 java当我刷新实时计时器的秒数时
  • 单击窗口后才检测到 keydown

    在我的 Web 应用程序中 我有一个用于打开菜单的键的事件侦听器 仅当我单击页面上的任意位置后 此功能才可以正常工作 我尝试将焦点添加到窗口加载 但这仍然不会让 keydown 函数运行 直到我单击页面上的某个位置之后 有谁知道这是否可能
  • 如何使用 BFG 删除受保护的提交

    使用 BFG 清理存储库时 https rtyley github io bfg repo cleaner https rtyley github io bfg repo cleaner 遇到以下情况 Protected commits T
  • TortoiseSVN 错误“工作副本已锁定”“sqlite:尝试写入只读数据库” - 这可能是由不正确的权限引起的吗?

    应用程序的工作副本在尝试更新时返回所描述的错误 此错误是否是由于没有足够的权限写入该文件夹 或其中的某些文件 而导致的 我尝试过 释放锁定 功能 乌龟告诉我没有锁定 我在 Windows 下使用 TortoiseSVN 时遇到了这个错误 显
  • 使用 foreach 循环和 XmlNodeList C# 将新节点附加到节点列表

    目前我处理的是这样的XML类型 XML FILE http 20drive google com open id 0By5BxgNi9eGcRldxcEZNU0FDTzQ 参考XML文件 我想检查一个节点 如果找不到该节点 我必须将该节点附
  • Rglpk - 梦幻足球阵容优化器 - For 循环输出的 Rbind

    我有一个使用 Rgplk 的梦幻足球阵容优化器 它使用for循环生成多个最佳阵容 其数量由用户输入 代码如下 Lineups lt list for i in 1 Lineup no matrix lt rbind as numeric D
  • 自定义 WPF 工具提示

    我想创建一个 WPF 工具提示 其中包含工具提示标题的标签 然后创建一个包含更详细文本的文本块 我在资源字典中创建了以下样式
  • 用于客户端存储和服务器端同步的javascript库[关闭]

    Closed 这个问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 help closed questions 目前不接受答案 我正在寻找一个 javascript 库 它可以让我将数据存储在客户端数据库中 并在后台自动将数据库同
  • 从 csv 中读取 pandas 数据帧,以非固定标头开始

    我有许多数据文件是由我的实验室中使用的一些相当黑客的脚本生成的 该脚本非常有趣 因为它在标头之前附加的行数因文件而异 尽管它们具有相同的格式并具有相同的标头 我正在编写一个批处理来将所有这些文件处理为数据帧 如果我不知道位置 如何让 pan
  • WebSocketStompClient 将无法连接到 SockJS 端点

    我正在尝试新的 从版本 4 2 开始 java STOMP 客户端支持 我的出发点是入门指南 使用 WebSocket 构建交互式 Web 应用程序 http spring io guides gs messaging stomp webs
  • NativeScript:禁用 iOS WebView 缩放控件的方法?

    我正在尝试找出一种方法来防止用户通过捏合手势和双击来放大和缩小 iOS WebView tns ios 3 4 1 本质上禁用所有缩放 就像苹果之前使用的 html 元标记一样让用户决定是否要使用 iOS 10 及更高版本进行缩放 我找到了
  • Rails-自定义删除前确认对话框的视图

    要删除 Rails 中的记录 我使用此代码 result of which I get dialog box like this But I wants this dialog box to look like this 有没有办法自定义确
  • 如何使用收益返回和递归获得字母的每个组合?

    我有几个像这样的字符串列表 可能有几十个列表 1 A B C 2 1 2 3 3 D E F 这三个仅作为示例 用户可以从几十个具有不同数量元素的类似列表中进行选择 再举个例子 这对于用户来说也是一个完全有效的选择 25 empty 4 1
  • 为什么严格模式下不允许使用八进制数字文字(解决方法是什么?)

    为什么八进制数字文字不允许JavaScript 严格模式 https developer mozilla org en docs Web JavaScript Reference Strict mode 有什么害处呢 use strict
  • 为什么某些 Git 分支名称中包含斜杠?

    我正在阅读本教程https www atlassian com git tutorials syncing git fetch https www atlassian com git tutorials syncing git fetch
  • 如何忽略Git中以数字开头的文件?

    在某个文件夹中 我有名为foo jpg bar png等等 我想将它们保留在版本控制中 除了那些命名为1 baz png 2 zaz jpg等 因为它们实际上是生成的 我应该添加什么条目 gitignore 正则表达式如 0 9 似乎不起作
  • Activity 上的 OnTouchListener 从不调用

    我使用了这段代码 但是当我在运行时单击活动时 它永远不会在 OnTouch 方法中命中 有人可以指导我我做错了什么吗 我需要设置此活动的内容视图吗 实际上我想要用户在执行过程中触摸的活动的坐标 public class TouchTestA
  • Scala 2.10,它对 JSON 库和案例类验证/创建的影响

    显然 在 Scala 2 10 中我们得到了改进的反射 这将如何影响 lift json jerkson sjson 和朋友 此外 我们能否期望在不久的将来 Scala 中会出现内置的 JSON 语言功能 如 Groovy 的出色 GSON