-
Notifications
You must be signed in to change notification settings - Fork 6
/
converter.go
106 lines (95 loc) · 3.19 KB
/
converter.go
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
package iconv
import (
"bytes"
"errors"
"io"
"io/ioutil"
"golang.org/x/text/encoding/charmap"
"golang.org/x/text/encoding/japanese"
"golang.org/x/text/encoding/simplifiedchinese"
"golang.org/x/text/encoding/traditionalchinese"
"golang.org/x/text/transform"
)
var (
ErrNotSupportCharset = errors.New("not support this charset for now")
)
var (
UTF8 = "UTF-8"
GBK = "GBK"
GB18030 = "GB-18030"
HZGB2312 = "HZ-GB2312"
Big5 = "Big5"
ISO88591 = "ISO-8859-1"
EUCJP = "EUC-JP"
ShiftJIS = "Shift_JIS"
charsets = []string{GBK, GB18030, Big5, ISO88591, EUCJP, ShiftJIS, HZGB2312}
charsetMap = map[string]transform.Transformer{}
)
// Converter ...
type Converter struct {
fromEncoding string
toEncoding string
}
func init() {
for _, charset := range charsets {
switch charset {
case GBK:
charsetMap[GBK+UTF8] = simplifiedchinese.GBK.NewDecoder()
charsetMap[UTF8+GBK] = simplifiedchinese.GBK.NewEncoder()
case GB18030:
charsetMap[GB18030+UTF8] = simplifiedchinese.GB18030.NewDecoder()
charsetMap[UTF8+GB18030] = simplifiedchinese.GB18030.NewEncoder()
case Big5:
charsetMap[Big5+UTF8] = traditionalchinese.Big5.NewDecoder()
charsetMap[UTF8+Big5] = traditionalchinese.Big5.NewEncoder()
case ISO88591:
charsetMap[ISO88591+UTF8] = charmap.ISO8859_1.NewDecoder()
charsetMap[UTF8+ISO88591] = charmap.ISO8859_1.NewEncoder()
case EUCJP:
charsetMap[EUCJP+UTF8] = japanese.EUCJP.NewDecoder()
charsetMap[UTF8+EUCJP] = japanese.EUCJP.NewEncoder()
case ShiftJIS:
charsetMap[ShiftJIS+UTF8] = japanese.ShiftJIS.NewDecoder()
charsetMap[UTF8+ShiftJIS] = japanese.ShiftJIS.NewEncoder()
case HZGB2312:
charsetMap[HZGB2312+UTF8] = simplifiedchinese.HZGB2312.NewDecoder()
charsetMap[UTF8+HZGB2312] = simplifiedchinese.HZGB2312.NewEncoder()
}
}
}
// NewConverter Initialize a new Converter. If fromEncoding or toEncoding are not supported
// then an error will be returned.
func NewConverter(fromEncoding string, toEncoding string) (*Converter, error) {
_, fromOK := charsetMap[fromEncoding+UTF8]
_, toOK := charsetMap[UTF8+toEncoding]
if _, ok := charsetMap[fromEncoding+toEncoding]; ok || (fromOK && toOK) {
return &Converter{fromEncoding: fromEncoding, toEncoding: toEncoding}, nil
}
return nil, ErrNotSupportCharset
}
// ConvertString Convert an input string
func (t *Converter) ConvertString(input string) (string, error) {
res, err := t.ConvertBytes([]byte(input))
if err != nil {
return "", err
}
return string(res), nil
}
// ConvertBytes ...
func (t *Converter) ConvertBytes(input []byte) ([]byte, error) {
reader := t.Convert(bytes.NewReader(input))
return ioutil.ReadAll(reader)
}
// Convert ...
func (t *Converter) Convert(reader io.Reader) io.Reader {
return t.convert(reader)
}
func (t *Converter) convert(reader io.Reader) io.Reader {
srcToDst := t.fromEncoding + t.toEncoding
if val, ok := charsetMap[srcToDst]; ok {
return transform.NewReader(reader, val)
}
resReader := transform.NewReader(reader, charsetMap[t.fromEncoding+UTF8])
resReader = transform.NewReader(resReader, charsetMap[UTF8+t.toEncoding])
return resReader
}