package parsekit_test import ( "testing" "git.makaay.nl/mauricem/go-parsekit" ) func TestGivenNilTokenHandler_WhenCallingOn_ParsekitPanics(t *testing.T) { p := parsekit.NewParser(func(p *parsekit.ParseAPI) { p.On(nil) }) RunPanicTest(t, PanicTest{ func() { p.Execute("") }, "internal parser error: tokenHandler argument for On() is nil"}) } func TestGivenStoppedParser_WhenCallingHandle_ParsekitPanics(t *testing.T) { otherHandler := func(p *parsekit.ParseAPI) { panic("This is not the handler you're looking for") } p := parsekit.NewParser(func(p *parsekit.ParseAPI) { p.Stop() p.Handle(otherHandler) }) RunPanicTest(t, PanicTest{ func() { p.Execute("") }, "Illegal call to ParseAPI.Handle() from git.makaay.nl/mauricem/go-parsekit_test." + "TestGivenStoppedParser_WhenCallingHandle_ParsekitPanics.func2: " + "no calls allowed after ParseAPI.Stop()"}) } func TestGivenParserWithError_WhenCallingHandle_ParsekitPanics(t *testing.T) { otherHandler := func(p *parsekit.ParseAPI) { panic("This is not the handler you're looking for") } p := parsekit.NewParser(func(p *parsekit.ParseAPI) { p.Error("It ends here") p.Handle(otherHandler) }) RunPanicTest(t, PanicTest{ func() { p.Execute("") }, "Illegal call to ParseAPI.Handle() from git.makaay.nl/mauricem/go-parsekit_test." + "TestGivenParserWithError_WhenCallingHandle_ParsekitPanics.func2: " + "no calls allowed after ParseAPI.Error()"}) } func TestGivenFilledStringBuffer_BufInterpreted_ReturnsInterpretedString(t *testing.T) { var interpreted string var literal string p := parsekit.NewParser(func(p *parsekit.ParseAPI) { p.On(parsekit.C.OneOrMore(parsekit.A.AnyRune)).Accept() literal = p.BufLiteral() interpreted, _ = p.BufInterpreted() }) p.Execute(`This\tis\ta\tcool\tstring`) if literal != `This\tis\ta\tcool\tstring` { t.Fatal("literal string is incorrect") } if interpreted != "This\tis\ta\tcool\tstring" { t.Fatal("interpreted string is incorrect") } } func TestGivenInputInvalidForStringInterpretation_BufInterpreted_SetsError(t *testing.T) { p := parsekit.NewParser(func(p *parsekit.ParseAPI) { p.On(parsekit.C.OneOrMore(parsekit.A.AnyRune)).Accept() p.BufInterpreted() }) err := p.Execute(`This \is wrongly escaped`) if err.Error() != `invalid string: This \is wrongly escaped (invalid syntax, forgot to escape a double quote or backslash maybe?)` { t.Fatalf("Got unexpected error: %s", err.Error()) } } type parserWithLoop struct { loopCounter int } func (l *parserWithLoop) first(p *parsekit.ParseAPI) { p.On(parsekit.A.ASCII).Accept() p.Handle(l.second) } func (l *parserWithLoop) second(p *parsekit.ParseAPI) { p.On(parsekit.A.ASCII).Accept() p.Handle(l.third) } func (l *parserWithLoop) third(p *parsekit.ParseAPI) { if l.loopCounter++; l.loopCounter > 100 { p.Error("Loop not detected by parsekit") return } p.On(parsekit.A.ASCII).Accept() p.Handle(l.first) } func TestGivenLoopingParserDefinition_ParserPanics(t *testing.T) { looper := &parserWithLoop{} parser := parsekit.NewParser(looper.first) RunPanicTest(t, PanicTest{ func() { parser.Execute("Het houdt niet op, niet vanzelf") }, "Loop detected in parser in git.makaay.nl/mauricem/go-parsekit_test." + "(*parserWithLoop).second at /home/ubuntu/Projects/Parsekit/go-parsekit" + "/parsehandler_test.go:87"}) } // This test incorporates an actual loop bug that I dropped on myself and // that I could not easily spot in my code. It sounded so logical: // I want to get chunks of 5 chars from the input, so I simply loop on: // // p.On(c.Max(5, a.AnyRune)) // // The problem here is that Max(5, ...) will also match when there is // no more input, since Max(5, ---) is actually MinMax(0, 5, ...). // Therefore the loop will never stop. Solving the loop was simple: // // p.On(c.MinMax(1, 5, a.AnyRune)) // // Now the loop stops when the parser finds no more matching input data. func TestGivenLoopingParserDefinition2_ParserPanics(t *testing.T) { parser := parsekit.NewParser(func(p *parsekit.ParseAPI) { for p.On(c.Max(5, a.AnyRune)).Accept() { p.BufClear() } p.Stop() }) RunPanicTest(t, PanicTest{ func() { parser.Execute("This will end soon") }, "Loop detected in parser in git.makaay.nl/mauricem/go-parsekit_test." + "TestGivenLoopingParserDefinition2_ParserPanics.func1 at " + "/home/ubuntu/Projects/Parsekit/go-parsekit/parsehandler_test.go:125"}) }