Giter VIP home page Giter VIP logo

keycloak-controller's Introduction

keycloak-controller

deploy

This controller manage Keycloak clients and realms over Kubernetes resources and creates a Kubernetes secret with the clientSecret for clients of type confidential.

Within the cluster, multiple Keycloak instances can be referenced. This become useful in a multi-tenant environment where different services has to be registered at different Keycloak instances.

By default, the controller watches only for events in its namespace. To enable watching in all namespaces set environment variable CONTROLLER_NAMESPACED=false.

Setup

Before deploying the controller, create the CustomResourceDefinition:

kubectl apply -f src/main/k8s/

The controller can then be deployed using the corresponding helm chart.

The Docker container can be found here: https://hub.docker.com/r/kiwigrid/keycloak-controller

Examples

See sub-dir examples for more sophisticated samples.

Keycloak

apiVersion: k8s.kiwigrid.com/v1beta1
kind: Keycloak
metadata:
  name: keycloak-instance-example
spec:
  url: https://keycloak.example.com/auth
  realm: master
  clientId: admin-cli
  username: admin
  passwordSecretName: keycloak-http

Realm

apiVersion: k8s.kiwigrid.com/v1beta1
kind: KeycloakRealm
metadata:
  name: realm-example
spec:
  keycloak: keycloak-instance-example
  realm: my-realm
  roles:
  - service
  - admin
  - operations

Client

apiVersion: k8s.kiwigrid.com/v1beta1
kind: KeycloakClient
metadata:
  name: client-example
spec:
  keycloak: keycloak-instance-example
  realm: my-realm
  clientId: client-example
  clientType: public
  directAccessGrantsEnabled: true
  standardFlowEnabled: false
  implicitFlowEnabled: false
  mapper:
  - name: example-service-audience
    protocolMapper: oidc-audience-mapper
    config:
      claim.name: audience
      access.token.claim: "true"
      included.client.audience: my-service

Development

To test the controller using the same process as Github Actions from a blank container, install act:

brew install act

And then trigger the pull request action:

act pull_request -P ubuntu-latest=nektos/act-environments-ubuntu:18.04

Machine Setup

To run Keycloak Controller locally some of the same scripts that power the Github Actions can be used, but you'll want to provision your machine locally instead, as you most likely don't want to delete all your installs and builds for every single change, or change your local environment in a forceful manner - such as installing versions of a tool that conflicts with another local tool you are using.

The tools you'll need to make sure are installed are kubectl, helm, kind, java, and maven.

Please look at their official documentation to find how to install each.

Once they are installed you can run the various ci scripts:

Here is an example of running the full pipeline, parallelized where possible - of course you could run them ad-hoc in any order that makes sense:

Setup

Build .jar and run a Kubernetes cluster in Docker:

bash .github/local.maven.sh &
bash .github/local.kind.sh &
wait

Build docker image using .jar from previous step, and get Helm ready:

bash .github/ci.docker-build.sh &
bash .github/ci.helm.sh &
wait

Install Keycloak and Keycloak Controller configured to use the image produced and uploaded to Kind in the last step:

bash .github/ci.keycloak.sh "9.0.1" & \
bash .github/ci.keycloak-controller.sh "0.6.1" & \
wait
Run Examples
bash .github/ci.example.sh &&
bash .github/ci.verify.sh
Make changes and see them running in Kubernetes
bash .github/local.maven.sh &&
bash .github/ci.docker-build.sh &&
kubectl rollout restart deployment -n keycloak keycloak-controller && 
kubectl rollout status deployment -n keycloak keycloak-controller
Teardown
kind delete clusters chart-testing

keycloak-controller's People

Contributors

1337andre avatar axdotl avatar manu11th avatar monotek avatar oscarfh avatar patrickleet avatar pravussum avatar wistefan avatar zhenntil avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

keycloak-controller's Issues

Document the process to start the controller

Hallöchen!

First of all thanks a lot for creating and open-sourcing the controller and the associated CRDs. It will greatly assist us in the creation and destruction of ephemeral environments in our CI/CD set-up.

