-
Notifications
You must be signed in to change notification settings - Fork 12
/
tmpl.code.go
137 lines (111 loc) · 5.66 KB
/
tmpl.code.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
// Copyright 2023 The searKing Author. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package option
import (
"fmt"
"strings"
slices_ "github.com/searKing/golang/go/exp/slices"
strings_ "github.com/searKing/golang/go/strings"
)
type TmplConfigRender struct {
// Print the header and package clause.
GoOptionToolName string
GoOptionToolArgs []string
GoOptionToolArgsJoined string
PackageName string
ImportPaths []string
ValDecls []string
TargetTypeName string // type name of target type
TargetTypeImport string // import path of target type
TargetTypeGenericDeclaration string // the Generic type of the struct type
TargetTypeGenericParams string // the Generic params of the struct type
TrimmedTypeName string // trimmed type name of target type
OptionInterfaceName string // option interface name of target type
OptionStructName string // option struct name of target type
ApplyOptionsAsMemberFunction bool // ApplyOptions can be registered as OptionType's member function
}
func (t *TmplConfigRender) Complete() {
t.GoOptionToolArgsJoined = strings.Join(t.GoOptionToolArgs, " ")
t.ApplyOptionsAsMemberFunction = strings.TrimSpace(t.TargetTypeImport) == ""
t.OptionInterfaceName = strings_.UpperCamelCaseSlice("option")
t.OptionStructName = strings_.UpperCamelCaseSlice("config")
if !*trim && t.TrimmedTypeName != "" {
t.OptionInterfaceName = strings_.UpperCamelCaseSlice(t.TrimmedTypeName, "option")
t.OptionStructName = strings_.UpperCamelCaseSlice(t.TrimmedTypeName, "config")
}
importPath := strings.TrimSpace(t.TargetTypeImport)
if importPath != "" {
t.ImportPaths = append(t.ImportPaths, fmt.Sprintf("%q", importPath))
}
t.ImportPaths = slices_.Filter(t.ImportPaths)
_, defaultValDecl := createValAndNameDecl(t.TargetTypeName)
if defaultValDecl != "" {
t.ValDecls = append(t.ValDecls, defaultValDecl)
}
}
const tmplConfig = `// Code generated by "{{.GoOptionToolName}} {{.GoOptionToolArgsJoined}}"; EDIT IT ANYWAY.
// Install {{.GoOptionToolName}} by "go get install github.com/searKing/golang/tools/{{.GoOptionToolName}}"
package {{.PackageName}}
import "fmt"
{{range $path := .ImportPaths}}
import {{$path}}
{{end}}
// {{.OptionStructName}} is config param as factory config
// Code borrowed from https://github.com/kubernetes/kubernetes
// call chains: New{{.OptionStructName}}{{.TargetTypeGenericDeclaration}} -> Complete{{.TargetTypeGenericParams}} -> Validate{{.TargetTypeGenericParams}} -> New{{.TargetTypeGenericParams}}|Apply{{.TargetTypeGenericParams}}
type {{.OptionStructName}}{{.TargetTypeGenericDeclaration}} struct {
// TODO Add config fields here
}
{{- if .ApplyOptionsAsMemberFunction }}
type completed{{.OptionStructName}}{{.TargetTypeGenericDeclaration}} struct {
*{{.OptionStructName}}{{.TargetTypeGenericParams}}
//===========================================================================
// values below here are filled in during completion
//===========================================================================
}
// Completed{{.OptionStructName}} is config ready to use.
type Completed{{.OptionStructName}}{{.TargetTypeGenericDeclaration}} struct {
// Embed a private pointer that cannot be instantiated outside of this package.
*completed{{.OptionStructName}}{{.TargetTypeGenericParams}}
}
// New{{.OptionStructName}} returns a Config struct with the default values
func New{{.OptionStructName}}{{.TargetTypeGenericDeclaration}}() *{{.OptionStructName}}{{.TargetTypeGenericParams}} {
// TODO Add default configs here
return &{{.OptionStructName}}{{.TargetTypeGenericParams}}{}
}
// Complete fills in any fields not set that are required to have valid data and can be derived
// from other fields. If you're going to ApplyOptions, do that first. It's mutating the receiver.
func (o *{{.OptionStructName}}{{.TargetTypeGenericParams}}) Complete() Completed{{.OptionStructName}}{{.TargetTypeGenericParams}} {
// TODO Add custom codes here
return Completed{{.OptionStructName}}{{.TargetTypeGenericParams}}{&completed{{.OptionStructName}}{{.TargetTypeGenericParams}}{o}}
}
// Validate checks {{.OptionStructName}}{{.TargetTypeGenericParams}} and return a slice of found errs.
func (o *{{.OptionStructName}}{{.TargetTypeGenericParams}}) Validate() []error {
var errs []error
// TODO Add custom validate codes here
return errs
}
// New creates a new server which logically combines the handling chain with the passed server.
// The handler chain in particular can be difficult as it starts delegating.
// New usually called after Complete
func (c completed{{.OptionStructName}}{{.TargetTypeGenericParams}}) New() (*{{.TargetTypeName}}{{.TargetTypeGenericParams}}, error) {
// TODO Add custom codes here
return nil, fmt.Errorf("not implemented")
}
// Apply set options and something else as global init, act likes New but without {{.OptionStructName}}'s instance
// Apply usually called after Complete
func (c completed{{.OptionStructName}}{{.TargetTypeGenericParams}}) Apply() error {
// TODO Add custom codes here
return fmt.Errorf("not implemented")
}
{{- else}}
// Complete fills in any fields not set that are required to have valid data and can be derived
// from other fields. If you're going to ApplyOptions, do that first. It's mutating the receiver.
func Complete{{.TargetTypeGenericDeclaration}}(o *{{.OptionStructName}}, options ...{{.OptionInterfaceName}}{{.TargetTypeGenericParams}}) Completed{{.OptionStructName}} {
ApplyOptions(o, options...)
// TODO Add custom codes here
return Completed{{.OptionStructName}}{{.TargetTypeGenericParams}}{&completed{{.OptionStructName}}{{.TargetTypeGenericParams}}{o}}
}
{{- end}}
`