support of decoding for Stringers

This commit is contained in:
Francesc Campoy 2015-01-31 12:21:55 +01:00
parent a673e22384
commit 5cd7ec204a
5 changed files with 70 additions and 22 deletions

View File

@ -6,8 +6,10 @@ package main
import ( import (
"encoding/json" "encoding/json"
"fmt"
"log" "log"
"os" "os"
"strings"
) )
//go:generate jsonenums -type=ShirtSize //go:generate jsonenums -type=ShirtSize
@ -37,6 +39,27 @@ const (
Sunday Sunday
) )
func (d WeekDay) String() string {
switch d {
case Monday:
return "Dilluns"
case Tuesday:
return "Dimarts"
case Wednesday:
return "Dimecres"
case Thursday:
return "Dijous"
case Friday:
return "Divendres"
case Saturday:
return "Dissabte"
case Sunday:
return "Diumenge"
default:
return "invalid WeekDay"
}
}
func main() { func main() {
v := struct { v := struct {
Size ShirtSize Size ShirtSize
@ -45,4 +68,10 @@ func main() {
if err := json.NewEncoder(os.Stdout).Encode(v); err != nil { if err := json.NewEncoder(os.Stdout).Encode(v); err != nil {
log.Fatal(err) log.Fatal(err)
} }
input := `{"Size":"XL", "Day":"Dimarts"}`
if err := json.NewDecoder(strings.NewReader(input)).Decode(&v); err != nil {
log.Fatal(err)
}
fmt.Printf("decoded %s as %+v\n", input, v)
} }

View File

@ -7,15 +7,13 @@ import (
"fmt" "fmt"
) )
var _ShirtSizeValueToName = map[ShirtSize]string{
NA: "NA", XS: "XS", S: "S", M: "M", L: "L", XL: "XL",
}
func (r ShirtSize) MarshalJSON() ([]byte, error) { func (r ShirtSize) MarshalJSON() ([]byte, error) {
if s, ok := r.(fmt.Stringer); ok { if s, ok := interface{}(r).(fmt.Stringer); ok {
return json.Marshal(s.String()) return json.Marshal(s.String())
} }
s, ok := _ShirtSizeValueToName[r] s, ok := map[ShirtSize]string{
NA: "NA", XS: "XS", S: "S", M: "M", L: "L", XL: "XL",
}[r]
if !ok { if !ok {
return nil, fmt.Errorf("invalid ShirtSize: %d", r) return nil, fmt.Errorf("invalid ShirtSize: %d", r)
} }
@ -26,6 +24,15 @@ var _ShirtSizeNameToValue = map[string]ShirtSize{
"NA": NA, "XS": XS, "S": S, "M": M, "L": L, "XL": XL, "NA": NA, "XS": XS, "S": S, "M": M, "L": L, "XL": XL,
} }
func init() {
var v ShirtSize
if _, ok := interface{}(v).(fmt.Stringer); ok {
_ShirtSizeNameToValue = map[string]ShirtSize{
interface{}(NA).(fmt.Stringer).String(): NA, interface{}(XS).(fmt.Stringer).String(): XS, interface{}(S).(fmt.Stringer).String(): S, interface{}(M).(fmt.Stringer).String(): M, interface{}(L).(fmt.Stringer).String(): L, interface{}(XL).(fmt.Stringer).String(): XL,
}
}
}
func (r *ShirtSize) UnmarshalJSON(data []byte) error { func (r *ShirtSize) UnmarshalJSON(data []byte) error {
var s string var s string
if err := json.Unmarshal(data, &s); err != nil { if err := json.Unmarshal(data, &s); err != nil {

View File

@ -7,15 +7,13 @@ import (
"fmt" "fmt"
) )
var _WeekDayValueToName = map[WeekDay]string{
Monday: "Monday", Tuesday: "Tuesday", Wednesday: "Wednesday", Thursday: "Thursday", Friday: "Friday", Saturday: "Saturday", Sunday: "Sunday",
}
func (r WeekDay) MarshalJSON() ([]byte, error) { func (r WeekDay) MarshalJSON() ([]byte, error) {
if s, ok := r.(fmt.Stringer); ok { if s, ok := interface{}(r).(fmt.Stringer); ok {
return json.Marshal(s.String()) return json.Marshal(s.String())
} }
s, ok := _WeekDayValueToName[r] s, ok := map[WeekDay]string{
Monday: "Monday", Tuesday: "Tuesday", Wednesday: "Wednesday", Thursday: "Thursday", Friday: "Friday", Saturday: "Saturday", Sunday: "Sunday",
}[r]
if !ok { if !ok {
return nil, fmt.Errorf("invalid WeekDay: %d", r) return nil, fmt.Errorf("invalid WeekDay: %d", r)
} }
@ -26,6 +24,15 @@ var _WeekDayNameToValue = map[string]WeekDay{
"Monday": Monday, "Tuesday": Tuesday, "Wednesday": Wednesday, "Thursday": Thursday, "Friday": Friday, "Saturday": Saturday, "Sunday": Sunday, "Monday": Monday, "Tuesday": Tuesday, "Wednesday": Wednesday, "Thursday": Thursday, "Friday": Friday, "Saturday": Saturday, "Sunday": Sunday,
} }
func init() {
var v WeekDay
if _, ok := interface{}(v).(fmt.Stringer); ok {
_WeekDayNameToValue = map[string]WeekDay{
interface{}(Monday).(fmt.Stringer).String(): Monday, interface{}(Tuesday).(fmt.Stringer).String(): Tuesday, interface{}(Wednesday).(fmt.Stringer).String(): Wednesday, interface{}(Thursday).(fmt.Stringer).String(): Thursday, interface{}(Friday).(fmt.Stringer).String(): Friday, interface{}(Saturday).(fmt.Stringer).String(): Saturday, interface{}(Sunday).(fmt.Stringer).String(): Sunday,
}
}
}
func (r *WeekDay) UnmarshalJSON(data []byte) error { func (r *WeekDay) UnmarshalJSON(data []byte) error {
var s string var s string
if err := json.Unmarshal(data, &s); err != nil { if err := json.Unmarshal(data, &s); err != nil {

View File

@ -154,8 +154,7 @@ type Package struct {
name string name string
files []*ast.File files []*ast.File
defs map[*ast.Ident]types.Object defs map[*ast.Ident]types.Object
types *types.Package
} }
// parsePackage parses the package in the given directory and returns it. // parsePackage parses the package in the given directory and returns it.
@ -188,8 +187,7 @@ func parsePackage(directory string, skipSuffix string) (*Package, error) {
defs := make(map[*ast.Ident]types.Object) defs := make(map[*ast.Ident]types.Object)
config := types.Config{FakeImportC: true} config := types.Config{FakeImportC: true}
info := &types.Info{Defs: defs} info := &types.Info{Defs: defs}
types, err := config.Check(directory, fs, files, info) if _, err := config.Check(directory, fs, files, info); err != nil {
if err != nil {
return nil, fmt.Errorf("type-checking package: %v", err) return nil, fmt.Errorf("type-checking package: %v", err)
} }
@ -197,7 +195,6 @@ func parsePackage(directory string, skipSuffix string) (*Package, error) {
name: files[0].Name.Name, name: files[0].Name.Name,
files: files, files: files,
defs: defs, defs: defs,
types: types,
}, nil }, nil
} }

View File

@ -19,15 +19,14 @@ import (
) )
{{range $typename, $values := .TypesAndValues}} {{range $typename, $values := .TypesAndValues}}
var _{{$typename}}ValueToName = map[{{$typename}}]string {
{{range $values}}{{.}}: "{{.}}",{{end}}
}
func (r {{$typename}}) MarshalJSON() ([]byte, error) { func (r {{$typename}}) MarshalJSON() ([]byte, error) {
if s, ok := r.(fmt.Stringer); ok { if s, ok := interface{}(r).(fmt.Stringer); ok {
return json.Marshal(s.String()) return json.Marshal(s.String())
} }
s, ok := _{{$typename}}ValueToName[r] s, ok := map[{{$typename}}]string {
{{range $values}}{{.}}: "{{.}}",{{end}}
}[r]
if !ok { if !ok {
return nil, fmt.Errorf("invalid {{$typename}}: %d", r) return nil, fmt.Errorf("invalid {{$typename}}: %d", r)
} }
@ -38,6 +37,15 @@ var _{{$typename}}NameToValue = map[string]{{$typename}} {
{{range $values}}"{{.}}": {{.}},{{end}} {{range $values}}"{{.}}": {{.}},{{end}}
} }
func init() {
var v {{$typename}}
if _, ok := interface{}(v).(fmt.Stringer); ok {
_{{$typename}}NameToValue = map[string]{{$typename}} {
{{range $values}}interface{}({{.}}).(fmt.Stringer).String(): {{.}},{{end}}
}
}
}
func (r *{{$typename}}) UnmarshalJSON(data []byte) error { func (r *{{$typename}}) UnmarshalJSON(data []byte) error {
var s string var s string
if err := json.Unmarshal(data, &s); err != nil { if err := json.Unmarshal(data, &s); err != nil {