Skip to content

Commit 295d925

Browse files
author
Mengqi Yu
committed
Merge branch 'master' into fix/v0.2
2 parents 363e5dd + f9735d8 commit 295d925

File tree

33 files changed

+232
-82
lines changed

33 files changed

+232
-82
lines changed

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[![CI Status](https://github.com/GoogleContainerTools/kpt-functions-catalog/workflows/CI/badge.svg?branch=master&event=push)](https://github.com/GoogleContainerTools/kpt-functions-catalog/actions?query=workflow%3ACI+event%3Apush+branch%3Amaster)
22

3-
# KPT Functions Catalog
3+
# kpt Functions Catalog
44

55
[Documentation]
66

@@ -12,7 +12,7 @@
1212

1313
[Code of Conduct]
1414

15-
[Documentation]: https://googlecontainertools.github.io/kpt/guides/consumer/function/
15+
[Documentation]: https://catalog.kpt.dev/
1616
[Contributor Guide]: CONTRIBUTING.md
1717
[Code of Conduct]: CODE_OF_CONDUCT.md
1818
[Release Process]: RELEASING.md

examples/ensure-name-substring-imperative/README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ $ kpt pkg get https://github.com/GoogleContainerTools/kpt-functions-catalog.git/
1818
Invoke the function by running the following commands:
1919

2020
```shell
21-
$ kpt fn eval ensure-name-substring-imperative --image gcr.io/kpt-fn/ensure-name-substring:unstable -- prepend=prod
21+
$ kpt fn eval ensure-name-substring-imperative --image gcr.io/kpt-fn/ensure-name-substring:unstable -- prepend=prod-
2222
```
2323

2424
The key-value pair(s) provided after `--` will be converted to `ConfigMap` by

examples/fix-simple/.expected/diff.patch

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
diff --git a/Kptfile b/Kptfile
2-
index a8e7f27..0d91da2 100644
2+
index a8e7f27..cccb738 100644
33
--- a/Kptfile
44
+++ b/Kptfile
55
@@ -1,20 +1,24 @@
@@ -37,7 +37,7 @@ index a8e7f27..0d91da2 100644
3737
+pipeline:
3838
+ mutators:
3939
+ - image: gcr.io/kpt-fn/apply-setters:v0.1
40-
+ configPath: setters-config.yaml
40+
+ configPath: setters.yaml
4141
diff --git a/resources.yaml b/resources.yaml
4242
index 9e30767..dae3005 100644
4343
--- a/resources.yaml
@@ -50,15 +50,15 @@ index 9e30767..dae3005 100644
5050
+ name: the-map # kpt-set: ${name}
5151
data:
5252
some-key: some-value
53-
diff --git a/setters-config.yaml b/setters-config.yaml
53+
diff --git a/setters.yaml b/setters.yaml
5454
new file mode 100644
55-
index 0000000..f39bb00
55+
index 0000000..b67bc21
5656
--- /dev/null
57-
+++ b/setters-config.yaml
57+
+++ b/setters.yaml
5858
@@ -0,0 +1,6 @@
5959
+apiVersion: v1
6060
+kind: ConfigMap
6161
+metadata:
62-
+ name: setters-config
62+
+ name: setters
6363
+data:
6464
+ name: the-map

examples/fix-simple/README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ info:
8383
pipeline:
8484
mutators:
8585
- image: gcr.io/kpt-fn/apply-setters:v0.1
86-
configPath: setters-config.yaml
86+
configPath: setters.yaml
8787
```
8888

8989
The transformed package is compatible with kpt 1.0 binary.

examples/starlark-validation/README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ keys in the `ConfigMap`.
5353
Invoke the function by running the following commands:
5454

5555
```shell
56-
$ kpt fn render starlark-validation
56+
$ kpt fn render starlark-validation --results-dir /tmp
5757
```
5858

5959
### Expected result

functions/contrib/ts/sops/package-lock.json

Lines changed: 3 additions & 3 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

functions/contrib/ts/sops/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@
3030
"devDependencies": {
3131
"@types/jasmine": "^3.7.6",
3232
"@types/js-yaml": "^3.12.5",
33-
"@types/node": "^14.17.1",
33+
"@types/node": "^14.17.2",
3434
"@types/rw": "file:@types/rw",
3535
"create-kpt-functions": "^0.17.0",
3636
"jasmine": "^3.7.0",

functions/go/Makefile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -118,7 +118,7 @@ func-fmt:
118118

119119
func-lint:
120120
(which $(GOPATH)/bin/golangci-lint || \
121-
curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(GOPATH)/bin v1.32.2)
121+
curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(GOPATH)/bin v1.41.1)
122122
cd $(CURRENT_FUNCTION) && $(GOPATH)/bin/golangci-lint run ./...
123123

124124
func-test:

functions/go/fix/fixpkg/fix.go

Lines changed: 54 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ import (
1414
"sigs.k8s.io/kustomize/kyaml/fieldmeta"
1515
"sigs.k8s.io/kustomize/kyaml/fn/runtime/runtimeutil"
1616
"sigs.k8s.io/kustomize/kyaml/kio"
17+
"sigs.k8s.io/kustomize/kyaml/kio/filters"
1718
"sigs.k8s.io/kustomize/kyaml/kio/kioutil"
1819
"sigs.k8s.io/kustomize/kyaml/openapi"
1920
"sigs.k8s.io/kustomize/kyaml/sets"
@@ -55,7 +56,7 @@ type Result struct {
5556
Message string
5657
}
5758

58-
const SettersConfigFileName = "setters-config.yaml"
59+
const SettersConfigFileName = "setters.yaml"
5960

6061
// Filter implements Fix as a yaml.Filter
6162
func (s *Fix) Filter(nodes []*yaml.RNode) ([]*yaml.RNode, error) {
@@ -230,15 +231,18 @@ func (s *Fix) FunctionsInPkg(nodes []*yaml.RNode, pkgPath string) []v1.Function
230231
}
231232
fnSpec := runtimeutil.GetFunctionSpec(node)
232233
if fnSpec != nil {
234+
// in order to make sure there is only one function config per file,
235+
// rename the file with the name(and hash(name)) of the function config resource
236+
fnFileName := fmt.Sprintf("%s.yaml", node.GetName())
233237
// in v1, fn-config must be present in the package directory
234238
// so configPath must be just the file name
235-
fnFileName := filepath.Base(meta.Annotations[kioutil.PathAnnotation])
239+
fnFilePath := filepath.Join(pkgPath, fnFileName)
236240
res = append(res, v1.Function{
237241
Image: fnSpec.Container.Image,
238242
ConfigPath: fnFileName,
239243
})
240244
// move the fn-config to the top level directory of the package
241-
meta.Annotations[kioutil.PathAnnotation] = filepath.Join(pkgPath, fnFileName)
245+
meta.Annotations[kioutil.PathAnnotation] = fnFilePath
242246
delete(meta.Annotations, runtimeutil.FunctionAnnotationKey)
243247
delete(meta.Annotations, "config.k8s.io/function")
244248
err = node.SetAnnotations(meta.Annotations)
@@ -278,7 +282,7 @@ func (s *Fix) FixKptfile(node *yaml.RNode, functions []v1.Function) (*yaml.RNode
278282
if kf.Pipeline != nil {
279283
for i, fn := range kf.Pipeline.Mutators {
280284
if strings.Contains(fn.Image, "apply-setters:v0.1") && len(fn.ConfigMap) > 0 {
281-
settersConfig, err := ConfigFromSetters(kf.Pipeline.Mutators[0].ConfigMap, settersConfigFilePath)
285+
settersConfig, err := SettersNodeFromSetters(kf.Pipeline.Mutators[0].ConfigMap, settersConfigFilePath)
282286
if err != nil {
283287
return node, err
284288
}
@@ -392,9 +396,9 @@ func (s *Fix) FixKptfile(node *yaml.RNode, functions []v1.Function) (*yaml.RNode
392396
if len(setters) > 0 {
393397
fn := v1.Function{
394398
Image: "gcr.io/kpt-fn/apply-setters:v0.1",
395-
ConfigPath: "setters-config.yaml",
399+
ConfigPath: SettersConfigFileName,
396400
}
397-
settersConfig, err := ConfigFromSetters(setters, settersConfigFilePath)
401+
settersConfig, err := SettersNodeFromSetters(setters, settersConfigFilePath)
398402
if err != nil {
399403
return node, err
400404
}
@@ -431,12 +435,12 @@ func (s *Fix) FixKptfile(node *yaml.RNode, functions []v1.Function) (*yaml.RNode
431435
return kNode, err
432436
}
433437

434-
// ConfigFromSetters returns the ConfigMap node with input setters in data field
435-
func ConfigFromSetters(setters map[string]string, path string) (*yaml.RNode, error) {
438+
// SettersNodeFromSetters returns the ConfigMap node with input setters in data field
439+
func SettersNodeFromSetters(setters map[string]string, path string) (*yaml.RNode, error) {
436440
configNode, err := yaml.Parse(fmt.Sprintf(`apiVersion: v1
437441
kind: ConfigMap
438442
metadata:
439-
name: setters-config
443+
name: setters
440444
annotations:
441445
%s: %s
442446
%s: "0"
@@ -452,28 +456,48 @@ metadata:
452456
sort.Strings(keys)
453457

454458
for _, k := range keys {
455-
v := setters[k]
456-
vNode, err := yaml.Parse(v)
459+
v, err := standardizeArrayValue(setters[k])
457460
if err != nil {
458461
return nil, err
459462
}
460-
if vNode.YNode().Kind == yaml.SequenceNode {
461-
// standardize array values to folded style
462-
vNode.YNode().Style = yaml.FoldedStyle
463-
v, err = vNode.String()
464-
if err != nil {
465-
return nil, err
466-
}
463+
vNode := yaml.NewScalarRNode(v)
464+
if v == "" {
465+
vNode.YNode().Style = yaml.DoubleQuotedStyle
467466
}
468-
469467
err = configNode.PipeE(
470468
yaml.LookupCreate(yaml.ScalarNode, "data", k),
471-
yaml.FieldSetter{Value: yaml.NewScalarRNode(v)})
469+
yaml.FieldSetter{Value: vNode, OverrideStyle: true})
472470
if err != nil {
473471
return nil, err
474472
}
475473
}
476-
return configNode, nil
474+
// format the created resource
475+
_, err = filters.FormatFilter{UseSchema: true}.Filter([]*yaml.RNode{configNode})
476+
return configNode, err
477+
}
478+
479+
// standardizeArrayValue returns the folded style array node string
480+
// e.g. for input value [foo, bar], it returns
481+
// - foo
482+
// - bar
483+
func standardizeArrayValue(val string) (string, error) {
484+
if !strings.HasPrefix(val, "[") {
485+
// the value is either standardized, or is not a sequence node value
486+
return val, nil
487+
}
488+
vNode, err := yaml.Parse(val)
489+
if err != nil {
490+
return val, fmt.Errorf("failed to parse the array node value %q with error %q", val, err.Error())
491+
}
492+
if vNode.YNode().Kind == yaml.SequenceNode {
493+
// standardize array values to folded style
494+
vNode.YNode().Style = yaml.FoldedStyle
495+
val, err = vNode.String()
496+
if err != nil {
497+
return val, fmt.Errorf("failed to serialize the array node value %q with error %q", val, err.Error())
498+
}
499+
}
500+
return val, nil
477501
}
478502

479503
// getPkgPathToSettersSchema returns the, map of pkgPath to the setters schema in Kptfile
@@ -507,13 +531,16 @@ func (s *Fix) visitMapping(object *yaml.RNode) error {
507531
// return if it is not a sequence node
508532
return nil
509533
}
510-
534+
oldCommentPrefixes := []string{`# {"$kpt-set":"`, `# {"$ref":"#/definitions/io.k8s.cli.`}
511535
comment := node.Key.YNode().LineComment
512-
// # {"$kpt-set":"foo"} must be converted to # kpt-set: ${foo}
513-
if strings.Contains(comment, "$kpt-set") {
514-
comment := strings.TrimPrefix(comment, `# {"$kpt-set":"`)
515-
comment = strings.TrimSuffix(comment, `"}`)
516-
node.Key.YNode().LineComment = fmt.Sprintf("kpt-set: ${%s}", comment)
536+
for _, cp := range oldCommentPrefixes {
537+
// # {"$kpt-set":"foo"} must be converted to # kpt-set: ${foo}
538+
// # {"$ref":"#/definitions/io.k8s.cli.list"} must be converted to # kpt-set: ${list}
539+
if strings.Contains(comment, cp) {
540+
comment := strings.TrimPrefix(comment, cp)
541+
comment = strings.TrimSuffix(comment, `"}`)
542+
node.Key.YNode().LineComment = fmt.Sprintf("kpt-set: ${%s}", comment)
543+
}
517544
}
518545
return nil
519546
})

