Fixed webhooks for local execution
This commit is contained in:
@@ -1,5 +1,5 @@
|
|||||||
# Shuffle
|
# Shuffle
|
||||||
[Shuffler](https://shuffler.io) is an automation platform for your security stack. It leverages docker for scaling and OpenAPI for integrations. It has the possibility to run across multiple isolated environments, and gives you powerful tools to track progress.
|
[Shuffle](https://shuffler.io) is an automation platform for your security stack. It leverages docker for scaling and OpenAPI for integrations. It has the possibility to run across multiple isolated environments, and gives you powerful tools to track progress.
|
||||||
|
|
||||||
## Try it
|
## Try it
|
||||||
Check out the [installation guide](https://github.com/frikky/shuffle/blob/master/install-guide.md)
|
Check out the [installation guide](https://github.com/frikky/shuffle/blob/master/install-guide.md)
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ ADD ./go-app/main.go /app
|
|||||||
ADD ./go-app/walkoff.go /app
|
ADD ./go-app/walkoff.go /app
|
||||||
ADD ./go-app/docker.go /app
|
ADD ./go-app/docker.go /app
|
||||||
ADD ./go-app/codegen.go /app
|
ADD ./go-app/codegen.go /app
|
||||||
|
ADD ./go-app/webhook.go /app
|
||||||
|
|
||||||
ADD ./go-app/go.mod /app
|
ADD ./go-app/go.mod /app
|
||||||
|
|
||||||
|
|||||||
@@ -17,6 +17,7 @@ require (
|
|||||||
github.com/go-git/go-billy/v5 v5.0.0
|
github.com/go-git/go-billy/v5 v5.0.0
|
||||||
github.com/go-git/go-git/v5 v5.0.0
|
github.com/go-git/go-git/v5 v5.0.0
|
||||||
github.com/google/go-github/v28 v28.1.1
|
github.com/google/go-github/v28 v28.1.1
|
||||||
|
github.com/gorilla/handlers v1.4.2 // indirect
|
||||||
github.com/gorilla/mux v1.7.4
|
github.com/gorilla/mux v1.7.4
|
||||||
github.com/h2non/filetype v1.0.12
|
github.com/h2non/filetype v1.0.12
|
||||||
github.com/opencontainers/go-digest v1.0.0-rc1 // indirect
|
github.com/opencontainers/go-digest v1.0.0-rc1 // indirect
|
||||||
|
|||||||
@@ -125,6 +125,8 @@ github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm4
|
|||||||
github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg=
|
github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg=
|
||||||
github.com/googleapis/gax-go/v2 v2.0.5 h1:sjZBwGj9Jlw33ImPtvFviGYvseOtDM7hkSKB7+Tv3SM=
|
github.com/googleapis/gax-go/v2 v2.0.5 h1:sjZBwGj9Jlw33ImPtvFviGYvseOtDM7hkSKB7+Tv3SM=
|
||||||
github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk=
|
github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk=
|
||||||
|
github.com/gorilla/handlers v1.4.2 h1:0QniY0USkHQ1RGCLfKxeNHK9bkDHGRYGNDFBCS+YARg=
|
||||||
|
github.com/gorilla/handlers v1.4.2/go.mod h1:Qkdc/uu4tH4g6mTK6auzZ766c4CA0Ng8+o/OAirnOIQ=
|
||||||
github.com/gorilla/mux v1.7.4 h1:VuZ8uybHlWmqV03+zRzdwKL4tUnIp1MAQtp1mIFE1bc=
|
github.com/gorilla/mux v1.7.4 h1:VuZ8uybHlWmqV03+zRzdwKL4tUnIp1MAQtp1mIFE1bc=
|
||||||
github.com/gorilla/mux v1.7.4/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So=
|
github.com/gorilla/mux v1.7.4/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So=
|
||||||
github.com/h2non/filetype v1.0.12 h1:yHCsIe0y2cvbDARtJhGBTD2ecvqMSTvlIcph9En/Zao=
|
github.com/h2non/filetype v1.0.12 h1:yHCsIe0y2cvbDARtJhGBTD2ecvqMSTvlIcph9En/Zao=
|
||||||
|
|||||||
+113
-56
@@ -316,13 +316,14 @@ type HookAction struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type Hook struct {
|
type Hook struct {
|
||||||
Id string `json:"id" datastore:"id"`
|
Id string `json:"id" datastore:"id"`
|
||||||
Info Info `json:"info" datastore:"info"`
|
Info Info `json:"info" datastore:"info"`
|
||||||
Actions []HookAction `json:"actions" datastore:"actions"`
|
Actions []HookAction `json:"actions" datastore:"actions"`
|
||||||
Type string `json:"type" datastore:"type"`
|
Type string `json:"type" datastore:"type"`
|
||||||
Owner string `json:"owner" datastore:"owner"`
|
Owner string `json:"owner" datastore:"owner"`
|
||||||
Status string `json:"status" datastore:"status"`
|
Status string `json:"status" datastore:"status"`
|
||||||
Running bool `json:"running" datastore:"running"`
|
Workflows []string `json:"workflows" datastore:"workflows"`
|
||||||
|
Running bool `json:"running" datastore:"running"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func createFileFromFile(ctx context.Context, bucket *storage.BucketHandle, remotePath, localPath string) error {
|
func createFileFromFile(ctx context.Context, bucket *storage.BucketHandle, remotePath, localPath string) error {
|
||||||
@@ -1332,7 +1333,7 @@ func handleSettings(resp http.ResponseWriter, request *http.Request) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Printf("%s %s", session.Session, UserInfo.Session)
|
//log.Printf("%s %s", session.Session, UserInfo.Session)
|
||||||
if session.Session != UserInfo.Session {
|
if session.Session != UserInfo.Session {
|
||||||
log.Printf("Session %s is not the latest. %s", session.Username, err)
|
log.Printf("Session %s is not the latest. %s", session.Username, err)
|
||||||
resp.WriteHeader(401)
|
resp.WriteHeader(401)
|
||||||
@@ -1394,7 +1395,7 @@ func handleInfo(resp http.ResponseWriter, request *http.Request) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Printf("%s %s", session.Session, UserInfo.Session)
|
//log.Printf("%s %s", session.Session, UserInfo.Session)
|
||||||
if session.Session != UserInfo.Session {
|
if session.Session != UserInfo.Session {
|
||||||
log.Printf("Session %s is not the latest. %s", session.Username, err)
|
log.Printf("Session %s is not the latest. %s", session.Username, err)
|
||||||
resp.WriteHeader(401)
|
resp.WriteHeader(401)
|
||||||
@@ -1833,7 +1834,7 @@ func handleGetEnvironments(resp http.ResponseWriter, request *http.Request) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Printf("Existing environments: %s", string(newjson))
|
//log.Printf("Existing environments: %s", string(newjson))
|
||||||
|
|
||||||
resp.WriteHeader(200)
|
resp.WriteHeader(200)
|
||||||
resp.Write(newjson)
|
resp.Write(newjson)
|
||||||
@@ -2708,46 +2709,88 @@ func handleNewSchedule(resp http.ResponseWriter, request *http.Request) {
|
|||||||
resp.Write([]byte(`{"success": true, "message": "Created new service"}`))
|
resp.Write([]byte(`{"success": true, "message": "Created new service"}`))
|
||||||
}
|
}
|
||||||
|
|
||||||
func handleWebhookRedirect(resp http.ResponseWriter, request *http.Request) {
|
// Does the webhook
|
||||||
|
func handleWebhookCallback(resp http.ResponseWriter, request *http.Request) {
|
||||||
|
// 1. Get callback data
|
||||||
|
// 2. Load the configuration
|
||||||
|
// 3. Execute the workflow
|
||||||
|
|
||||||
path := strings.Split(request.URL.String(), "/")
|
path := strings.Split(request.URL.String(), "/")
|
||||||
if len(path) < 4 {
|
if len(path) < 4 {
|
||||||
resp.WriteHeader(403)
|
resp.WriteHeader(403)
|
||||||
|
resp.Write([]byte(`{"success": false}`))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
//http.Redirect(resp, request, "http://www.google.com", 301)
|
// 1. Get config with hookId
|
||||||
//https://europe-west1-shuffler.cloudfunctions.net/webhook_e843bfe2-fc36-4fa5-b682-97cdfa0c0091
|
//fmt.Sprintf("%s/api/v1/hooks/%s", callbackUrl, hookId)
|
||||||
|
ctx := context.Background()
|
||||||
|
location := strings.Split(request.URL.String(), "/")
|
||||||
|
|
||||||
body, err := ioutil.ReadAll(request.Body)
|
var hookId string
|
||||||
|
if location[1] == "api" {
|
||||||
|
if len(location) <= 4 {
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
hookId = location[4]
|
||||||
|
}
|
||||||
|
|
||||||
|
// ID: webhook_<UID>
|
||||||
|
if len(hookId) != 44 {
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false, "message": "ID not valid"}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
hookId = hookId[8:len(hookId)]
|
||||||
|
|
||||||
|
log.Printf("HookID: %s", hookId)
|
||||||
|
hook, err := getHook(ctx, hookId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
http.Error(resp, err.Error(), http.StatusInternalServerError)
|
log.Printf("Failed getting hook: %s", err)
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false}`))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// you can reassign the body if you need to parse it as multipart
|
log.Printf("HOOK FOUND: %#v", hook)
|
||||||
request.Body = ioutil.NopCloser(bytes.NewReader(body))
|
// Execute the workflow
|
||||||
|
//executeWorkflow(resp, request)
|
||||||
|
|
||||||
// create a new url from the raw RequestURI sent by the client
|
//resp.WriteHeader(200)
|
||||||
proxyScheme := "https"
|
//resp.Write([]byte(`{"success": true}`))
|
||||||
url := fmt.Sprintf("%s://%s-%s.cloudfunctions.net/%s", proxyScheme, defaultLocation, gceProject, path[3])
|
if hook.Status == "stopped" {
|
||||||
log.Println(url)
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "The webhook isn't running. Click start to start it"}`)))
|
||||||
proxyReq, err := http.NewRequest(request.Method, url, bytes.NewReader(body))
|
|
||||||
|
|
||||||
// We may want to filter some headers, otherwise we could just use a shallow copy
|
|
||||||
// proxyReq.Header = req.Header
|
|
||||||
proxyReq.Header = make(http.Header)
|
|
||||||
for h, val := range request.Header {
|
|
||||||
proxyReq.Header[h] = val
|
|
||||||
}
|
|
||||||
|
|
||||||
httpClient := &http.Client{}
|
|
||||||
newresp, err := httpClient.Do(proxyReq)
|
|
||||||
if err != nil {
|
|
||||||
http.Error(resp, err.Error(), http.StatusBadGateway)
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
defer newresp.Body.Close()
|
|
||||||
|
if len(hook.Workflows) == 0 {
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "No workflows are defined"}`)))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, item := range hook.Workflows {
|
||||||
|
log.Printf("Running for workflow: %s", item)
|
||||||
|
workflow := Workflow{
|
||||||
|
ID: "",
|
||||||
|
}
|
||||||
|
|
||||||
|
workflowExecution, executionResp, err := handleExecution(item, workflow, request)
|
||||||
|
|
||||||
|
if err == nil {
|
||||||
|
resp.WriteHeader(200)
|
||||||
|
resp.Write([]byte(fmt.Sprintf(`{"success": true, "execution_id": "%s", "authorization": "%s"}`, workflowExecution.ExecutionId, workflowExecution.Authorization)))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
resp.WriteHeader(500)
|
||||||
|
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "%s"}`, executionResp)))
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Starts a new webhook
|
// Starts a new webhook
|
||||||
@@ -2780,6 +2823,9 @@ func handleNewHook(resp http.ResponseWriter, request *http.Request) {
|
|||||||
resp.Write([]byte(`{"success": false}`))
|
resp.Write([]byte(`{"success": false}`))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
log.Println("Data: %s", string(body))
|
||||||
|
|
||||||
ctx := context.Background()
|
ctx := context.Background()
|
||||||
var requestdata requestData
|
var requestdata requestData
|
||||||
err = yaml.Unmarshal([]byte(body), &requestdata)
|
err = yaml.Unmarshal([]byte(body), &requestdata)
|
||||||
@@ -2827,7 +2873,8 @@ func handleNewHook(resp http.ResponseWriter, request *http.Request) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
hook := Hook{
|
hook := Hook{
|
||||||
Id: newId,
|
Id: newId,
|
||||||
|
Workflows: []string{requestdata.Workflow},
|
||||||
Info: Info{
|
Info: Info{
|
||||||
Name: requestdata.Name,
|
Name: requestdata.Name,
|
||||||
Description: requestdata.Description,
|
Description: requestdata.Description,
|
||||||
@@ -2847,6 +2894,9 @@ func handleNewHook(resp http.ResponseWriter, request *http.Request) {
|
|||||||
Running: false,
|
Running: false,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
log.Printf("Hello")
|
||||||
|
|
||||||
|
// FIXME: Add cloud function execution?
|
||||||
//b, err := json.Marshal(hook)
|
//b, err := json.Marshal(hook)
|
||||||
//if err != nil {
|
//if err != nil {
|
||||||
// log.Printf("Failed marshalling: %s", err)
|
// log.Printf("Failed marshalling: %s", err)
|
||||||
@@ -2855,21 +2905,21 @@ func handleNewHook(resp http.ResponseWriter, request *http.Request) {
|
|||||||
// return
|
// return
|
||||||
//}
|
//}
|
||||||
|
|
||||||
environmentVariables := map[string]string{
|
//environmentVariables := map[string]string{
|
||||||
"FUNCTION_APIKEY": user.ApiKey,
|
// "FUNCTION_APIKEY": user.ApiKey,
|
||||||
"CALLBACKURL": "https://shuffler.io",
|
// "CALLBACKURL": "https://shuffler.io",
|
||||||
"HOOKID": hook.Id,
|
// "HOOKID": hook.Id,
|
||||||
}
|
//}
|
||||||
|
|
||||||
applocation := fmt.Sprintf("gs://%s/triggers/webhook.zip", bucketName)
|
//applocation := fmt.Sprintf("gs://%s/triggers/webhook.zip", bucketName)
|
||||||
hookname := fmt.Sprintf("webhook_%s", hook.Id)
|
//hookname := fmt.Sprintf("webhook_%s", hook.Id)
|
||||||
err = deployWebhookFunction(ctx, hookname, defaultLocation, applocation, environmentVariables)
|
//err = deployWebhookFunction(ctx, hookname, defaultLocation, applocation, environmentVariables)
|
||||||
if err != nil {
|
//if err != nil {
|
||||||
log.Printf("Error deploying hook: %s", err)
|
// log.Printf("Error deploying hook: %s", err)
|
||||||
resp.WriteHeader(401)
|
// resp.WriteHeader(401)
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Issue with starting hook. Please wait a second and try again"}`)))
|
// resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Issue with starting hook. Please wait a second and try again"}`)))
|
||||||
return
|
// return
|
||||||
}
|
//}
|
||||||
|
|
||||||
hook.Status = "running"
|
hook.Status = "running"
|
||||||
hook.Running = true
|
hook.Running = true
|
||||||
@@ -5465,6 +5515,7 @@ func init() {
|
|||||||
var err error
|
var err error
|
||||||
ctx := context.Background()
|
ctx := context.Background()
|
||||||
|
|
||||||
|
log.Printf("Running INIT process")
|
||||||
dbclient, err = datastore.NewClient(ctx, gceProject)
|
dbclient, err = datastore.NewClient(ctx, gceProject)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatalf("DBclient error during init: %s", err)
|
log.Fatalf("DBclient error during init: %s", err)
|
||||||
@@ -5483,11 +5534,11 @@ func init() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
r := mux.NewRouter()
|
log.Printf("Finished INIT")
|
||||||
r.HandleFunc("_ah/health", healthCheckHandler)
|
|
||||||
|
r := mux.NewRouter()
|
||||||
|
r.HandleFunc("/api/v1/_ah/health", healthCheckHandler)
|
||||||
|
|
||||||
// Webhook redirect to the correct cloud function
|
|
||||||
r.HandleFunc("/functions/webhooks/{key}", handleWebhookRedirect).Methods("POST", "OPTIONS")
|
|
||||||
// Sends an email if the right things are specified
|
// Sends an email if the right things are specified
|
||||||
r.HandleFunc("/functions/sendmail", handleSendalert).Methods("POST", "OPTIONS")
|
r.HandleFunc("/functions/sendmail", handleSendalert).Methods("POST", "OPTIONS")
|
||||||
r.HandleFunc("/functions/outlook/register", handleNewOutlookRegister).Methods("GET", "OPTIONS")
|
r.HandleFunc("/functions/outlook/register", handleNewOutlookRegister).Methods("GET", "OPTIONS")
|
||||||
@@ -5552,11 +5603,17 @@ func init() {
|
|||||||
r.HandleFunc("/api/v1/workflows/{key}", getSpecificWorkflow).Methods("GET", "OPTIONS")
|
r.HandleFunc("/api/v1/workflows/{key}", getSpecificWorkflow).Methods("GET", "OPTIONS")
|
||||||
r.HandleFunc("/api/v1/workflows/{key}", saveWorkflow).Methods("PUT", "OPTIONS")
|
r.HandleFunc("/api/v1/workflows/{key}", saveWorkflow).Methods("PUT", "OPTIONS")
|
||||||
r.HandleFunc("/api/v1/workflows/{key}", deleteWorkflow).Methods("DELETE", "OPTIONS")
|
r.HandleFunc("/api/v1/workflows/{key}", deleteWorkflow).Methods("DELETE", "OPTIONS")
|
||||||
|
|
||||||
|
// Triggers
|
||||||
|
// Webhook redirect to the correct cloud function
|
||||||
r.HandleFunc("/api/v1/hooks/new", handleNewHook).Methods("POST", "OPTIONS")
|
r.HandleFunc("/api/v1/hooks/new", handleNewHook).Methods("POST", "OPTIONS")
|
||||||
|
r.HandleFunc("/api/v1/hooks/{key}", handleWebhookCallback).Methods("POST", "OPTIONS")
|
||||||
r.HandleFunc("/api/v1/hooks/{key}/delete", handleDeleteHook).Methods("DELETE", "OPTIONS")
|
r.HandleFunc("/api/v1/hooks/{key}/delete", handleDeleteHook).Methods("DELETE", "OPTIONS")
|
||||||
|
|
||||||
|
// Trigger hmm
|
||||||
r.HandleFunc("/api/v1/triggers/{key}", handleGetSpecificTrigger).Methods("GET", "OPTIONS")
|
r.HandleFunc("/api/v1/triggers/{key}", handleGetSpecificTrigger).Methods("GET", "OPTIONS")
|
||||||
|
|
||||||
// Weird API's for random things
|
// OpenAPI configuration
|
||||||
r.HandleFunc("/api/v1/verify_swagger", verifySwagger).Methods("POST", "OPTIONS")
|
r.HandleFunc("/api/v1/verify_swagger", verifySwagger).Methods("POST", "OPTIONS")
|
||||||
r.HandleFunc("/api/v1/verify_openapi", verifySwagger).Methods("POST", "OPTIONS")
|
r.HandleFunc("/api/v1/verify_openapi", verifySwagger).Methods("POST", "OPTIONS")
|
||||||
r.HandleFunc("/api/v1/get_openapi_uri", echoOpenapiData).Methods("POST", "OPTIONS")
|
r.HandleFunc("/api/v1/get_openapi_uri", echoOpenapiData).Methods("POST", "OPTIONS")
|
||||||
|
|||||||
+117
-160
@@ -167,21 +167,23 @@ type Action struct {
|
|||||||
|
|
||||||
// Added environment for location to execute
|
// Added environment for location to execute
|
||||||
type Trigger struct {
|
type Trigger struct {
|
||||||
AppName string `json:"app_name" datastore:"app_name"`
|
AppName string `json:"app_name" datastore:"app_name"`
|
||||||
Status string `json:"status" datastore:"status"`
|
Description string `json:"description" datastore:"description"`
|
||||||
AppVersion string `json:"app_version" datastore:"app_version"`
|
LongDescription string `json:"long_description" datastore:"long_description"`
|
||||||
Errors []string `json:"errors" datastore:"errors"`
|
Status string `json:"status" datastore:"status"`
|
||||||
ID string `json:"id" datastore:"id"`
|
AppVersion string `json:"app_version" datastore:"app_version"`
|
||||||
IsValid bool `json:"is_valid" datastore:"is_valid"`
|
Errors []string `json:"errors" datastore:"errors"`
|
||||||
IsStartNode bool `json:"isStartNode" datastore:"isStartNode"`
|
ID string `json:"id" datastore:"id"`
|
||||||
Label string `json:"label" datastore:"label"`
|
IsValid bool `json:"is_valid" datastore:"is_valid"`
|
||||||
SmallImage string `json:"small_image" datastore:"small_image,noindex" required:false yaml:"small_image"`
|
IsStartNode bool `json:"isStartNode" datastore:"isStartNode"`
|
||||||
LargeImage string `json:"large_image" datastore:"large_image,noindex" yaml:"large_image" required:false`
|
Label string `json:"label" datastore:"label"`
|
||||||
Environment string `json:"environment" datastore:"environment"`
|
SmallImage string `json:"small_image" datastore:"small_image,noindex" required:false yaml:"small_image"`
|
||||||
TriggerType string `json:"trigger_type" datastore:"trigger_type"`
|
LargeImage string `json:"large_image" datastore:"large_image,noindex" yaml:"large_image" required:false`
|
||||||
Name string `json:"name" datastore:"name"`
|
Environment string `json:"environment" datastore:"environment"`
|
||||||
Parameters []WorkflowAppActionParameter `json:"parameters" datastore: "parameters,noindex"`
|
TriggerType string `json:"trigger_type" datastore:"trigger_type"`
|
||||||
Position struct {
|
Name string `json:"name" datastore:"name"`
|
||||||
|
Parameters []WorkflowAppActionParameter `json:"parameters" datastore: "parameters,noindex"`
|
||||||
|
Position struct {
|
||||||
X float64 `json:"x" datastore:"x"`
|
X float64 `json:"x" datastore:"x"`
|
||||||
Y float64 `json:"y" datastore:"y"`
|
Y float64 `json:"y" datastore:"y"`
|
||||||
} `json:"position"`
|
} `json:"position"`
|
||||||
@@ -1546,74 +1548,17 @@ func cleanupExecutions(resp http.ResponseWriter, request *http.Request) {
|
|||||||
resp.Write([]byte("OK"))
|
resp.Write([]byte("OK"))
|
||||||
}
|
}
|
||||||
|
|
||||||
func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
func handleExecution(id string, workflow Workflow, request *http.Request) (WorkflowExecution, string, error) {
|
||||||
cors := handleCors(resp, request)
|
ctx := context.Background()
|
||||||
if cors {
|
if workflow.ID == "" || workflow.ID != id {
|
||||||
return
|
log.Printf("UPDATING WORKFLOW")
|
||||||
}
|
tmpworkflow, err := getWorkflow(ctx, id)
|
||||||
|
if err != nil {
|
||||||
user, err := handleApiAuthentication(resp, request)
|
log.Printf("Failed getting the workflow locally: %s", err)
|
||||||
if err != nil {
|
return WorkflowExecution{}, "Failed getting workflow", err
|
||||||
log.Printf("Api authentication failed in execute workflow: %s", err)
|
|
||||||
resp.WriteHeader(401)
|
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
location := strings.Split(request.URL.String(), "/")
|
|
||||||
|
|
||||||
var fileId string
|
|
||||||
if location[1] == "api" {
|
|
||||||
if len(location) <= 4 {
|
|
||||||
resp.WriteHeader(401)
|
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fileId = location[4]
|
workflow = *tmpworkflow
|
||||||
}
|
|
||||||
|
|
||||||
if len(fileId) != 36 {
|
|
||||||
resp.WriteHeader(401)
|
|
||||||
resp.Write([]byte(`{"success": false, "reason": "Workflow ID to execute is not valid"}`))
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
//memcacheName := fmt.Sprintf("%s_%s", user.Username, fileId)
|
|
||||||
var workflow Workflow
|
|
||||||
ctx := context.Background()
|
|
||||||
//if item, err := memcache.Get(ctx, memcacheName); err == memcache.ErrCacheMiss {
|
|
||||||
// // Not in cache
|
|
||||||
// log.Printf("Workflow %s not in cache.", memcacheName)
|
|
||||||
tmpworkflow, err := getWorkflow(ctx, fileId)
|
|
||||||
if err != nil {
|
|
||||||
log.Printf("Failed getting the workflow locally: %s", err)
|
|
||||||
resp.WriteHeader(401)
|
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
workflow = *tmpworkflow
|
|
||||||
//} else if err != nil {
|
|
||||||
// log.Printf("Error getting item: %v", err)
|
|
||||||
//} else {
|
|
||||||
// // FIXME - verify if value is ok? Can unmarshal etc.
|
|
||||||
// log.Printf("Got workflow %s from cache", fileId)
|
|
||||||
// err = json.Unmarshal(item.Value, &workflow)
|
|
||||||
// if err != nil {
|
|
||||||
// log.Printf("Failed cache unmarshal in executeworkflow for %s", fileId)
|
|
||||||
// resp.WriteHeader(401)
|
|
||||||
// resp.Write([]byte(`{"success": false}`))
|
|
||||||
// }
|
|
||||||
//}
|
|
||||||
|
|
||||||
// FIXME - have a check for org etc too..
|
|
||||||
// FIXME - admin check like this? idk
|
|
||||||
if user.Id != workflow.Owner && user.Role != "admin" && user.Role != "scheduler" && user.Role != fmt.Sprintf("workflow_%s", fileId) {
|
|
||||||
log.Printf("Wrong user (%s) for workflow %s (execute)", user.Username, workflow.ID)
|
|
||||||
resp.WriteHeader(401)
|
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(workflow.Actions) == 0 {
|
if len(workflow.Actions) == 0 {
|
||||||
@@ -1631,17 +1576,13 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
|
|
||||||
if !workflow.IsValid {
|
if !workflow.IsValid {
|
||||||
log.Printf("Stopped execution as workflow %s is not valid.", workflow.ID)
|
log.Printf("Stopped execution as workflow %s is not valid.", workflow.ID)
|
||||||
resp.WriteHeader(403)
|
return WorkflowExecution{}, fmt.Sprintf(`workflow %s is invalid`, workflow.ID), errors.New("Failed getting workflow")
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "workflow %s is invalid"}`, workflow.ID)))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
workflowBytes, err := json.Marshal(workflow)
|
workflowBytes, err := json.Marshal(workflow)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Failed workflow unmarshal in execution: %s", err)
|
log.Printf("Failed workflow unmarshal in execution: %s", err)
|
||||||
resp.WriteHeader(http.StatusInternalServerError)
|
return WorkflowExecution{}, "", err
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//log.Println(workflow)
|
//log.Println(workflow)
|
||||||
@@ -1649,29 +1590,22 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
err = json.Unmarshal(workflowBytes, &workflowExecution.Workflow)
|
err = json.Unmarshal(workflowBytes, &workflowExecution.Workflow)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Failed execution unmarshaling: %s", err)
|
log.Printf("Failed execution unmarshaling: %s", err)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, "Failed unmarshal during execution", err
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
makeNew := true
|
makeNew := true
|
||||||
if request.Method == "POST" {
|
if request.Method == "POST" {
|
||||||
|
|
||||||
body, err := ioutil.ReadAll(request.Body)
|
body, err := ioutil.ReadAll(request.Body)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Failed hook unmarshaling: %s", err)
|
log.Printf("Failed request POST read: %s", err)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, "Failed getting body", err
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
var execution ExecutionRequest
|
var execution ExecutionRequest
|
||||||
err = json.Unmarshal(body, &execution)
|
err = json.Unmarshal(body, &execution)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Failed execution POST unmarshaling: %s", err)
|
log.Printf("Failed execution POST unmarshaling: %s", err)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, "", err
|
||||||
resp.Write([]byte(`{"success": false}`))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME - this should have "execution_argument" from executeWorkflow frontend
|
// FIXME - this should have "execution_argument" from executeWorkflow frontend
|
||||||
@@ -1706,16 +1640,12 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
oldExecution, err := getWorkflowExecution(ctx, referenceId[0])
|
oldExecution, err := getWorkflowExecution(ctx, referenceId[0])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Failed getting execution (execution) %s: %s", referenceId[0], err)
|
log.Printf("Failed getting execution (execution) %s: %s", referenceId[0], err)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, fmt.Sprintf("Failed getting execution ID %s because it doesn't exist.", referenceId[0]), err
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Failed getting execution ID %s because it doesn't exist."}`, referenceId[0])))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if oldExecution.Workflow.ID != fileId {
|
if oldExecution.Workflow.ID != id {
|
||||||
log.Println("Wrong workflowid!")
|
log.Println("Wrong workflowid!")
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, fmt.Sprintf("Bad ID %s", referenceId), errors.New("Bad ID")
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Bad ID %s"}`, referenceId)))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
newResults := []ActionResult{}
|
newResults := []ActionResult{}
|
||||||
@@ -1745,14 +1675,10 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
err = setWorkflowExecution(ctx, *oldExecution)
|
err = setWorkflowExecution(ctx, *oldExecution)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Error saving workflow execution actionresult setting: %s", err)
|
log.Printf("Error saving workflow execution actionresult setting: %s", err)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, fmt.Sprintf("Failed setting workflowexecution actionresult in execution: %s", err), err
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Failed setting workflowexecution actionresult in execution: %s"}`, err)))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
resp.WriteHeader(200)
|
return WorkflowExecution{}, "", nil
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": true, "reason": "Updating %s with your information."}`, referenceId[0])))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1762,9 +1688,7 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
oldExecution, err := getWorkflowExecution(ctx, referenceId[0])
|
oldExecution, err := getWorkflowExecution(ctx, referenceId[0])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Failed getting execution (execution) %s: %s", referenceId[0], err)
|
log.Printf("Failed getting execution (execution) %s: %s", referenceId[0], err)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, fmt.Sprintf("Failed getting execution ID %s because it doesn't exist.", referenceId[0]), err
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Failed getting execution ID %s because it doesn't exist."}`, referenceId[0])))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
workflowExecution = *oldExecution
|
workflowExecution = *oldExecution
|
||||||
@@ -1790,9 +1714,7 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
// FIXME - regex uuid, and check if already exists?
|
// FIXME - regex uuid, and check if already exists?
|
||||||
if len(workflowExecution.ExecutionId) != 36 {
|
if len(workflowExecution.ExecutionId) != 36 {
|
||||||
log.Printf("Invalid uuid: %s", workflowExecution.ExecutionId)
|
log.Printf("Invalid uuid: %s", workflowExecution.ExecutionId)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, "Invalid uuid", err
|
||||||
resp.Write([]byte(`{"success": false, "reason": "Invalid uuid."}`))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME - find owner of workflow
|
// FIXME - find owner of workflow
|
||||||
@@ -1841,9 +1763,7 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
//log.Println(action.Environment)
|
//log.Println(action.Environment)
|
||||||
|
|
||||||
if action.Environment == "" {
|
if action.Environment == "" {
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, fmt.Sprintf("Environment is not defined for %s", action.Name), errors.New("Environment not defined!")
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Environment is not defined for %s"}`, action.Name)))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
newActions = append(newActions, action)
|
newActions = append(newActions, action)
|
||||||
}
|
}
|
||||||
@@ -1875,9 +1795,7 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
err = setWorkflowExecution(ctx, workflowExecution)
|
err = setWorkflowExecution(ctx, workflowExecution)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("Error saving workflow execution for updates %s: %s", topic, err)
|
log.Printf("Error saving workflow execution for updates %s: %s", topic, err)
|
||||||
resp.WriteHeader(401)
|
return WorkflowExecution{}, "Failed getting workflowexecution", err
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "Failed setting workflowexecution"}`)))
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Printf("Environments: %#v", environments)
|
log.Printf("Environments: %#v", environments)
|
||||||
@@ -1914,32 +1832,71 @@ func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//body, err := json.Marshal(workflow)
|
return workflowExecution, "", nil
|
||||||
//if err != nil {
|
}
|
||||||
// log.Printf("Failed workflow SET marshalling: %s", err)
|
|
||||||
// resp.WriteHeader(http.StatusInternalServerError)
|
|
||||||
// resp.Write([]byte(`{"success": false}`))
|
|
||||||
// return
|
|
||||||
//}
|
|
||||||
|
|
||||||
//item := &memcache.Item{
|
func executeWorkflow(resp http.ResponseWriter, request *http.Request) {
|
||||||
// Key: memcacheName,
|
cors := handleCors(resp, request)
|
||||||
// Value: body,
|
if cors {
|
||||||
// Expiration: time.Minute * 10,
|
return
|
||||||
//}
|
}
|
||||||
//if err := memcache.Add(ctx, item); err == memcache.ErrNotStored {
|
|
||||||
// if err := memcache.Set(ctx, item); err != nil {
|
|
||||||
// log.Printf("Error setting item: %v", err)
|
|
||||||
// }
|
|
||||||
//} else if err != nil {
|
|
||||||
// log.Printf("error adding item: %v", err)
|
|
||||||
//} else {
|
|
||||||
// log.Printf("Set cache for %s", item.Key)
|
|
||||||
//}
|
|
||||||
|
|
||||||
resp.WriteHeader(200)
|
user, err := handleApiAuthentication(resp, request)
|
||||||
resp.Write([]byte(fmt.Sprintf(`{"success": true, "execution_id": "%s", "authorization": "%s"}`, workflowExecution.ExecutionId, workflowExecution.Authorization)))
|
if err != nil {
|
||||||
return
|
log.Printf("Api authentication failed in execute workflow: %s", err)
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
location := strings.Split(request.URL.String(), "/")
|
||||||
|
|
||||||
|
var fileId string
|
||||||
|
if location[1] == "api" {
|
||||||
|
if len(location) <= 4 {
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
fileId = location[4]
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(fileId) != 36 {
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false, "reason": "Workflow ID to execute is not valid"}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
//memcacheName := fmt.Sprintf("%s_%s", user.Username, fileId)
|
||||||
|
ctx := context.Background()
|
||||||
|
workflow, err := getWorkflow(ctx, fileId)
|
||||||
|
if err != nil {
|
||||||
|
log.Printf("Failed getting the workflow locally: %s", err)
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// FIXME - have a check for org etc too..
|
||||||
|
// FIXME - admin check like this? idk
|
||||||
|
if user.Id != workflow.Owner && user.Role != "admin" && user.Role != "scheduler" && user.Role != fmt.Sprintf("workflow_%s", fileId) {
|
||||||
|
log.Printf("Wrong user (%s) for workflow %s (execute)", user.Username, workflow.ID)
|
||||||
|
resp.WriteHeader(401)
|
||||||
|
resp.Write([]byte(`{"success": false}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
workflowExecution, executionResp, err := handleExecution(fileId, *workflow, request)
|
||||||
|
|
||||||
|
if err == nil {
|
||||||
|
resp.WriteHeader(200)
|
||||||
|
resp.Write([]byte(fmt.Sprintf(`{"success": true, "execution_id": "%s", "authorization": "%s"}`, workflowExecution.ExecutionId, workflowExecution.Authorization)))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
resp.WriteHeader(500)
|
||||||
|
resp.Write([]byte(fmt.Sprintf(`{"success": false, "reason": "%s"}`, executionResp)))
|
||||||
}
|
}
|
||||||
|
|
||||||
func stopSchedule(resp http.ResponseWriter, request *http.Request) {
|
func stopSchedule(resp http.ResponseWriter, request *http.Request) {
|
||||||
@@ -3434,21 +3391,21 @@ func handleDeleteHook(resp http.ResponseWriter, request *http.Request) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// This is here to force stop and remove the old webhook
|
// This is here to force stop and remove the old webhook
|
||||||
image := "webhook"
|
//image := "webhook"
|
||||||
err = removeWebhookFunction(ctx, fileId)
|
//err = removeWebhookFunction(ctx, fileId)
|
||||||
if err != nil {
|
//if err != nil {
|
||||||
log.Printf("Function removal issue for %s-%s: %s", image, fileId, err)
|
// log.Printf("Function removal issue for %s-%s: %s", image, fileId, err)
|
||||||
if strings.Contains(err.Error(), "does not exist") {
|
// if strings.Contains(err.Error(), "does not exist") {
|
||||||
resp.WriteHeader(200)
|
// resp.WriteHeader(200)
|
||||||
resp.Write([]byte(`{"success": true, "reason": "Stopped webhook"}`))
|
// resp.Write([]byte(`{"success": true, "reason": "Stopped webhook"}`))
|
||||||
|
|
||||||
} else {
|
// } else {
|
||||||
resp.WriteHeader(401)
|
// resp.WriteHeader(401)
|
||||||
resp.Write([]byte(`{"success": false, "reason": "Couldn't stop webhook, please try again later"}`))
|
// resp.Write([]byte(`{"success": false, "reason": "Couldn't stop webhook, please try again later"}`))
|
||||||
}
|
// }
|
||||||
|
|
||||||
return
|
// return
|
||||||
}
|
//}
|
||||||
|
|
||||||
log.Printf("Successfully deleted webhook %s", fileId)
|
log.Printf("Successfully deleted webhook %s", fileId)
|
||||||
resp.WriteHeader(200)
|
resp.WriteHeader(200)
|
||||||
|
|||||||
+21
-4
@@ -1,7 +1,7 @@
|
|||||||
#curl localhost:5000/api/v1/hooks
|
#curl localhost:5000/api/v1/hooks
|
||||||
|
|
||||||
# Starts a webhook
|
# Starts a webhook
|
||||||
# curl localhost:5000/api/v1/hooks/d6ef8912e8bd37776e654cbc14c2629c/start
|
#curl localhost:5000/api/v1/hooks/d6ef8912e8bd37776e654cbc14c2629c/start
|
||||||
|
|
||||||
# Runs a request towards the webhook created
|
# Runs a request towards the webhook created
|
||||||
#curl -XPOST localhost:5002/webhook -d '{"helo": "hi"}'
|
#curl -XPOST localhost:5002/webhook -d '{"helo": "hi"}'
|
||||||
@@ -14,11 +14,28 @@
|
|||||||
|
|
||||||
#curl -X POST "https://europe-west1-shuffle-241517.cloudfunctions.net/webhook_982995716e67c3a549092d3a3a7921cd" -H "Content-Type:application/json" -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26" --data '{"name":"Keyboard Cat"}' -v
|
#curl -X POST "https://europe-west1-shuffle-241517.cloudfunctions.net/webhook_982995716e67c3a549092d3a3a7921cd" -H "Content-Type:application/json" -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26" --data '{"name":"Keyboard Cat"}' -v
|
||||||
|
|
||||||
|
## GET HOOK
|
||||||
|
#curl http://localhost:5001/api/v1/hooks/b4ba07c9-45d4-41f2-b260-83c8e99eba0c -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26"
|
||||||
|
|
||||||
#jcurl http://localhost:5001/api/v1/hooks/b4ba07c9-45d4-41f2-b260-83c8e99eba0c -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26"
|
|
||||||
#curl https://shuffler.io/api/v1/hooks/b4ba07c9-45d4-41f2-b260-83c8e99eba0c -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26"
|
#curl https://shuffler.io/api/v1/hooks/b4ba07c9-45d4-41f2-b260-83c8e99eba0c -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26"
|
||||||
#curl -X POST "http://localhost:8080" -H "Content-Type:application/json" -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
|
||||||
|
|
||||||
#curl -X POST "https://europe-west1-shuffle-241517.cloudfunctions.net/webhook_3ceff795-ce9a-43a2-a2f5-d4401a6e772d" -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26" --data 'wut'
|
#curl -X POST "https://europe-west1-shuffle-241517.cloudfunctions.net/webhook_3ceff795-ce9a-43a2-a2f5-d4401a6e772d" -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26" --data 'wut'
|
||||||
curl POST "https://europe-west1-shuffler.cloudfunctions.net/outlooktrigger_be4dbb0a-d396-4544-bc36-e57d1bdb2e40" -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26" --data 'wut' -vvv
|
#curl POST "https://europe-west1-shuffler.cloudfunctions.net/outlooktrigger_be4dbb0a-d396-4544-bc36-e57d1bdb2e40" -H "Authorization: Bearer 144308d0-6aab-4d4f-8bb2-75189281ee26" --data 'wut' -vvv
|
||||||
|
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
curl -X POST "http://localhost:5001/api/v1/hooks/webhook_9a4efb03-089c-48b7-82f3-f76500a3ebc0" -H "Content-Type:application/json" --data '{"test": {"hello": "HEYOOOO"}}' -v
|
||||||
|
|||||||
@@ -6,8 +6,8 @@ docker build . -t webhook
|
|||||||
docker run -d \
|
docker run -d \
|
||||||
-e "HOOKPORT=5001" \
|
-e "HOOKPORT=5001" \
|
||||||
-e "URIPATH=/webhook" \
|
-e "URIPATH=/webhook" \
|
||||||
-e "CALLBACKURL=http://192.168.159.151:5000/api/v1/hooks/d6ef8912e8bd37776e654cbc14c2629c/result" \
|
-e "CALLBACKURL=http://192.168.3.6:5001/api/v1/hooks/d6ef8912e8bd37776e654cbc14c2629c/result" \
|
||||||
-p 5001:5001 \
|
-p 6000:6000 \
|
||||||
--name webhook \
|
--name webhook \
|
||||||
-h webhook \
|
-h webhook \
|
||||||
--restart always \
|
--restart always \
|
||||||
|
|||||||
File diff suppressed because one or more lines are too long
Reference in New Issue
Block a user