func (b *Builder) ParseLiteral(ctx *builderCtx) node.Node { t := b.NextNonSpace(ctx) switch t.Type() { case ItemDoubleQuotedString, ItemSingleQuotedString: v := t.Value() return node.NewTextNode(t.Pos(), v[1:len(v)-1]) case ItemNumber: v := t.Value() // XXX TODO: parse hex/oct/bin if strings.Contains(v, ".") { f, err := strconv.ParseFloat(v, 64) if err != nil { // shouldn't happen, as we were able to lex it b.Unexpected(ctx, "Could not parse number: %s", err) } return node.NewFloatNode(t.Pos(), f) } i, err := strconv.ParseInt(v, 10, 64) if err != nil { b.Unexpected(ctx, "Could not parse number: %s", err) } return node.NewIntNode(t.Pos(), i) default: b.Unexpected(ctx, "Expected literal value, got %s", t) } return nil }
func (b *Builder) ParseRawString(ctx *builderCtx) node.Node { const whiteSpace = " \t\r\n" token := b.NextNonSpace(ctx) if token.Type() != ItemRawString { b.Unexpected(ctx, "Expected raw string, got %s", token) } value := token.Value() if ctx.PostChomp { value = strings.TrimLeft(value, whiteSpace) ctx.PostChomp = false } // Look for signs of pre-chomp if b.PeekNonSpace(ctx).Type() == ItemTagStart { start := b.NextNonSpace(ctx) next := b.PeekNonSpace(ctx) b.Backup2(ctx, start) if next.Type() == ItemMinus { // prechomp! value = strings.TrimRight(value, whiteSpace) } } n := node.NewPrintRawNode(token.Pos()) n.Append(node.NewTextNode(token.Pos(), value)) return n }