functions/go/fix/fixpkg/fix_test.go

Lines changed: 79 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,8 @@ func TestFixV1alpha1ToV1(t *testing.T) {
3737
message: Transformed "packageMetadata" to "info"
3838
- filepath: Kptfile
3939
message: Transformed "upstream" to "upstream" and "upstreamLock"
40+
- filepath: Kptfile
41+
message: Added "gcr.io/kpt-fn/set-annotations:v0.1" to mutators list, please move it to validators section if it is a validator function
4042
- filepath: Kptfile
4143
message: Added "gcr.io/kpt-fn/set-labels:v0.1" to mutators list, please move it to validators section if it is a validator function
4244
- filepath: Kptfile
@@ -78,11 +80,86 @@ func TestFixV1alpha2ToV1(t *testing.T) {
7880
assert.NoError(t, err)
7981
assert.Equal(t, `- filepath: Kptfile
8082
message: Updated apiVersion to kpt.dev/v1
81-
- filepath: setters-config.yaml
83+
- filepath: setters.yaml
8284
message: Moved setters from configMap to configPath
8385
- filepath: hello-world/Kptfile
8486
message: Updated apiVersion to kpt.dev/v1
85-
- filepath: hello-world/setters-config.yaml
87+
- filepath: hello-world/setters.yaml
8688
message: Moved setters from configMap to configPath
8789
`, string(results))
8890
}
91+
92+
type settersNodeTest struct {
93+
name string
94+
setters map[string]string
95+
path string
96+
expected string
97+
errMsg string
98+
}
99+
100+
var settersNodeFromSettersCases = []settersNodeTest{
101+
{
102+
name: "Create setters file with all types",
103+
path: `foo/bar`,
104+
setters: map[string]string{
105+
"environment": "",
106+
"integer": "10",
107+
"number": "1.1",
108+
"boolean": "true",
109+
"string": "foo",
110+
"region": "us-east-1",
111+
"flow-style-setter": "[dev, prod]",
112+
"folded-style-setter": "- hi\n- hello",
113+
},
114+
expected: `apiVersion: v1
115+
kind: ConfigMap
116+
metadata:
117+
name: setters
118+
annotations:
119+
config.kubernetes.io/index: "0"
120+
config.kubernetes.io/path: foo/bar
121+
data:
122+
boolean: "true"
123+
environment: ""
124+
flow-style-setter: |
125+
- dev
126+
- prod
127+
folded-style-setter: |-
128+
- hi
129+
- hello
130+
integer: "10"
131+
number: "1.1"
132+
region: us-east-1
133+
string: foo
134+
`,
135+
},
136+
{
137+
name: "invalid flow-style sequence node",
138+
path: `foo/bar`,
139+
setters: map[string]string{
140+
"setter": "[dev, prod,",
141+
},
142+
errMsg: `failed to parse the array node value "[dev, prod," with error "yaml: line 1: did not find expected node content"`,
143+
},
144+
}
145+
146+
func TestSettersNodeFromSetters(t *testing.T) {
147+
for i := range settersNodeFromSettersCases {
148+
test := settersNodeFromSettersCases[i]
149+
t.Run(test.name, func(t *testing.T) {
150+
res, err := SettersNodeFromSetters(test.setters, test.path)
151+
if test.errMsg == "" {
152+
assert.NoError(t, err)
153+
} else {
154+
assert.Error(t, err)
155+
assert.Equal(t, test.errMsg, err.Error())
156+
return
157+
}
158+
actual, err := res.String()
159+
assert.NoError(t, err)
160+
if !assert.Equal(t, test.expected, actual) {
161+
t.FailNow()
162+
}
163+
})
164+
}
165+
}

0 commit comments

Comments
 (0)