# Which Problems Are Solved Actions v2 is not a feature flag anymore, include functionality on executions is not used and json tags of proto messages are handled incorrectly. # How the Problems Are Solved - Remove actions from the feature flags on system and instance level - Remove include type on executions, only in the API, later maybe in the handling logic as well - Use protojson in request and response handling of actions v2 # Additional Changes - Correct integration tests for request and response handling - Use json.RawMessage for events, so that the event payload is not base64 encoded - Added separate context for async webhook calls, that executions are not cancelled when called async # Additional Context Related to #9759 Closes #9710 --------- Co-authored-by: Livio Spring <[email protected]>
5.1 KiB
title
| title |
|---|
| Test Actions Request |
This guide shows you how to leverage the ZITADEL actions feature to react to API requests in your ZITADEL instance. You can use the actions feature to create a target that will be called when a specific API request occurs. This is useful for information provisioning in between systems or for triggering workflows based on API requests in ZITADEL.
Prerequisites
Before you start, make sure you have everything set up correctly.
- You need to be at least a ZITADEL IAM_OWNER
- Your ZITADEL instance needs to have the actions feature enabled.
:::info
Note that this guide assumes that ZITADEL is running on the same machine as the target and can be reached via localhost.
In case you are using a different setup, you need to adjust the target URL accordingly and will need to make sure that the target is reachable from ZITADEL.
:::
:::warning To marshal and unmarshal the request please use a package like protojson, as the request is a protocol buffer message, to avoid potential problems with the attribute names. :::
Start example target
To test the actions feature, you need to create a target that will be called when an API endpoint is called. You will need to implement a listener that can receive HTTP requests and process the request. For this example, we will use a simple Go HTTP server that will print the received request to standard output.
:::info The signature of the received request can be checked, please refer to the example for more information on how to. :::
package main
import (
"fmt"
"io"
"net/http"
)
// webhook HandleFunc to read the request body and then print out the contents
func webhook(w http.ResponseWriter, req *http.Request) {
// read the body content
sentBody, err := io.ReadAll(req.Body)
if err != nil {
// if there was an error while reading the body return an error
http.Error(w, "error", http.StatusInternalServerError)
return
}
defer req.Body.Close()
// print out the read content
fmt.Println(string(sentBody))
}
func main() {
// handle the HTTP call under "/webhook"
http.HandleFunc("/webhook", webhook)
// start an HTTP server with the before defined function to handle the endpoint under "http://localhost:8090"
http.ListenAndServe(":8090", nil)
}
Create target
As you see in the example above the target is created with HTTP and port '8090' and if we want to use it as webhook, the target can be created as follows:
See Create a target for more detailed information.
curl -L -X POST 'https://$CUSTOM-DOMAIN/v2beta/actions/targets' \
-H 'Content-Type: application/json' \
-H 'Accept: application/json' \
-H 'Authorization: Bearer <TOKEN>' \
--data-raw '{
"name": "local webhook",
"restWebhook": {
"interruptOnError": true
},
"endpoint": "http://localhost:8090/webhook",
"timeout": "10s"
}'
Save the returned ID to set in the execution.
Set execution
To configure ZITADEL to call the target when an API endpoint is called, you need to set an execution and define the request condition.
See Set an execution for more detailed information.
curl -L -X PUT 'https://$CUSTOM-DOMAIN/v2beta/actions/executions' \
-H 'Content-Type: application/json' \
-H 'Accept: application/json' \
-H 'Authorization: Bearer <TOKEN>' \
--data-raw '{
"condition": {
"request": {
"method": "/zitadel.user.v2.UserService/AddHumanUser"
}
},
"targets": [
{
"target": "<TargetID returned>"
}
]
}'
Example call
Now that you have set up the target and execution, you can test it by creating a user through the Console UI or by calling the ZITADEL API to create a human user.
curl -L -X PUT 'https://$CUSTOM-DOMAIN/v2/users/human' \
-H 'Content-Type: application/json' \
-H 'Accept: application/json' \
-H 'Authorization: Bearer <TOKEN>' \
--data-raw '{
"profile": {
"givenName": "Test",
"familyName": "User"
},
"email": {
"email": "[email protected]"
}
}'
Your server should now print out something like the following. Check out the Sent information Request payload description.
{
"fullMethod": "/zitadel.user.v2.UserService/AddHumanUser",
"instanceID": "262851882718855632",
"orgID": "262851882718921168",
"projectID": "262851882719052240",
"userID": "262851882718986704",
"request": {
"profile": {
"given_name": "Test",
"family_name": "User"
},
"email": {
"email": "[email protected]"
}
}
}
Conclusion
You have successfully set up a target and execution to react to API requests in your ZITADEL instance. This feature can now be used to provision information in between systems or for triggering workflows based on API requests in ZITADEL. Find more information about the actions feature in the API documentation.