I'm having trouble deploying the controller on my cluster: I managed to build the Docker image by replicating the mvn commands from Travis CI, but when I run it I get the following error:

16:05:15.952 1-thread-1 WARN  io.fabric8.kubernetes.client.Config Error reading service account token from: [/var/run/secrets/kubernetes.io/serviceaccount/token]. Ignoring.

I suppose a service account token needs to be mounted as a secret in the container, could you please help me figure out which permissions this service account should have, what its name should be, etc.?

Any pointer would be very much appreciated!

Danke im Voraus,
Loïc

Keycloak server compatibility versions ?

Hi,
First of all - great job on this keycloak controller, it's really useful and a lot easier way to manage a keycloak cluster compare to the traditional way with the json files to import.

So I have a question and suggestion at once:

  • which version of keycloak server this keycloak-controller si compatible with ?

It would be great to have a compatibility matrix in the README.md.

Why ?

Because when changing an existing KeycloakRealm by changing the roles for example, I'm seeing an error on the logs that seems to be related to an attribute that can't be parsed by the keycloak api probably because my keycloak server is ahead:

keycloak-instance/onboarding: unable to create realm
javax.ws.rs.client.ResponseProcessingException: javax.ws.rs.ProcessingException: 
com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException: Unrecognized field \"webAuthnPolicyRpEntityName\"
 (class org.keycloak.representations.idm.RealmRepresentation), not marked as ignorable (106 known properties:
  \"userFederationMappers\", \"rememberMe\", \"duplicateEmailsAllowed\", \"adminEventsDetailsEnabled\", \"users\",
   \"components\", \"otpPolicyType\", \"accessCodeLifespanUserAction\", \"id\", \"enabledEventTypes\", \"applications\",
    \"eventsListeners\", \"ssoSessionMaxLifespanRememberMe\", \"defaultDefaultClientScopes\", \"notBefore\", \"publicKey\", 
    \"smtpServer\", \"resetPasswordAllowed\", \"accessTokenLifespanForImplicitFlow\", \"clientScopes\", 
    \"internationalizationEnabled\", \"attributes\", \"accessTokenLifespan\", \"passwordCredentialGrantAllowed\", 
    \"federatedUsers\", \"applicationScopeMappings\", \"displayName\", \"refreshTokenMaxReuse\", \"oauthClients\",
     \"defaultGroups\", \"browserFlow\", \"failureFactor\", \"directGrantFlow\", \"otpPolicyDigits\", 
     \"revokeRefreshToken\", \"otpSupportedApplications\", \"registrationFlow\", \"editUsernameAllowed\",
      \"ssoSessionIdleTimeoutRememberMe\", \"emailTheme\", \"realm\", \"actionTokenGeneratedByAdminLifespan\",
       \"authenticatorConfig\", \"offlineSessionMaxLifespan\", \"protocolMappers\", \"accountTheme\",
        \"maxDeltaTimeSeconds\" [truncated]])\n at [Source: (org.jboss.resteasy.client.jaxrs.internal.ClientResponse$InputStreamWrapper);

Unrecognized field "clientSessionIdleTimeout" while creating Clients

Hey there, hoping someone can point me in the right direction where to troubleshoot. I've been trying to create client scopes and clients unsuccessfully; however realms create just fine.

Using the example client creation below:

apiVersion: k8s.kiwigrid.com/v1beta1
kind: KeycloakClient
metadata:
  name: some-client
spec:
  keycloak: keycloak
  realm: gubbins
  clientId: some-client
  clientType: public
  defaultClientScopes:
    - realmhelm-scope

Gives me the following on the controller:

00:48:25.390 96.0.1/... ERROR     com.kiwigrid.keycloak.controller.client.ClientController Failed to ADDED resource gubbins/some-client.
javax.ws.rs.client.ResponseProcessingException: javax.ws.rs.ProcessingException: com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException: Unrecognized field "clientSessionIdleTimeout" (class org.keycloak.representations.idm.RealmRepresentation), not marked as ignorable (126 known properties: "userFederationMappers", "rememberMe", "duplicateEmailsAllowed", "adminEventsDetailsEnabled", "users", "webAuthnPolicyRequireResidentKey", "webAuthnPolicyPasswordlessAvoidSameAuthenticatorRegister", "components", "otpPolicyType", "accessCodeLifespanUserAction", "id", "webAuthnPolicyAttestationConveyancePreference", "enabledEventTypes", "applications", "webAuthnPolicyPasswordlessSignatureAlgorithms", "eventsListeners", "ssoSessionMaxLifespanRememberMe", "defaultDefaultClientScopes", "webAuthnPolicyPasswordlessCreateTimeout", "notBefore", "publicKey", "smtpServer", "resetPasswordAllowed", "webAuthnPolicyAvoidSameAuthenticatorRegister", "accessTokenLifespanForImplicitFlow", "webAuthnPolicyPasswordlessUserVerificationRequirement", "clientScopes", "internationalizationEnabled", "attributes", "accessTokenLifespan", "passwordCredentialGrantAllowed", "federatedUsers", "applicationScopeMappings", "displayName", "refreshTokenMaxReuse", "oauthClients", "defaultGroups", "browserFlow" [truncated]])
 at [Source: (org.jboss.resteasy.client.jaxrs.internal.ClientResponse$InputStreamWrapper); line: 1, column: 469] (through reference chain: org.keycloak.representations.idm.RealmRepresentation["clientSessionIdleTimeout"])
        at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.extractResult(ClientInvocation.java:156)
        at org.jboss.resteasy.client.jaxrs.internal.proxy.extractors.BodyEntityExtractor.extractEntity(BodyEntityExtractor.java:60)
        at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invokeSync(ClientInvoker.java:150)
        at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invoke(ClientInvoker.java:112)
        at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientProxy.invoke(ClientProxy.java:76)
        at com.sun.proxy.$Proxy59.toRepresentation(Unknown Source)
        at com.kiwigrid.keycloak.controller.client.ClientController.lambda$realm$2(ClientController.java:161)
        at java.base/java.util.Optional.filter(Optional.java:223)
        at com.kiwigrid.keycloak.controller.client.ClientController.realm(ClientController.java:159)
        at com.kiwigrid.keycloak.controller.client.ClientController.apply(ClientController.java:48)
        at com.kiwigrid.keycloak.controller.client.ClientController.apply(ClientController.java:28)
        at com.kiwigrid.keycloak.controller.KubernetesController.eventReceived(KubernetesController.java:67)
        at com.kiwigrid.keycloak.controller.KubernetesController.eventReceived(KubernetesController.java:14)
        at io.fabric8.kubernetes.client.utils.WatcherToggle.eventReceived(WatcherToggle.java:49)
        at io.fabric8.kubernetes.client.dsl.internal.WatchConnectionManager$1.onMessage(WatchConnectionManager.java:232)
        at okhttp3.internal.ws.RealWebSocket.onReadMessage(RealWebSocket.java:323)
        at okhttp3.internal.ws.WebSocketReader.readMessageFrame(WebSocketReader.java:219)
        at okhttp3.internal.ws.WebSocketReader.processNextFrame(WebSocketReader.java:105)
        at okhttp3.internal.ws.RealWebSocket.loopReader(RealWebSocket.java:274)
        at okhttp3.internal.ws.RealWebSocket$2.onResponse(RealWebSocket.java:214)
        at okhttp3.RealCall$AsyncCall.execute(RealCall.java:206)
        at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)
        at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
        at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
        at java.base/java.lang.Thread.run(Thread.java:834)
