Skip to content

Commit 95cff61

Browse files
authored
[feat] add uuid and base32 for random lib (#48)
* add uuid and b32 * b32 * dash it * S * add docs * fix typo
1 parent 5963327 commit 95cff61

File tree

7 files changed

+162
-0
lines changed

7 files changed

+162
-0
lines changed

cmd/starlet/go.mod

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ require (
1717
github.com/aymanbagabas/go-osc52 v1.0.3 // indirect
1818
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e // indirect
1919
github.com/gonutz/w32 v1.0.0 // indirect
20+
github.com/google/uuid v1.6.0 // indirect
2021
github.com/lucasb-eyer/go-colorful v1.2.0 // indirect
2122
github.com/mattn/go-isatty v0.0.16 // indirect
2223
github.com/mattn/go-runewidth v0.0.14 // indirect

cmd/starlet/go.sum

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1 h1:q763qf9huN11kDQavWs
1515
github.com/gonutz/w32 v1.0.0 h1:3t1z6ZfkFvirjFYBx9pHeHBuKoN/VBVk9yHb/m2Ll/k=
1616
github.com/gonutz/w32 v1.0.0/go.mod h1:Rc/YP5K9gv0FW4p6X9qL3E7Y56lfMflEol1fLElfMW4=
1717
github.com/google/go-cmp v0.5.1 h1:JFrFEBb2xKufg6XkJsJr+WbKb4FQlURi5RUcBveYu9k=
18+
github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0=
19+
github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
1820
github.com/lucasb-eyer/go-colorful v1.2.0 h1:1nnpGOrhyZZuNyfu1QjKiUICQ74+3FNCN69Aj6K7nkY=
1921
github.com/lucasb-eyer/go-colorful v1.2.0/go.mod h1:R4dSotOR9KMtayYi1e77YzuveK+i7ruzyGqttikkLy0=
2022
github.com/mattn/go-isatty v0.0.16 h1:bq3VjFmv/sOjHtdEhmkEV4x1AJtvUvOJ2PFAZ5+peKQ=

go.mod

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ go 1.18
44

55
require (
66
github.com/1set/starlight v0.0.8
7+
github.com/google/uuid v1.6.0
78
go.starlark.net v0.0.0-20231121155337-90ade8b19d09
89
)
910

go.sum

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e h1:fY5BOSpyZCqRo5O
55
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI=
66
github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1 h1:q763qf9huN11kDQavWsoZXJNW3xEE4JJyHa5Q25/sd8=
77
github.com/google/go-cmp v0.5.1 h1:JFrFEBb2xKufg6XkJsJr+WbKb4FQlURi5RUcBveYu9k=
8+
github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0=
9+
github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
810
go.starlark.net v0.0.0-20231121155337-90ade8b19d09 h1:hzy3LFnSN8kuQK8h9tHl4ndF6UruMj47OqwqsS+/Ai4=
911
go.starlark.net v0.0.0-20231121155337-90ade8b19d09/go.mod h1:LcLNIzVOMp4oV+uusnpk+VU+SzXaJakUuBjoCSWH5dM=
1012
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8 h1:0A+M6Uqn+Eje4kHMK80dtF3JCXC4ykBgQG4Fe06QRhQ=

lib/random/README.md

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,30 @@ print(s)
5151
# Output: "enfknqfbra"
5252
```
5353

54+
### `randb32(n, sep)`
55+
56+
Generate a random base32 string containing n number of bytes with optional separator dash for every sep characters.
57+
58+
#### Parameters
59+
60+
| name | type | description |
61+
|-------|-------|---------------------------------------------------------------------------------------------------------------|
62+
| `n` | `int` | The number of bytes to generate. If n is non-positive or not supplied, a reasonable default is used. |
63+
| `sep` | `int` | The number of characters to separate with a dash, if it's non-positive or not supplied, no separator is used. |
64+
65+
#### Examples
66+
67+
**basic**
68+
69+
Generate a random base32 string containing 10 bytes with no separator.
70+
71+
```python
72+
load("random", "randb32")
73+
s = randb32(10, 4)
74+
print(s)
75+
# Output: 2RXQ-H45H-WV
76+
```
77+
5478
### `randint(a,b)`
5579

5680
Return a random integer N such that a <= N <= b.
@@ -117,6 +141,23 @@ print(n)
117141
# Output: 7.309677873766576
118142
```
119143

144+
### `uuid4()`
145+
146+
Generate a random UUID (RFC 4122 version 4).
147+
148+
#### Examples
149+
150+
**basic**
151+
152+
Generate a random UUID.
153+
154+
```python
155+
load("random", "uuid")
156+
u = uuid()
157+
print(u)
158+
# Output: 6e360b7a-f677-4f6c-9c57-8b09694d66b3
159+
```
160+
120161
### `choice(seq)`
121162

122163
Return a random element from the non-empty sequence seq.

lib/random/random.go

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import (
88
"sync"
99

1010
itn "github.com/1set/starlet/internal"
11+
guuid "github.com/google/uuid"
1112
"go.starlark.net/starlark"
1213
"go.starlark.net/starlarkstruct"
1314
)
@@ -29,11 +30,13 @@ func LoadModule() (starlark.StringDict, error) {
2930
Members: starlark.StringDict{
3031
"randbytes": starlark.NewBuiltin("random.randbytes", randbytes),
3132
"randstr": starlark.NewBuiltin("random.randstr", randstr),
33+
"randb32": starlark.NewBuiltin("random.randb32", randb32),
3234
"randint": starlark.NewBuiltin("random.randint", randint),
3335
"choice": starlark.NewBuiltin("random.choice", choice),
3436
"shuffle": starlark.NewBuiltin("random.shuffle", shuffle),
3537
"random": starlark.NewBuiltin("random.random", random),
3638
"uniform": starlark.NewBuiltin("random.uniform", uniform),
39+
"uuid": starlark.NewBuiltin("random.uuid", uuid),
3740
},
3841
},
3942
}
@@ -91,6 +94,44 @@ func randstr(thread *starlark.Thread, bn *starlark.Builtin, args starlark.Tuple,
9194
return starlark.String(s), nil
9295
}
9396

97+
// randb32(n, sep) returns a random base32 string of length n with optional separator dash for every sep characters.
98+
func randb32(thread *starlark.Thread, bn *starlark.Builtin, args starlark.Tuple, kwargs []starlark.Tuple) (starlark.Value, error) {
99+
// precondition checks
100+
var n, sep starlark.Int
101+
if err := starlark.UnpackArgs(bn.Name(), args, kwargs, "n?", &n, "sep?", &sep); err != nil {
102+
return nil, err
103+
}
104+
// set default value if n is not provided correctly
105+
nInt := n.BigInt()
106+
if nInt.Sign() <= 0 {
107+
nInt = defaultLenN
108+
}
109+
nSep := sep.BigInt()
110+
if nSep.Sign() <= 0 {
111+
nSep = big.NewInt(0)
112+
}
113+
// get random strings
114+
const ab = `ABCDEFGHIJKLMNOPQRSTUVWXYZ234567` // standard base32 encoding chars, as defined in RFC 4648.
115+
s, err := getRandStr(ab, nInt.Int64())
116+
if err != nil {
117+
return nil, err
118+
}
119+
// add separator
120+
if n := int(nSep.Int64()); n > 0 && n < len(s) {
121+
// add separator every n chars
122+
var buf []rune
123+
for i, r := range s {
124+
if i > 0 && i%n == 0 {
125+
buf = append(buf, '-', r)
126+
} else {
127+
buf = append(buf, r)
128+
}
129+
}
130+
s = string(buf)
131+
}
132+
return starlark.String(s), nil
133+
}
134+
94135
// randint(a, b) returns a random integer N such that a <= N <= b. Alias for randrange(a, b+1).
95136
func randint(thread *starlark.Thread, bn *starlark.Builtin, args starlark.Tuple, kwargs []starlark.Tuple) (starlark.Value, error) {
96137
// precondition checks
@@ -193,6 +234,12 @@ func random(thread *starlark.Thread, _ *starlark.Builtin, args starlark.Tuple, k
193234
return starlark.Float(f), nil
194235
}
195236

237+
// uuid() returns a random UUID (RFC 4122 version 4).
238+
func uuid(thread *starlark.Thread, _ *starlark.Builtin, args starlark.Tuple, kwargs []starlark.Tuple) (starlark.Value, error) {
239+
u := guuid.New()
240+
return starlark.String(u.String()), nil
241+
}
242+
196243
// uniform(a, b) returns a random floating point number N such that a <= N <= b for a <= b and b <= N <= a for b < a. The end-point value b may or may not be included in the range depending on floating-point rounding in the equation a + (b-a) * random().
197244
func uniform(thread *starlark.Thread, bn *starlark.Builtin, args starlark.Tuple, kwargs []starlark.Tuple) (starlark.Value, error) {
198245
// precondition checks

lib/random/random_test.go

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -405,6 +405,74 @@ func TestLoadModule_Random(t *testing.T) {
405405
return f >= 1 && f < 2
406406
},
407407
},
408+
{
409+
name: "uuid",
410+
script: itn.HereDoc(`
411+
load('random', 'uuid')
412+
val = uuid()
413+
print(val)
414+
assert.eq(len(val), 36)
415+
assert.eq(len(val.replace("-", "")), 32)
416+
`),
417+
},
418+
{
419+
name: "randb32 with 0 or 1 args",
420+
script: itn.HereDoc(`
421+
load('random', 'randb32')
422+
x = randb32()
423+
assert.eq(len(x), 10)
424+
425+
y = randb32(6)
426+
assert.eq(len(y), 6)
427+
`),
428+
},
429+
{
430+
name: "randb32 with incorrect args",
431+
script: itn.HereDoc(`
432+
load('random', 'randb32')
433+
x = randb32(-2)
434+
assert.eq(len(x), 10)
435+
y = randb32(0)
436+
assert.eq(len(y), 10)
437+
`),
438+
},
439+
{
440+
name: "randb32 with invalid type",
441+
script: itn.HereDoc(`
442+
load('random', 'randb32')
443+
randb32('1')
444+
`),
445+
wantErr: `random.randb32: for parameter n: got string, want int`,
446+
},
447+
{
448+
name: "randb32 with sep",
449+
script: itn.HereDoc(`
450+
load('random', 'randb32')
451+
x = randb32(20, 5)
452+
assert.eq(len(x), 20+3)
453+
assert.eq(x[5], '-')
454+
assert.eq(len(x.split('-')), 4)
455+
456+
y = randb32(20, 0)
457+
assert.eq(len(y), 20)
458+
459+
z = randb32(20, -1)
460+
assert.eq(len(z), 20)
461+
462+
w = randb32(20, 20)
463+
assert.eq(len(w), 20)
464+
465+
t = randb32(20, 21)
466+
assert.eq(len(t), 20)
467+
468+
u = randb32(20, 22)
469+
470+
v = randb32(20, 1)
471+
assert.eq(len(v), 20+19)
472+
assert.eq(v[1], '-')
473+
assert.eq(len(v.split('-')), 20)
474+
`),
475+
},
408476
}
409477
for _, tt := range tests {
410478
t.Run(tt.name, func(t *testing.T) {

0 commit comments

Comments
 (0)