Skip to content
This repository has been archived by the owner on Dec 21, 2023. It is now read-only.

Support for generic webhook execution #3822

Closed
6 tasks
jetzlstorfer opened this issue Apr 20, 2021 · 8 comments
Closed
6 tasks

Support for generic webhook execution #3822

jetzlstorfer opened this issue Apr 20, 2021 · 8 comments

Comments

@jetzlstorfer
Copy link
Member

User Story

Currently, the support for webhooks is only possible via the generic executor service that needs to be installed as an extension to Keptn.

As a user, I want to be able to call arbitrary URLs via webhooks that are registered on Keptn events to interact with systems outside of Keptn.

Details

I'd like to have a built-in integration in Keptn that allows calling webhooks.

It should have support for

  • Different HTTP request methods (GET, POST, ...)
  • Templating to convert a cloud event into a custom payload (see details below)
  • Authentication methods, e.g. Basic Auth
  • Custom return code depending on HTTP status codes

It should be possible to operate this service in two modes:

  • silent mode: subscribing to arbitrary Keptn events but not interfering with the execution of a task sequence (as defined in the shipyard). Therefore, the service should not send back a .started or .triggered event but a .status.changed event to indicate the execution of the service (this should be discussed before implementing if it is the right way to do it).
  • task execution mode: subscribing to .triggered events and sending back a .started event upon retrieval of the .triggered event and after executing the webhook and depending on its status code a .finished event with the corresponding details of success/unsuccessful execution.

Templating

The templating should support basic constructs to build custom payloads by using placeholders that are filled with data from the cloud event.
In addition, it should support data fields such as date/random-id/... that are generated upon the execution of the webhook service.

Research task: Before implementation, a research phase should provide more technical details on how this is done in other projects and how it can be realized for Keptn.

Acceptance Criteria

  • User can define a template for each webhook
  • Webhook is triggered upon an event subscription to interact with an external system

Definition of done

  • Research completed on templating mechanisms/solutions for webhooks (that leads to the implementation concept)
  • Story is implemented by a webhook service
  • Integration test available
  • Documentation updated
@jetzlstorfer jetzlstorfer changed the title Support for Generic webhook execution Support for generic webhook execution Apr 20, 2021
@jetzlstorfer
Copy link
Member Author

This topic is reserved for LFX mentorship 2021 Spring term https://github.com/cncf/mentoring/tree/master/lfx-mentorship/2021/02-Summer

@jetzlstorfer jetzlstorfer self-assigned this Apr 20, 2021
@adigeak
Copy link
Contributor

adigeak commented May 6, 2021

Hi! I would like to work on it over the summers.

@github-actions
Copy link
Contributor

github-actions bot commented May 6, 2021

@check-spelling-bot: Could not perform request. Commenter (@adigeak) isn't author (@jetzlstorfer) / collaborator

@PrayagS
Copy link
Contributor

PrayagS commented May 29, 2021

Below given is what I learned after roughly going through the k8s admission controllers feature.

Research phase (proposed)

We take a look at Kubernetes Admission Controllers. According to this article at K8s blog,

In a nutshell, Kubernetes admission controllers are plugins that govern and enforce how the cluster is used. They can be thought of as a gatekeeper that intercepts (authenticated) API requests and may change the request object or deny the request altogether.

Enabling the service

The set of enabled admission controllers is configured by passing a flag to the Kubernetes API server. Most of the common ones including the webhook ones are enabled by default.

kube-apiserver --enable-admission-plugins=ValidatingAdmissionWebhook,MutatingAdmissionWebhook

We can implement something similar in Keptn CLI to enable support for webhooks during installation or at a later stage.

Configuration

Considering the case of MutatingAdmissionWebhook, it can be configured by defining MutatingWebhookConfiguration (a cluster level object in k8s). An example config is shown below:

apiVersion: admissionregistration.k8s.io/v1beta1
kind: MutatingWebhookConfiguration
metadata:
  name: demo-webhook
webhooks:
  - name: webhook-server.webhook-demo.svc
    clientConfig:
      service:
        name: webhook-server
        namespace: webhook-demo
        path: "/mutate"
      caBundle: ${CA_PEM_B64}
    rules:
      - operations: [ "CREATE" ]
        apiGroups: [""]
        apiVersions: ["v1"]
        resources: ["pods"]

We can implement a similar configuration setup in Keptn where one can define the hostname, CA Bundle (for authentication purposes, more on this given below), endpoint, and also define the events on which the webhook should be registered. I'm not sure how we'll let the user define the payload template here. Maybe we can let the user point to an HTTP script that contains the template. Separating the template and the list of events to subscribe to is maybe a better way than what the generic-executor-service does, where the name of the script denotes the event it subscribes to. This can be discussed before implementation.

Authentication

Kubernetes requires that the webhook is served via HTTPS and hence, needs proper TLS certificates for the server that is hosting the webhook. I'm sure there are other ways to implement basic authentication. This can be discussed before implementation.

Architecture

In the case of k8s, the kube-apiserver calls the webhook service and the webhook service is supposed to reply (send a POST request) to the API server. In our case, on receiving a cloud event, the webhook service sends a request to an arbitrary URL. Please correct me if my understanding is wrong.

I'm still unsure about this, but my first notion is to deploy a separate service (add one to the existing set of core Keptn services when the user enables this feature), attach a Keptn distributor to it, and implement all the features inside the service. But then, how is it different from installing one of the many Keptn services and more specifically, just installing the generic-executor-service directly.

References

I'd appreciate any feedback or suggestions on this. Thank you!

@jetzlstorfer
Copy link
Member Author

This topic is reserved for LFX mentorship 2021 Spring term https://github.com/cncf/mentoring/tree/master/lfx-mentorship/2021/02-Summer

This issue has not been assigned for mentorship

@jetzlstorfer jetzlstorfer removed their assignment Jun 1, 2021
@jetzlstorfer
Copy link
Member Author

Hi @PrayagS - thanks for your detailed implementation proposal.
However, the idea is not to open a webhook for the outside to allow control to Keptn from the outside, but rather to have the possibility to call a webhook of a 3rd party service from Keptn.

Bascially, the flow when using the webhook service is that it will receive a Keptn event and translate it into a payload that can be consumed by a 3rd party service:

Keptn event --> webhook service (that manages auth, payload, HTTP type, ...) --> 3rd party

@PrayagS
Copy link
Contributor

PrayagS commented Jun 1, 2021

@jetzlstorfer Yes, I do understand the type of implementation you are proposing.

You are correct to note that the k8s feature is slightly different from what keptn requires. In the case of k8s the steps are as follows,

  • user sends a request to kube-apiserver
  • kube-apiserver calls the webhook hosted on a different ns
  • webhook service replies back to kube-apiserver

In the case of Keptn, as you mentioned,

  • Keptn event occurs
  • Webhook service calls an external webhook
  • The webhook may or may not reply back. Depends on the type of request.

What's common among the two,

  • kube-apiserver -> webhook
  • Keptn's webhook service -> webhook

By using the example of k8s, I was trying to take inspiration from their architecture and implementations of both configuring the webhook and also the authentication process. The functionality of the webhook can always be implemented differently as per our case.

@stale
Copy link

stale bot commented Sep 14, 2021

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

@stale stale bot added the stale label Sep 14, 2021
@stale stale bot closed this as completed Sep 21, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

4 participants