all repos

clerk @ e62c721834fb47cfeef8999135930083eda81e4e

missing tooling for ledger/hledger

clerk/journal/printer/directives.go (view raw)

Oleksandr Smirnov Oleksandr Smirnov
olexsmir@gmail.com
fix directives printer, support quoted tags, 1 month ago
1
package printer
2
3
import (
4
	"strconv"
5
	"strings"
6
7
	"olexsmir.xyz/clerk/journal/ast"
8
)
9
10
func (p *printer) writeIncludeDirective(i *ast.IncludeDirective) {
11
	p.buf.WriteString("include ")
12
	p.buf.WriteString(quoteString(i.Path))
13
	p.writeInlineComment(i.Comment)
14
}
15
16
func (p *printer) writeAccountDirective(a *ast.AccountDirective) {
17
	p.buf.WriteString("account ")
18
	p.buf.WriteString(a.Account.String())
19
	p.writeInlineComment(a.Comment)
20
}
21
22
func (p *printer) writeCommodityDirective(c *ast.CommodityDirective) {
23
	p.buf.WriteString("commodity ")
24
	if c.Format.Quantity.IsZero() {
25
		p.buf.WriteString(c.Commodity)
26
		p.writeInlineComment(c.Comment)
27
		return
28
	}
29
	prec := max(c.Format.QuantityFmt.Precision, 2)
30
	switch c.Format.CommodityPos {
31
	case ast.CommodityBefore:
32
		p.buf.WriteString(c.Format.Commodity)
33
		if c.Format.HasSpace {
34
			p.buf.WriteByte(' ')
35
		}
36
		p.writeDecimal(c.Format.Quantity, c.Format.QuantityFmt, prec)
37
	case ast.CommodityAfter:
38
		p.writeDecimal(c.Format.Quantity, c.Format.QuantityFmt, prec)
39
		if c.Format.HasSpace {
40
			p.buf.WriteByte(' ')
41
		}
42
		p.buf.WriteString(c.Format.Commodity)
43
	}
44
	p.writeInlineComment(c.Comment)
45
}
46
47
func (p *printer) writeAliasDirective(a *ast.AliasDirective) {
48
	p.buf.WriteString("alias ")
49
	p.buf.WriteString(a.From.String())
50
	p.buf.WriteString(" = ")
51
	p.buf.WriteString(a.To.String())
52
	p.writeInlineComment(a.Comment)
53
}
54
55
func (p *printer) writePayeeDirective(pd *ast.PayeeDirective) {
56
	p.buf.WriteString("payee ")
57
	p.buf.WriteString(quoteString(pd.Name))
58
	p.writeInlineComment(pd.Comment)
59
}
60
61
func (p *printer) writeTagDirective(t *ast.TagDirective) {
62
	p.buf.WriteString("tag ")
63
	p.buf.WriteString(quoteString(t.Name))
64
	p.writeInlineComment(t.Comment)
65
}
66
67
func (p *printer) writeYearDirective(y *ast.YearDirective) {
68
	p.buf.WriteString("year ")
69
	p.writeInt(y.Year, 4)
70
	p.writeInlineComment(y.Comment)
71
}
72
73
func (p *printer) writeDecimalMarkDirective(d *ast.DecimalMarkDirective) {
74
	p.buf.WriteString("decimal-mark ")
75
	p.buf.WriteByte(d.Mark)
76
	p.writeInlineComment(d.Comment)
77
}
78
79
func (p *printer) writeDefaultCommodityDirective(d *ast.DefaultCommodityDirective) {
80
	p.buf.WriteString("D ")
81
	p.writeAmount(&d.Amount)
82
	p.writeInlineComment(d.Comment)
83
}
84
85
func (p *printer) writeConversionDirective(c *ast.ConversionDirective) {
86
	p.buf.WriteString("C ")
87
	p.writeAmount(&c.From)
88
	p.buf.WriteString(" = ")
89
	p.writeAmount(&c.To)
90
	p.writeInlineComment(c.Comment)
91
}
92
93
func (p *printer) writeMarketPriceDirective(m *ast.MarketPriceDirective) {
94
	p.buf.WriteString("P ")
95
	p.writeDate(m.DateTime.Date)
96
	p.writeTime(m.DateTime.Time)
97
	p.buf.WriteByte(' ')
98
	p.buf.WriteString(m.Commodity)
99
	p.buf.WriteByte(' ')
100
	p.writeAmount(&m.Amount)
101
	p.writeInlineComment(m.Comment)
102
}
103
104
func (p *printer) writeCommentBlockDirective(cb *ast.CommentBlockDirective) {
105
	p.buf.WriteString("comment")
106
	if cb.Header != "" {
107
		p.buf.WriteByte(' ')
108
		p.buf.WriteString(cb.Header)
109
	}
110
	p.buf.WriteByte('\n')
111
	if cb.Content != "" {
112
		p.buf.WriteString(cb.Content)
113
		if !strings.HasSuffix(cb.Content, "\n") {
114
			p.buf.WriteByte('\n')
115
		}
116
	}
117
	p.buf.WriteString("end")
118
	if cb.Header != "" {
119
		p.buf.WriteByte(' ')
120
		p.buf.WriteString(cb.Header)
121
	}
122
}
123
124
func (p *printer) writeApplyDirective(a *ast.ApplyDirective) {
125
	p.buf.WriteString("apply ")
126
	p.buf.WriteString(a.Expr)
127
	p.writeInlineComment(a.Comment)
128
}
129
130
func (p *printer) writeEndDirective(e *ast.EndDirective) {
131
	p.buf.WriteString("end")
132
	if e.Expr != "" {
133
		p.buf.WriteByte(' ')
134
		p.buf.WriteString(e.Expr)
135
	}
136
	p.writeInlineComment(e.Comment)
137
}
138
139
func (p *printer) writeIgnoredDirective(e *ast.IgnoredDirective) {
140
	p.buf.WriteString("N ")
141
	p.buf.WriteString(e.Text)
142
	p.writeInlineComment(e.Comment)
143
}
144
145
func quoteString(s string) string {
146
	needsQuote := false
147
	for _, c := range s {
148
		if c == ' ' || c == '\t' || c == '"' || c == ';' || c == '#' {
149
			needsQuote = true
150
			break
151
		}
152
	}
153
	if !needsQuote {
154
		return s
155
	}
156
	return strconv.Quote(s)
157
}