在swagger ui中如何展示模型
来源:stackoverflow
2024-02-28 08:42:25
0浏览
收藏
本篇文章给大家分享《在swagger ui中如何展示模型》,覆盖了Golang的常见基础知识,其实一个语言的全部知识点一篇文章是不可能说完的,但希望通过这些问题,让读者对自己的掌握程度有一定的认识(B 数),从而弥补自己的不足,更好的掌握它。
问题内容
我有一本用 golang 构建的书本 api,一切正常,我正在尝试为文档添加 swagger,我已经做到了,但我遇到了问题,我只能看到路线,但是当我点击它,看不到描述,也看不到任何型号信息, 这是我在 main.go 上的代码
package main
import (
//"fmt"
"time"
"github.com/cosimmichael/assessment/app/db_client"
"github.com/cosimmichael/assessment/app/controllers"
"github.com/gin-gonic/gin"
"github.com/gin-contrib/cors"
// "github.com/swaggo/gin-swagger"
// "github.com/swaggo/files"
//"github.com/swaggo/swag/example/celler/controller"
//_ "github.com/swaggo/swag/example/celler/docs"
_ "github.com/cosimmichael/assessment/app/docs"
//"github.com/swaggo/swag/example/celler/httputil"
swaggerfiles "github.com/swaggo/files"
ginswagger "github.com/swaggo/gin-swagger"
// you need to import go mod init for this parkage to work
// "github.com/cosimmichael/assessment/app/strutil"
// "github.com/cosimmichael/assessment/app/routers"
// "net/http"
)
// @title simple book dashboard api
// @version 1.0
// @description this is for book management.
// @termsofservice http://swagger.io/terms/
// @contact.name books api support
// @contact.url http://www.swagger.io/support
// @contact.email [email protected]
// @license.name apache 2.0
// @license.url http://www.apache.org/licenses/license-2.0.html
// @host localhost:3000
// @basepath /api/v1/products
// @query.collection.format multi
// @securitydefinitions.basic basicauth
// @securitydefinitions.apikey apikeyauth
// @in header
// @name authorization, x-api-key
// @securitydefinitions.oauth2.application oauth2application
// @tokenurl https://example.com/oauth/token
// @scope.write grants write access
// @scope.admin grants read and write access to administrative information
// @securitydefinitions.oauth2.implicit oauth2implicit
// @authorizationurl https://example.com/oauth/authorize
// @scope.write grants write access
// @scope.admin grants read and write access to administrative information
// @securitydefinitions.oauth2.password oauth2password
// @tokenurl https://example.com/oauth/token
// @scope.read grants read access
// @scope.write grants write access
// @scope.admin grants read and write access to administrative information
// @securitydefinitions.oauth2.accesscode oauth2accesscode
// @tokenurl https://example.com/oauth/token
// @authorizationurl https://example.com/oauth/authorize
// @scope.admin grants read and write access to administrative information
// @x-extension-openapi {"example": "value on a json format"}
func main(){
db_client.initialisedbconnection()
r := gin.default()
//r.use(cors.default())
r.use(cors.new(cors.config{
alloworigins: []string{"http://localhost:8080"},
allowmethods: []string{"put", "patch","post","get","delete"},
allowheaders: []string{"origin","authorization","x-api-key","content-type"},
exposeheaders: []string{"content-length"},
allowcredentials: true,
alloworiginfunc: func(origin string) bool {
return origin == "http://localhost:8080"
},
maxage: 12 * time.hour,
}))
// router.handleroutes()
r.post("api/v1/products/login", controller.login)
r.post("api/v1/products/create", controller.createproducts)
r.get("api/v1/products", controller.getproducts)
r.get("api/v1/products/:id/show", controller.getsingleproduct)
r.put("api/v1/products/:id/update", controller.updatesingleproduct)
r.delete("api/v1/products/:id/delete", controller.deletesingleproduct)
//r.post("api/v1/products/check", controller.checkheader)
r.get("/swagger/*any", ginswagger.wraphandler(swaggerfiles.handler))
if err := r.run(":3000"); err != nil {
panic(err.error())
}
// router.handleroutes()
// fmt.println("server starting.. @ port :3000")
// http.listenandserve(":3000", nil)
}
这是我在控制器上的代码
package controller
import (
"net/http"
"strconv"
"github.com/gin-gonic/gin"
"github.com/cosimmichael/assessment/app/db_client"
"github.com/cosimmichael/assessment/app/model"
// "github.com/swaggo/swag/example/celler/httputil"
// "github.com/swaggo/swag/example/celler/model"
)
type testheader struct {
token string `header:"x-api-key"`
}
// login godoc
// @summary log in to admin account
// @description authentication
// @id get-string-by-int
// @accept json
// @produce json
// @param admin body admin true "add account"
// @router /login [post]
func login(c *gin.context) {
var reqbody model.admin
if err := c.shouldbindjson(&reqbody); err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
row := db_client.dbclient.queryrow("select id, username, password from admin where username = ?;", reqbody.username)
var myacc model.admin
if err := row.scan(&myacc.id, &myacc.username, &myacc.password); err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "something is wrong with request",
})
return
}
if myacc.password == reqbody.password {
c.json(http.statuscreated, gin.h{
"error": false,
"user": myacc.username,
"token": "7b215b90-df8d-4077-8852-0907b0c1034e",
})
return
}else{
c.json(http.statuscreated, gin.h{
"error": true,
"message": "invalid details",
})
return
}
}
// createproducts godoc
// @summary create new book
// @description saving new book detail
// @id get-string-by-int
// @accept json
// @produce json
// @param post body post true "add post"
// @router /create [post]
func createproducts(c *gin.context) {
h := testheader{}
if err := c.shouldbindheader(&h); err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "access denied",
})
return
}
if h.token != "7b215b90-df8d-4077-8852-0907b0c1034e"{
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid access",
})
return
}
var reqbody model.post
if err := c.shouldbindjson(&reqbody); err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
if reqbody.title == ""{
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "insert product title",
})
return
}
var posts []model.post
rows, err := db_client.dbclient.query("select id, title, description from products;")
if err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
for rows.next(){
var singlepost model.post
rows.scan(&singlepost.id, &singlepost.title, &singlepost.description)
if singlepost.title == reqbody.title {
c.json(http.statuscreated, gin.h{
"error": true,
"message": "title already exists",
})
return
}
posts = append(posts, singlepost)
}
res, err := db_client.dbclient.exec("insert into products (title, description) values (?, ?);",
reqbody.title,//"testing",
reqbody.description,//"just testing something",
)
if err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid request body2",
})
return
}
id, err := res.lastinsertid()
if err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid request body3",
})
return
}
c.json(http.statuscreated, gin.h{
"error": false,
"id": id,
})
}
// getproducts godoc
// @summary get all books info
// @description fetch all books from database
// @id get-string-by-int
// @accept json
// @produce json
// @router / [get]
func getproducts(c *gin.context){
var posts []model.post
h := testheader{}
if err := c.shouldbindheader(&h); err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "access denied",
})
return
}
if h.token != "7b215b90-df8d-4077-8852-0907b0c1034e"{
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid access",
})
return
}
rows, err := db_client.dbclient.query("select id, title, description from products;")
if err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
for rows.next(){
var singlepost model.post
if err := rows.scan(&singlepost.id, &singlepost.title, &singlepost.description); err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
posts = append(posts, singlepost)
}
c.json(http.statusok, posts)
}
// getsingleproduct godoc
// @summary get a single book info
// @description fetch a book from database by id
// @id get-string-by-int
// @accept json
// @produce json
// @param id path int true "post id"
// @router /:id/show [get]
func getsingleproduct(c *gin.context){
idstr := c.param("id")
id, _ := strconv.atoi(idstr)
h := testheader{}
if err := c.shouldbindheader(&h); err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "access denied",
})
return
}
if h.token != "7b215b90-df8d-4077-8852-0907b0c1034e"{
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid access",
})
return
}
row := db_client.dbclient.queryrow("select id, title, description from products where id = ?;", id)
var post model.post
if err := row.scan(&post.id, &post.title, &post.description); err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "something is wrong with request",
})
return
}
c.json(http.statusok, post)
}
// updatesingleproduct godoc
// @summary get a books info
// @description change info of a book
// @id get-string-by-int
// @accept json
// @produce json
// // @param id path int true "post id"
// @router /:id/update [put]
func updatesingleproduct(c *gin.context){
var reqbody model.post
h := testheader{}
if err := c.shouldbindheader(&h); err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "access denied",
})
return
}
if h.token != "7b215b90-df8d-4077-8852-0907b0c1034e"{
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid access",
})
return
}
idstr := c.param("id")
id, _ := strconv.atoi(idstr)
if err := c.shouldbindjson(&reqbody); err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
if reqbody.title == ""{
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "insert product title",
})
return
}
//checking if user changed the title value
row := db_client.dbclient.queryrow("select id, title, description from products where id = ?;", id)
var post model.post
row.scan(&post.id, &post.title, &post.description)
if post.title != reqbody.title {
//user changed tille
var posts []model.post
rows, _ := db_client.dbclient.query("select id, title, description from products;")
for rows.next(){
var singlepost model.post
rows.scan(&singlepost.id, &singlepost.title, &singlepost.description)
if singlepost.title == reqbody.title {
c.json(http.statuscreated, gin.h{
"error": true,
"message": "another product already has this title",
})
return
}
posts = append(posts, singlepost)
}
}
_, err := db_client.dbclient.exec("update products set title = ?, description = ? where id = ?;",
reqbody.title,
reqbody.description,
id,
)
if err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid request body2",
})
return
}
c.json(http.statuscreated, gin.h{
"error": false,
"id": id,
"newtitle": reqbody.title,
"newdescription": reqbody.description,
})
}
// deletesingleproduct godoc
// @summary delete a book
// @description remove a book from database
// @id get-string-by-int
// @accept json
// @produce json
// @param id path int true "post id"
// @router /:id/delete [delete]
func deletesingleproduct(c *gin.context){
idstr := c.param("id")
id, _ := strconv.atoi(idstr)
h := testheader{}
if err := c.shouldbindheader(&h); err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "access denied",
})
return
}
if h.token != "7b215b90-df8d-4077-8852-0907b0c1034e"{
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid access",
})
return
}
_,err := db_client.dbclient.exec("delete from products where id = ?;", id)
if err != nil {
c.json(http.statusinternalservererror, gin.h{
"error": true,
"message": "invalid request body2",
})
return
}
var posts []model.post
rows, err := db_client.dbclient.query("select id, title, description from products;")
if err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
for rows.next(){
var singlepost model.post
if err := rows.scan(&singlepost.id, &singlepost.title, &singlepost.description); err != nil {
c.json(http.statusunprocessableentity, gin.h{
"error": true,
"message": "invalid request body",
})
return
}
posts = append(posts, singlepost)
}
c.json(http.statusok, posts)
}
关于管理模型
package model
// admin example
type admin struct {
id int64 `json: "id" example:"1"`
username string `json: "username" example:"admin name"`
password string `json: "password" example:"h56yggy7uj"`
}
我的帖子模型
package model
type Post struct {
ID int64 `json: "id"`
Title string `json: "title"`
Description *string `json: "description"`
}
请我不知道我做错了什么,我需要帮助,因为我希望显示所有信息
正确答案
swagger 使用注释来生成文档和描述,注释行之间不应有空格。我所做的只是删除评论之间的空行
好了,本文到此结束,带大家了解了《在swagger ui中如何展示模型》,希望本文对你有所帮助!关注golang学习网公众号,给大家分享更多Golang知识!
版本声明
本文转载于:stackoverflow 如有侵犯,请联系study_golang@163.com删除
利用字符串分割和键值对创建嵌套映射
- 上一篇
- 利用字符串分割和键值对创建嵌套映射
- 下一篇
- 比亚迪秦 PLUS 荣耀版发布,引领“电动节油”时代,起价7.98万
查看更多
最新文章
-
- Golang · Go问答 | 1年前 |
- 在读取缓冲通道中的内容之前退出
- 139浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 戈兰岛的全球 GOPRIVATE 设置
- 204浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 如何将结构作为参数传递给 xml-rpc
- 325浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 如何用golang获得小数点以下两位长度?
- 478浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 如何通过 client-go 和 golang 检索 Kubernetes 指标
- 486浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 将多个“参数”映射到单个可变参数的习惯用法
- 439浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 将 HTTP 响应正文写入文件后出现 EOF 错误
- 357浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 结构中映射的匿名列表的“复合文字中缺少类型”
- 352浏览 收藏
-
- Golang · Go问答 | 1年前 |
- NATS Jetstream 的性能
- 101浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 如何将复杂的字符串输入转换为mapstring?
- 440浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 相当于GoLang中Java将Object作为方法参数传递
- 212浏览 收藏
-
- Golang · Go问答 | 1年前 |
- 如何确保所有 goroutine 在没有 time.Sleep 的情况下终止?
- 143浏览 收藏
查看更多
课程推荐
-
- 前端进阶之JavaScript设计模式
- 设计模式是开发人员在软件开发过程中面临一般问题时的解决方案,代表了最佳的实践。本课程的主打内容包括JS常见设计模式以及具体应用场景,打造一站式知识长龙服务,适合有JS基础的同学学习。
- 543次学习
-
- GO语言核心编程课程
- 本课程采用真实案例,全面具体可落地,从理论到实践,一步一步将GO核心编程技术、编程思想、底层实现融会贯通,使学习者贴近时代脉搏,做IT互联网时代的弄潮儿。
- 516次学习
-
- 简单聊聊mysql8与网络通信
- 如有问题加微信:Le-studyg;在课程中,我们将首先介绍MySQL8的新特性,包括性能优化、安全增强、新数据类型等,帮助学生快速熟悉MySQL8的最新功能。接着,我们将深入解析MySQL的网络通信机制,包括协议、连接管理、数据传输等,让
- 500次学习
-
- JavaScript正则表达式基础与实战
- 在任何一门编程语言中,正则表达式,都是一项重要的知识,它提供了高效的字符串匹配与捕获机制,可以极大的简化程序设计。
- 487次学习
-
- 从零制作响应式网站—Grid布局
- 本系列教程将展示从零制作一个假想的网络科技公司官网,分为导航,轮播,关于我们,成功案例,服务流程,团队介绍,数据部分,公司动态,底部信息等内容区块。网站整体采用CSSGrid布局,支持响应式,有流畅过渡和展现动画。
- 485次学习
查看更多
AI推荐
-
- ChatExcel酷表
- ChatExcel酷表是由北京大学团队打造的Excel聊天机器人,用自然语言操控表格,简化数据处理,告别繁琐操作,提升工作效率!适用于学生、上班族及政府人员。
- 3204次使用
-
- Any绘本
- 探索Any绘本(anypicturebook.com/zh),一款开源免费的AI绘本创作工具,基于Google Gemini与Flux AI模型,让您轻松创作个性化绘本。适用于家庭、教育、创作等多种场景,零门槛,高自由度,技术透明,本地可控。
- 3417次使用
-
- 可赞AI
- 可赞AI,AI驱动的办公可视化智能工具,助您轻松实现文本与可视化元素高效转化。无论是智能文档生成、多格式文本解析,还是一键生成专业图表、脑图、知识卡片,可赞AI都能让信息处理更清晰高效。覆盖数据汇报、会议纪要、内容营销等全场景,大幅提升办公效率,降低专业门槛,是您提升工作效率的得力助手。
- 3446次使用
-
- 星月写作
- 星月写作是国内首款聚焦中文网络小说创作的AI辅助工具,解决网文作者从构思到变现的全流程痛点。AI扫榜、专属模板、全链路适配,助力新人快速上手,资深作者效率倍增。
- 4555次使用
-
- MagicLight
- MagicLight.ai是全球首款叙事驱动型AI动画视频创作平台,专注于解决从故事想法到完整动画的全流程痛点。它通过自研AI模型,保障角色、风格、场景高度一致性,让零动画经验者也能高效产出专业级叙事内容。广泛适用于独立创作者、动画工作室、教育机构及企业营销,助您轻松实现创意落地与商业化。
- 3824次使用
查看更多
相关文章
-
- GoLand调式动态执行代码
- 2023-01-13 502浏览
-
- 用Nginx反向代理部署go写的网站。
- 2023-01-17 502浏览
-
- Golang取得代码运行时间的问题
- 2023-02-24 501浏览
-
- 请问 go 代码如何实现在代码改动后不需要Ctrl+c,然后重新 go run *.go 文件?
- 2023-01-08 501浏览
-
- 如何从同一个 io.Reader 读取多次
- 2023-04-11 501浏览

