Closed reyesdiego closed 1 year ago
OpenAPI reflector already supports embeddings of maps and slices, however standard encoding/json
does not (to my best knowledge), so you need to implement a custom marshaler on your output structure to overcome the limitation.
package main
import (
"context"
"encoding/json"
"github.com/swaggest/rest/web"
swgui "github.com/swaggest/swgui/v4emb"
"github.com/swaggest/usecase"
"log"
"net/http"
)
type Vehicle struct {
Name string `json:"name"`
}
type Vehicles []Vehicle
// Declare output port type.
type helloOutput struct {
Total int `header:"X-Total-Count" json:"-"`
Vehicles
}
func (ho helloOutput) MarshalJSON() ([]byte, error) {
return json.Marshal(ho.Vehicles)
}
func main() {
s := web.DefaultService()
// Create use case interactor with references to input/output types and interaction function.
u := usecase.NewInteractor(func(ctx context.Context, input struct{}, output *helloOutput) error {
output.Vehicles = Vehicles{Vehicle{Name: "foo"}, Vehicle{Name: "bar"}}
output.Total = 2
return nil
})
// Add use case handler to router.
s.Get("/hello", u)
// Swagger UI endpoint at /docs.
s.Docs("/docs", swgui.New)
// Start server.
log.Println("http://localhost:8011/docs")
if err := http.ListenAndServe("localhost:8011", s); err != nil {
log.Fatal(err)
}
}
Viacheslav ! Thank you very much. Actually it was a philosophical discussion to use or not to use an envelop for the arrays results, the fact is that I am migrating from node to Go and the frontend it using without enveloping the arrays. Anyway, I really appreciate your answer. And I'm sorry, I opened and Issue which may be it was not :)
I personally prefer to avoid unnecessary contract changes, so if an existing API uses plain arrays, I'd rather keep them, so that clients don't have to upgrade. And no worries about opening the issue, all questions are welcome (especially this case is a bit tricky)!
I would like to be able to return (when paginating) an array in the response body and the total count of the query in a header response X-Total-Count. But If I set a struct for the response like for instance // Declare output port type. type helloOutput struct { TotalCount int64
header:"X-Total-Count" json:"-"
Data []Vehiclesjson:"vehicles"
} I need the response to be [{ vehicle:1 },{ vehicle:2} ] and NOT { data: [{ vehicle:1 },{ vehicle:2} ] }Is there any suggestion ?