我正在开发一个简单的Go服务来连接到数据库以进行基本查询。我用来sqlc生成Go与数据库交互的函数。lib/pq当从现在切换驱动程序时,pgx/v5数据库字段的类型而pgtypes不是Go类型。这是一个例子:
而不是这个:
type ListAccountsParams struct {
Owner string `json:"owner"`
Limit int32 `json:"limit"`
Offset int32 `json:"offset"`
}
Run Code Online (Sandbox Code Playgroud)
我现在明白了:
type ListAccountsParams struct {
Owner pgtype.Text `json:"owner"`
Limit pgtype.Int4 `json:"limit"`
Offset pgtype.Int4 `json:"offset"`
}
Run Code Online (Sandbox Code Playgroud)
然而我发现使用的唯一方法pgtypes是这个:
owner := pgtype.Text{
String: "Craigs List",
Valid: true,
}
Run Code Online (Sandbox Code Playgroud)
而不是仅仅做owner := "Craigs List"。对于数字类型就更矫枉过正了,我找到的所有实现都是这样的:
pgtype.Numeric{
Int: big.NewInt(-543),
Exp: 3,
Status: pgtype.Present
}
Run Code Online (Sandbox Code Playgroud)
使用sqlc配置文件,我可以覆盖这些类型以支持标准类型,但对我来说必须覆盖 postgres类型等等Go是没有意义的......textstring
在我看来,这不是使用这些类型的最佳方式,这对我来说是违反直觉的。所以我的问题是,我做得对吗?有不同的方法吗?最终,有没有一种方法可以配置sqlc为使用Go类型而不是pgtypes同时使用pgx/v5驱动程序?
您可以编辑sqlc配置文件来为要使用 Go 类型而不是类型的字段指定自定义类型,并通过在文件pgtype中指定所需的 Go 类型来覆盖类型sqlc.yaml
types:
- name: ListAccountsParams
fields:
- name: Owner
goType: string
- name: Limit
goType: int32
- name: Offset
goType: int32
Run Code Online (Sandbox Code Playgroud)
请注意,直接使用 Go 类型可能会导致与数据库交互时潜在的类型不匹配或其他问题,而pgtype类型是专门为处理 PostgreSQL 特定的数据类型而设计的,并提供一定程度的类型安全性和兼容性!
更新
根据您的评论,当使用pgx/v5驱动程序时sqlc,生成的代码使用pgtype类型来处理 PostgreSQL 特定的数据类型,这是sqlc使用驱动程序时的默认行为,并且您使用类型(例如和)pgx/v5描述的方式是正确的处理这些类型的方式,例如,在处理类型时,您需要将字段设置为所需的值并将字段设置为。pgtypepgtype.Textpgtype.Int4pgtype.TextStringValidtrue
对于数值类型,该pgtype.Numeric类型需要设置Int、Exp、 和字段,这是因为该类型将数值表示为任意精度整数 ( )、指数 ( ) 和状态 ( ) 指示该值是否为存在或无效!Statuspgtype.NumericIntExpStatus