Caused by: javax.ws.rs.ProcessingException: com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException: Unrecognized field "clientSessionIdleTimeout" (class org.keycloak.representations.idm.RealmRepresentation), not marked as ignorable (126 known properties: "userFederationMappers", "rememberMe", "duplicateEmailsAllowed", "adminEventsDetailsEnabled", "users", "webAuthnPolicyRequireResidentKey", "webAuthnPolicyPasswordlessAvoidSameAuthenticatorRegister", "components", "otpPolicyType", "accessCodeLifespanUserAction", "id", "webAuthnPolicyAttestationConveyancePreference", "enabledEventTypes", "applications", "webAuthnPolicyPasswordlessSignatureAlgorithms", "eventsListeners", "ssoSessionMaxLifespanRememberMe", "defaultDefaultClientScopes", "webAuthnPolicyPasswordlessCreateTimeout", "notBefore", "publicKey", "smtpServer", "resetPasswordAllowed", "webAuthnPolicyAvoidSameAuthenticatorRegister", "accessTokenLifespanForImplicitFlow", "webAuthnPolicyPasswordlessUserVerificationRequirement", "clientScopes", "internationalizationEnabled", "attributes", "accessTokenLifespan", "passwordCredentialGrantAllowed", "federatedUsers", "applicationScopeMappings", "displayName", "refreshTokenMaxReuse", "oauthClients", "defaultGroups", "browserFlow" [truncated]])
 at [Source: (org.jboss.resteasy.client.jaxrs.internal.ClientResponse$InputStreamWrapper); line: 1, column: 469] (through reference chain: org.keycloak.representations.idm.RealmRepresentation["clientSessionIdleTimeout"])
        at org.jboss.resteasy.client.jaxrs.internal.ClientResponse.readFrom(ClientResponse.java:375)
        at org.jboss.resteasy.client.jaxrs.internal.ClientResponse.readEntity(ClientResponse.java:268)
        at org.jboss.resteasy.specimpl.BuiltResponse.readEntity(BuiltResponse.java:231)
        at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.extractResult(ClientInvocation.java:120)
        ... 24 common frames omitted

