golang现代化REST/GraphQL API开发框架插件Huma的使用
Golang现代化REST/GraphQL API开发框架插件Huma的使用
什么是Huma?
Huma是一个现代化、简单、快速且灵活的微框架,用于在Go中构建HTTP REST/RPC API,基于OpenAPI 3和JSON Schema。它的目标是提供:
- 逐步采用现有服务的团队
- 现代REST或HTTP RPC API后端框架
- 防止常见错误的防护措施
- 不会过时的文档
- 高质量生成的开发者工具
安装Huma
使用go get
安装。注意需要Go 1.23或更新版本。
# After: go mod init ...
go get -u github.com/danielgtaylor/huma/v2
完整示例代码
以下是使用Huma构建"Hello World" API的完整示例:
package main
import (
"context"
"fmt"
"net/http"
"github.com/danielgtaylor/huma/v2"
"github.com/danielgtaylor/huma/v2/adapters/humachi"
"github.com/danielgtaylor/huma/v2/humacli"
"github.com/go-chi/chi/v5"
_ "github.com/danielgtaylor/huma/v2/formats/cbor"
)
// Options for the CLI. Pass `--port` or set the `SERVICE_PORT` env var.
type Options struct {
Port int `help:"Port to listen on" short:"p" default:"8888"`
}
// GreetingOutput represents the greeting operation response.
type GreetingOutput struct {
Body struct {
Message string `json:"message" example:"Hello, world!" doc:"Greeting message"`
}
}
func main() {
// Create a CLI app which takes a port option.
cli := humacli.New(func(hooks humacli.Hooks, options *Options) {
// Create a new router & API
router := chi.NewMux()
api := humachi.New(router, huma.DefaultConfig("My API", "1.0.0"))
// Add the operation handler to the API.
huma.Get(api, "/greeting/{name}", func(ctx context.Context, input *struct{
Name string `path:"name" maxLength:"30" example:"world" doc:"Name to greet"`
}) (*GreetingOutput, error) {
resp := &GreetingOutput{}
resp.Body.Message = fmt.Sprintf("Hello, %s!", input.Name)
return resp, nil
})
// Tell the CLI how to start your router.
hooks.OnStart(func() {
http.ListenAndServe(fmt.Sprintf(":%d", options.Port), router)
})
})
// Run the CLI. When passed no commands, it starts the server.
cli.Run()
}
你可以使用go run greet.go
运行这个示例(可选地通过--port
参数改变默认端口),并使用Restish或curl进行测试:
# Get the message from the server
$ restish :8888/greeting/world
HTTP/1.1 200 OK
...
{
$schema: "http://localhost:8888/schemas/GreetingOutputBody.json",
message: "Hello, world!"
}
主要特性
- 在你选择的路由器上的声明式接口
- 使用RFC9457的JSON错误
- 每个操作的请求大小限制
- 服务器和客户端之间的内容协商
- 条件请求支持
- 自动生成PATCH操作
- 输入和输出模型的注释Go类型
- 使用Stoplight Elements生成文档
- 内置可选CLI
- 生成OpenAPI以访问丰富的工具生态系统
- 生成JSON Schema
文档
完整的文档可以在Huma网站上找到。官方Go包文档可以在pkg.go.dev上找到。
评价
“这是我最喜欢的Go web框架。它受到FastAPI的启发,FastAPI也很棒,并且符合许多常见的Web RFC…我真的很喜欢它的功能集,它可以使用Chi的事实,以及它仍然相对简单的事实。” - Jeb_Jenky
“在使用Golang一年多后,我偶然发现了Huma,这个受FastAPI启发的web框架。这是我一直在期待的圣诞奇迹!这个框架拥有一切!” - Hana Mohan
“我爱Huma。真诚地感谢这个很棒的包。我已经使用它一段时间了,它很棒!” - plscott
更多关于golang现代化REST/GraphQL API开发框架插件Huma的使用的实战教程也可以访问 https://www.itying.com/category-94-b0.html
更多关于golang现代化REST/GraphQL API开发框架插件Huma的使用的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html
Huma框架:现代化REST/GraphQL API开发框架
Huma是一个现代化的Go语言API开发框架,专注于简化REST和GraphQL API的创建过程。它结合了高性能和开发效率,提供了许多开箱即用的功能。
Huma核心特性
- 同时支持REST和GraphQL
- 自动OpenAPI/Swagger文档生成
- 内置验证和序列化
- 高性能路由
- 简洁的API设计
安装Huma
go get github.com/danielgtaylor/huma/v2
基本REST API示例
package main
import (
"context"
"fmt"
"net/http"
"github.com/danielgtaylor/huma/v2"
"github.com/danielgtaylor/huma/v2/adapters/humagin"
"github.com/gin-gonic/gin"
)
// 定义输入模型
type GreetingInput struct {
Name string `path:"name" maxLength:"30" example:"world" doc:"Name to greet"`
}
// 定义响应模型
type GreetingResponse struct {
Message string `json:"message" example:"Hello, world!"`
}
func main() {
// 创建路由
router := gin.New()
// 创建Huma API实例
api := humagin.New(router, huma.DefaultConfig("My API", "1.0.0"))
// 注册路由
huma.Register(api, huma.Operation{
OperationID: "get-greeting",
Method: http.MethodGet,
Path: "/greet/{name}",
Summary: "Get a greeting",
Description: "Get a personalized greeting for the given name.",
}, func(ctx context.Context, input *GreetingInput) (*GreetingResponse, error) {
resp := &GreetingResponse{
Message: fmt.Sprintf("Hello, %s!", input.Name),
}
return resp, nil
})
// 启动服务器
http.ListenAndServe(":8888", router)
}
GraphQL支持示例
Huma也提供了GraphQL支持:
package main
import (
"context"
"fmt"
"net/http"
"github.com/danielgtaylor/huma/v2"
"github.com/danielgtaylor/huma/v2/graphql"
"github.com/danielgtaylor/huma/v2/adapters/humagin"
"github.com/gin-gonic/gin"
)
type Todo struct {
ID string `json:"id"`
Title string `json:"title"`
Done bool `json:"done"`
}
var todos = []Todo{
{ID: "1", Title: "Buy milk", Done: false},
{ID: "2", Title: "Walk dog", Done: true},
}
func main() {
router := gin.New()
api := humagin.New(router, huma.DefaultConfig("Todo API", "1.0.0"))
// 注册GraphQL处理器
graphqlHandler := graphql.NewHandler(api)
// 添加GraphQL路由
api.AddHandler(huma.Operation{
Method: http.MethodPost,
Path: "/graphql",
}, graphqlHandler)
// 定义GraphQL查询
graphqlHandler.Register(
graphql.Query("todos", "Get all todos", func(ctx context.Context) ([]Todo, error) {
return todos, nil
}),
graphql.Query("todo", "Get a todo by ID", func(ctx context.Context, args struct {
ID string `graphql:"id"`
}) (*Todo, error) {
for _, todo := range todos {
if todo.ID == args.ID {
return &todo, nil
}
}
return nil, fmt.Errorf("todo not found")
}),
)
http.ListenAndServe(":8888", router)
}
高级功能
中间件支持
func LoggerMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
start := time.Now()
next.ServeHTTP(w, r)
duration := time.Since(start)
log.Printf("%s %s took %v", r.Method, r.URL.Path, duration)
})
}
func main() {
router := gin.New()
api := humagin.New(router, huma.DefaultConfig("My API", "1.0.0"))
// 添加中间件
api.UseMiddleware(LoggerMiddleware)
// ...注册路由等
}
验证器
Huma内置了强大的验证功能:
type CreateUserInput struct {
Body struct {
Username string `json:"username" minLength:"3" maxLength:"20" pattern:"^[a-zA-Z0-9]+$"`
Email string `json:"email" format:"email"`
Age int `json:"age" minimum:"18" maximum:"120"`
}
}
huma.Register(api, huma.Operation{
OperationID: "create-user",
Method: http.MethodPost,
Path: "/users",
}, func(ctx context.Context, input *CreateUserInput) (*huma.NoResponse, error) {
// 输入会自动验证
// 处理逻辑...
return nil, nil
})
自动文档
Huma会自动生成OpenAPI文档,可通过以下端点访问:
/openapi.json
- OpenAPI规范JSON/docs
- 交互式API文档界面
性能考虑
Huma在性能方面做了优化:
- 使用高效的路由实现
- 零或最小化的反射使用
- 智能的序列化/反序列化
- 内置缓存机制
总结
Huma框架为Go开发者提供了创建现代化API的完整解决方案,主要优势包括:
- 简洁直观的API设计
- 同时支持REST和GraphQL
- 自动化的文档生成
- 内置验证和序列化
- 良好的性能特性
对于需要快速开发高质量API的项目,Huma是一个值得考虑的选择。它特别适合需要同时提供REST和GraphQL接口,或者需要自动生成API文档的场景。