stillbox/util/omitempty/omitempty.go

99 lines
2.1 KiB
Go
Raw Normal View History

2024-11-25 16:04:07 -05:00
// This is here until https://github.com/sqlc-dev/sqlc/pull/3117 is merged.
package main
import (
"bytes"
"go/ast"
"go/format"
"go/parser"
"go/token"
"log"
"os"
"strings"
)
const filePath = "./pkg/database/models.go"
func main() {
// Parse the source code
fset := token.NewFileSet()
f, err := parser.ParseFile(fset, filePath, nil, parser.ParseComments)
if err != nil {
log.Fatal(err)
}
// Modify the AST
ast.Inspect(f, func(n ast.Node) bool {
switch x := n.(type) {
case *ast.StructType:
for _, field := range x.Fields.List {
if field.Tag == nil {
continue
}
if field.Tag.Value == "" || field.Tag.Kind != token.STRING {
continue
}
field.Tag.Value = modifyJSONTag(field.Tag.Value)
}
}
return true
})
// Write the output back to the original file
var buf bytes.Buffer
err = format.Node(&buf, fset, f)
if err != nil {
log.Fatal(err)
}
outputFile, err := os.Create(filePath)
if err != nil {
log.Fatal(err)
}
defer outputFile.Close()
_, err = outputFile.Write(buf.Bytes())
if err != nil {
log.Fatal(err)
}
}
func modifyJSONTag(tagValue string) string {
tagValue = strings.Trim(tagValue, "`")
tags := strings.Split(tagValue, " ")
var modifiedTags []string
for _, tag := range tags {
// Only modify JSON tags, leave others as they are.
if !strings.HasPrefix(tag, "json:") {
modifiedTags = append(modifiedTags, tag)
continue
}
jsonQuoted := tag[5:] // Remove "json:" prefix
jsonValue := strings.Trim(jsonQuoted, "\"") // Remove quotes
jsonOptions := strings.Split(jsonValue, ",") // Split options
// Check if "omitempty" is already present
hasOmitempty := false
for _, opt := range jsonOptions {
if opt == "omitempty" {
hasOmitempty = true
break
}
}
// Add "omitempty" if not present and the field is not ignored
if !hasOmitempty && jsonOptions[0] != "-" {
jsonOptions = append(jsonOptions, "omitempty")
}
// Reconstruct the JSON tag
newJSONTag := "json:\"" + strings.Join(jsonOptions, ",") + "\""
modifiedTags = append(modifiedTags, newJSONTag)
}
// Reconstruct the full tag
return "`" + strings.Join(modifiedTags, " ") + "`"
}