I'm not sure if it matters or not but I am running Keycloak 11.0.1. Maybe some new fields were added and that's what it's complaining about?

KubernetesClientException: Failure executing: POST /api/v1/namespaces/**/secrets

Is this a request for help?:


Is this a BUG REPORT or FEATURE REQUEST? (choose one):

Bug Report

Version of Keycloak-controller:

Helm chart: 0.6.1
controller version: 3.0.0

Version of Keycloak:

11

Version of Kubernetes:

1.16

What happened:

Creating a new KeycloakClient results in an error which requires a manual restart of the keycloak-controller pod. The mappers for the client are not created until this restart happens.

{"timestampSeconds":1599684661,"timestampNanos":491000000,"severity":"ERROR","thread":"OkHttp https://172.20.0.1/...","logger":"com.kiwigrid.keycloak.controller.client.ClientController","message":"keycloak-jx-production/thecareerpathai/nsf-pathway-app-jx-production: KubernetesClientException: Failure executing: POST at: https://172.20.0.1/api/v1/namespaces/jx-production/secrets. Message: resourceVersion should not be set on objects to be created. Received status: Status(apiVersion=v1, code=500, details=null, kind=Status, message=resourceVersion should not be set on objects to be created, metadata=ListMeta(_continue=null, resourceVersion=null, selfLink=null, additionalProperties={}), reason=null, status=Failure, additionalProperties={}).","context":"default","serviceContext":{"version":"1.0","service":"keycloak-controller"}}

What you expected to happen:

Two things:

  1. I wouldn't expect there to be an error creating the secret, especially because the secret is actually created despite the error. Maybe it's trying to do it twice.
  2. If there is an error the process should crash hard so it restarts and then we don't need to restart it manually. While ideally the error wouldn't happen or would be handled appropriately, a hard crash would make the manual intervention unnecessary at least.

How to reproduce it (as minimally and precisely as possible):

Create a new client:

apiVersion: k8s.kiwigrid.com/v1beta1
kind: KeycloakClient
metadata:
  name: {{ template "keycloakclient" . }}
