Skip to content

Commit

Permalink
Update jsonschema output for booleans and timestamps (mcuadros#5)
Browse files Browse the repository at this point in the history
* Update bool type -> boolean

* Add support for time.Time JSONSchema format
  • Loading branch information
CJ authored and mcuadros committed Nov 22, 2016
1 parent e4349fe commit b230f13
Show file tree
Hide file tree
Showing 2 changed files with 34 additions and 22 deletions.
45 changes: 27 additions & 18 deletions jsonschema.go
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ func (d *Document) String() string {

type property struct {
Type string `json:"type,omitempty"`
Format string `json:"format,omitempty"`
Items *item `json:"items,omitempty"`
Properties map[string]*property `json:"properties,omitempty"`
Required []string `json:"required,omitempty"`
Expand All @@ -55,11 +56,13 @@ type item struct {
}

func (p *property) read(t reflect.Type, opts tagOptions) {
kind := t.Kind()

if jsType := getTypeFromMapping(kind); jsType != "" {
jsType, format, kind := getTypeFromMapping(t)
if jsType != "" {
p.Type = jsType
}
if format != "" {
p.Format = format
}

switch kind {
case reflect.Slice:
Expand All @@ -74,22 +77,20 @@ func (p *property) read(t reflect.Type, opts tagOptions) {
}

func (p *property) readFromSlice(t reflect.Type) {
k := t.Elem().Kind()
if k == reflect.Uint8 {
jsType, _, kind := getTypeFromMapping(t.Elem())
if kind == reflect.Uint8 {
p.Type = "string"
} else {
if jsType := getTypeFromMapping(k); jsType != "" {
p.Items = &item{Type: jsType}
}
} else if jsType != "" {
p.Items = &item{Type: jsType}
}
}

func (p *property) readFromMap(t reflect.Type) {
k := t.Elem().Kind()
jsType, format, _ := getTypeFromMapping(t.Elem())

if jsType := getTypeFromMapping(k); jsType != "" {
if jsType != "" {
p.Properties = make(map[string]*property, 0)
p.Properties[".*"] = &property{Type: jsType}
p.Properties[".*"] = &property{Type: jsType, Format: format}
} else {
p.AdditionalProperties = true
}
Expand Down Expand Up @@ -122,8 +123,12 @@ func (p *property) readFromStruct(t reflect.Type) {
}
}

var mapping = map[reflect.Kind]string{
reflect.Bool: "bool",
var formatMapping = map[string][]string{
"time.Time": []string{"string", "date-time"},
}

var kindMapping = map[reflect.Kind]string{
reflect.Bool: "boolean",
reflect.Int: "integer",
reflect.Int8: "integer",
reflect.Int16: "integer",
Expand All @@ -142,12 +147,16 @@ var mapping = map[reflect.Kind]string{
reflect.Map: "object",
}

func getTypeFromMapping(k reflect.Kind) string {
if t, ok := mapping[k]; ok {
return t
func getTypeFromMapping(t reflect.Type) (string, string, reflect.Kind) {
if v, ok := formatMapping[t.String()]; ok {
return v[0], v[1], reflect.String
}

if v, ok := kindMapping[t.Kind()]; ok {
return v, "", t.Kind()
}

return ""
return "", "", t.Kind()
}

type tagOptions string
Expand Down
11 changes: 7 additions & 4 deletions jsonschema_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package jsonschema

import (
"testing"
"time"

. "gopkg.in/check.v1"
)
Expand All @@ -13,7 +14,7 @@ type propertySuite struct{}
var _ = Suite(&propertySuite{})

type ExampleJSONBasic struct {
Omitted string `json:"-,omitempty"`
Omitted string `json:"-,omitempty"`
Bool bool `json:",omitempty"`
Integer int `json:",omitempty"`
Integer8 int8 `json:",omitempty"`
Expand All @@ -30,6 +31,7 @@ type ExampleJSONBasic struct {
Float32 float32 `json:",omitempty"`
Float64 float64
Interface interface{}
Timestamp time.Time `json:",omitempty"`
}

func (self *propertySuite) TestLoad(c *C) {
Expand All @@ -42,7 +44,7 @@ func (self *propertySuite) TestLoad(c *C) {
Type: "object",
Required: []string{"Float64", "Interface"},
Properties: map[string]*property{
"Bool": &property{Type: "bool"},
"Bool": &property{Type: "boolean"},
"Integer": &property{Type: "integer"},
"Integer8": &property{Type: "integer"},
"Integer16": &property{Type: "integer"},
Expand All @@ -58,6 +60,7 @@ func (self *propertySuite) TestLoad(c *C) {
"Float32": &property{Type: "number"},
"Float64": &property{Type: "number"},
"Interface": &property{},
"Timestamp": &property{Type: "string", Format: "date-time"},
},
},
})
Expand All @@ -77,7 +80,7 @@ func (self *propertySuite) TestLoadWithTag(c *C) {
Type: "object",
Required: []string{"test"},
Properties: map[string]*property{
"test": &property{Type: "bool"},
"test": &property{Type: "boolean"},
},
},
})
Expand Down Expand Up @@ -189,7 +192,7 @@ func (self *propertySuite) TestString(c *C) {

expected := "{\n" +
" \"$schema\": \"http://json-schema.org/schema#\",\n" +
" \"type\": \"bool\"\n" +
" \"type\": \"boolean\"\n" +
"}"

c.Assert(j.String(), Equals, expected)
Expand Down

0 comments on commit b230f13

Please sign in to comment.