File: token.go

package info (click to toggle)
golang-github-mitch000001-go-hbci 0.4.0-2
  • links: PTS, VCS
  • area: main
  • in suites: bookworm, forky, sid, trixie
  • size: 2,468 kB
  • sloc: java: 1,092; makefile: 5
file content (160 lines) | stat: -rw-r--r-- 4,329 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
package token

import "fmt"

// Token represents a HBCI token.
type Token interface {
	Type() Type
	Value() []byte
	String() string
	Pos() int
	IsSyntaxSymbol() bool
}

// A Iterator iterates over a slice of Tokens
type Iterator struct {
	tokens []Token
	pos    int
}

// HasNext returns true if there are tokens less to emit, false otherwise.
func (t *Iterator) HasNext() bool {
	return t.pos < len(t.tokens)
}

// Next returns the next Token within the iterator. If there are no more tokens
// it will return an EOF Token signalling that the iterator has reached the
// last element.
func (t *Iterator) Next() Token {
	if t.pos >= len(t.tokens) {
		return New(EOF, []byte{}, t.pos)
	}
	token := t.tokens[t.pos]
	t.pos++
	return token
}

// Backup moves the iterator one position back.
func (t *Iterator) Backup() {
	t.pos--
}

// New creates a Token with the given type, value and position
func New(typ Type, val []byte, pos int) Token {
	return elementToken{typ, val, pos}
}

// elementToken represents a token returned from the scanner.
type elementToken struct {
	typ Type   // Type, such as FLOAT
	val []byte // Value, such as "23.2".
	pos int    // position of token in input
}

func (e elementToken) Type() Type {
	return e.typ
}

func (e elementToken) Value() []byte {
	return e.val
}
func (e elementToken) Pos() int {
	return e.pos
}

func (e elementToken) IsSyntaxSymbol() bool {
	switch e.typ {
	case GROUP_DATA_ELEMENT_SEPARATOR:
		return true
	case DATA_ELEMENT_SEPARATOR:
		return true
	case SEGMENT_END_MARKER:
		return true
	default:
		return false
	}
}

func (e elementToken) String() string {
	switch e.typ {
	case EOF:
		return "EOF"
	case ERROR:
		return string(e.val)
	}
	if len(e.val) > 10 {
		return fmt.Sprintf("%s(%.10q...)", e.typ.String(), e.val)
	}
	return fmt.Sprintf("%s(%q)", e.typ.String(), e.val)
}

const (
	ILLEGAL Type = iota // An illegal/unknown character
	ERROR               // error occurred;

	DATA_ELEMENT_SEPARATOR       // Datenelement (DE)-Trennzeichen
	GROUP_DATA_ELEMENT_SEPARATOR // Gruppendatenelement (GD)-Trennzeichen
	SEGMENT_END_MARKER           // Segmentende-Zeichen
	BINARY_DATA_LENGTH           // Binärdaten Länge
	BINARY_DATA                  // Binärdaten
	BINARY_DATA_MARKER           // Binärdatenkennzeichen
	ALPHA_NUMERIC                // an
	TEXT                         // txt
	DTAUS_CHARSET                // dta
	NUMERIC                      // num: 0-9 without leading 0
	DIGIT                        // dig: 0-9 with optional leading 0
	FLOAT                        // float
	YES_NO                       // jn
	DATE                         // dat
	VIRTUAL_DATE                 // vdat
	TIME                         // tim
	IDENTIFICATION               // id
	COUNTRY_CODE                 // ctr: ISO 3166-1 numeric
	CURRENCY                     // cur: ISO 4217
	VALUE                        // wrt
	EOF
)

// Types implements the sort.Sort interface
type Types []Type

func (t Types) Len() int           { return len(t) }
func (t Types) Less(i, j int) bool { return t[i] < t[j] }
func (t Types) Swap(i, j int)      { t[i], t[j] = t[j], t[i] }

// Type identifies the type of lex tokens.
type Type int

var tokenName = map[Type]string{
	ERROR: "error",
	// value is text of error
	DATA_ELEMENT_SEPARATOR:       "dataElementSeparator",
	GROUP_DATA_ELEMENT_SEPARATOR: "groupDataElementSeparator",
	SEGMENT_END_MARKER:           "segmentEndMarker",
	BINARY_DATA_LENGTH:           "binaryDataLength",
	BINARY_DATA:                  "binaryData",
	BINARY_DATA_MARKER:           "binaryDataMarker",
	ALPHA_NUMERIC:                "alphaNumeric",
	TEXT:                         "text",
	DTAUS_CHARSET:                "dtausCharset",
	NUMERIC:                      "numeric",
	DIGIT:                        "digit",
	FLOAT:                        "float",
	YES_NO:                       "yesNo",
	DATE:                         "date",
	VIRTUAL_DATE:                 "virtualDate",
	TIME:                         "time",
	IDENTIFICATION:               "identification",
	COUNTRY_CODE:                 "countryCode",
	CURRENCY:                     "currency",
	VALUE:                        "value",
	EOF:                          "eof",
}

func (t Type) String() string {
	s := tokenName[t]
	if s == "" {
		return fmt.Sprintf("Token%d", int(t))
	}
	return s
}