【问题标题】:FRP Interstellar, transforming, chaining signalsFRP 星际,转换,链接信号
【发布时间】:2015-11-20 08:44:31
【问题描述】:

假设有两个对 API 的异步请求需要按顺序执行。 第一个请求的结果是字典,第二个请求使用它来获取最终字典。 Interstellar (https://github.com/JensRavens/Interstellar) 允许以一种按顺序依次执行异步请求的方式链接异步请求: 例如:

typealias JSONDictionary = [String: AnyObject]

func create(parameters: JSONDictionary, completion: Result<JSONDictionary> -> Void) {
    Request.POST("objects", parameters: parameters, completion: completion)
}

func verify(parameters: JSONDictionary, completion: Result<JSONDictionary> -> Void) {
    guard let id = parameters["id"] as? String else {
        let error = NSError(domain: "", code: 401, userInfo: nil)
        completion(.Error(error))
        return
    }
    Request.POST(String(format: "objects/%@/verify", id), parameters: nil, completion: completion)
}

“create”需要先执行,结果字典将用于执行“verify”: 这很好用:

address.flatMap(Address.create).flatMap(Address.verify)
.next { dictionary in
    expectation.fulfill()
}
.error { error in
    print("There was a an error: \(message)")
}
address.update(self.parameters)

下面的代码(来自星际幻灯片):

infix operator >>> { associativity left precedence 160 }
func >>> <A, B> (left: Signal<A>, right: A->Result<B>) -> Signal<B> {
   return left.flatMap(right)
}
func >>> <A, B> (left: Signal<A>, right: (A, (Result<B> -> Void)) -> Void) -> Signal<B> {
   return left.flatMap(right)
}
func >>> <A, B> (left: Signal<A>, right: A -> B) -> Signal<B> {
   return left.flatMap(right)
}

可以使用:

address >>> Address.create >>> Address.verify

这更清楚。但是,如果验证被定义为(接受 id 而不是字典):

func verify2(id: String, completion: Result<[String: String]> -> Void) { ... }

为了链接它,我定义了另一个函数:

static func idValue(dictionary: JSONDictionary, completion: Result<String> -> Void) { ... )

这基本上是从字典中解压缩 id 键的值(将字典转换为字符串),而不是我可以使用的:

address >>> Address.create >>> Address.idValue >>> Address.verify2

这是 FRP 的常见做法吗?我可以避开中间的那一步吗?

【问题讨论】:

    标签: swift frp


    【解决方案1】:

    很高兴听到您正在使用这个库。是的 - 这就是它应该工作的方式。这里有一些小想法如何使它更容易阅读:

    • 在发布 lib 之前删除了自定义运算符,主要是因为开发人员不喜欢它(他们也改变了我的想法。flatMap 在复杂情况下更具可读性)
    • 函数式编程的主要思想之一是让类型系统为您工作。如果Address.create返回一个Address-struct,那么下一次调用就可以使用它的id-property。一旦通信变得复杂,使用 json 作为参数几乎永远不会起作用。
    • 另一个想法是使用Lens,正如 Chris Eidhof 在Lenses in Swift 中解释的那样。

    【讨论】:

    • 太棒了!感谢镜头链接,将使用它来测试这个想法
    猜你喜欢
    • 2013-12-01
    • 1970-01-01
    • 1970-01-01
    • 2014-05-24
    • 2019-04-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多