diff --git a/docker-compose.yml b/docker-compose.yml index 4b7230c6d..9e7490c7d 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -4,7 +4,13 @@ services: node_1: image: ${SCYLLA_IMAGE} privileged: true - command: --smp 2 --memory 768M --seeds 192.168.100.11 --overprovisioned 1 + command: | + --smp 2 + --memory 768M + --seeds 192.168.100.11 + --overprovisioned 1 + --experimental-features udf + --enable-user-defined-functions true networks: public: ipv4_address: 192.168.100.11 diff --git a/recreate.go b/recreate.go index af4a585e1..64a4a20bb 100644 --- a/recreate.go +++ b/recreate.go @@ -109,10 +109,10 @@ var functionTemplate = template.Must(template.New("functions"). "stripFrozen": cqlHelpers.stripFrozen, }). Parse(` -CREATE FUNCTION {{ escape .keyspaceName }}.{{ escape .fm.Name }} ( +CREATE FUNCTION {{ .keyspaceName }}.{{ .fm.Name }} ( {{- range $i, $args := zip .fm.ArgumentNames .fm.ArgumentTypes }} {{- if ne $i 0 }}, {{ end }} - {{- escape (index $args 0) }} + {{- (index $args 0) }} {{ stripFrozen (index $args 1) }} {{- end -}}) {{ if .fm.CalledOnNullInput }}CALLED{{ else }}RETURNS NULL{{ end }} ON NULL INPUT @@ -167,19 +167,19 @@ var aggregatesTemplate = template.Must(template.New("aggregate"). }). Parse(` CREATE AGGREGATE {{ .Keyspace }}.{{ .Name }}( - {{- range $arg, $i := .ArgumentTypes }} + {{- range $i, $arg := .ArgumentTypes }} {{- if ne $i 0 }}, {{ end }} {{ stripFrozen $arg }} {{- end -}}) SFUNC {{ .StateFunc.Name }} - STYPE {{ stripFrozen .State }} + STYPE {{ stripFrozen .StateType }} {{- if ne .FinalFunc.Name "" }} FINALFUNC {{ .FinalFunc.Name }} {{- end -}} {{- if ne .InitCond "" }} INITCOND {{ .InitCond }} {{- end -}} -); +; `)) func (km *KeyspaceMetadata) aggregateToCQL(w io.Writer, am *AggregateMetadata) error { diff --git a/recreate_test.go b/recreate_test.go index 609ba85c4..ee6976deb 100644 --- a/recreate_test.go +++ b/recreate_test.go @@ -61,6 +61,12 @@ func TestRecreateSchema(t *testing.T) { Input: "testdata/recreate/udt.cql", Golden: "testdata/recreate/udt_golden.cql", }, + { + Name: "Aggregates", + Keyspace: "gocqlx_aggregates", + Input: "testdata/recreate/aggregates.cql", + Golden: "testdata/recreate/aggregates_golden.cql", + }, } for i := range tcs { diff --git a/testdata/recreate/aggregates.cql b/testdata/recreate/aggregates.cql new file mode 100644 index 000000000..f12e47ee1 --- /dev/null +++ b/testdata/recreate/aggregates.cql @@ -0,0 +1,31 @@ +CREATE KEYSPACE gocqlx_aggregates WITH replication = { + 'class': 'SimpleStrategy', + 'replication_factor': '2' +}; + +CREATE FUNCTION gocqlx_aggregates.avgstate( + state tuple, + val double) +CALLED ON NULL INPUT +RETURNS frozen> +LANGUAGE lua +AS $$ + return { state[1]+1, state[2]+val } + $$; + +CREATE FUNCTION gocqlx_aggregates.avgfinal( + state tuple) +CALLED ON NULL INPUT +RETURNS double +LANGUAGE lua +as $$ + r=0 + r=state[2] + r=r/state[1] + return r + $$; + +CREATE AGGREGATE gocqlx_aggregates.average(double) +SFUNC avgstate STYPE tuple +FINALFUNC avgfinal +INITCOND (0,0.0); diff --git a/testdata/recreate/aggregates_golden.cql b/testdata/recreate/aggregates_golden.cql new file mode 100644 index 000000000..cad3c528f --- /dev/null +++ b/testdata/recreate/aggregates_golden.cql @@ -0,0 +1,33 @@ +CREATE KEYSPACE gocqlx_aggregates WITH replication = { + 'class': 'SimpleStrategy', + 'replication_factor': '2' +}; + +CREATE FUNCTION gocqlx_aggregates.avgstate (state + tuple, val + double) + CALLED ON NULL INPUT + RETURNS frozen> + LANGUAGE lua + AS $$ + return { state[1]+1, state[2]+val } + $$; + +CREATE FUNCTION gocqlx_aggregates.avgfinal (state + tuple) + CALLED ON NULL INPUT + RETURNS double + LANGUAGE lua + AS $$ + r=0 + r=state[2] + r=r/state[1] + return r + $$; + +CREATE AGGREGATE gocqlx_aggregates.average( + double) + SFUNC avgstate + STYPE tuple + FINALFUNC avgfinal + INITCOND (0, 0);