spec:
  keycloak: {{ .Values.keycloak.keycloak }}
  realm: {{ .Values.keycloak.realm }}
  clientId: {{ template "keycloakclient" . }}
  clientType: confidential
  defaultClientScopes:
  - email
  - profile
  - roles
  directAccessGrantsEnabled: true
  standardFlowEnabled: true
  implicitFlowEnabled: false
  redirectUris:
{{- if .Values.keycloak.redirectUris.allowAll }}
  - http://*
  - https://*
{{- end }}
{{- if .Values.keycloak.redirectUris.allowLocalhost }}
  - http://localhost*
{{- end }}
{{- if .Values.keycloak.redirectUris.includeNamespace }}
  - https://{{ .Values.keycloak.redirectUris.serviceName }}-{{ .Release.Namespace}}.{{ .Values.keycloak.redirectUris.domain }}/*
  - https://{{ .Values.keycloak.redirectUris.serviceName }}-{{ .Release.Namespace}}.{{ .Values.keycloak.redirectUris.domain }}
{{- else }}
  - https://{{ .Values.keycloak.redirectUris.serviceName }}.{{ .Values.keycloak.redirectUris.domain }}/*
  - https://{{ .Values.keycloak.redirectUris.serviceName }}.{{ .Values.keycloak.redirectUris.domain }}
{{- end }}
  mapper:
  - name: audience
    protocolMapper: oidc-audience-mapper
    config:
      claim.name: audience
      access.token.claim: "true"
      included.client.audience: {{ template "keycloakclient" . }}
  - name: username
    protocolMapper: oidc-usermodel-property-mapper
    config:
      access.token.claim: "true"
      claim.name: username
      jsonType.label: String
      user.attribute: username
  - name: clientRoles
    protocolMapper: oidc-usermodel-client-role-mapper
    config:
      access.token.claim: "true"
      claim.name: clientRoles
      jsonType.label: String
      multivalued: "true"
  - name: roles
    protocolMapper: oidc-usermodel-realm-role-mapper
    config:
      access.token.claim: "true"
      claim.name: roles
      jsonType.label: String
      multivalued: "true"

Anything else we need to know:

No

Arrays sorting is non-deterministic and results in lots of changes in DB

Is this a request for help?:


Is this a BUG REPORT or FEATURE REQUEST? (choose one):

BUG REPORT

Version of Keycloak-controller:

latest (5 hours ago on 10/22 - no version tag)

Version of Keycloak:

11

Version of Kubernetes:

16

What happened:

Arrays are non-deterministic / unsorted, which results in updates being made over and over just to change the order of the array:

change defaultClientScopes from [profile, roles, email] to [email, profile, roles]"

I've seen it happen with redirectURIs as well

What you expected to happen:

If the values of the array sorted are the same, don't update the resource

How to reproduce it (as minimally and precisely as possible):

Happens with normal usage

Anything else we need to know:

Way to run tests locally

Is this a request for help?:


Is this a BUG REPORT or FEATURE REQUEST? (choose one):

FEATURE REQUEST

It's hard to iterate quickly due to the tests being tied to github actions - it'd be nice to script out a local test runner using a lot of the same pieces - Kind, etc

Version of Keycloak-controller:

all

Version of Keycloak:

any

Version of Kubernetes:

any

nginx-ingress integration

This is a really interesting project. :)

Feature idea, what if the controller could also drive nginx-ingress ingress rules and an oauth2 deployment to plugin the authentication into the process. Maybe that is a different crd, or an annotation on an ingress?

It would make it significantly easier to not only get a client but also start using it.

make sure that client scope is created before client

If both a KeycloakClient and a KeycloakClientScope are created at the same time, the client scope is not assigned to the client. It only works if the KeycloakClientScope is created first while the client doesn't exist.

For example, this will not work:

apiVersion: k8s.kiwigrid.com/v1beta1
kind: KeycloakClientScope
metadata:
  name: some-scope
spec:
  keycloak: keycloak
  realm: realm
  name: some-scope
---
apiVersion: k8s.kiwigrid.com/v1beta1
kind: KeycloakClient
metadata:
  name: some-client
spec:
  keycloak: keycloak
  realm: realm
  clientId: some-client
  clientType: public
  defaultClientScopes:
    - some-scope

Error message "RESTEASY004655: Unable to invoke request"

I am getting that error message. My keycloaks.k8s.kiwigrid.com looks like this:

