Skip to content

Commit dd6fe23

Browse files
authored
feat(strings): add strings package with functions to trim/change string case (#943)
1 parent 3219298 commit dd6fe23

7 files changed

Lines changed: 559 additions & 0 deletions

File tree

‎docs/SPEC.md‎

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3111,6 +3111,37 @@ If you need to convert other columns use the `map` function directly with the `u
31113111

31123112
[IMPL#242](https://github.com/influxdata/platform/issues/242) Update specification around type conversion functions.
31133113

3114+
#### String operations
3115+
3116+
##### trim
3117+
3118+
Remove leading and trailing characters specified in cutset from a string.
3119+
3120+
Example: `trim(v: ".abc.", cutset: ".")` returns the string `abc`.
3121+
3122+
##### trimSpace
3123+
3124+
Remove leading and trailing spaces from a string.
3125+
3126+
Example: `trimSpace(v: " abc ")` returns the string `abc`.
3127+
3128+
##### title
3129+
3130+
Convert a string to title case.
3131+
3132+
Example: `title(v: "a flux of foxes")` returns the string `A Flux Of Foxes`.
3133+
3134+
##### toUpper
3135+
3136+
Convert a string to upper case.
3137+
3138+
Example: `toUpper(v: "koala")` returns the string `KOALA`.
3139+
3140+
##### toLower
3141+
3142+
Convert a string to lower case.
3143+
3144+
Example: `toLower(v: "KOALA")` returns the string `koala`.
31143145

31153146
### Composite data types
31163147

‎stdlib/packages.go‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
_ "github.com/influxdata/flux/stdlib/influxdata/influxdb/v1"
1111
_ "github.com/influxdata/flux/stdlib/kafka"
1212
_ "github.com/influxdata/flux/stdlib/sql"
13+
_ "github.com/influxdata/flux/stdlib/strings"
1314
_ "github.com/influxdata/flux/stdlib/system"
1415
_ "github.com/influxdata/flux/stdlib/testing"
1516
_ "github.com/influxdata/flux/stdlib/universe"

‎stdlib/strings/flux_gen.go‎

Lines changed: 246 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,246 @@
1+
// DO NOT EDIT: This file is autogenerated via the builtin command.
2+
3+
package strings
4+
5+
import (
6+
flux "github.com/influxdata/flux"
7+
ast "github.com/influxdata/flux/ast"
8+
)
9+
10+
func init() {
11+
flux.RegisterPackage(pkgAST)
12+
}
13+
14+
var pkgAST = &ast.Package{
15+
BaseNode: ast.BaseNode{
16+
Errors: nil,
17+
Loc: nil,
18+
},
19+
Files: []*ast.File{&ast.File{
20+
BaseNode: ast.BaseNode{
21+
Errors: nil,
22+
Loc: &ast.SourceLocation{
23+
End: ast.Position{
24+
Column: 18,
25+
Line: 8,
26+
},
27+
File: "strings.flux",
28+
Source: "package strings\n\n// Transformation functions\nbuiltin trim\nbuiltin toUpper\nbuiltin toLower\nbuiltin title\nbuiltin trimSpace",
29+
Start: ast.Position{
30+
Column: 1,
31+
Line: 1,
32+
},
33+
},
34+
},
35+
Body: []ast.Statement{&ast.BuiltinStatement{
36+
BaseNode: ast.BaseNode{
37+
Errors: nil,
38+
Loc: &ast.SourceLocation{
39+
End: ast.Position{
40+
Column: 13,
41+
Line: 4,
42+
},
43+
File: "strings.flux",
44+
Source: "builtin trim",
45+
Start: ast.Position{
46+
Column: 1,
47+
Line: 4,
48+
},
49+
},
50+
},
51+
ID: &ast.Identifier{
52+
BaseNode: ast.BaseNode{
53+
Errors: nil,
54+
Loc: &ast.SourceLocation{
55+
End: ast.Position{
56+
Column: 13,
57+
Line: 4,
58+
},
59+
File: "strings.flux",
60+
Source: "trim",
61+
Start: ast.Position{
62+
Column: 9,
63+
Line: 4,
64+
},
65+
},
66+
},
67+
Name: "trim",
68+
},
69+
}, &ast.BuiltinStatement{
70+
BaseNode: ast.BaseNode{
71+
Errors: nil,
72+
Loc: &ast.SourceLocation{
73+
End: ast.Position{
74+
Column: 16,
75+
Line: 5,
76+
},
77+
File: "strings.flux",
78+
Source: "builtin toUpper",
79+
Start: ast.Position{
80+
Column: 1,
81+
Line: 5,
82+
},
83+
},
84+
},
85+
ID: &ast.Identifier{
86+
BaseNode: ast.BaseNode{
87+
Errors: nil,
88+
Loc: &ast.SourceLocation{
89+
End: ast.Position{
90+
Column: 16,
91+
Line: 5,
92+
},
93+
File: "strings.flux",
94+
Source: "toUpper",
95+
Start: ast.Position{
96+
Column: 9,
97+
Line: 5,
98+
},
99+
},
100+
},
101+
Name: "toUpper",
102+
},
103+
}, &ast.BuiltinStatement{
104+
BaseNode: ast.BaseNode{
105+
Errors: nil,
106+
Loc: &ast.SourceLocation{
107+
End: ast.Position{
108+
Column: 16,
109+
Line: 6,
110+
},
111+
File: "strings.flux",
112+
Source: "builtin toLower",
113+
Start: ast.Position{
114+
Column: 1,
115+
Line: 6,
116+
},
117+
},
118+
},
119+
ID: &ast.Identifier{
120+
BaseNode: ast.BaseNode{
121+
Errors: nil,
122+
Loc: &ast.SourceLocation{
123+
End: ast.Position{
124+
Column: 16,
125+
Line: 6,
126+
},
127+
File: "strings.flux",
128+
Source: "toLower",
129+
Start: ast.Position{
130+
Column: 9,
131+
Line: 6,
132+
},
133+
},
134+
},
135+
Name: "toLower",
136+
},
137+
}, &ast.BuiltinStatement{
138+
BaseNode: ast.BaseNode{
139+
Errors: nil,
140+
Loc: &ast.SourceLocation{
141+
End: ast.Position{
142+
Column: 14,
143+
Line: 7,
144+
},
145+
File: "strings.flux",
146+
Source: "builtin title",
147+
Start: ast.Position{
148+
Column: 1,
149+
Line: 7,
150+
},
151+
},
152+
},
153+
ID: &ast.Identifier{
154+
BaseNode: ast.BaseNode{
155+
Errors: nil,
156+
Loc: &ast.SourceLocation{
157+
End: ast.Position{
158+
Column: 14,
159+
Line: 7,
160+
},
161+
File: "strings.flux",
162+
Source: "title",
163+
Start: ast.Position{
164+
Column: 9,
165+
Line: 7,
166+
},
167+
},
168+
},
169+
Name: "title",
170+
},
171+
}, &ast.BuiltinStatement{
172+
BaseNode: ast.BaseNode{
173+
Errors: nil,
174+
Loc: &ast.SourceLocation{
175+
End: ast.Position{
176+
Column: 18,
177+
Line: 8,
178+
},
179+
File: "strings.flux",
180+
Source: "builtin trimSpace",
181+
Start: ast.Position{
182+
Column: 1,
183+
Line: 8,
184+
},
185+
},
186+
},
187+
ID: &ast.Identifier{
188+
BaseNode: ast.BaseNode{
189+
Errors: nil,
190+
Loc: &ast.SourceLocation{
191+
End: ast.Position{
192+
Column: 18,
193+
Line: 8,
194+
},
195+
File: "strings.flux",
196+
Source: "trimSpace",
197+
Start: ast.Position{
198+
Column: 9,
199+
Line: 8,
200+
},
201+
},
202+
},
203+
Name: "trimSpace",
204+
},
205+
}},
206+
Imports: nil,
207+
Name: "strings.flux",
208+
Package: &ast.PackageClause{
209+
BaseNode: ast.BaseNode{
210+
Errors: nil,
211+
Loc: &ast.SourceLocation{
212+
End: ast.Position{
213+
Column: 16,
214+
Line: 1,
215+
},
216+
File: "strings.flux",
217+
Source: "package strings",
218+
Start: ast.Position{
219+
Column: 1,
220+
Line: 1,
221+
},
222+
},
223+
},
224+
Name: &ast.Identifier{
225+
BaseNode: ast.BaseNode{
226+
Errors: nil,
227+
Loc: &ast.SourceLocation{
228+
End: ast.Position{
229+
Column: 16,
230+
Line: 1,
231+
},
232+
File: "strings.flux",
233+
Source: "strings",
234+
Start: ast.Position{
235+
Column: 9,
236+
Line: 1,
237+
},
238+
},
239+
},
240+
Name: "strings",
241+
},
242+
},
243+
}},
244+
Package: "strings",
245+
Path: "strings",
246+
}

‎stdlib/strings/strings.flux‎

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
package strings
2+
3+
// Transformation functions
4+
builtin trim
5+
builtin toUpper
6+
builtin toLower
7+
builtin title
8+
builtin trimSpace

‎stdlib/strings/strings.go‎

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
package strings
2+
3+
import (
4+
"fmt"
5+
"strings"
6+
7+
"github.com/influxdata/flux"
8+
"github.com/influxdata/flux/semantic"
9+
"github.com/influxdata/flux/values"
10+
)
11+
12+
func generateStringFunction(name string, stringFn func(string) string) values.Function {
13+
return values.NewFunction(
14+
name,
15+
semantic.NewFunctionType(semantic.FunctionSignature{
16+
Parameters: map[string]semantic.Type{stringArg: semantic.String},
17+
Required: semantic.LabelSet{stringArg},
18+
Return: semantic.String,
19+
}),
20+
func(args values.Object) (values.Value, error) {
21+
var str string
22+
23+
v, ok := args.Get(stringArg)
24+
if !ok {
25+
return nil, errMissingV
26+
}
27+
28+
if v.Type().Nature() == semantic.String {
29+
str = v.Str()
30+
31+
str = stringFn(str)
32+
return values.NewString(str), nil
33+
}
34+
35+
return nil, fmt.Errorf("cannot convert argument of type %v to upper case", v.Type().Nature())
36+
}, false,
37+
)
38+
}
39+
40+
func init() {
41+
flux.RegisterPackageValue("strings", "trim", generateMultiArgStringFunction("trim", strings.Trim))
42+
flux.RegisterPackageValue("strings", "trimSpace", generateStringFunction("trimSpace", strings.TrimSpace))
43+
flux.RegisterPackageValue("strings", "title", generateStringFunction("title", strings.Title))
44+
flux.RegisterPackageValue("strings", "toUpper", generateStringFunction("toUpper", strings.ToUpper))
45+
flux.RegisterPackageValue("strings", "toLower", generateStringFunction("toLower", strings.ToLower))
46+
}

0 commit comments

Comments
 (0)