func (fs LambdaStatement) Parse(block string, lineNum int, nextBlockScanner *parser.ScanPeeker, factory *StatementFactory) (Statement, parser.SyntaxError) { lines := parser.Lines(block) factory = fetchNewFactory(factory) typeDef, err, rest := expressionParsing.ParseTypeDef(lines[0]) if err != nil { return nil, parser.NewSyntaxError(err.Error(), lineNum, 0) } var ftd expressionParsing.FuncTypeDefinition var ok bool if ftd, ok = typeDef.(expressionParsing.FuncTypeDefinition); !ok { return nil, nil } var codeBlock []string if len(strings.TrimSpace(rest)) > 0 { var first string if len(lines) > 1 { return nil, parser.NewSyntaxError("Inline lambdas can only be one line", lineNum, 0) } else if first, rest = parser.Tokenize(rest); first != "->" { return nil, parser.NewSyntaxError("Misplaced tokens: "+rest, lineNum, 0) } codeBlock = []string{rest} } else { codeBlock = parser.RemoveTabs(lines[1:]) } innerStatements, synErr := fetchInnerStatements(codeBlock, factory, lineNum+1) if synErr != nil { return nil, synErr } synErr = verifyInnerStatements(innerStatements, lineNum) if synErr != nil { return nil, synErr } return newLambdaStatement(lineNum, ftd, innerStatements, fs.packageLevel, fs.name), nil }
d, err := statementParser.Parse(code, 0, nil, factory) ds := d.(*LetStatement) Expect(err).To(BeNil()) Expect(ds).ToNot(BeNil()) Expect(ds.VariableName()).To(Equal("a")) Expect(stripWhitespace(ds.CodeBlock())).To(Equal("b+9")) }) It("Should return nil for a non declaration", func() { code := "if true\n\t9\nelse\n\t10" d, err := statementParser.Parse(code, 0, nil, factory) Expect(err).To(BeNil()) Expect(d).To(BeNil()) }) }) Context("GenerateGo", func() { It("Should return proper go code", func() { code := "let a = 9 + 6" d, err := statementParser.Parse(code, 0, nil, factory) fm := expressionParsing.NewFunctionMap() gocode, returnType, err := d.GenerateGo(fm) Expect(err).To(BeNil()) intType, _, _ := expressionParsing.ParseTypeDef("int32") Expect(returnType.GenerateGo()).To(Equal(intType.GenerateGo())) Expect(gocode).To(Equal("var a func() int32\na = func(){\n\treturn (9+6)\n}")) fd := fm.GetFunction("a") Expect(fd).ToNot(BeNil()) Expect(fd.GenerateGo()).To(Equal(intType.GenerateGo())) }) }) })
. "github.com/onsi/gomega" ) var _ = Describe("LambdaStatement", func() { var statementParser StatementParser var factory *StatementFactory BeforeEach(func() { retParser := NewReturnStatementParser() declParser := NewLetParser() statementParser = NewLambdaStatementParser() factory = NewStatementFactory(declParser, statementParser, retParser) }) Context("Parse", func() { var expectedType expressionParsing.TypeDefinition BeforeEach(func() { expectedType, _, _ = expressionParsing.ParseTypeDef("func a A -> b B -> int32") }) It("Should distinguish a lambda statement", func() { code := "func a A -> b B -> int32\n\t5+9" f, err := statementParser.Parse(code, 0, nil, factory) Expect(f).ToNot(BeNil()) fs := f.(*LambdaStatement) Expect(err).To(BeNil()) Expect(fs).ToNot(BeNil()) Expect(fs.TypeDef.GenerateGo()).To(Equal(expectedType.GenerateGo())) Expect(fs.InnerStatements).ToNot(BeNil()) Expect(fs.InnerStatements).To(HaveLen(1)) }) It("Should distinguish a single line lambda statement", func() { code := "func a A -> b B -> int32 -> 5+9" f, err := statementParser.Parse(code, 0, nil, factory)
Expect(r).ToNot(BeNil()) }) }) Context("GenerateGo", func() { var funcMap expressionParsing.FunctionMap BeforeEach(func() { funcMap = expressionParsing.NewFunctionMap() }) Context("No functions", func() { It("Should generate the proper Go code", func() { code := "( 1 + 11 ) - 10 / 2" r, err := statementParser.Parse(code, 0, nil, factory) Expect(err).To(BeNil()) genGo, returnType, err := r.GenerateGo(funcMap) Expect(err).To(BeNil()) intType, _, _ := expressionParsing.ParseTypeDef("int32") Expect(returnType.GenerateGo()).To(Equal(intType.GenerateGo())) Expect(genGo).To(Equal("((1+11)-(10/2))")) }) It("Should generate the proper Go code with proper numeric types", func() { code := "( 1b + 11b ) - 10b / 2b" r, err := statementParser.Parse(code, 0, nil, factory) Expect(err).To(BeNil()) genGo, returnType, err := r.GenerateGo(funcMap) Expect(err).To(BeNil()) intType, _, _ := expressionParsing.ParseTypeDef("int8") Expect(returnType.GenerateGo()).To(Equal(intType.GenerateGo())) Expect(genGo).To(Equal("((int8(1)+int8(11))-(int8(10)/int8(2)))")) }) }) Context("With functions", func() {