apiVersion: k8s.kiwigrid.com/v1beta1
kind: Keycloak
metadata:
  name: keycloak-test1
spec:
  clientId: admin-cli
  passwordSecretKey: password
  passwordSecretName: keycloak-http
  passwordSecretNamespace: keycloak-test1
  realm: master
  url: https://keycloak-test1.mydomain.org/auth
  username: admin

The secret also exists and was created this way

kubectl create secret generic keycloak-http \
  --from-literal=password=$(openssl rand -base64 32 | tr -d "\n" | base64)

What can I do to debug this further?

API

I'm trying to convince the Keycloak Operator developers to support pointing at an external Keycloak so their management CRD's can be used the same way as they keycloak-controller. If they can not be convinced, could the keycloak-controller support the use of the keycloak-operator's management CRD's so that users don't have to switch between API's moving between the keycloak-operator and keycloak-controller?

Open for Adoption

Kiwigrid Teams customized the keycloak instances in kubernetes over a longer period of time with this operator. Now we are moving toward https://github.com/keycloak/keycloak-operator and don't maintain this code base in the next future.

So with this issue I'd like to inform that we're searching for a new owner and home of this project. If you're interested please comment with some details how you'd like to shape the future of the operator.

There are already some issues recorded that requires attention.

If we won't find a new home we're gonna archive the repository at some point in time.

Question: Why is custom resources Keycloak not namespaced?

I would like to create a Keycloak instance in a certain namespace. I am also fine having this instance and the controller in the same namespace. In that case I also wouldn't need the serviceaccount and rolebindings, I think.

$ kubectl api-resources --api-group k8s.kiwigrid.com

NAME              SHORTNAMES   APIGROUP           NAMESPACED   KIND
keycloakclients   kcc          k8s.kiwigrid.com   true         KeycloakClient
keycloakrealms    kcr          k8s.kiwigrid.com   false        KeycloakRealm
keycloaks         kc           k8s.kiwigrid.com   false        Keycloak

Is there a special reasoning to not have these resources namespaced?

Creating KeycloakClient while Keycloak server is down

We are creating Keycloak clients with keycloak-controller for existing Keycloak
server (7.0.0). For that to happen, first we're creating Keycloak object
pointing to the Keycloak server(url points to internal kubernetes service here,
which works great by the way):

apiVersion: k8s.kiwigrid.com/v1beta1
kind: Keycloak
metadata:
  name: fully-configured-keycloak
  namespace: keycloak
spec:
  url: http://keycloak-http.keycloak.svc.cluster.local/auth
  realm: master
  clientId: admin-cli
  username: keycloak
  passwordSecretNamespace: keycloak
  passwordSecretName: keycloak-http
  passwordSecretKey: password

Output shows it is connected:

INFO  com.kiwigrid.keycloak.controller.keycloak.KeycloakController Connected to fully-configured-keycloak in version 7.0.0.

While keycloak is availabe/ready, clients are created succefully and
available via keycloak UI. Example of KeycloakClient object:

apiVersion: k8s.kiwigrid.com/v1beta1
kind: KeycloakClient
metadata:
  name: client-example
  namespace: keycloak
spec:
  keycloak: fully-configured-keycloak
  realm: myrealm
  clientId: client-example
  clientType: confidential
  directAccessGrantsEnabled: false
  standardFlowEnabled: true
  implicitFlowEnabled: false
  secretNamespace: keycloak
  secretName: clinet-example-client-secret
  secretKey: secret
  mapper:
  - name: example-service-audience
    protocolMapper: oidc-audience-mapper
    config:
      claim.name: audience
      access.token.claim: "true"
      id.token.claim: "true"
      included.custom.audience: my-service

Error occurs when we are creating KeycloakClient, while keycloak is not
available. There may be several reasons for that e.g. keycloak pod restart
due to upgrade procedures either of keycloak itself or other pieces of
infrastructure.

The error itself is obvious - keycloak is not avilable during KeycloakClient
object creation:

