3
0

Added registry, updated handlers

Updated modules

Added function definition endpoint
This commit is contained in:
Peter Grlica
2021-07-06 17:21:29 +02:00
parent 2388158141
commit 4e43020bf0
18 changed files with 529 additions and 248 deletions

View File

@@ -10,10 +10,13 @@ import (
automationRest "github.com/cortezaproject/corteza-server/automation/rest"
composeRest "github.com/cortezaproject/corteza-server/compose/rest"
"github.com/cortezaproject/corteza-server/compose/service"
"github.com/cortezaproject/corteza-server/docs"
federationRest "github.com/cortezaproject/corteza-server/federation/rest"
"github.com/cortezaproject/corteza-server/pkg/actionlog"
"github.com/cortezaproject/corteza-server/pkg/api/server"
"github.com/cortezaproject/corteza-server/pkg/apigw"
"github.com/cortezaproject/corteza-server/pkg/eventbus"
"github.com/cortezaproject/corteza-server/pkg/logger"
"github.com/cortezaproject/corteza-server/pkg/options"
"github.com/cortezaproject/corteza-server/pkg/webapp"
@@ -104,6 +107,12 @@ func (app *CortezaApp) mountHttpRoutes(r chi.Router) {
r.Route("/federation", federationRest.MountRoutes)
}
// temp api gateway support
{
apigw.Setup(struct{}{}, app.Log, eventbus.Service(), service.DefaultStore)
r.Route("/gateway", apigw.Service().Router(context.Background()))
}
var fullpathDocs = options.CleanBase(ho.BaseUrl, ho.ApiBaseUrl, "docs")
app.Log.Info(
"API docs enabled",

5
go.mod
View File

@@ -3,6 +3,7 @@ module github.com/cortezaproject/corteza-server
go 1.16
require (
github.com/0xAX/notificator v0.0.0-20191016112426-3962a5ea8da1 // indirect
github.com/766b/chi-prometheus v0.0.0-20180509160047-46ac2b31aa30
github.com/99designs/basicauth-go v0.0.0-20160802081356-2a93ba0f464d
github.com/Masterminds/goutils v1.1.0 // indirect
@@ -14,6 +15,8 @@ require (
github.com/SentimensRG/ctx v0.0.0-20180729130232-0bfd988c655d
github.com/asaskevich/govalidator v0.0.0-20210307081110-f21760c49a8d
github.com/brianvoe/gofakeit/v6 v6.5.0
github.com/codegangsta/envy v0.0.0-20141216192214-4b78388c8ce4 // indirect
github.com/codegangsta/gin v0.0.0-20171026143024-cafe2ce98974 // indirect
github.com/crewjam/saml v0.4.5
github.com/crusttech/go-oidc v0.0.0-20180918092017-982855dad3e1
github.com/davecgh/go-spew v1.1.1
@@ -50,6 +53,7 @@ require (
github.com/lestrrat-go/strftime v1.0.3
github.com/lib/pq v1.1.0
github.com/markbates/goth v1.67.1
github.com/mattn/go-shellwords v1.0.12 // indirect
github.com/mattn/go-sqlite3 v1.14.0
github.com/microcosm-cc/bluemonday v1.0.10
github.com/minio/minio-go/v6 v6.0.39
@@ -80,6 +84,7 @@ require (
gopkg.in/ini.v1 v1.51.0 // indirect
gopkg.in/mail.v2 v2.3.1
gopkg.in/square/go-jose.v2 v2.3.1 // indirect
gopkg.in/urfave/cli.v1 v1.20.0 // indirect
gopkg.in/yaml.v2 v2.3.0
gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776
rsc.io/qr v0.2.0

10
go.sum
View File

@@ -33,6 +33,8 @@ cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohl
cloud.google.com/go/storage v1.8.0/go.mod h1:Wv1Oy7z6Yz3DshWRJFhqM/UCfaWIRTdp0RXyy7KQOVs=
cloud.google.com/go/storage v1.10.0/go.mod h1:FLPqc6j+Ki4BU591ie1oL6qBQGu2Bl/tZ9ullr3+Kg0=
dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU=
github.com/0xAX/notificator v0.0.0-20191016112426-3962a5ea8da1 h1:j9HaafapDbPbGRDku6e/HRs6KBMcKHiWcm1/9Sbxnl4=
github.com/0xAX/notificator v0.0.0-20191016112426-3962a5ea8da1/go.mod h1:NtXa9WwQsukMHZpjNakTTz0LArxvGYdPA9CjIcUSZ6s=
github.com/766b/chi-prometheus v0.0.0-20180509160047-46ac2b31aa30 h1:bNHbCMKiQxpRNe4Pk2W09N1aXXc4ICOawQFKIDEicqc=
github.com/766b/chi-prometheus v0.0.0-20180509160047-46ac2b31aa30/go.mod h1:X/LhbmoBoRu8TxoGIOIraVNhfz3hhikJoaelrOuhdPY=
github.com/99designs/basicauth-go v0.0.0-20160802081356-2a93ba0f464d h1:j6oB/WPCigdOkxtuPl1VSIiLpy7Mdsu6phQffbF19Ng=
@@ -90,6 +92,10 @@ github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5P
github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU=
github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc=
github.com/codegangsta/envy v0.0.0-20141216192214-4b78388c8ce4 h1:ihrIKrLQzm6Q6NJHBMemvaIGTFxgxQUEkn2AjN0Aulw=
github.com/codegangsta/envy v0.0.0-20141216192214-4b78388c8ce4/go.mod h1:X7wHz0C25Lga6CnJ4WAQNbUQ9P/8eWSNv8qIO71YkSM=
github.com/codegangsta/gin v0.0.0-20171026143024-cafe2ce98974 h1:ysuVNDVE4LIky6I+6JlgAKG+wBNKMpVv3m3neVpvFVw=
github.com/codegangsta/gin v0.0.0-20171026143024-cafe2ce98974/go.mod h1:UBYuwaH3dMw91EZ7tGVaFF6GDj5j46S7zqB9lZPIe58=
github.com/crewjam/httperr v0.0.0-20190612203328-a946449404da h1:WXnT88cFG2davqSFqvaFfzkSMC0lqh/8/rKZ+z7tYvI=
github.com/crewjam/httperr v0.0.0-20190612203328-a946449404da/go.mod h1:+rmNIXRvYMqLQeR4DHyTvs6y0MEMymTz4vyFpFkKTPs=
github.com/crewjam/saml v0.4.5 h1:H9u+6CZAESUKHxMyxUbVn0IawYvKZn4nt3d4ccV4O/M=
@@ -288,6 +294,8 @@ github.com/mattermost/xml-roundtrip-validator v0.0.0-20201213122252-bcd7e1b9601e
github.com/mattermost/xml-roundtrip-validator v0.0.0-20201213122252-bcd7e1b9601e/go.mod h1:qccnGMcpgwcNaBnxqpJpWWUiPNr5H3O8eDgGV9gT5To=
github.com/mattn/go-colorable v0.1.7/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc=
github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU=
github.com/mattn/go-shellwords v1.0.12 h1:M2zGm7EW6UQJvDeQxo4T51eKPurbeFbe8WtebGE2xrk=
github.com/mattn/go-shellwords v1.0.12/go.mod h1:EZzvwXDESEeg03EKmM+RmDnNOPKG4lLtQsUlTZDWQ8Y=
github.com/mattn/go-sqlite3 v1.9.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc=
github.com/mattn/go-sqlite3 v1.14.0 h1:mLyGNKR8+Vv9CAU7PphKa2hkEqxxhn8i32J6FPj1/QA=
github.com/mattn/go-sqlite3 v1.14.0/go.mod h1:JIl7NbARA7phWnGvh0LKTyg7S9BA+6gx71ShQilpsus=
@@ -739,6 +747,8 @@ gopkg.in/mail.v2 v2.3.1/go.mod h1:htwXN1Qh09vZJ1NVKxQqHPBaCBbzKhp5GzuJEA4VJWw=
gopkg.in/square/go-jose.v2 v2.3.1 h1:SK5KegNXmKmqE342YYN2qPHEnUYeoMiXXl1poUlI+o4=
gopkg.in/square/go-jose.v2 v2.3.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI=
gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw=
gopkg.in/urfave/cli.v1 v1.20.0 h1:NdAVW6RYxDif9DhDHaAortIu956m2c0v+09AZBPTbE0=
gopkg.in/urfave/cli.v1 v1.20.0/go.mod h1:vuBzUtMdQeixQj8LVd+/98pzhxNGQoyuPBlsXHOQNO0=
gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=

View File

@@ -173,3 +173,16 @@ func (s *apigw) Init(ctx context.Context, route ...*route) {
}
}
}
func (s *apigw) Funcs(kind string) (list functionMetaList) {
list = s.reg.All()
if kind != "" {
list, _ = list.Filter(func(fm *functionMeta) (bool, error) {
// return fm.
return fm.Kind == kind, nil
})
}
return
}

View File

@@ -2,51 +2,56 @@ package apigw
import (
"context"
"encoding/json"
"fmt"
"net/http"
"net/http/httptest"
"github.com/cortezaproject/corteza-server/pkg/expr"
"github.com/cortezaproject/corteza-server/pkg/wfexec"
"github.com/cortezaproject/corteza-server/system/types"
"github.com/davecgh/go-spew/spew"
)
type (
redirectExpediterArgs struct {
Location string
expediterRedirection struct{}
errorHandler struct {
name string
args []string
weight int
step int
}
)
func redirectExpediter(c context.Context, params *expr.Vars) wfHandler {
var (
clv = redirectExpediterArgs{}
)
return func(c context.Context, er *wfexec.ExecRequest) (r wfexec.ExecResponse, err error) {
params.Decode(&clv)
spew.Dump("redirect expediter fn()", clv)
e := er.Scope.GetValue()["envelope"]
ee := e.Get().(envelope)
http.Redirect(ee.Writer, ee.Request, clv.Location, http.StatusTemporaryRedirect)
r = &expr.Vars{}
return
func (h expediterRedirection) Meta(f *types.Function) functionMeta {
return functionMeta{
Step: 3,
Name: "expediterRedirection",
Label: "Redirection expediter",
Kind: "expediter",
Weight: int(f.Weight),
Params: f.Params,
}
}
func expediterErrorFn(c context.Context, er *wfexec.ExecRequest) (r wfexec.ExecResponse, err error) {
// spew.Dump("expediter error fn()", er)
func (h expediterRedirection) Handler() handlerFunc {
return func(ctx context.Context, scope *scp, params map[string]interface{}, ff functionHandler) error {
scope.writer.Header().Add(fmt.Sprintf("step_%d", ff.step), ff.name)
http.Redirect(scope.writer, scope.req, params["location"].(string), http.StatusFound)
e := er.Scope.GetValue()["error"]
values := er.Scope.GetValue()["writer"]
writer := values.Get()
eValue := e.Get()
fmt.Fprintf(writer.(*httptest.ResponseRecorder), fmt.Sprintf(`{"msg": "%s"}`, eValue))
writer.(*httptest.ResponseRecorder).Code = http.StatusBadGateway
r = &expr.Vars{}
return
return nil
}
}
func (pp errorHandler) Exec(ctx context.Context, scope *scp, err error) {
type (
responseHelper struct {
Msg string `json:"msg"`
}
)
resp := responseHelper{
Msg: err.Error(),
}
spew.Dump("ERR in expediter", err, resp)
json.NewEncoder(scope.writer).Encode(resp)
}

View File

@@ -7,6 +7,8 @@ import (
)
type (
functionMetaList []*functionMeta
Handler interface {
Handler() handlerFunc
Meta(f *types.Function) functionMeta
@@ -15,12 +17,20 @@ type (
handlerFunc func(context.Context, *scp, map[string]interface{}, functionHandler) error
functionMeta struct {
step int
weight int
name string
label string
kind string
params map[string]interface{}
Step int `json:"step"`
Weight int `json:"-"`
Name string `json:"name"`
Label string `json:"label"`
Kind string `json:"kind"`
Params map[string]interface{} `json:"-"`
Args []*functionMetaArg `json:"params,omitempty"`
}
functionMetaArg struct {
Label string `json:"label"`
Type string `json:"type"`
Example string `json:"example"`
Options map[string]interface{} `json:"options"`
}
functionHandler struct {
@@ -43,12 +53,12 @@ func (ff *functionHandler) SetHandler(h handlerFunc) {
}
func (ff *functionHandler) Merge(ctx context.Context, p functionMeta) {
ff.step = p.step
ff.kind = p.kind
ff.label = p.label
ff.name = p.name
ff.weight = p.weight
ff.params = p.params
ff.step = p.Step
ff.kind = p.Kind
ff.label = p.Label
ff.name = p.Name
ff.weight = p.Weight
ff.params = p.Params
}
func (ff functionHandler) Weight() int {
@@ -56,3 +66,17 @@ func (ff functionHandler) Weight() int {
// per step, we're doing something wrong
return ff.step*1000 + ff.weight
}
func (fm functionMetaList) Filter(f func(*functionMeta) (bool, error)) (out functionMetaList, err error) {
var ok bool
out = functionMetaList{}
for i := range fm {
if ok, err = f(fm[i]); err != nil {
return
} else if ok {
out = append(out, fm[i])
}
}
return
}

View File

@@ -1,42 +0,0 @@
package apigw
import (
"context"
"errors"
"github.com/cortezaproject/corteza-server/pkg/expr"
"github.com/cortezaproject/corteza-server/pkg/wfexec"
"github.com/davecgh/go-spew/spew"
)
type (
authenticationOriginMatcherArgs struct {
Origin string
}
)
func authenticationOriginMatcher(c context.Context, params *expr.Vars) wfHandler {
var (
aomp = authenticationOriginMatcherArgs{}
)
return func(c context.Context, er *wfexec.ExecRequest) (r wfexec.ExecResponse, err error) {
params.Decode(&aomp)
spew.Dump("authentication origin matcher fn()", aomp)
e := er.Scope.GetValue()["envelope"]
ee := e.Get().(envelope)
origin := ee.Request.Header.Get("Origin")
spew.Dump("input, real", aomp.Origin, origin)
if aomp.Origin != origin {
err = errors.New("origin fail")
return
}
r = &expr.Vars{}
return
}
}

View File

@@ -3,53 +3,88 @@ package apigw
import (
"context"
"github.com/cortezaproject/corteza-server/pkg/expr"
"github.com/cortezaproject/corteza-server/pkg/wfexec"
"github.com/davecgh/go-spew/spew"
"github.com/cortezaproject/corteza-server/pkg/eventbus"
"github.com/cortezaproject/corteza-server/system/types"
)
func formDataProcesserFn(c context.Context, er *wfexec.ExecRequest) (r wfexec.ExecResponse, err error) {
type (
formDataProcesserResponse struct {
Name string `json:"name"`
}
)
type (
dispatcher interface {
Dispatch(ctx context.Context, ev eventbus.Event)
}
spew.Dump("step processer fn()")
processerWorkflow struct {
d dispatcher
}
)
e := er.Scope.GetValue()["envelope"]
ee := e.Get()
// ee.(envelope).Writer.WriteHeader(int(id))
ee.(envelope).Writer.Write([]byte(`{"test":"foobar"}`))
e.Assign(ee)
// req := values.Get()
// ww := wr.Get()
// writer := ww.(http.ResponseWriter)
// formValue := req.(*http.Request).PostFormValue("name")
// resp := formDataProcesserResponse{
// // Name: fmt.Sprintf("AA %s AA", formValue),
// Name: "formValue",
// }
// encoder := json.NewEncoder(writer)
// encoder.Encode(resp)
// writer.(*httptest.ResponseRecorder).Header()["Content-Type"] = []string{"application/json"}
// writer.Header().Set("Content-Type", "application/json3")
// spew.Dump(writer.(*httptest.ResponseRecorder).Header())
// a, b := expr.NewKV(writer)
// spew.Dump("Aaaaaaaaaaa", a)
vv := &expr.Vars{}
// vv.Set("writer", writer)
r = vv
return
func (h processerWorkflow) Meta(f *types.Function) functionMeta {
return functionMeta{
Step: 2,
Name: "processerWorkflow",
Label: "Workflow processer",
Kind: "processer",
Weight: int(f.Weight),
Params: f.Params,
Args: []*functionMetaArg{
{
Type: "workflow",
Label: "workflow",
Options: map[string]interface{}{},
},
},
}
}
func (h processerWorkflow) Handler() handlerFunc {
return func(ctx context.Context, scope *scp, params map[string]interface{}, ff functionHandler) error {
// h.d.Dispatch(c, event.ApiOnProcess(&envlp))
return nil
}
}
// func formDataProcesserFn(c context.Context, er *wfexec.ExecRequest) (r wfexec.ExecResponse, err error) {
// type (
// formDataProcesserResponse struct {
// Name string `json:"name"`
// }
// )
// spew.Dump("step processer fn()")
// e := er.Scope.GetValue()["envelope"]
// ee := e.Get()
// // ee.(envelope).Writer.WriteHeader(int(id))
// ee.(envelope).Writer.Write([]byte(`{"test":"foobar"}`))
// e.Assign(ee)
// // req := values.Get()
// // ww := wr.Get()
// // writer := ww.(http.ResponseWriter)
// // formValue := req.(*http.Request).PostFormValue("name")
// // resp := formDataProcesserResponse{
// // // Name: fmt.Sprintf("AA %s AA", formValue),
// // Name: "formValue",
// // }
// // encoder := json.NewEncoder(writer)
// // encoder.Encode(resp)
// // writer.(*httptest.ResponseRecorder).Header()["Content-Type"] = []string{"application/json"}
// // writer.Header().Set("Content-Type", "application/json3")
// // spew.Dump(writer.(*httptest.ResponseRecorder).Header())
// // a, b := expr.NewKV(writer)
// // spew.Dump("Aaaaaaaaaaa", a)
// vv := &expr.Vars{}
// // vv.Set("writer", writer)
// r = vv
// return
// }

52
pkg/apigw/registry.go Normal file
View File

@@ -0,0 +1,52 @@
package apigw
import (
"fmt"
"github.com/cortezaproject/corteza-server/system/types"
)
type (
registry struct {
h map[string]Handler
}
)
func NewRegistry() *registry {
return &registry{
h: map[string]Handler{},
}
}
func (r *registry) Add(n string, h Handler) {
r.h[n] = h
}
func (r *registry) Get(identifier string) (Handler, error) {
var (
ok bool
f Handler
)
if f, ok = r.h[identifier]; !ok {
return nil, fmt.Errorf("could not get element from registry: %s", identifier)
}
return f, nil
}
func (r *registry) All() (list functionMetaList) {
for _, handler := range r.h {
m := handler.Meta(&types.Function{})
list = append(list, &m)
}
return
}
func (r *registry) Preload() {
r.Add("verifierQueryParam", verifierQueryParam{})
r.Add("verifierOrigin", verifierOrigin{})
r.Add("expediterRedirection", expediterRedirection{})
r.Add("processerWorkflow", processerWorkflow{})
}

View File

@@ -3,62 +3,30 @@ package apigw
import (
"context"
"net/http"
"github.com/cortezaproject/corteza-server/pkg/expr"
"github.com/cortezaproject/corteza-server/pkg/logger"
"github.com/cortezaproject/corteza-server/pkg/wfexec"
"github.com/davecgh/go-spew/spew"
)
type (
route struct {
ID uint64
endpoint string
method string
graph *wfexec.Graph
steps []wfexec.Step
fns wfHandlerList
pipe *pl
}
)
func (r route) validate(req *http.Request) (err error) {
// if req.Method != r.method {
// err = errors.New("http method invalid")
// }
return
}
func (r route) ServeHTTP(w http.ResponseWriter, req *http.Request) {
if err := r.validate(req); err != nil {
spew.Dump("ERR", err)
return
}
var (
ctx = context.Background()
scope = scp{
req: req,
writer: w,
}
)
sess := wfexec.NewSession(context.Background(), r.graph, wfexec.SetLogger(logger.Default()), wfexec.SetHandler(func(ss wfexec.SessionStatus, s1 *wfexec.State, s2 *wfexec.Session) {
// spew.Dump("event handler here!", ss)
}))
scope := &expr.Vars{}
scope.Set("envelope", envelope{
Request: req,
Writer: w,
})
if len(r.steps) == 0 {
// dont serve, do what? return default response?
return
}
err := sess.Exec(context.Background(), r.steps[0], scope)
// if err != nil {
// fmt.Fprintf(w, "no go, err on exec: %s", err)
// return
// }
err = sess.Wait(context.Background())
err := r.pipe.Exec(ctx, &scope)
if err != nil {
// log error
}
}

View File

@@ -1,40 +0,0 @@
package apigw
import (
"context"
"errors"
"github.com/cortezaproject/corteza-server/pkg/expr"
"github.com/cortezaproject/corteza-server/pkg/wfexec"
"github.com/davecgh/go-spew/spew"
)
type (
contentLengthValidatorArgs struct {
Length int
}
)
func contentLengthValidator(c context.Context, params *expr.Vars) wfHandler {
var (
clv = contentLengthValidatorArgs{}
)
return func(c context.Context, er *wfexec.ExecRequest) (r wfexec.ExecResponse, err error) {
params.Decode(&clv)
spew.Dump("body size validator fn()", clv)
e := er.Scope.GetValue()["envelope"]
ee := e.Get().(envelope)
cl := ee.Request.ContentLength
if clv.Length < int(cl) {
err = errors.New("content length overriden")
return
}
r = &expr.Vars{}
return
}
}

157
pkg/apigw/verifier.go Normal file
View File

@@ -0,0 +1,157 @@
package apigw
import (
"context"
"fmt"
"github.com/cortezaproject/corteza-server/pkg/expr"
"github.com/cortezaproject/corteza-server/system/types"
"github.com/davecgh/go-spew/spew"
)
type (
verifierQueryParam struct{}
verifierOrigin struct{}
)
func (h verifierQueryParam) Meta(f *types.Function) functionMeta {
return functionMeta{
Step: 0,
Name: "verifierQueryParam",
Label: "Query parameters verifier",
Kind: "verifier",
Weight: int(f.Weight),
Params: f.Params,
Args: []*functionMetaArg{
{
Type: "expr",
Label: "expr",
Options: map[string]interface{}{},
},
},
}
}
func (h verifierOrigin) Meta(f *types.Function) functionMeta {
return functionMeta{
Step: 0,
Name: "verifierOrigin",
Label: "Origin verifier",
Kind: "verifier",
Weight: int(f.Weight),
Params: f.Params,
Args: []*functionMetaArg{
{
Type: "expr",
Label: "expr",
Options: map[string]interface{}{},
},
},
}
}
func (h verifierQueryParam) Handler() handlerFunc {
return func(ctx context.Context, scope *scp, params map[string]interface{}, ff functionHandler) error {
for k := range ff.params {
v, ok := params[k]
if !ok {
spew.Dump("not in params", k)
continue
}
vv := map[string]interface{}{}
vals := scope.req.URL.Query()
for k, v := range vals {
vv[k] = v[0]
}
// get the request data and put it into vars
out, err := expr.NewVars(vv)
if err != nil {
// spew.Dump("ERR!", err)
return err
}
pp := expr.NewParser()
tt, err := pp.Parse(v.(string))
if err != nil {
// spew.Dump("ERR!", err)
return err
}
b, err := tt.Test(ctx, out)
if err != nil {
// spew.Dump("ERR!", err)
return err
}
spew.Dump("BBBB", b)
if !b {
return fmt.Errorf("failed on step %d, function %s", ff.step, ff.name)
}
}
// testing
scope.req.Header.Add(fmt.Sprintf("step_%d", ff.step), ff.name)
return nil
}
}
func (h verifierOrigin) Handler() handlerFunc {
return func(ctx context.Context, scope *scp, params map[string]interface{}, ff functionHandler) error {
for k := range ff.params {
v, ok := params[k]
if !ok {
spew.Dump("not in params", k)
continue
}
vv := map[string]interface{}{
"origin": scope.req.Header.Get("Origin"),
}
// get the request data and put it into vars
out, err := expr.NewVars(vv)
if err != nil {
spew.Dump("ERR!", err)
return err
}
pp := expr.NewParser()
tt, err := pp.Parse(v.(string))
if err != nil {
spew.Dump("ERR!", err)
return err
}
b, err := tt.Test(ctx, out)
if err != nil {
spew.Dump("ERR!", err)
return err
}
spew.Dump("BBBB", b)
if !b {
return fmt.Errorf("failed on step %d, function %s", ff.step, ff.name)
}
}
// testing
scope.req.Header.Add(fmt.Sprintf("step_%d", ff.step), ff.name)
return nil
}
}

View File

@@ -1510,7 +1510,6 @@ endpoints:
entrypoint: route
authentication: []
imports:
# - github.com/cortezaproject/corteza-server/system/types
- github.com/cortezaproject/corteza-server/pkg/label
apis:
- name: list
@@ -1521,8 +1520,8 @@ endpoints:
get:
- { name: routeID, type: "[]string", title: "Filter by route ID" }
- { name: query, type: "string", title: "Filter routes" }
- { name: deleted, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) deleted routes" }
- { name: disabled, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) disabled routes" }
- { name: deleted, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) deleted routes" }
- { name: disabled, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) disabled routes" }
- { name: labels, type: "map[string]string", title: "Labels", parser: "label.ParseStrings" }
- { name: limit, type: "uint", title: "Limit" }
- { name: pageCursor, type: "string", title: "Page cursor" }
@@ -1535,10 +1534,9 @@ endpoints:
post:
- { name: endpoint, type: string, required: true, title: "Route endpoint" }
- { name: method, type: string, title: "Route method" }
# - { name: meta, type: "*types.RouteMeta", title: "Route meta data", parser: "types.ParseRouteMeta" }
- { name: debug, type: bool, title: "Debug route" }
- { name: enabled, type: bool, title: "Is route enabled" }
- { name: group, type: uint64, title: "Route group" }
- { name: group, type: uint64, title: "Route group" }
- name: update
method: PUT
title: Update route details
@@ -1550,7 +1548,7 @@ endpoints:
- { name: method, type: string, title: "Route method" }
- { name: debug, type: bool, title: "Debug route" }
- { name: enabled, type: bool, title: "Is route enabled" }
- { name: group, type: uint64, title: "Route group" }
- { name: group, type: uint64, title: "Route group" }
- name: read
method: GET
title: Read route details
@@ -1585,7 +1583,6 @@ endpoints:
authentication: []
imports:
- github.com/cortezaproject/corteza-server/system/types
# - github.com/cortezaproject/corteza-server/pkg/label
apis:
- name: list
method: GET
@@ -1593,26 +1590,25 @@ endpoints:
path: "/"
parameters:
get:
- { name: functionID, type: "[]string", title: "Filter by function ID" }
- { name: routeID, type: "string", title: "Filter by route ID" }
- { name: query, type: "string", title: "Filter functions" }
- { name: deleted, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) deleted functions" }
- { name: disabled, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) disabled functions" }
# - { name: labels, type: "map[string]string", title: "Labels", parser: "label.ParseStrings" }
- { name: limit, type: "uint", title: "Limit" }
- { name: pageCursor, type: "string", title: "Page cursor" }
- { name: sort, type: "string", title: "Sort items" }
- { name: functionID, type: "[]string", title: "Filter by function ID" }
- { name: routeID, type: "string", title: "Filter by route ID" }
- { name: query, type: "string", title: "Filter functions" }
- { name: deleted, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) deleted functions" }
- { name: disabled, type: "uint64", title: "Exclude (0, default), include (1) or return only (2) disabled functions" }
- { name: limit, type: "uint", title: "Limit" }
- { name: pageCursor, type: "string", title: "Page cursor" }
- { name: sort, type: "string", title: "Sort items" }
- name: create
method: PUT
title: Create function
path: ""
parameters:
post:
- { name: routeID, type: uint64, required: true, title: "Route" }
- { name: weight, type: uint64, title: "Function priority" }
- { name: kind, type: "types.ApigwFunctionKind", title: "Function kind" }
- { name: ref, type: string, title: "Function ref" }
- { name: params, type: "types.FuncParams", title: "Function parameters", parser: "types.ParseApigwfFunctionParams" }
- { name: routeID, type: uint64, title: "Route", required: true }
- { name: weight, type: uint64, title: "Function priority" }
- { name: kind, type: "types.ApigwFunctionKind", title: "Function kind" }
- { name: ref, type: string, title: "Function ref" }
- { name: params, type: "types.FuncParams", title: "Function parameters", parser: "types.ParseApigwfFunctionParams" }
- name: update
method: POST
title: Update route details
@@ -1620,11 +1616,11 @@ endpoints:
parameters:
path: [ { name: functionID, type: uint64, required: true, title: "Function ID" } ]
post:
- { name: routeID, type: uint64, required: true, title: "Route" }
- { name: weight, type: uint64, title: "Function priority" }
- { name: kind, type: "types.ApigwFunctionKind", title: "Function kind" }
- { name: ref, type: string, title: "Function ref" }
- { name: params, type: "types.FuncParams", title: "Function parameters", parser: "types.ParseApigwfFunctionParams" }
- { name: routeID, type: uint64, title: "Route", required: true }
- { name: weight, type: uint64, title: "Function priority" }
- { name: kind, type: "types.ApigwFunctionKind", title: "Function kind" }
- { name: ref, type: string, title: "Function ref" }
- { name: params, type: "types.FuncParams", title: "Function parameters", parser: "types.ParseApigwfFunctionParams" }
- name: read
method: GET
title: Read function details
@@ -1640,3 +1636,10 @@ endpoints:
title: Undelete function
path: "/{functionID}/undelete"
parameters: { path: [ { name: functionID, type: uint64, required: true, title: "Function ID" } ] }
- name: definitions
method: GET
title: Function definitions
path: "/def"
parameters:
get:
- { name: kind, type: "string", title: "Filter functions by kind" }

View File

@@ -32,6 +32,7 @@ type (
Update(ctx context.Context, upd *types.Function) (*types.Function, error)
DeleteByID(ctx context.Context, ID uint64) error
UndeleteByID(ctx context.Context, ID uint64) error
Definitions(context.Context, string) (interface{}, error)
}
)
@@ -106,6 +107,10 @@ func (ctrl *Function) Delete(ctx context.Context, r *request.FunctionDelete) (in
return api.OK(), ctrl.svc.DeleteByID(ctx, r.FunctionID)
}
func (ctrl *Function) Definitions(ctx context.Context, r *request.FunctionDefinitions) (interface{}, error) {
return ctrl.svc.Definitions(ctx, r.Kind)
}
func (ctrl *Function) Undelete(ctx context.Context, r *request.FunctionUndelete) (interface{}, error) {
return api.OK(), ctrl.svc.UndeleteByID(ctx, r.FunctionID)
}

View File

@@ -25,16 +25,18 @@ type (
Read(context.Context, *request.FunctionRead) (interface{}, error)
Delete(context.Context, *request.FunctionDelete) (interface{}, error)
Undelete(context.Context, *request.FunctionUndelete) (interface{}, error)
Definitions(context.Context, *request.FunctionDefinitions) (interface{}, error)
}
// HTTP API interface
Function struct {
List func(http.ResponseWriter, *http.Request)
Create func(http.ResponseWriter, *http.Request)
Update func(http.ResponseWriter, *http.Request)
Read func(http.ResponseWriter, *http.Request)
Delete func(http.ResponseWriter, *http.Request)
Undelete func(http.ResponseWriter, *http.Request)
List func(http.ResponseWriter, *http.Request)
Create func(http.ResponseWriter, *http.Request)
Update func(http.ResponseWriter, *http.Request)
Read func(http.ResponseWriter, *http.Request)
Delete func(http.ResponseWriter, *http.Request)
Undelete func(http.ResponseWriter, *http.Request)
Definitions func(http.ResponseWriter, *http.Request)
}
)
@@ -134,6 +136,22 @@ func NewFunction(h FunctionAPI) *Function {
return
}
api.Send(w, r, value)
},
Definitions: func(w http.ResponseWriter, r *http.Request) {
defer r.Body.Close()
params := request.NewFunctionDefinitions()
if err := params.Fill(r); err != nil {
api.Send(w, r, err)
return
}
value, err := h.Definitions(r.Context(), params)
if err != nil {
api.Send(w, r, err)
return
}
api.Send(w, r, value)
},
}
@@ -148,5 +166,6 @@ func (h Function) MountRoutes(r chi.Router, middlewares ...func(http.Handler) ht
r.Get("/apigw/function/{functionID}", h.Read)
r.Delete("/apigw/function/{functionID}", h.Delete)
r.Post("/apigw/function/{functionID}/undelete", h.Undelete)
r.Get("/apigw/function/def", h.Definitions)
})
}

View File

@@ -155,6 +155,13 @@ type (
// Function ID
FunctionID uint64 `json:",string"`
}
FunctionDefinitions struct {
// Kind GET parameter
//
// Filter functions by kind
Kind string
}
)
// NewFunctionList request
@@ -615,3 +622,38 @@ func (r *FunctionUndelete) Fill(req *http.Request) (err error) {
return err
}
// NewFunctionDefinitions request
func NewFunctionDefinitions() *FunctionDefinitions {
return &FunctionDefinitions{}
}
// Auditable returns all auditable/loggable parameters
func (r FunctionDefinitions) Auditable() map[string]interface{} {
return map[string]interface{}{
"kind": r.Kind,
}
}
// Auditable returns all auditable/loggable parameters
func (r FunctionDefinitions) GetKind() string {
return r.Kind
}
// Fill processes request and fills internal variables
func (r *FunctionDefinitions) Fill(req *http.Request) (err error) {
{
// GET params
tmp := req.URL.Query()
if val, ok := tmp["kind"]; ok && len(val) > 0 {
r.Kind, err = val[0], nil
if err != nil {
return err
}
}
}
return err
}

View File

@@ -4,6 +4,7 @@ import (
"context"
"github.com/cortezaproject/corteza-server/pkg/actionlog"
"github.com/cortezaproject/corteza-server/pkg/apigw"
a "github.com/cortezaproject/corteza-server/pkg/auth"
"github.com/cortezaproject/corteza-server/store"
"github.com/cortezaproject/corteza-server/system/types"
@@ -221,3 +222,8 @@ func (svc *function) Search(ctx context.Context, filter types.FunctionFilter) (r
return r, f, svc.recordAction(ctx, aProps, FunctionActionSearch, err)
}
func (svc *function) Definitions(ctx context.Context, kind string) (interface{}, error) {
// get the definitions from registry
return apigw.Service().Funcs(kind), nil
}

10
vendor/modules.txt vendored
View File

@@ -1,5 +1,7 @@
# cloud.google.com/go v0.67.0
cloud.google.com/go/compute/metadata
# github.com/0xAX/notificator v0.0.0-20191016112426-3962a5ea8da1
## explicit
# github.com/766b/chi-prometheus v0.0.0-20180509160047-46ac2b31aa30
## explicit
github.com/766b/chi-prometheus
@@ -48,6 +50,10 @@ github.com/brianvoe/gofakeit/v6/data
github.com/cespare/xxhash/v2
# github.com/chris-ramon/douceur v0.2.0
## explicit
# github.com/codegangsta/envy v0.0.0-20141216192214-4b78388c8ce4
## explicit
# github.com/codegangsta/gin v0.0.0-20171026143024-cafe2ce98974
## explicit
# github.com/crewjam/httperr v0.0.0-20190612203328-a946449404da
github.com/crewjam/httperr
# github.com/crewjam/saml v0.4.5
@@ -192,6 +198,8 @@ github.com/markbates/goth/providers/linkedin
github.com/markbates/goth/providers/openidConnect
# github.com/mattermost/xml-roundtrip-validator v0.0.0-20201213122252-bcd7e1b9601e
github.com/mattermost/xml-roundtrip-validator
# github.com/mattn/go-shellwords v1.0.12
## explicit
# github.com/mattn/go-sqlite3 v1.14.0
## explicit
github.com/mattn/go-sqlite3
@@ -443,6 +451,8 @@ gopkg.in/mail.v2
gopkg.in/square/go-jose.v2
gopkg.in/square/go-jose.v2/cipher
gopkg.in/square/go-jose.v2/json
# gopkg.in/urfave/cli.v1 v1.20.0
## explicit
# gopkg.in/yaml.v2 v2.3.0
## explicit
gopkg.in/yaml.v2