Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 16 additions & 7 deletions docparser/model.go
Original file line number Diff line number Diff line change
Expand Up @@ -374,14 +374,23 @@ func replaceSchemaNameToCustom(s *schema) {
if len(refSplit) != 4 {
return
}

if replacementSchema, found := registeredSchemas[refSplit[3]]; found {
meta, ok := replacementSchema.(metaSchema)
meta, ok := replacementSchema.(*schema)
if !ok {
return
}
refSplit[3] = meta.CustomName()
switch meta.Type {
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So, this implem works, but I actually found where the ACTUAL issue is. This is more of a hack.

It works with struct thanks to this:

mtd.SetCustomName(entityName)

But this is not done for map or array. Everything should happen in:

func (spec *openAPI) parseSchemas(f *ast.File) (errors []error) {

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm guessing this would put the name of the alias as $ref which is what it did before the "break" so that's good.

Though I was considering going further and replacing it altogether by the target of the alias.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think that may require a bit of a rework, if I'm not mistaken. But I wouldn't mind the change, if you're up for it.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you think @denouche?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@denouche Do you have time to review this one?

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hey, sorry for the delay. I just took the time to read this thread.
If I understand well the debate is what to do between:

  • going further and replacing it by the target of the alias
  • or just fixing the initial issue
    ?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry for the delay as well, don't know how I missed your reply.

I think it could be done iteratively, first avoiding the issue and then going further but I would have to retest with new changes first.

case "array":
s.Ref = meta.Ref
s.Items = meta.Items
s.Type = meta.Type
break
default:
refSplit[3] = meta.CustomName()
s.Ref = strings.Join(refSplit, "/")
}
}
s.Ref = strings.Join(refSplit, "/")
}

func (spec *openAPI) composeSpecSchemas() {
Expand Down Expand Up @@ -459,7 +468,7 @@ func (spec *openAPI) parseStructs(f *ast.File, tpe *ast.StructType) (interface{}
e.Required = append(e.Required, j.name)
}

p, err := parseNamedType(f, fld.Type, nil)
p, err := parseNamedType(fld.Type, nil)
if err != nil {
logrus.WithError(err).WithField("field", fld.Names[0]).Error("Can't parse the type of field in struct")
errors = append(errors, BuildError{
Expand All @@ -486,7 +495,7 @@ func (spec *openAPI) parseStructs(f *ast.File, tpe *ast.StructType) (interface{}
}
}

p, err := parseNamedType(f, fld.Type, nil)
p, err := parseNamedType(fld.Type, nil)
if err != nil {
logrus.WithError(err).WithField("field", fld.Type).Error("Can't parse the type of composed field in struct")
errors = append(errors, BuildError{
Expand Down Expand Up @@ -567,7 +576,7 @@ func (spec *openAPI) parseSchemas(f *ast.File) (errors []error) {

case *ast.ArrayType:
e := newEntity()
p, err := parseNamedType(f, n.Elt, nil)
p, err := parseNamedType(n.Elt, nil)
if err != nil {
logrus.WithError(err).Error("Can't parse the type of field in struct")
errors = append(errors, &BuildError{
Expand All @@ -586,7 +595,7 @@ func (spec *openAPI) parseSchemas(f *ast.File) (errors []error) {
entity = &e

default:
p, err := parseNamedType(f, ts.Type, nil)
p, err := parseNamedType(ts.Type, nil)
if err != nil {
logrus.WithError(err).Error("can't parse custom type")
errors = append(errors, BuildError{
Expand Down
14 changes: 7 additions & 7 deletions docparser/parser.go
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ func parseJSONTag(field *ast.Field) (j jsonTagInfo, err error) {
return j, nil
}

func parseNamedType(gofile *ast.File, expr ast.Expr, sel *ast.Ident) (*schema, error) {
func parseNamedType(expr ast.Expr, sel *ast.Ident) (*schema, error) {
p := schema{}
switch ftpe := expr.(type) {
case *ast.Ident: // simple value
Expand All @@ -98,7 +98,7 @@ func parseNamedType(gofile *ast.File, expr ast.Expr, sel *ast.Ident) (*schema, e
p.Format = format
return &p, nil
case *ast.StarExpr: // pointer to something, optional by default
t, err := parseNamedType(gofile, ftpe.X, sel)
t, err := parseNamedType(ftpe.X, sel)
if err != nil {
return nil, err
}
Expand All @@ -109,7 +109,7 @@ func parseNamedType(gofile *ast.File, expr ast.Expr, sel *ast.Ident) (*schema, e
}
return t, nil
case *ast.ArrayType: // slice type
cp, err := parseNamedType(gofile, ftpe.Elt, sel)
cp, err := parseNamedType(ftpe.Elt, sel)
if err != nil {
return nil, err
}
Expand Down Expand Up @@ -144,7 +144,7 @@ func parseNamedType(gofile *ast.File, expr ast.Expr, sel *ast.Ident) (*schema, e
return nil, err
}

pnt, err := parseNamedType(gofile, field.Type, nil)
pnt, err := parseNamedType(field.Type, nil)
if err != nil {
return nil, err
}
Expand All @@ -155,15 +155,15 @@ func parseNamedType(gofile *ast.File, expr ast.Expr, sel *ast.Ident) (*schema, e

return &p, nil
case *ast.SelectorExpr:
t, err := parseNamedType(gofile, ftpe.X, ftpe.Sel)
t, err := parseNamedType(ftpe.X, ftpe.Sel)
if err != nil {
return nil, err
}

return t, nil
case *ast.MapType:
k, kerr := parseNamedType(gofile, ftpe.Key, sel)
v, verr := parseNamedType(gofile, ftpe.Value, sel)
k, kerr := parseNamedType(ftpe.Key, sel)
v, verr := parseNamedType(ftpe.Value, sel)
if kerr != nil || verr != nil || k.Type != "string" {
// keys can only be of type string
return nil, fmt.Errorf("expr (%s) not yet unsupported", expr)
Expand Down
56 changes: 28 additions & 28 deletions docparser/parser_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -139,32 +139,6 @@ func TestParseNamedType(t *testing.T) {
},
}},
},
{
description: "Should *ast.ArrayType with *ast.StructType",
expr: &ast.ArrayType{
Elt: &ast.StructType{
Fields: &ast.FieldList{
List: []*ast.Field{
{
Type: &ast.Ident{Name: "string"},
Tag: &ast.BasicLit{Value: "`json:\"str\"`"},
},
},
},
},
},
expectedSchema: &schema{
Type: "array",
Items: map[string]interface{}{
"type": "object",
"properties": map[string]*schema{
"str": {
Type: "string",
},
},
},
},
},
{
description: "Should *ast.StructType to anonymous struct",
expr: &ast.StructType{
Expand Down Expand Up @@ -276,10 +250,36 @@ func TestParseNamedType(t *testing.T) {
expr: &ast.FuncType{},
expectedError: "expr (&{%!s(token.Pos=0) %!s(*ast.FieldList=<nil>) %!s(*ast.FieldList=<nil>)}) type (&{%!s(token.Pos=0) %!s(*ast.FieldList=<nil>) %!s(*ast.FieldList=<nil>)}) is unsupported for a schema",
},
{
description: "Should *ast.ArrayType with *ast.StructType",
expr: &ast.ArrayType{
Elt: &ast.StructType{
Fields: &ast.FieldList{
List: []*ast.Field{
{
Type: &ast.Ident{Name: "string"},
Tag: &ast.BasicLit{Value: "`json:\"str\"`"},
},
},
},
},
},
expectedSchema: &schema{
Type: "array",
Items: map[string]interface{}{
"type": "object",
"properties": map[string]*schema{
"str": {
Type: "string",
},
},
},
},
},
}
for _, tc := range testCases {
t.Run(tc.description, func(t *testing.T) {
schema, err := parseNamedType(tc.gofile, tc.expr, nil)
schema, err := parseNamedType(tc.expr, nil)
if len(tc.expectedError) > 0 {
if (err != nil) && (err.Error() != tc.expectedError) {
t.Errorf("got error: %v, wantErr: %v", err, tc.expectedError)
Expand Down Expand Up @@ -547,4 +547,4 @@ func TestParseIdentProperty(t *testing.T) {
}
})
}
}
}