09:00:35.689 16.0.1/... ERROR     com.kiwigrid.keycloak.controller.client.ClientController Failed to ADDED resource keycloak/client-example.
javax.ws.rs.ProcessingException: javax.ws.rs.ServiceUnavailableException: HTTP 503 Service Unavailable
	at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.filterRequest(ClientInvocation.java:599)
	at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.invoke(ClientInvocation.java:436)
	at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invokeSync(ClientInvoker.java:148)
	at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invoke(ClientInvoker.java:112)
	at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientProxy.invoke(ClientProxy.java:76)
	at com.sun.proxy.$Proxy59.toRepresentation(Unknown Source)
	at com.kiwigrid.keycloak.controller.client.ClientController.lambda$realm$2(ClientController.java:159)
	at java.base/java.util.Optional.filter(Optional.java:223)
	at com.kiwigrid.keycloak.controller.client.ClientController.realm(ClientController.java:157)
	at com.kiwigrid.keycloak.controller.client.ClientController.apply(ClientController.java:46)
	at com.kiwigrid.keycloak.controller.client.ClientController.apply(ClientController.java:26)
	at com.kiwigrid.keycloak.controller.KubernetesController.eventReceived(KubernetesController.java:67)
	at com.kiwigrid.keycloak.controller.KubernetesController.eventReceived(KubernetesController.java:14)
	at io.fabric8.kubernetes.client.utils.WatcherToggle.eventReceived(WatcherToggle.java:49)
	at io.fabric8.kubernetes.client.dsl.internal.WatchConnectionManager$1.onMessage(WatchConnectionManager.java:232)
	at okhttp3.internal.ws.RealWebSocket.onReadMessage(RealWebSocket.java:323)
	at okhttp3.internal.ws.WebSocketReader.readMessageFrame(WebSocketReader.java:219)
	at okhttp3.internal.ws.WebSocketReader.processNextFrame(WebSocketReader.java:105)
	at okhttp3.internal.ws.RealWebSocket.loopReader(RealWebSocket.java:274)
	at okhttp3.internal.ws.RealWebSocket$2.onResponse(RealWebSocket.java:214)
	at okhttp3.RealCall$AsyncCall.execute(RealCall.java:206)
	at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
	at java.base/java.lang.Thread.run(Thread.java:834)
Caused by: javax.ws.rs.ServiceUnavailableException: HTTP 503 Service Unavailable
	at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.handleErrorStatus(ClientInvocation.java:231)
	at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.extractResult(ClientInvocation.java:191)
	at org.jboss.resteasy.client.jaxrs.internal.proxy.extractors.BodyEntityExtractor.extractEntity(BodyEntityExtractor.java:60)
	at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invokeSync(ClientInvoker.java:150)
	at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invoke(ClientInvoker.java:112)
	at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientProxy.invoke(ClientProxy.java:76)
	at com.sun.proxy.$Proxy47.refreshToken(Unknown Source)
	at org.keycloak.admin.client.token.TokenManager.refreshToken(TokenManager.java:106)
	at org.keycloak.admin.client.token.TokenManager.getAccessToken(TokenManager.java:71)
	at org.keycloak.admin.client.token.TokenManager.getAccessTokenString(TokenManager.java:64)
	at org.keycloak.admin.client.resource.BearerAuthFilter.filter(BearerAuthFilter.java:52)
	at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.filterRequest(ClientInvocation.java:586)
	... 24 common frames omitted

What we are missing here is a sort of resilience - while Keycloak is down,
KeycloakClient object is created by controller, but no actual client is created
in the Keycloak even when it is up again. The only fix we've found is either
to restart keycloak-controller or to delete/apply KeycloakClient again once
Keycloak server is ready.

Would be nice to have a feature when keycloak-controller tries to recover
connection to keycloak on attempt to create KeycloakClient, if keycloak is not
available at that moment. Same approach is used when controller tries to connect
to keycloak on start and logging WARN each 60s:

WARN  com.kiwigrid.keycloak.controller.keycloak.KeycloakController Connecting to fully-configured-keycloak failed: Keycloak returned 503 with: no healthy upstream

What do you think about this / how you're solving this?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.