This repository has k8s tools to manage AppCat services.
Documentation: https://vshn.github.io/appcat
.
├── apis
| ├── appcat // API server related apis
| ├── exoscale // exoscale apis
| ├── v1 // common apis
| ├── vshn // VSHN managed services apis
├── cmd // cobra command lines for each AppCat tool
| ├── apiserver.go
| ├── controller.go
| ├── grpc.go
│ └── sliexporter.go
├── config // kubernetes resources
| ├── apiserver
│ ├── controller
│ └── sliexporter // uses kustomize
├── crds // VSHN exposed resources from apis
├── docs
├── pkg // go code for each AppCat tool
| ├── apiserver
| ├── controller
| ├── grpc
│ └── sliexporter
├── test // mocks, test cases, grps test client
├── Dockerfile
├── log.go
├── main.go
├── probes
├── README.md
└── tools.go
In /apis
there is code in Go to generate the XRDs (composites) as this is in OpenAPI.
This code generates the OpenAPI scheme using Kubebuilder.
See following pages for learning how to do that:
If you make changes to the auto generated code you'll need to run code generation. This can be done with make:
make generate
See make help
for a list of build targets.
make build
: Build binary for linux/amd64make build -e GOOS=darwin -e GOARCH=arm64
: Build binary for macos/arm64make docker-build
: Build Docker image for local environment
You can setup a [kind]-based local environment with all dependencies in kindev.
The AppCat Controller resolves certain issues that cannot be achieved with crossplane.
The controller manages and achieves the following:
RESOURCE | GOAL | DESCRIPTION |
---|---|---|
XVSHNPostgreSQL |
Deletion Protection Support | Manages finalizers before and after deletion |
validation webhooks |
Provide validation webhooks for AppCat services | See Goal |
This assumes that you've already applied the vshn golden test in component-appcat!
Also you might need to set the right host ip:
HOSTIP=$(docker inspect kindev-control-plane | jq '.[0].NetworkSettings.Networks.kind.Gateway') # On kind MacOS/Windows
HOSTIP=host.docker.internal # On Docker Desktop distributions
HOSTIP=host.lima.internal # On Lima backed Docker distributions
For Linux users: `ip -4 addr show dev docker0 | grep inet | awk -F' ' '{print $2}' | awk -F'/' '{print $1}'`
Then you can apply the webhook registration changes:
export KUBECONFIG=...
make webhook-debug -e webhook_service_name=$HOSTIP
Then run the controller with the correct certdir flag:
go run . controller --certdir .work/webhook
Creating a PostgreSQL or Redis instance will now go through the Webhook instance.
The exporter exposes a histogram appcat_probes_seconds
with five labels
service
, the service type that was probed (e.g.VSHNPostgreSQL
)namespace
, the namespace of the claim that was monitoredname
, the name of the claim that was monitoredsla
, the service level. Can either bebesteffort
orguaranteed
high_available
, whether this instance is high available (1 or more nodes)reason
, if the probe was successful. Can either besuccess
,fail-timeout
, orfail-unkown
To add a prober for a new service, add a file in pkg/sliexporter/probes/
that adds another implementation of the Prober
interface.
There should be a separate controller per AppCat Claim type.
Add another controller for each service that should be probed in pkg/sliexporter/
.
If possible SLA exceptions should be implemented as a middleware for the Prober
interface.
The gRPC Server that manages crossplane composition functions. The functions are found in pkg/comp-functions/functions
There package pkg/comp-functions/runtime
contains a library with helper methods which helps with adding new functions.
The framework is designed to easily add new composition functions to any AppCat service.
A function-io corresponds to one and only one composition thus multiple transformation go functions
can be added to a function-io.
For instance, in vshn-postgres-func
there are multiple transformation go functions such as url
or alerting
.
To add a new function to PostgreSQL by VSHN:
- Create a new package under
./pkg/comp-functions/functions/
in case one does not exist for a composition. - Implement a
Transform()
go function by using the helper functions fromruntime/desired.go
andruntime/observed.go
. - Add a new transform go function to the
images
variable in./cmd/grpc.go
.
entrypoint to start working with gRPC server is to run:
go run main.go --log-level 1 functions --insecure
This will start the GRPC server listening on a TCP port. Afterward you can configure the composition to use this connection in the component:
# HOSTIP=$(docker inspect kindev-control-plane | jq '.[0].NetworkSettings.Networks.kind.Gateway') # On kind MacOS/Windows
# HOSTIP=host.docker.internal # On Docker Desktop distributions
# HOSTIP=host.lima.internal # On Lima backed Docker distributions
# For Linux users: `ip -4 addr show dev docker0 | grep inet | awk -F' ' '{print $2}' | awk -F'/' '{print $1}'`
services:
vshn:
enabled: true
externalDatabaseConnectionsEnabled: true
emailAlerting:
enabled: true
smtpPassword: "whatever"
postgres:
grpcEndpoint: $HOSTIP:9547
proxyFunction: true
Each service should have these params configured.
If you prefer to set the proxy endpoint directly in the composition, it's passed via the input.data.proxyEndpoint
field.
Then install the function proxy in kind:
make install-proxy
It's also possible to trigger fake request to gRPC server via the crank renderer:
go run github.com/crossplane/crossplane/cmd/crank beta render xr.yaml composition.yaml functions.yaml -r
Crank will return a list of all the objects this specific request would have produced, including the result messages.
Please have a look at the hack/
folder for an example.