[Node] Use Result enum

This commit is contained in:
Kyle Fuller
2014-10-26 17:43:20 +00:00
parent 51410d2ce9
commit fb30915c6a
3 changed files with 71 additions and 39 deletions

View File

@@ -15,7 +15,7 @@ struct NodeError : Error {
}
public protocol Node {
func render(context:Context) -> (String?, Error?)
func render(context:Context) -> Result
}
extension Array {
@@ -38,15 +38,18 @@ extension Array {
}
public func renderNodes(nodes:[Node], context:Context) -> Result {
let result:(results:[String]?, error:Error?) = nodes.map {
return $0.render(context)
var result = ""
for item in nodes {
switch item.render(context) {
case .Success(let string):
result += string
case .Error(let error):
return .Error(error:error)
}
}
if let result = result.0 {
return .Success(string:"".join(result))
}
return .Error(error:result.1!)
return .Success(string:result)
}
public class TextNode : Node {
@@ -56,8 +59,8 @@ public class TextNode : Node {
self.text = text
}
public func render(context:Context) -> (String?, Error?) {
return (self.text, nil)
public func render(context:Context) -> Result {
return .Success(string:self.text)
}
}
@@ -72,16 +75,16 @@ public class VariableNode : Node {
self.variable = Variable(variable)
}
public func render(context:Context) -> (String?, Error?) {
public func render(context:Context) -> Result {
let result:AnyObject? = variable.resolve(context)
if let result = result as? String {
return (result, nil)
return .Success(string:result)
} else if let result = result as? NSObject {
return (result.description, nil)
return .Success(string:result.description)
}
return (nil, nil)
return .Success(string:"")
}
}
@@ -107,7 +110,7 @@ public class NowNode : Node {
}
}
public func render(context: Context) -> (String?, Error?) {
public func render(context: Context) -> Result {
let date = NSDate()
let format: AnyObject? = self.format.resolve(context)
var formatter:NSDateFormatter?
@@ -118,11 +121,10 @@ public class NowNode : Node {
formatter = NSDateFormatter()
formatter!.dateFormat = format
} else {
// TODO Error
return (nil, nil)
return .Success(string:"")
}
return ("\(formatter!.stringFromDate(date))", nil)
return .Success(string:formatter!.stringFromDate(date))
}
}
@@ -176,7 +178,7 @@ public class ForNode : Node {
self.nodes = nodes
}
public func render(context: Context) -> (String?, Error?) {
public func render(context: Context) -> Result {
let values = variable.resolve(context) as? [AnyObject]
var output = ""
@@ -191,12 +193,12 @@ public class ForNode : Node {
case .Success(let string):
output += string
case .Error(let error):
return (nil, error)
return .Error(error:error)
}
}
}
return (output, nil)
return .Success(string:output)
}
}
@@ -269,7 +271,7 @@ public class IfNode : Node {
self.falseNodes = falseNodes
}
public func render(context: Context) -> (String?, Error?) {
public func render(context: Context) -> Result {
let result: AnyObject? = variable.resolve(context)
var truthy = false
@@ -285,11 +287,6 @@ public class IfNode : Node {
let output = renderNodes(truthy ? trueNodes : falseNodes, context)
context.pop()
switch output {
case .Success(let string):
return (string, nil)
case .Error(let error):
return (nil, error)
}
return output
}
}

View File

@@ -9,9 +9,9 @@ class ErrorNodeError : Error {
}
class ErrorNode : Node {
func render(context: Context) -> (String?, Error?) {
func render(context: Context) -> Result {
return (nil, ErrorNodeError())
return .Error(error:ErrorNodeError())
}
}
@@ -32,7 +32,12 @@ class TextNodeTests: NodeTests {
let node = TextNode(text:"Hello World")
let result = node.render(context)
XCTAssertEqual(result.0!, "Hello World")
switch node.render(context) {
case .Success(let string):
XCTAssertEqual(string, "Hello World")
case .Error(let error):
XCTAssert(false, "Unexpected error")
}
}
}
@@ -41,14 +46,24 @@ class VariableNodeTests: NodeTests {
let node = VariableNode(variable:Variable("name"))
let result = node.render(context)
XCTAssertEqual(result.0!, "Kyle")
switch node.render(context) {
case .Success(let string):
XCTAssertEqual(string, "Kyle")
case .Error(let error):
XCTAssert(false, "Unexpected error")
}
}
func testVariableNodeResolvesNonStringVariable() {
let node = VariableNode(variable:Variable("age"))
let result = node.render(context)
XCTAssertEqual(result.0!, "27")
switch node.render(context) {
case .Success(let string):
XCTAssertEqual(string, "27")
case .Error(let error):
XCTAssert(false, "Unexpected error")
}
}
}
@@ -80,7 +95,12 @@ class ForNodeTests: NodeTests {
let node = ForNode(variable: "items", loopVariable: "item", nodes: [VariableNode(variable: "item")], emptyNodes:[])
let result = node.render(context)
XCTAssertEqual(result.0!, "123")
switch node.render(context) {
case .Success(let string):
XCTAssertEqual(string, "123")
case .Error(let error):
XCTAssert(false, "Unexpected error")
}
}
}
@@ -160,14 +180,24 @@ class IfNodeTests: NodeTests {
let node = IfNode(variable: "items", trueNodes: [TextNode(text: "true")], falseNodes: [TextNode(text: "false")])
let result = node.render(context)
XCTAssertEqual(result.0!, "true")
switch node.render(context) {
case .Success(let string):
XCTAssertEqual(string, "true")
case .Error(let error):
XCTAssert(false, "Unexpected error")
}
}
func testIfNodeRenderFalse() {
let node = IfNode(variable: "unknown", trueNodes: [TextNode(text: "true")], falseNodes: [TextNode(text: "false")])
let result = node.render(context)
XCTAssertEqual(result.0!, "false")
switch node.render(context) {
case .Success(let string):
XCTAssertEqual(string, "false")
case .Error(let error):
XCTAssert(false, "Unexpected error")
}
}
}
@@ -208,7 +238,12 @@ class NowNodeTests: NodeTests {
formatter.dateFormat = "yyyy-MM-dd"
let date = formatter.stringFromDate(NSDate())
XCTAssertEqual(result.0!, date)
switch node.render(context) {
case .Success(let string):
XCTAssertEqual(string, date)
case .Error(let error):
XCTAssert(false, "Unexpected error")
}
}
}

View File

@@ -21,8 +21,8 @@ func assertFailure(result:TokenParser.Results, description:String) {
}
class CustomNode : Node {
func render(context:Context) -> (String?, Error?) {
return ("Hello World", nil)
func render(context:Context) -> Result {
return .Success(string:"Hello World")
}
}